Improve native menu and status indicator icons conversion and checks.
This commit is contained in:
parent
e96ad5af98
commit
28ec2240c4
4 changed files with 44 additions and 88 deletions
|
@ -3172,42 +3172,13 @@ void DisplayServerMacOS::set_icon(const Ref<Image> &p_icon) {
|
||||||
|
|
||||||
DisplayServer::IndicatorID DisplayServerMacOS::create_status_indicator(const Ref<Texture2D> &p_icon, const String &p_tooltip, const Callable &p_callback) {
|
DisplayServer::IndicatorID DisplayServerMacOS::create_status_indicator(const Ref<Texture2D> &p_icon, const String &p_tooltip, const Callable &p_callback) {
|
||||||
NSImage *nsimg = nullptr;
|
NSImage *nsimg = nullptr;
|
||||||
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0) {
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
Ref<Image> img = p_icon->get_image();
|
Ref<Image> img = p_icon->get_image();
|
||||||
img = img->duplicate();
|
img = img->duplicate();
|
||||||
img->convert(Image::FORMAT_RGBA8);
|
if (img->is_compressed()) {
|
||||||
|
img->decompress();
|
||||||
NSBitmapImageRep *imgrep = [[NSBitmapImageRep alloc]
|
|
||||||
initWithBitmapDataPlanes:nullptr
|
|
||||||
pixelsWide:img->get_width()
|
|
||||||
pixelsHigh:img->get_height()
|
|
||||||
bitsPerSample:8
|
|
||||||
samplesPerPixel:4
|
|
||||||
hasAlpha:YES
|
|
||||||
isPlanar:NO
|
|
||||||
colorSpaceName:NSDeviceRGBColorSpace
|
|
||||||
bytesPerRow:img->get_width() * 4
|
|
||||||
bitsPerPixel:32];
|
|
||||||
if (imgrep) {
|
|
||||||
uint8_t *pixels = [imgrep bitmapData];
|
|
||||||
|
|
||||||
int len = img->get_width() * img->get_height();
|
|
||||||
const uint8_t *r = img->get_data().ptr();
|
|
||||||
|
|
||||||
/* Premultiply the alpha channel */
|
|
||||||
for (int i = 0; i < len; i++) {
|
|
||||||
uint8_t alpha = r[i * 4 + 3];
|
|
||||||
pixels[i * 4 + 0] = (uint8_t)(((uint16_t)r[i * 4 + 0] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 1] = (uint8_t)(((uint16_t)r[i * 4 + 1] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 2] = (uint8_t)(((uint16_t)r[i * 4 + 2] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 3] = alpha;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsimg = [[NSImage alloc] initWithSize:NSMakeSize(img->get_width(), img->get_height())];
|
|
||||||
if (nsimg) {
|
|
||||||
[nsimg addRepresentation:imgrep];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
nsimg = _convert_to_nsimg(img);
|
||||||
}
|
}
|
||||||
|
|
||||||
IndicatorData idat;
|
IndicatorData idat;
|
||||||
|
@ -3235,42 +3206,13 @@ void DisplayServerMacOS::status_indicator_set_icon(IndicatorID p_id, const Ref<T
|
||||||
ERR_FAIL_COND(!indicators.has(p_id));
|
ERR_FAIL_COND(!indicators.has(p_id));
|
||||||
|
|
||||||
NSImage *nsimg = nullptr;
|
NSImage *nsimg = nullptr;
|
||||||
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0) {
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
Ref<Image> img = p_icon->get_image();
|
Ref<Image> img = p_icon->get_image();
|
||||||
img = img->duplicate();
|
img = img->duplicate();
|
||||||
img->convert(Image::FORMAT_RGBA8);
|
if (img->is_compressed()) {
|
||||||
|
img->decompress();
|
||||||
NSBitmapImageRep *imgrep = [[NSBitmapImageRep alloc]
|
|
||||||
initWithBitmapDataPlanes:nullptr
|
|
||||||
pixelsWide:img->get_width()
|
|
||||||
pixelsHigh:img->get_height()
|
|
||||||
bitsPerSample:8
|
|
||||||
samplesPerPixel:4
|
|
||||||
hasAlpha:YES
|
|
||||||
isPlanar:NO
|
|
||||||
colorSpaceName:NSDeviceRGBColorSpace
|
|
||||||
bytesPerRow:img->get_width() * 4
|
|
||||||
bitsPerPixel:32];
|
|
||||||
if (imgrep) {
|
|
||||||
uint8_t *pixels = [imgrep bitmapData];
|
|
||||||
|
|
||||||
int len = img->get_width() * img->get_height();
|
|
||||||
const uint8_t *r = img->get_data().ptr();
|
|
||||||
|
|
||||||
/* Premultiply the alpha channel */
|
|
||||||
for (int i = 0; i < len; i++) {
|
|
||||||
uint8_t alpha = r[i * 4 + 3];
|
|
||||||
pixels[i * 4 + 0] = (uint8_t)(((uint16_t)r[i * 4 + 0] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 1] = (uint8_t)(((uint16_t)r[i * 4 + 1] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 2] = (uint8_t)(((uint16_t)r[i * 4 + 2] * alpha) / 255);
|
|
||||||
pixels[i * 4 + 3] = alpha;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsimg = [[NSImage alloc] initWithSize:NSMakeSize(img->get_width(), img->get_height())];
|
|
||||||
if (nsimg) {
|
|
||||||
[nsimg addRepresentation:imgrep];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
nsimg = _convert_to_nsimg(img);
|
||||||
}
|
}
|
||||||
|
|
||||||
NSStatusItem *item = indicators[p_id].item;
|
NSStatusItem *item = indicators[p_id].item;
|
||||||
|
|
|
@ -436,7 +436,7 @@ int NativeMenuMacOS::add_icon_item(const RID &p_rid, const Ref<Texture2D> &p_ico
|
||||||
obj->max_states = 0;
|
obj->max_states = 0;
|
||||||
obj->state = 0;
|
obj->state = 0;
|
||||||
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
||||||
if (ds && p_icon.is_valid()) {
|
if (ds && p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
obj->img = p_icon->get_image();
|
obj->img = p_icon->get_image();
|
||||||
obj->img = obj->img->duplicate();
|
obj->img = obj->img->duplicate();
|
||||||
if (obj->img->is_compressed()) {
|
if (obj->img->is_compressed()) {
|
||||||
|
@ -467,7 +467,7 @@ int NativeMenuMacOS::add_icon_check_item(const RID &p_rid, const Ref<Texture2D>
|
||||||
obj->max_states = 0;
|
obj->max_states = 0;
|
||||||
obj->state = 0;
|
obj->state = 0;
|
||||||
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
||||||
if (ds && p_icon.is_valid()) {
|
if (ds && p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
obj->img = p_icon->get_image();
|
obj->img = p_icon->get_image();
|
||||||
obj->img = obj->img->duplicate();
|
obj->img = obj->img->duplicate();
|
||||||
if (obj->img->is_compressed()) {
|
if (obj->img->is_compressed()) {
|
||||||
|
@ -518,7 +518,7 @@ int NativeMenuMacOS::add_icon_radio_check_item(const RID &p_rid, const Ref<Textu
|
||||||
obj->max_states = 0;
|
obj->max_states = 0;
|
||||||
obj->state = 0;
|
obj->state = 0;
|
||||||
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
||||||
if (ds && p_icon.is_valid()) {
|
if (ds && p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
obj->img = p_icon->get_image();
|
obj->img = p_icon->get_image();
|
||||||
obj->img = obj->img->duplicate();
|
obj->img = obj->img->duplicate();
|
||||||
if (obj->img->is_compressed()) {
|
if (obj->img->is_compressed()) {
|
||||||
|
@ -1212,7 +1212,7 @@ void NativeMenuMacOS::set_item_icon(const RID &p_rid, int p_idx, const Ref<Textu
|
||||||
GodotMenuItem *obj = [menu_item representedObject];
|
GodotMenuItem *obj = [menu_item representedObject];
|
||||||
ERR_FAIL_NULL(obj);
|
ERR_FAIL_NULL(obj);
|
||||||
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
DisplayServerMacOS *ds = (DisplayServerMacOS *)DisplayServer::get_singleton();
|
||||||
if (ds && p_icon.is_valid()) {
|
if (ds && p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
obj->img = p_icon->get_image();
|
obj->img = p_icon->get_image();
|
||||||
obj->img = obj->img->duplicate();
|
obj->img = obj->img->duplicate();
|
||||||
if (obj->img->is_compressed()) {
|
if (obj->img->is_compressed()) {
|
||||||
|
|
|
@ -3171,9 +3171,12 @@ void DisplayServerWindows::set_icon(const Ref<Image> &p_icon) {
|
||||||
|
|
||||||
DisplayServer::IndicatorID DisplayServerWindows::create_status_indicator(const Ref<Texture2D> &p_icon, const String &p_tooltip, const Callable &p_callback) {
|
DisplayServer::IndicatorID DisplayServerWindows::create_status_indicator(const Ref<Texture2D> &p_icon, const String &p_tooltip, const Callable &p_callback) {
|
||||||
HICON hicon = nullptr;
|
HICON hicon = nullptr;
|
||||||
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0) {
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
Ref<Image> img = p_icon->get_image();
|
Ref<Image> img = p_icon->get_image();
|
||||||
img = img->duplicate();
|
img = img->duplicate();
|
||||||
|
if (img->is_compressed()) {
|
||||||
|
img->decompress();
|
||||||
|
}
|
||||||
img->convert(Image::FORMAT_RGBA8);
|
img->convert(Image::FORMAT_RGBA8);
|
||||||
|
|
||||||
int w = img->get_width();
|
int w = img->get_width();
|
||||||
|
@ -3241,9 +3244,12 @@ void DisplayServerWindows::status_indicator_set_icon(IndicatorID p_id, const Ref
|
||||||
ERR_FAIL_COND(!indicators.has(p_id));
|
ERR_FAIL_COND(!indicators.has(p_id));
|
||||||
|
|
||||||
HICON hicon = nullptr;
|
HICON hicon = nullptr;
|
||||||
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0) {
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
Ref<Image> img = p_icon->get_image();
|
Ref<Image> img = p_icon->get_image();
|
||||||
img = img->duplicate();
|
img = img->duplicate();
|
||||||
|
if (img->is_compressed()) {
|
||||||
|
img->decompress();
|
||||||
|
}
|
||||||
img->convert(Image::FORMAT_RGBA8);
|
img->convert(Image::FORMAT_RGBA8);
|
||||||
|
|
||||||
int w = img->get_width();
|
int w = img->get_width();
|
||||||
|
|
|
@ -35,6 +35,8 @@
|
||||||
#include "scene/resources/image_texture.h"
|
#include "scene/resources/image_texture.h"
|
||||||
|
|
||||||
HBITMAP NativeMenuWindows::_make_bitmap(const Ref<Image> &p_img) const {
|
HBITMAP NativeMenuWindows::_make_bitmap(const Ref<Image> &p_img) const {
|
||||||
|
p_img->convert(Image::FORMAT_RGBA8);
|
||||||
|
|
||||||
Vector2i texture_size = p_img->get_size();
|
Vector2i texture_size = p_img->get_size();
|
||||||
UINT image_size = texture_size.width * texture_size.height;
|
UINT image_size = texture_size.width * texture_size.height;
|
||||||
|
|
||||||
|
@ -349,12 +351,14 @@ int NativeMenuWindows::add_icon_item(const RID &p_rid, const Ref<Texture2D> &p_i
|
||||||
item_data->checkable_type = CHECKABLE_TYPE_NONE;
|
item_data->checkable_type = CHECKABLE_TYPE_NONE;
|
||||||
item_data->max_states = 0;
|
item_data->max_states = 0;
|
||||||
item_data->state = 0;
|
item_data->state = 0;
|
||||||
item_data->img = p_icon->get_image();
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
item_data->img = item_data->img->duplicate();
|
item_data->img = p_icon->get_image();
|
||||||
if (item_data->img->is_compressed()) {
|
item_data->img = item_data->img->duplicate();
|
||||||
item_data->img->decompress();
|
if (item_data->img->is_compressed()) {
|
||||||
|
item_data->img->decompress();
|
||||||
|
}
|
||||||
|
item_data->bmp = _make_bitmap(item_data->img);
|
||||||
}
|
}
|
||||||
item_data->bmp = _make_bitmap(item_data->img);
|
|
||||||
|
|
||||||
Char16String label = p_label.utf16();
|
Char16String label = p_label.utf16();
|
||||||
MENUITEMINFOW item;
|
MENUITEMINFOW item;
|
||||||
|
@ -389,12 +393,14 @@ int NativeMenuWindows::add_icon_check_item(const RID &p_rid, const Ref<Texture2D
|
||||||
item_data->checkable_type = CHECKABLE_TYPE_CHECK_BOX;
|
item_data->checkable_type = CHECKABLE_TYPE_CHECK_BOX;
|
||||||
item_data->max_states = 0;
|
item_data->max_states = 0;
|
||||||
item_data->state = 0;
|
item_data->state = 0;
|
||||||
item_data->img = p_icon->get_image();
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
item_data->img = item_data->img->duplicate();
|
item_data->img = p_icon->get_image();
|
||||||
if (item_data->img->is_compressed()) {
|
item_data->img = item_data->img->duplicate();
|
||||||
item_data->img->decompress();
|
if (item_data->img->is_compressed()) {
|
||||||
|
item_data->img->decompress();
|
||||||
|
}
|
||||||
|
item_data->bmp = _make_bitmap(item_data->img);
|
||||||
}
|
}
|
||||||
item_data->bmp = _make_bitmap(item_data->img);
|
|
||||||
|
|
||||||
Char16String label = p_label.utf16();
|
Char16String label = p_label.utf16();
|
||||||
MENUITEMINFOW item;
|
MENUITEMINFOW item;
|
||||||
|
@ -462,12 +468,14 @@ int NativeMenuWindows::add_icon_radio_check_item(const RID &p_rid, const Ref<Tex
|
||||||
item_data->checkable_type = CHECKABLE_TYPE_RADIO_BUTTON;
|
item_data->checkable_type = CHECKABLE_TYPE_RADIO_BUTTON;
|
||||||
item_data->max_states = 0;
|
item_data->max_states = 0;
|
||||||
item_data->state = 0;
|
item_data->state = 0;
|
||||||
item_data->img = p_icon->get_image();
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
item_data->img = item_data->img->duplicate();
|
item_data->img = p_icon->get_image();
|
||||||
if (item_data->img->is_compressed()) {
|
item_data->img = item_data->img->duplicate();
|
||||||
item_data->img->decompress();
|
if (item_data->img->is_compressed()) {
|
||||||
|
item_data->img->decompress();
|
||||||
|
}
|
||||||
|
item_data->bmp = _make_bitmap(item_data->img);
|
||||||
}
|
}
|
||||||
item_data->bmp = _make_bitmap(item_data->img);
|
|
||||||
|
|
||||||
Char16String label = p_label.utf16();
|
Char16String label = p_label.utf16();
|
||||||
MENUITEMINFOW item;
|
MENUITEMINFOW item;
|
||||||
|
@ -1082,7 +1090,7 @@ void NativeMenuWindows::set_item_icon(const RID &p_rid, int p_idx, const Ref<Tex
|
||||||
if (item_data->bmp) {
|
if (item_data->bmp) {
|
||||||
DeleteObject(item_data->bmp);
|
DeleteObject(item_data->bmp);
|
||||||
}
|
}
|
||||||
if (p_icon.is_valid()) {
|
if (p_icon.is_valid() && p_icon->get_width() > 0 && p_icon->get_height() > 0 && p_icon->get_image().is_valid()) {
|
||||||
item_data->img = p_icon->get_image();
|
item_data->img = p_icon->get_image();
|
||||||
item_data->img = item_data->img->duplicate();
|
item_data->img = item_data->img->duplicate();
|
||||||
if (item_data->img->is_compressed()) {
|
if (item_data->img->is_compressed()) {
|
||||||
|
|
Loading…
Reference in a new issue