Allow using an Fl_SVG_Image object as window icon.

Fix for issue #90: Setting an svg image as a window icon causes a segfault.
This commit is contained in:
ManoloFLTK 2020-06-15 19:05:34 +02:00
parent 91b78572c7
commit 46b89686df
6 changed files with 24 additions and 3 deletions

View File

@ -273,6 +273,7 @@ public:
static bool register_images_done;
};
class Fl_SVG_Image;
/**
The Fl_RGB_Image class supports caching and drawing
@ -291,6 +292,7 @@ class FL_EXPORT Fl_RGB_Image : public Fl_Image {
public:
/** Points to the start of the object's data array
\see class Fl_SVG_Image which delays initialization of this member variable.
*/
const uchar *array;
/** If non-zero, the object's data array is delete[]'d when deleting the object.
@ -332,6 +334,12 @@ public:
\sa void Fl_RGB_Image::max_size(size_t)
*/
static size_t max_size() {return max_size_;}
/** Returns whether an image is an Fl_SVG_Image or not.
This virtual method returns a pointer to the Fl_SVG_Image if this object is an instance of Fl_SVG_Image or NULL if not. */
virtual Fl_SVG_Image *as_svg_image() { return NULL; }
/** Makes sure the object is fully initialized.
In particular, makes sure member variable \ref array is non-null. */
virtual void normalize() {}
};
#endif // !Fl_Image_H

View File

@ -31,7 +31,7 @@ struct NSVGimage;
if the file could not be opened or read, and ERR_FORMAT if the SVG format could not be decoded.
If the image has loaded correctly, w(), h(), and d() should return values greater than zero.
Rasterization is not done until the image is first drawn or resize() is called. Therefore,
Rasterization is not done until the image is first drawn or resize() or normalize() is called. Therefore,
\ref array is NULL until then. The delayed rasterization ensures an Fl_SVG_Image is always rasterized
to the exact screen resolution at which it is drawn.
@ -161,6 +161,8 @@ public:
virtual void color_average(Fl_Color c, float i);
virtual void draw(int X, int Y, int W, int H, int cx = 0, int cy = 0);
void draw(int X, int Y) { draw(X, Y, w(), h(), 0, 0); }
virtual Fl_SVG_Image *as_svg_image() { return this; };
virtual void normalize();
};
#endif // FL_SVG_IMAGE_H

View File

@ -266,6 +266,12 @@ void Fl_SVG_Image::color_average(Fl_Color c, float i) {
Fl_RGB_Image::color_average(c, i);
}
/** Makes sure the object is fully initialized.
This function rasterizes the SVG image if that was not done before. */
void Fl_SVG_Image::normalize() {
if (!array) resize(w(), h());
}
#endif // FLTK_USE_NANOSVG
//

View File

@ -4516,6 +4516,7 @@ void Fl_Cocoa_Window_Driver::icons(const Fl_RGB_Image *icons[], int count) {
[icon_image release];
icon_image = nil;
if (count >= 1 && pWindow->border() && pWindow->label() && strlen(pWindow->label())) {
((Fl_RGB_Image*)icons[0])->normalize();
icon_image = rgb_to_nsimage(icons[0]);
}
}

View File

@ -379,8 +379,10 @@ void Fl_WinAPI_Window_Driver::icons(const Fl_RGB_Image *icons[], int count) {
icon_->icons = new Fl_RGB_Image*[count];
icon_->count = count;
// FIXME: Fl_RGB_Image lacks const modifiers on methods
for (int i = 0;i < count;i++)
for (int i = 0;i < count;i++) {
icon_->icons[i] = (Fl_RGB_Image*)((Fl_RGB_Image*)icons[i])->copy();
icon_->icons[i]->normalize();
}
}
if (Fl_X::i(pWindow))

View File

@ -356,8 +356,10 @@ void Fl_X11_Window_Driver::icons(const Fl_RGB_Image *icons[], int count) {
icon_->icons = new Fl_RGB_Image*[count];
icon_->count = count;
// FIXME: Fl_RGB_Image lacks const modifiers on methods
for (int i = 0;i < count;i++)
for (int i = 0;i < count;i++) {
icon_->icons[i] = (Fl_RGB_Image*)((Fl_RGB_Image*)icons[i])->copy();
icon_->icons[i]->normalize();
}
}
if (Fl_X::i(pWindow))