{%MainUnit customdrawnwsmenus.pas} // used from the MenuMadness example function NSMenuCheckmark: NSImage; begin Result:=NSImage.imageNamed(NSString.alloc.initWithCString('NSMenuCheckmark')); end; function NSMenuRadio: NSImage; begin Result:=NSImage.imageNamed(NSString.alloc.initWithCString('NSMenuRadio')) end; function isSeparator(const ACaption: AnsiString): Boolean; begin Result:=ACaption='-'; end; function MenuCaption(const ACaption: AnsiString): AnsiString; var i : Integer; begin i:=Pos('&', ACaption); if i>0 then Result:=Copy(ACaption, 1, i-1)+Copy(ACaption,i+1, length(ACaption)) else Result:=ACaption; end; { TCDWSMenu } {------------------------------------------------------------------------------ Method: TCDWSMenu.CreateHandle Params: AMenu - LCL menu Returns: Handle to the menu in Cocoa interface Creates new menu in Cocoa interface ------------------------------------------------------------------------------} class function TCDWSMenu.CreateHandle(const AMenu: TMenu): HMENU; begin Result:=HMENU(TCocoaMenu.alloc.initWithTitle(NSString.alloc.initWithCString('hello world'))); end; { TCDWSMenuItem } {------------------------------------------------------------------------------ Method: TCDWSMenuItem.AttachMenu Params: AMenuItem - LCL menu item Attaches menu item to its parent menu in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSMenuItem.AttachMenu(const AMenuItem: TMenuItem); var ParObj : NSObject; Parent : TCocoaMenu; item : NSMenuItem; begin if not Assigned(AMenuItem) or (AMenuItem.Handle=0) or not Assigned(AMenuItem.Parent) or (AMenuItem.Parent.Handle=0) then Exit; ParObj:=NSObject(AMenuItem.Parent.Handle); if ParObj.isKindOfClass_(NSMenuItem) then begin item:=NSMenuItem(AMenuItem.Handle); if not item.hasSubmenu then item.setSubmenu(TCocoaMenu.alloc.initWithTitle(NSSTR(''))); Parent:=TCocoaMenu(item.submenu); end else if ParObj.isKindOfClass_(NSMenu) then Parent:=TCocoaMenu(ParObj) else Exit; item:=NSMenuItem(AMenuItem.Handle); Parent.insertItem_atIndex(item, Parent.itemArray.count); end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.CreateHandle Params: AMenuItem - LCL menu item Returns: Handle to the menu item in Cocoa interface Creates new menu item in Cocoa interface ------------------------------------------------------------------------------} class function TCDWSMenuItem.CreateHandle(const AMenuItem: TMenuItem): HMENU; var item : NSMenuItem; ns : NSString; begin if not Assigned(AMenuItem) then Exit; if AMenuItem.Caption='-' then item:=NSMenuItem.separatorItem else begin ns := NSStringUtf8(AMenuItem.Caption); item:=TCocoaMenuItem.alloc.initWithTitle_action_keyEquivalent( NSStringUtf8(AMenuItem.Caption), objcselector('lclItemSelected:'), NSString.alloc.init); ns.release; item.setTarget(item); item.setEnabled(AMenuItem.Enabled); end; Result:=HMENU(item); end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.DestroyHandle Params: AMenuItem - LCL menu item Destroys menu item in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSMenuItem.DestroyHandle(const AMenuItem: TMenuItem); begin end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetCaption Params: AMenuItem - LCL menu item ACaption - Menu item caption Sets the caption of menu item in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSMenuItem.SetCaption(const AMenuItem: TMenuItem; const ACaption: string); var ns : NSString; begin if not Assigned(AMenuItem) or (AMenuItem.Handle=0) then Exit; ns:=NSStringUtf8(ACaption); NSMenuItem(AMenuItem.Handle).setTitle(ns); ns.release; end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetShortCut Params: AMenuItem - LCL menu item ShortCutK1 and ShortCutK2 - New shortcut key1 and key2 Sets the shortcut of menu item in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSMenuItem.SetShortCut(const AMenuItem: TMenuItem; const ShortCutK1, ShortCutK2: TShortCut); begin end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetVisible Params: AMenuItem - LCL menu item Visible - Menu item visibility Sets the visibility of menu item in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSMenuItem.SetVisible(const AMenuItem: TMenuItem; const Visible: boolean); begin if not Assigned(AMenuItem) or (AMenuItem.Handle=0) then Exit; NSMenuItem(AMenuItem.Handle).setHidden( not Visible ); end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetCheck Params: AMenuItem - LCL menu item Checked - Menu item checked Returns: If the function succeeds Sets the check of menu item in Cocoa interface ------------------------------------------------------------------------------} class function TCDWSMenuItem.SetCheck(const AMenuItem: TMenuItem; const Checked: boolean): boolean; const menustate : array [Boolean] of NSInteger = (NSOffState, NSOnState); begin Result:=Assigned(AMenuItem) and (AMenuItem.Handle<>0); if not Result then Exit; NSMenuItem(AMenuItem.Handle).setOnStateImage( NSMenuCheckmark ); NSMenuItem(AMenuItem.Handle).setState( menustate[Checked] ); end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetEnable Params: AMenuItem - LCL menu item Enabled - Menu item enabled Returns: If the function succeeds Sets the enabled of menu item in Cocoa interface ------------------------------------------------------------------------------} class function TCDWSMenuItem.SetEnable(const AMenuItem: TMenuItem; const Enabled: boolean): boolean; begin Result:=Assigned(AMenuItem) and (AMenuItem.Handle<>0); if not Result then Exit; NSMenuItem(AMenuItem.Handle).setEnabled( Enabled ); end; {------------------------------------------------------------------------------ Method: TCDWSMenuItem.SetRadioItem Params: AMenuItem - LCL menu item RadioItem - Menu item has radio Returns: If the function succeeds Sets the radio behaviour of menu item in Cocoa interface ------------------------------------------------------------------------------} class function TCDWSMenuItem.SetRadioItem(const AMenuItem: TMenuItem; const RadioItem: boolean): boolean; const menustate : array [Boolean] of NSInteger = (NSOffState, NSOnState); begin Result:=Assigned(AMenuItem) and (AMenuItem.Handle<>0); if not Result then Exit; //todo: disable relative radio items NSMenuItem(AMenuItem.Handle).setOnStateImage( NSMenuRadio ); NSMenuItem(AMenuItem.Handle).setState( menustate[RadioItem] ); end; class function TCDWSMenuItem.SetRightJustify(const AMenuItem: TMenuItem; const Justified: boolean): boolean; begin end; class procedure TCDWSMenuItem.UpdateMenuIcon(const AMenuItem: TMenuItem; const HasIcon: Boolean; const AIcon: TBitmap); begin end; { TCDWSPopupMenu } {------------------------------------------------------------------------------ Method: TCDWSPopupMenu.Popup Params: APopupMenu - LCL popup menu X, Y - Screen coordinates to popup Popups menu in Cocoa interface ------------------------------------------------------------------------------} class procedure TCDWSPopupMenu.Popup(const APopupMenu: TPopupMenu; const X, Y: integer); var w : NSWindow; begin // todo: there's no way to control X,Y coordinates of the Popup menu in the OSX // prior to 10.6. Check the if there's the method and use it, if available if Assigned(APopupMenu) and (APopupMenu.Handle<>0) then begin w:=NSApp.keyWindow; if Assigned(w) then NSMenu.popUpContextMenu_withEvent_forView( TCocoaMenu(APopupMenu.Handle), NSApp.currentEvent, NSView(w.contentView)); end; end;