mirror of
https://github.com/amyinspace/MagicSetEditor2.git
synced 2026-06-11 13:17:00 -04:00
Merge pull request #34 from haganbmj/dfc_images
feat: script functions for generating and manipulating card images
This commit is contained in:
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: 关键词
|
keyword: 关键词
|
||||||
keywords: 关键词
|
keywords: 关键词
|
||||||
#_ADD pack: pack type
|
#_ADD pack: pack type
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: 图形
|
shape: 图形
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: 關鍵詞
|
keyword: 關鍵詞
|
||||||
keywords: 關鍵詞
|
keywords: 關鍵詞
|
||||||
#_ADD pack: pack type
|
#_ADD pack: pack type
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: 圖形
|
shape: 圖形
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: keyword
|
keyword: keyword
|
||||||
keywords: keywords
|
keywords: keywords
|
||||||
pack: pack type
|
pack: pack type
|
||||||
|
card region: card region
|
||||||
|
card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: shape
|
shape: shape
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: keyword
|
keyword: keyword
|
||||||
keywords: keywords
|
keywords: keywords
|
||||||
pack: pack type
|
pack: pack type
|
||||||
|
card region: card region
|
||||||
|
card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: shape
|
shape: shape
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: keyword
|
keyword: keyword
|
||||||
keywords: keywords
|
keywords: keywords
|
||||||
pack: pack type
|
pack: pack type
|
||||||
|
card region: card region
|
||||||
|
card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: shape
|
shape: shape
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: palabra clave
|
keyword: palabra clave
|
||||||
keywords: palabras clave
|
keywords: palabras clave
|
||||||
pack: mazo
|
pack: mazo
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: forma
|
shape: forma
|
||||||
|
|||||||
@@ -898,6 +898,8 @@ type:
|
|||||||
circle: cercle
|
circle: cercle
|
||||||
ellipse: ellipse
|
ellipse: ellipse
|
||||||
pack: type de pack
|
pack: type de pack
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
square: carré
|
square: carré
|
||||||
rectangle: rectangle
|
rectangle: rectangle
|
||||||
triangle: triangle
|
triangle: triangle
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: parola-chiave
|
keyword: parola-chiave
|
||||||
keywords: parole chiave
|
keywords: parole chiave
|
||||||
pack: tipo busta
|
pack: tipo busta
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: forma
|
shape: forma
|
||||||
|
|||||||
@@ -889,6 +889,8 @@ type:
|
|||||||
keyword: キーワード
|
keyword: キーワード
|
||||||
keywords: キーワード
|
keywords: キーワード
|
||||||
#_ADD pack: pack type
|
#_ADD pack: pack type
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: 形
|
shape: 形
|
||||||
|
|||||||
@@ -924,6 +924,8 @@ type:
|
|||||||
keyword: słowo kluczowe (keyword)
|
keyword: słowo kluczowe (keyword)
|
||||||
keywords: słowa kluczowe (keywords)
|
keywords: słowa kluczowe (keywords)
|
||||||
pack: rodzaj paczki (pack type)
|
pack: rodzaj paczki (pack type)
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: kształt
|
shape: kształt
|
||||||
|
|||||||
@@ -891,6 +891,8 @@ type:
|
|||||||
keyword: palavra-chave
|
keyword: palavra-chave
|
||||||
keywords: palavras-chaves
|
keywords: palavras-chaves
|
||||||
pack: tipo de pacote
|
pack: tipo de pacote
|
||||||
|
#_ADD card region: card region
|
||||||
|
#_ADD card regions: card regions
|
||||||
|
|
||||||
# Symbol editor shapes
|
# Symbol editor shapes
|
||||||
shape: forma
|
shape: forma
|
||||||
|
|||||||
@@ -0,0 +1,25 @@
|
|||||||
|
//+----------------------------------------------------------------------------+
|
||||||
|
//| Description: Magic Set Editor - Program to make Magic (tm) cards |
|
||||||
|
//| Copyright: (C) Twan van Laarhoven and the other MSE developers |
|
||||||
|
//| License: GNU General Public License 2 or later (see file COPYING) |
|
||||||
|
//+----------------------------------------------------------------------------+
|
||||||
|
|
||||||
|
#include <util/prec.hpp>
|
||||||
|
#include <data/card_region.hpp>
|
||||||
|
|
||||||
|
CardRegion::CardRegion()
|
||||||
|
: name("")
|
||||||
|
, x(0.0)
|
||||||
|
, y(0.0)
|
||||||
|
, width(0)
|
||||||
|
, height(0)
|
||||||
|
{}
|
||||||
|
CardRegion::~CardRegion() {}
|
||||||
|
|
||||||
|
IMPLEMENT_REFLECTION(CardRegion) {
|
||||||
|
REFLECT(name);
|
||||||
|
REFLECT(x);
|
||||||
|
REFLECT(y);
|
||||||
|
REFLECT(width);
|
||||||
|
REFLECT(height);
|
||||||
|
}
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
//+----------------------------------------------------------------------------+
|
||||||
|
//| Description: Magic Set Editor - Program to make Magic (tm) cards |
|
||||||
|
//| Copyright: (C) Twan van Laarhoven and the other MSE developers |
|
||||||
|
//| License: GNU General Public License 2 or later (see file COPYING) |
|
||||||
|
//+----------------------------------------------------------------------------+
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <util/prec.hpp>
|
||||||
|
#include <util/reflect.hpp>
|
||||||
|
#include <script/scriptable.hpp>
|
||||||
|
|
||||||
|
DECLARE_POINTER_TYPE(CardRegion);
|
||||||
|
|
||||||
|
class CardRegion : public IntrusivePtrBase<CardRegion> {
|
||||||
|
public:
|
||||||
|
CardRegion();
|
||||||
|
virtual ~CardRegion();
|
||||||
|
|
||||||
|
String name;
|
||||||
|
double x, y;
|
||||||
|
int width, height;
|
||||||
|
|
||||||
|
private:
|
||||||
|
DECLARE_REFLECTION();
|
||||||
|
};
|
||||||
|
|
||||||
|
inline String type_name(const CardRegion&) {
|
||||||
|
return _TYPE_("card region");
|
||||||
|
}
|
||||||
|
|
||||||
|
inline String type_name(const vector<CardRegionP>&) {
|
||||||
|
return _TYPE_("card regions");
|
||||||
|
}
|
||||||
@@ -100,10 +100,10 @@ void export_image(const SetP& set, const CardP& card, const String& filename);
|
|||||||
|
|
||||||
/// Generate a bitmap image of a card
|
/// Generate a bitmap image of a card
|
||||||
Bitmap export_bitmap(const SetP& set, const CardP& card);
|
Bitmap export_bitmap(const SetP& set, const CardP& card);
|
||||||
|
Bitmap export_bitmap(const SetP& set, const CardP& card, const double zoom, const Radians angle_radians);
|
||||||
|
|
||||||
/// Export a set to Magic Workstation format
|
/// Export a set to Magic Workstation format
|
||||||
void export_mws(Window* parent, const SetP& set);
|
void export_mws(Window* parent, const SetP& set);
|
||||||
|
|
||||||
/// Export a set to Apprentice
|
/// Export a set to Apprentice
|
||||||
void export_apprentice(Window* parent, const SetP& set);
|
void export_apprentice(Window* parent, const SetP& set);
|
||||||
|
|
||||||
|
|||||||
@@ -26,14 +26,34 @@ void export_image(const SetP& set, const CardP& card, const String& filename) {
|
|||||||
|
|
||||||
class UnzoomedDataViewer : public DataViewer {
|
class UnzoomedDataViewer : public DataViewer {
|
||||||
public:
|
public:
|
||||||
|
UnzoomedDataViewer();
|
||||||
|
UnzoomedDataViewer(double zoom, double angle);
|
||||||
virtual ~UnzoomedDataViewer() {};
|
virtual ~UnzoomedDataViewer() {};
|
||||||
Rotation getRotation() const override;
|
Rotation getRotation() const override;
|
||||||
private:
|
private:
|
||||||
double angle = 0.0;
|
double zoom;
|
||||||
|
double angle;
|
||||||
|
bool declared_values;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
UnzoomedDataViewer::UnzoomedDataViewer()
|
||||||
|
: zoom(1.0)
|
||||||
|
, angle(0.0)
|
||||||
|
, declared_values(false)
|
||||||
|
{}
|
||||||
|
|
||||||
|
UnzoomedDataViewer::UnzoomedDataViewer(const double zoom, const Radians angle = 0.0)
|
||||||
|
: zoom(zoom)
|
||||||
|
, angle(angle)
|
||||||
|
, declared_values(true)
|
||||||
|
{}
|
||||||
|
|
||||||
Rotation UnzoomedDataViewer::getRotation() const {
|
Rotation UnzoomedDataViewer::getRotation() const {
|
||||||
if (!stylesheet) stylesheet = set->stylesheet;
|
if (!stylesheet) stylesheet = set->stylesheet;
|
||||||
|
if (declared_values) {
|
||||||
|
return Rotation(angle, stylesheet->getCardRect(), zoom, 1.0, ROTATION_ATTACH_TOP_LEFT);
|
||||||
|
}
|
||||||
|
|
||||||
double export_zoom = settings.stylesheetSettingsFor(set->stylesheetFor(card)).export_zoom();
|
double export_zoom = settings.stylesheetSettingsFor(set->stylesheetFor(card)).export_zoom();
|
||||||
bool use_viewer_rotation = !settings.stylesheetSettingsFor(set->stylesheetFor(card)).card_normal_export();
|
bool use_viewer_rotation = !settings.stylesheetSettingsFor(set->stylesheetFor(card)).card_normal_export();
|
||||||
|
|
||||||
@@ -46,14 +66,31 @@ Rotation UnzoomedDataViewer::getRotation() const {
|
|||||||
|
|
||||||
Bitmap export_bitmap(const SetP& set, const CardP& card) {
|
Bitmap export_bitmap(const SetP& set, const CardP& card) {
|
||||||
if (!set) throw Error(_("no set"));
|
if (!set) throw Error(_("no set"));
|
||||||
// create viewer
|
|
||||||
UnzoomedDataViewer viewer = UnzoomedDataViewer();
|
UnzoomedDataViewer viewer = UnzoomedDataViewer();
|
||||||
viewer.setSet(set);
|
viewer.setSet(set);
|
||||||
viewer.setCard(card);
|
viewer.setCard(card);
|
||||||
// size of cards
|
// size of cards
|
||||||
RealSize size = viewer.getRotation().getExternalSize();
|
RealSize size = viewer.getRotation().getExternalSize();
|
||||||
// create bitmap & dc
|
// create bitmap & dc
|
||||||
Bitmap bitmap((int) size.width, (int) size.height);
|
Bitmap bitmap((int)size.width, (int)size.height);
|
||||||
|
if (!bitmap.Ok()) throw InternalError(_("Unable to create bitmap"));
|
||||||
|
wxMemoryDC dc;
|
||||||
|
dc.SelectObject(bitmap);
|
||||||
|
// draw
|
||||||
|
viewer.draw(dc);
|
||||||
|
dc.SelectObject(wxNullBitmap);
|
||||||
|
return bitmap;
|
||||||
|
}
|
||||||
|
|
||||||
|
Bitmap export_bitmap(const SetP& set, const CardP& card, const double zoom, const Radians angle = 0.0) {
|
||||||
|
if (!set) throw Error(_("no set"));
|
||||||
|
UnzoomedDataViewer viewer = UnzoomedDataViewer(zoom, angle);
|
||||||
|
viewer.setSet(set);
|
||||||
|
viewer.setCard(card);
|
||||||
|
// size of cards
|
||||||
|
RealSize size = viewer.getRotation().getExternalSize();
|
||||||
|
// create bitmap & dc
|
||||||
|
Bitmap bitmap((int)size.width, (int)size.height);
|
||||||
if (!bitmap.Ok()) throw InternalError(_("Unable to create bitmap"));
|
if (!bitmap.Ok()) throw InternalError(_("Unable to create bitmap"));
|
||||||
wxMemoryDC dc;
|
wxMemoryDC dc;
|
||||||
dc.SelectObject(bitmap);
|
dc.SelectObject(bitmap);
|
||||||
|
|||||||
@@ -98,6 +98,7 @@ IMPLEMENT_REFLECTION(StyleSheet) {
|
|||||||
REFLECT(card_height);
|
REFLECT(card_height);
|
||||||
REFLECT(card_dpi);
|
REFLECT(card_dpi);
|
||||||
REFLECT(card_background);
|
REFLECT(card_background);
|
||||||
|
REFLECT(card_regions);
|
||||||
REFLECT(init_script);
|
REFLECT(init_script);
|
||||||
// styling
|
// styling
|
||||||
REFLECT(styling_fields);
|
REFLECT(styling_fields);
|
||||||
|
|||||||
@@ -12,11 +12,16 @@
|
|||||||
#include <util/io/package.hpp>
|
#include <util/io/package.hpp>
|
||||||
#include <util/real_point.hpp>
|
#include <util/real_point.hpp>
|
||||||
#include <script/scriptable.hpp>
|
#include <script/scriptable.hpp>
|
||||||
|
// This isn't strictly needed for this file,
|
||||||
|
// but CardRegion needs to be referenced from _somewhere_ in the codebase for compilation reasons.
|
||||||
|
// Eventually if somewhere else is using the type then this can be removed.
|
||||||
|
#include <data/card_region.hpp>
|
||||||
|
|
||||||
DECLARE_POINTER_TYPE(Game);
|
DECLARE_POINTER_TYPE(Game);
|
||||||
DECLARE_POINTER_TYPE(StyleSheet);
|
DECLARE_POINTER_TYPE(StyleSheet);
|
||||||
DECLARE_POINTER_TYPE(Field);
|
DECLARE_POINTER_TYPE(Field);
|
||||||
DECLARE_POINTER_TYPE(Style);
|
DECLARE_POINTER_TYPE(Style);
|
||||||
|
DECLARE_POINTER_TYPE(CardRegion);
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : StyleSheet
|
// ----------------------------------------------------------------------------- : StyleSheet
|
||||||
|
|
||||||
@@ -34,6 +39,7 @@ public:
|
|||||||
double card_height; ///< The height of a card in pixels
|
double card_height; ///< The height of a card in pixels
|
||||||
double card_dpi; ///< The resolution of a card in dots per inch
|
double card_dpi; ///< The resolution of a card in dots per inch
|
||||||
Color card_background; ///< The background color of cards
|
Color card_background; ///< The background color of cards
|
||||||
|
vector<CardRegionP> card_regions;
|
||||||
/// The styling for card fields
|
/// The styling for card fields
|
||||||
/** The indices should correspond to the card_fields in the Game */
|
/** The indices should correspond to the card_fields in the Game */
|
||||||
IndexMap<FieldP, StyleP> card_style;
|
IndexMap<FieldP, StyleP> card_style;
|
||||||
|
|||||||
@@ -443,6 +443,17 @@ bool BuiltInImage::operator == (const GeneratedImage& that) const {
|
|||||||
return that2 && name == that2->name;
|
return that2 && name == that2->name;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------- : ArbitraryImage
|
||||||
|
|
||||||
|
Image ArbitraryImage::generate(const Options& opt) const {
|
||||||
|
return image;
|
||||||
|
}
|
||||||
|
bool ArbitraryImage::operator == (const GeneratedImage& that) const {
|
||||||
|
const ArbitraryImage* that2 = dynamic_cast<const ArbitraryImage*>(&that);
|
||||||
|
return that2 && image.IsSameAs(that2->image);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : SymbolToImage
|
// ----------------------------------------------------------------------------- : SymbolToImage
|
||||||
|
|
||||||
SymbolToImage::SymbolToImage(bool is_local, const LocalFileName& filename, Age age, const SymbolVariationP& variation)
|
SymbolToImage::SymbolToImage(bool is_local, const LocalFileName& filename, Age age, const SymbolVariationP& variation)
|
||||||
|
|||||||
@@ -348,6 +348,19 @@ private:
|
|||||||
String name;
|
String name;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------- : Arbitrary
|
||||||
|
|
||||||
|
class ArbitraryImage : public GeneratedImage {
|
||||||
|
public:
|
||||||
|
inline ArbitraryImage(const Image image)
|
||||||
|
: image(image)
|
||||||
|
{}
|
||||||
|
Image generate(const Options& opt) const override;
|
||||||
|
bool operator == (const GeneratedImage& that) const override;
|
||||||
|
private:
|
||||||
|
Image image;
|
||||||
|
};
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : SymbolToImage
|
// ----------------------------------------------------------------------------- : SymbolToImage
|
||||||
|
|
||||||
/// Use a symbol as an image
|
/// Use a symbol as an image
|
||||||
|
|||||||
@@ -16,6 +16,7 @@
|
|||||||
#include <data/stylesheet.hpp>
|
#include <data/stylesheet.hpp>
|
||||||
#include <data/symbol.hpp>
|
#include <data/symbol.hpp>
|
||||||
#include <data/field/symbol.hpp>
|
#include <data/field/symbol.hpp>
|
||||||
|
#include <data/format/formats.hpp>
|
||||||
#include <gfx/generated_image.hpp>
|
#include <gfx/generated_image.hpp>
|
||||||
#include <render/symbol/filter.hpp>
|
#include <render/symbol/filter.hpp>
|
||||||
|
|
||||||
@@ -28,8 +29,35 @@ SCRIPT_FUNCTION(to_image) {
|
|||||||
return input;
|
return input;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SCRIPT_FUNCTION(to_card_image) {
|
||||||
|
SCRIPT_PARAM(Set*, set);
|
||||||
|
SCRIPT_PARAM(CardP, input);
|
||||||
|
SCRIPT_PARAM_DEFAULT(double, zoom, 100);
|
||||||
|
SCRIPT_PARAM_DEFAULT(Degrees, angle, 0);
|
||||||
|
SCRIPT_PARAM_DEFAULT(bool, use_user_settings, false);
|
||||||
|
if (use_user_settings) {
|
||||||
|
// Use the User's Preferences for Export Zoom and Angle settings.
|
||||||
|
return make_intrusive<ArbitraryImage>(export_bitmap(set, input).ConvertToImage());
|
||||||
|
} else {
|
||||||
|
// Use the provided (or defaulted) Zoom and Angle.
|
||||||
|
return make_intrusive<ArbitraryImage>(export_bitmap(set, input, (zoom / 100), deg_to_rad(angle)).ConvertToImage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : Image functions
|
// ----------------------------------------------------------------------------- : Image functions
|
||||||
|
|
||||||
|
SCRIPT_FUNCTION(width_of) {
|
||||||
|
SCRIPT_PARAM(GeneratedImageP, input);
|
||||||
|
Image image = input->generate(GeneratedImage::Options());
|
||||||
|
SCRIPT_RETURN(image.GetWidth());
|
||||||
|
}
|
||||||
|
|
||||||
|
SCRIPT_FUNCTION(height_of) {
|
||||||
|
SCRIPT_PARAM(GeneratedImageP, input);
|
||||||
|
Image image = input->generate(GeneratedImage::Options());
|
||||||
|
SCRIPT_RETURN(image.GetHeight());
|
||||||
|
}
|
||||||
|
|
||||||
SCRIPT_FUNCTION(linear_blend) {
|
SCRIPT_FUNCTION(linear_blend) {
|
||||||
SCRIPT_PARAM(GeneratedImageP, image1);
|
SCRIPT_PARAM(GeneratedImageP, image1);
|
||||||
SCRIPT_PARAM(GeneratedImageP, image2);
|
SCRIPT_PARAM(GeneratedImageP, image2);
|
||||||
@@ -210,6 +238,9 @@ SCRIPT_FUNCTION(built_in_image) {
|
|||||||
|
|
||||||
void init_script_image_functions(Context& ctx) {
|
void init_script_image_functions(Context& ctx) {
|
||||||
ctx.setVariable(_("to_image"), script_to_image);
|
ctx.setVariable(_("to_image"), script_to_image);
|
||||||
|
ctx.setVariable(_("to_card_image"), script_to_card_image);
|
||||||
|
ctx.setVariable(_("width_of"), script_width_of);
|
||||||
|
ctx.setVariable(_("height_of"), script_height_of);
|
||||||
ctx.setVariable(_("linear_blend"), script_linear_blend);
|
ctx.setVariable(_("linear_blend"), script_linear_blend);
|
||||||
ctx.setVariable(_("masked_blend"), script_masked_blend);
|
ctx.setVariable(_("masked_blend"), script_masked_blend);
|
||||||
ctx.setVariable(_("combine_blend"), script_combine_blend);
|
ctx.setVariable(_("combine_blend"), script_combine_blend);
|
||||||
|
|||||||
Reference in New Issue
Block a user