diff --git a/src/data/field.cpp b/src/data/field.cpp index 617aca62..dd781981 100644 --- a/src/data/field.cpp +++ b/src/data/field.cpp @@ -183,8 +183,8 @@ void Style::removeListener(StyleListener* listener) { listeners.end() ); } -void Style::tellListeners() { - FOR_EACH(l, listeners) l->onStyleChange(); +void Style::tellListeners(bool already_prepared) { + FOR_EACH(l, listeners) l->onStyleChange(already_prepared); } StyleListener::StyleListener(const StyleP& style) diff --git a/src/data/field.hpp b/src/data/field.hpp index 8a7c5211..5f26f68b 100644 --- a/src/data/field.hpp +++ b/src/data/field.hpp @@ -132,7 +132,7 @@ class Style : public IntrusivePtrVirtualBase { /// Remove a StyleListener void removeListener(StyleListener*); /// Tell the StyleListeners that this style has changed - void tellListeners(); + void tellListeners(bool already_prepared); private: DECLARE_REFLECTION_VIRTUAL(); @@ -156,7 +156,8 @@ class StyleListener : public IntrusivePtrVirtualBase { virtual ~StyleListener(); /// Called when a (scripted) property of the viewed style has changed - virtual void onStyleChange() {} + /** already_prepared indicates that this change happend after preparing text for content properties */ + virtual void onStyleChange(bool already_prepared) {} protected: const StyleP styleP; ///< The style we are listening to }; diff --git a/src/data/field/choice.cpp b/src/data/field/choice.cpp index 8bc2984c..f9227187 100644 --- a/src/data/field/choice.cpp +++ b/src/data/field/choice.cpp @@ -252,7 +252,7 @@ void ChoiceStyle::invalidate(Context& ctx) { thumbnails_status[i] = THUMB_CHANGED; } } - if (change) tellListeners(); + if (change) tellListeners(false); } void ChoiceStyle::loadMask(Package& pkg) { diff --git a/src/render/card/viewer.cpp b/src/render/card/viewer.cpp index 2c8370c1..ea8b6a29 100644 --- a/src/render/card/viewer.cpp +++ b/src/render/card/viewer.cpp @@ -83,7 +83,7 @@ void DataViewer::updateStyles(bool only_content_dependent) { Style& s = *v->getStyle(); if (only_content_dependent && !s.content_dependent) continue; if (s.update(ctx)) { - s.tellListeners(); + s.tellListeners(only_content_dependent); } } } diff --git a/src/render/text/viewer.cpp b/src/render/text/viewer.cpp index ec5eda3b..276d5827 100644 --- a/src/render/text/viewer.cpp +++ b/src/render/text/viewer.cpp @@ -146,6 +146,9 @@ void TextViewer::reset() { elements.clear(); lines.clear(); } +bool TextViewer::prepared() const { + return !lines.empty(); +} // ----------------------------------------------------------------------------- : Positions diff --git a/src/render/text/viewer.hpp b/src/render/text/viewer.hpp index 03aa4ca6..bf79c168 100644 --- a/src/render/text/viewer.hpp +++ b/src/render/text/viewer.hpp @@ -58,6 +58,8 @@ class TextViewer { bool prepare(RotatedDC& dc, const String& text, TextStyle& style, Context&); /// Reset the cached data, at a new call to draw it will be recalculated void reset(); + /// Is the viewer prepare()d? + bool prepared() const; // --------------------------------------------------- : Positions diff --git a/src/render/value/choice.cpp b/src/render/value/choice.cpp index fae43ab1..4769a6c5 100644 --- a/src/render/value/choice.cpp +++ b/src/render/value/choice.cpp @@ -72,6 +72,6 @@ void ChoiceValueViewer::draw(RotatedDC& dc) { } } -void ChoiceValueViewer::onStyleChange() { - viewer.redraw(*this); +void ChoiceValueViewer::onStyleChange(bool already_prepared) { + if (!already_prepared) viewer.redraw(*this); } diff --git a/src/render/value/choice.hpp b/src/render/value/choice.hpp index 95419dd9..2f13b147 100644 --- a/src/render/value/choice.hpp +++ b/src/render/value/choice.hpp @@ -21,7 +21,7 @@ class ChoiceValueViewer : public ValueViewer { DECLARE_VALUE_VIEWER(Choice) : ValueViewer(parent,style) {} virtual void draw(RotatedDC& dc); - virtual void onStyleChange(); + virtual void onStyleChange(bool); }; // ----------------------------------------------------------------------------- : EOF diff --git a/src/render/value/color.cpp b/src/render/value/color.cpp index 7f030174..125a5cf0 100644 --- a/src/render/value/color.cpp +++ b/src/render/value/color.cpp @@ -86,9 +86,9 @@ bool ColorValueViewer::containsPoint(const RealPoint& p) const { } } -void ColorValueViewer::onStyleChange() { +void ColorValueViewer::onStyleChange(bool already_prepared) { alpha_mask = AlphaMaskP(); - viewer.redraw(*this); + if (!already_prepared) viewer.redraw(*this); } void ColorValueViewer::loadMask(const Rotation& rot) const { diff --git a/src/render/value/color.hpp b/src/render/value/color.hpp index 4cf39104..462e6dbc 100644 --- a/src/render/value/color.hpp +++ b/src/render/value/color.hpp @@ -25,7 +25,7 @@ class ColorValueViewer : public ValueViewer { virtual void draw(RotatedDC& dc); virtual bool containsPoint(const RealPoint& p) const; - virtual void onStyleChange(); + virtual void onStyleChange(bool); private: mutable AlphaMaskP alpha_mask; diff --git a/src/render/value/image.cpp b/src/render/value/image.cpp index 3f8c4c10..7b3e5df9 100644 --- a/src/render/value/image.cpp +++ b/src/render/value/image.cpp @@ -77,10 +77,10 @@ void ImageValueViewer::onValueChange() { bitmap = Bitmap(); } -void ImageValueViewer::onStyleChange() { +void ImageValueViewer::onStyleChange(bool already_prepared) { bitmap = Bitmap(); alpha_mask = AlphaMaskP(); // TODO: only reload whatever has changed - viewer.redraw(*this); + if (!already_prepared) viewer.redraw(*this); } void ImageValueViewer::loadMask(const Rotation& rot) const { diff --git a/src/render/value/image.hpp b/src/render/value/image.hpp index 440701dc..4dcc195e 100644 --- a/src/render/value/image.hpp +++ b/src/render/value/image.hpp @@ -27,7 +27,7 @@ class ImageValueViewer : public ValueViewer { virtual bool containsPoint(const RealPoint& p) const; virtual void onValueChange(); - virtual void onStyleChange(); + virtual void onStyleChange(bool); private: Bitmap bitmap; diff --git a/src/render/value/text.cpp b/src/render/value/text.cpp index 5c25e251..23eedee3 100644 --- a/src/render/value/text.cpp +++ b/src/render/value/text.cpp @@ -21,12 +21,14 @@ bool TextValueViewer::prepare(RotatedDC& dc) { style().mask.load(image); } } - v.prepare(dc, value().value(), style(), viewer.getContext()); - return true; + return v.prepare(dc, value().value(), style(), viewer.getContext()); } void TextValueViewer::draw(RotatedDC& dc) { drawFieldBorder(dc); + if (!v.prepared()) { + v.prepare(dc, value().value(), style(), viewer.getContext()); + } v.draw(dc, style(), (DrawWhat)( DRAW_NORMAL | (viewer.drawBorders() ? DRAW_BORDERS : 0) @@ -38,7 +40,7 @@ void TextValueViewer::onValueChange() { v.reset(); } -void TextValueViewer::onStyleChange() { +void TextValueViewer::onStyleChange(bool already_prepared) { v.reset(); - viewer.redraw(*this); + if (!already_prepared) viewer.redraw(*this); } diff --git a/src/render/value/text.hpp b/src/render/value/text.hpp index 4d8e7ce6..9eafd66e 100644 --- a/src/render/value/text.hpp +++ b/src/render/value/text.hpp @@ -24,7 +24,7 @@ class TextValueViewer : public ValueViewer { virtual bool prepare(RotatedDC& dc); virtual void draw(RotatedDC& dc); virtual void onValueChange(); - virtual void onStyleChange(); + virtual void onStyleChange(bool); protected: TextViewer v; diff --git a/src/render/value/viewer.hpp b/src/render/value/viewer.hpp index a001dc44..53607a2f 100644 --- a/src/render/value/viewer.hpp +++ b/src/render/value/viewer.hpp @@ -57,7 +57,8 @@ class ValueViewer : public StyleListener { */ virtual void onValueChange() {} /// Called when a (scripted) property of the associated style has changed - virtual void onStyleChange() {} + /** If alread_prepared, should make sure the viewer stays in a state similair to that after prepare() */ + virtual void onStyleChange(bool already_prepared) {} /// Called when an action is performed on the associated value virtual void onAction(const Action&, bool undone) { onValueChange(); } diff --git a/src/script/script_manager.cpp b/src/script/script_manager.cpp index 4ed0f048..be96c492 100644 --- a/src/script/script_manager.cpp +++ b/src/script/script_manager.cpp @@ -226,7 +226,7 @@ void SetScriptManager::updateStyles(Context& ctx, const IndexMap& try { if (s->update(ctx)) { // style has changed, tell listeners - s->tellListeners(); + s->tellListeners(only_content_dependent); } } catch (const ScriptError& e) { throw ScriptError(e.what() + _("\n while updating styles for '") + s->fieldP->name + _("'"));