8252015: [macos11] java.awt.TrayIcon requires updates for template images

Co-authored-by: Tres Finocchiaro <tres.finocchiaro@gmail.com>
Co-authored-by: Peter Zhelezniakov <peterz@openjdk.org>
Reviewed-by: serb
This commit is contained in:
Peter Zhelezniakov 2021-01-12 11:50:19 +00:00 committed by Alexander Scherbatiy
parent ac2dee567b
commit 400dc76f68
4 changed files with 28 additions and 39 deletions

View File

@ -45,6 +45,8 @@ import java.awt.geom.Point2D;
import java.awt.image.BufferedImage;
import java.awt.image.ImageObserver;
import java.awt.peer.TrayIconPeer;
import java.security.AccessController;
import java.security.PrivilegedAction;
import javax.swing.Icon;
import javax.swing.UIManager;
@ -69,6 +71,10 @@ public class CTrayIcon extends CFRetainedResource implements TrayIconPeer {
// events between MOUSE_PRESSED and MOUSE_RELEASED for particular button
private static int mouseClickButtons = 0;
private final static boolean useTemplateImages = AccessController.doPrivileged((PrivilegedAction<Boolean>)
() -> Boolean.getBoolean("apple.awt.enableTemplateImages")
);
CTrayIcon(TrayIcon target) {
super(0, true);
@ -211,13 +217,13 @@ public class CTrayIcon extends CFRetainedResource implements TrayIconPeer {
if (cimage != null) {
cimage.execute(imagePtr -> {
execute(ptr -> {
setNativeImage(ptr, imagePtr, imageAutoSize);
setNativeImage(ptr, imagePtr, imageAutoSize, useTemplateImages);
});
});
}
}
private native void setNativeImage(final long model, final long nsimage, final boolean autosize);
private native void setNativeImage(final long model, final long nsimage, final boolean autosize, final boolean template);
private void postEvent(final AWTEvent event) {
SunToolkit.executeOnEventHandlerThread(target, new Runnable() {

View File

@ -52,7 +52,7 @@ extern "C" {
- (void) setTooltip:(NSString *)tooltip;
- (NSStatusItem *)theItem;
- (jobject) peer;
- (void) setImage:(NSImage *) imagePtr sizing:(BOOL)autosize;
- (void) setImage:(NSImage *) imagePtr sizing:(BOOL)autosize template:(BOOL)isTemplate;
- (NSPoint) getLocationOnScreen;
- (void) deliverJavaMouseEvent:(NSEvent*) event;
@ -61,16 +61,14 @@ extern "C" {
//==================================================================================
/*
* AWTTrayIconView */
@interface AWTTrayIconView : NSView <NSMenuDelegate> {
@interface AWTTrayIconView : NSStatusBarButton <NSMenuDelegate> {
@public
AWTTrayIcon *trayIcon;
NSImage* image;
NSTrackingArea *trackingArea;
BOOL isHighlighted;
}
-(id)initWithTrayIcon:(AWTTrayIcon *)theTrayIcon;
-(void)setHighlighted:(BOOL)aFlag;
-(void)setImage:(NSImage*)anImage;
-(void)setTrayIcon:(AWTTrayIcon*)theTrayIcon;
-(void)addTrackingArea;

View File

@ -104,7 +104,7 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
return peer;
}
- (void) setImage:(NSImage *) imagePtr sizing:(BOOL)autosize {
- (void) setImage:(NSImage *) imagePtr sizing:(BOOL)autosize template:(BOOL)isTemplate {
NSSize imageSize = [imagePtr size];
NSSize scaledSize = ScaledImageSizeForStatusBar(imageSize, autosize);
if (imageSize.width != scaledSize.width ||
@ -115,6 +115,7 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
CGFloat itemLength = scaledSize.width + 2.0*kImageInset;
[theItem setLength:itemLength];
[imagePtr setTemplate: isTemplate];
[view setImage:imagePtr];
}
@ -176,8 +177,8 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
self = [super initWithFrame:NSMakeRect(0, 0, 1, 1)];
[self setTrayIcon: theTrayIcon];
[self setImage: nil];
isHighlighted = NO;
image = nil;
trackingArea = nil;
[self addTrackingArea];
@ -197,7 +198,6 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
}
-(void) dealloc {
[image release];
[trackingArea release];
[super dealloc];
}
@ -210,16 +210,6 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
}
}
- (void)setImage:(NSImage*)anImage {
[anImage retain];
[image release];
image = anImage;
if (image != nil) {
[self setNeedsDisplay:YES];
}
}
-(void)setTrayIcon:(AWTTrayIcon*)theTrayIcon {
trayIcon = theTrayIcon;
}
@ -237,29 +227,15 @@ static NSSize ScaledImageSizeForStatusBar(NSSize imageSize, BOOL autosize) {
- (void)drawRect:(NSRect)dirtyRect
{
if (image == nil) {
if (self.image == nil) {
return;
}
NSRect bounds = [self bounds];
NSSize imageSize = [image size];
NSRect drawRect = {{ (bounds.size.width - imageSize.width) / 2.0,
(bounds.size.height - imageSize.height) / 2.0 }, imageSize};
// don't cover bottom pixels of the status bar with the image
if (drawRect.origin.y < 1.0) {
drawRect.origin.y = 1.0;
}
drawRect = NSIntegralRect(drawRect);
[trayIcon.theItem drawStatusBarBackgroundInRect:bounds
withHighlight:isHighlighted];
[image drawInRect:drawRect
fromRect:NSZeroRect
operation:NSCompositeSourceOver
fraction:1.0
];
[super drawRect: dirtyRect];
}
- (void)mouseDown:(NSEvent *)event {
@ -377,15 +353,15 @@ JNF_COCOA_EXIT(env);
/*
* Class: sun_lwawt_macosx_CTrayIcon
* Method: setNativeImage
* Signature: (JJZ)V
* Signature: (JJZZ)V
*/
JNIEXPORT void JNICALL Java_sun_lwawt_macosx_CTrayIcon_setNativeImage
(JNIEnv *env, jobject self, jlong model, jlong imagePtr, jboolean autosize) {
(JNIEnv *env, jobject self, jlong model, jlong imagePtr, jboolean autosize, jboolean isTemplate) {
JNF_COCOA_ENTER(env);
AWTTrayIcon *icon = jlong_to_ptr(model);
[ThreadUtilities performOnMainThreadWaiting:YES block:^(){
[icon setImage:jlong_to_ptr(imagePtr) sizing:autosize];
[icon setImage:jlong_to_ptr(imagePtr) sizing:autosize template:isTemplate];
}];
JNF_COCOA_EXIT(env);

View File

@ -71,6 +71,15 @@ import java.security.AccessController;
* a {@code TrayIcon}. Otherwise the constructor will throw a
* SecurityException.
*
* <p>
* @implnote
* When the {@systemProperty apple.awt.enableTemplateImages} property is
* set, all images associated with instances of this class are treated
* as template images by the native desktop system. This means all color
* information is discarded, and the image is adapted automatically to
* be visible when desktop theme and/or colors change. This property
* only affects MacOSX.
*
* <p> See the {@link SystemTray} class overview for an example on how
* to use the {@code TrayIcon} API.
*