Recent

Author Topic: [Solved] menu not accessible after window creation osx  (Read 3856 times)

Key-Real

  • New Member
  • *
  • Posts: 44
[Solved] menu not accessible after window creation osx
« on: October 05, 2021, 10:33:45 am »
I create a window:
Code: Pascal  [Select][+][-]
  1.  
  2. var
  3.    window:NSWindow;
  4.    screenwidth,screenheight:dword;
  5.  
  6. type
  7.  
  8.     TCocoaAppDelegate = objcclass (NSObject, NSApplicationDelegateProtocol)
  9.     end;
  10.  
  11.     TCocoaApp = objcclass (NSApplication)
  12.       procedure poll; message 'poll';
  13.   end;
  14.  
  15.  
  16.   TCocoaWindow = objcclass (NSWindow)
  17.         function initWithContentRect_styleMask_backing_defer (contentRect: NSRect; aStyle: NSUInteger; bufferingType: NSBackingStoreType; flag: boolean): id; message 'initWithContentRect:styleMask:backing:defer:';
  18.     procedure dealloc; override;
  19.  
  20.     function windowShouldClose (notification: NSNotification):boolean; message 'windowShouldClose:';
  21.     procedure screenParametersChanged (notification: NSNotification); message 'screenParametersChanged:';
  22.     end;
  23.  
  24.  
  25.  
  26.  
  27. procedure TCocoaWindow.screenParametersChanged (notification: NSNotification);
  28. var theframe:NSRect;
  29. begin
  30.   theframe := NSMakeRect(0,0,screenwidth,screenheight); // NSScreen.mainScreen.frame;
  31.     setFrame_display(theframe, true);
  32. end;
  33.  
  34. function TCocoaWindow.windowShouldClose (notification: NSNotification):boolean;
  35. begin
  36.   gfxDone:=true;
  37.   result:=true;
  38. end;
  39.  
  40.  
  41. procedure TCocoaWindow.dealloc;
  42. begin
  43.   NSNotificationCenter.defaultCenter.removeObserver(self);
  44.   inherited dealloc;
  45. end;
  46.  
  47.  
  48. function TCocoaWindow.initWithContentRect_styleMask_backing_defer (contentRect: NSRect; aStyle: NSUInteger; bufferingType: NSBackingStoreType; flag: boolean): id;
  49. begin
  50.   result := inherited initWithContentRect_styleMask_backing_defer(contentRect, aStyle, bufferingType, flag);
  51.   if result <> nil then
  52.     NSNotificationCenter(NSNotificationCenter.defaultCenter).addObserver_selector_name_object(result, objcselector('screenParametersChanged:'), NSApplicationDidChangeScreenParametersNotification, nil);
  53. end;
  54.  
  55.  
  56.  
  57. procedure TCocoaApp.poll;
  58. var
  59.   event: NSEvent;
  60.   pool: NSAutoreleasePool;
  61.   myType:longint;
  62.   mySendEvent : boolean;
  63.   myKeyCode:longint;
  64.   myMouseX,myMouseY:longint;
  65. begin
  66.   pool := NSAutoreleasePool.alloc.init;
  67.   event := nextEventMatchingMask_untilDate_inMode_dequeue(NSAnyEventMask, {NSDate.distantPast}nil, NSDefaultRunLoopMode, true);
  68.  
  69.  
  70.   if event<>nil then begin
  71.       fillchar(gfxMessanger^,sizeof(longint)*4,0);
  72.  
  73.       myType:=event.type_;
  74.  
  75.       mySendEvent:=true;
  76.  
  77.       if (myType = NSKeyDown) or (myType = NSKeyUp) then begin myKeyCode:=event.keycode; mySendEvent:=false; end;
  78.       if myType = NSMouseMoved then myMouseX:=round(event.locationInWindow.x);
  79.       if myType = NSMouseMoved then myMouseY:=round(vscreen.height-event.locationInWindow.y);
  80.  
  81.       system.move(myType,gfxMessanger^,sizeof(longint));
  82.       system.move(myKeyCode,(gfxMessanger+sizeof(longint))^,sizeof(longint));
  83.       system.move(myMouseX,(gfxMessanger+sizeof(longint)*2)^,sizeof(longint));
  84.       system.move(myMouseY,(gfxMessanger+sizeof(longint)*3)^,sizeof(longint));
  85.  
  86.       if mySendEvent then begin
  87.         sendEvent(event);
  88.         updateWindows;
  89.       end;
  90.  
  91.  
  92.   end;
  93.  
  94.  
  95.   pool.release;
  96. end;
  97.  
  98.  
  99.  
  100.  
  101.  
  102.  
  103. procedure cocoaCreateWindow(width,height:dword;title:string;fullscreen:boolean);
  104. var
  105.   windowFlags: NSUInteger = 0;
  106.   frame:NSRect;
  107.  
  108.   bar : NSMenu;
  109.   appmenu:NSMenu;
  110.   menuItem: NSMenuItem;
  111. begin
  112.  
  113. screenwidth:=width;
  114. screenheight:=height;
  115.  
  116.  
  117. // frame := NSMakeRect(0,0,NSScreen.mainScreen.frame.size.width,NSScreen.mainScreen.frame.size.height);
  118.  
  119. frame := NSMakeRect(0,0,screenwidth,screenheight);
  120.  
  121.  
  122. if fullscreen then windowFlags:=NSBorderlessWindowMask;
  123. if not fullscreen then windowFlags:=NSTitledWindowMask or NSClosableWindowMask; // or NSMiniaturizableWindowMask; //or NSResizableWindowMask;
  124.  
  125.  
  126.  window := TCocoaWindow.alloc.initWithContentRect_styleMask_backing_defer(frame,windowFlags,NSBackingStoreBuffered,false);
  127.  
  128.  
  129.  
  130.  window.setTitle(NSSTR(title));
  131.  
  132.  
  133.  
  134. if fullscreen then window.setCollectionBehavior(NSWindowCollectionBehaviorStationary or NSWindowCollectionBehaviorCanJoinAllSpaces or NSWindowCollectionBehaviorFullScreenPrimary  );
  135. if not fullscreen then window.setCollectionBehavior(NSWindowCollectionBehaviorManaged);
  136.  
  137.  
  138. if fullscreen then window.toggleFullscreen(nil);
  139.  
  140.  
  141. if fullscreen then NSApp.setPresentationOptions(NSApplicationPresentationFullScreen or  NSApplicationPresentationHideDock or NSApplicationPresentationHideMenuBar);
  142. if not fullscreen then NSApp.setPresentationOptions(NSApplicationPresentationDefault);
  143.  
  144.  
  145.  
  146.  
  147.  
  148. window.makeKeyAndOrderFront(nil);
  149.  
  150. window.setAcceptsMouseMovedEvents(true);
  151.  
  152. end;
  153.  
  154.  
  155.  
  156. procedure Cocoa_PollEvents;
  157. begin
  158.   TCocoaApp(TCocoaApp.sharedApplication).poll;
  159.   //NSApp.performSelectorOnMainThread_withObject_waitUntilDone(objcselector('poll'), nil, true);
  160. end;
  161.  
  162.  
  163.  
  164.  
  165. procedure CocoaInit;
  166. var
  167.   app: TCocoaApp;
  168.   delegate: TCocoaAppDelegate;
  169. begin
  170.   app := TCocoaApp(TCocoaApp.sharedApplication);
  171.   delegate := TCocoaAppDelegate.alloc.init;
  172.   app.setDelegate(delegate);
  173.  
  174.   NSApp.setActivationPolicy(NSApplicationActivationPolicyRegular);
  175.   NSApp.activateIgnoringOtherApps(true);
  176.   NSApp.finishLaunching;
  177. end;
  178.  
  179.  
  180.  
  181.  
  182.  
  183. procedure CocoaClose;
  184. begin
  185.  window.close;
  186.  Cocoa_PollEvents;
  187. end;
  188.  
  189.  
It is possible to switch in fullscreen mode with this code, but i mean window mode.

The window ist shown. But If i click on the menu (the apple menu at the top of the Screen) it does not react. I have to click away from my created window or click on another App, and when i select my window again now i can access the menu.

What to do?
« Last Edit: March 14, 2022, 08:47:47 am by Key-Real »

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: menu not accessible after window creation osx
« Reply #1 on: October 08, 2021, 12:32:07 am »
Can you attach a minimal compilable project showing the issue? (Use Lazarus > Project > Publish Project).
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

Key-Real

  • New Member
  • *
  • Posts: 44
Re: menu not accessible after window creation osx
« Reply #2 on: October 10, 2021, 11:58:59 am »
Here the minimal compilable program:

Code: Pascal  [Select][+][-]
  1. {$MODE OBJFPC}
  2. {$modeswitch objectivec1}
  3. uses CocoaAll, ctypes, MacOSAll, sysutils;
  4.  
  5. var
  6.    window:NSWindow;
  7.    done:boolean = false;
  8.  
  9.  
  10. type
  11.  
  12.     TCocoaAppDelegate = objcclass (NSObject, NSApplicationDelegateProtocol)
  13.     end;
  14.  
  15.     TCocoaApp = objcclass (NSApplication)
  16.       procedure poll; message 'poll';
  17.     end;
  18.  
  19.  
  20.     TCocoaWindow = objcclass (NSWindow)
  21.       function initWithContentRect_styleMask_backing_defer (contentRect: NSRect; aStyle: NSUInteger; bufferingType: NSBackingStoreType; flag: boolean): id; message 'initWithContentRect:styleMask:backing:defer:';
  22.       procedure dealloc; override;
  23.  
  24.       function windowShouldClose (notification: NSNotification):boolean; message 'windowShouldClose:';
  25.     end;
  26.  
  27.  
  28. function TCocoaWindow.windowShouldClose (notification: NSNotification):boolean;
  29. begin
  30.   done:=true;
  31.   result:=true;
  32. end;
  33.  
  34.  
  35. procedure TCocoaWindow.dealloc;
  36. begin
  37.   NSNotificationCenter.defaultCenter.removeObserver(self);
  38.   inherited dealloc;
  39. end;
  40.  
  41.  
  42. function TCocoaWindow.initWithContentRect_styleMask_backing_defer (contentRect: NSRect; aStyle: NSUInteger; bufferingType: NSBackingStoreType; flag: boolean): id;
  43. begin
  44.   result := inherited initWithContentRect_styleMask_backing_defer(contentRect, aStyle, bufferingType, flag);
  45.   if result <> nil then
  46.     NSNotificationCenter(NSNotificationCenter.defaultCenter).addObserver_selector_name_object(result, objcselector('screenParametersChanged:'), NSApplicationDidChangeScreenParametersNotification, nil);
  47. end;
  48.  
  49.  
  50. procedure TCocoaApp.poll;
  51. var
  52.   event: NSEvent;
  53.   pool: NSAutoreleasePool;
  54. begin
  55.   pool := NSAutoreleasePool.alloc.init;
  56.   event := nextEventMatchingMask_untilDate_inMode_dequeue(NSAnyEventMask, {NSDate.distantPast}nil, NSDefaultRunLoopMode, true);
  57.  
  58.   if event<>nil then begin
  59.       sendEvent(event);
  60.       updateWindows;
  61.   end;
  62.  
  63.   pool.release;
  64. end;
  65.  
  66.  
  67. procedure CocoaCreateWindow(width,height:dword;title:string);
  68. var
  69.   windowFlags: NSUInteger = 0;
  70.   frame:NSRect;
  71. begin
  72.  frame := NSMakeRect(0,0,width,height);
  73.  
  74.  windowFlags:=NSTitledWindowMask or NSClosableWindowMask; // or NSMiniaturizableWindowMask; //or NSResizableWindowMask;
  75.  window := TCocoaWindow.alloc.initWithContentRect_styleMask_backing_defer(frame,windowFlags,NSBackingStoreBuffered,false);
  76.  
  77.  window.setTitle(NSSTR(title));
  78.  
  79.  window.setCollectionBehavior(NSWindowCollectionBehaviorManaged);
  80.  NSApp.setPresentationOptions(NSApplicationPresentationDefault);
  81.  
  82.  window.makeKeyAndOrderFront(nil);
  83.  window.setAcceptsMouseMovedEvents(true);
  84. end;
  85.  
  86.  
  87. procedure CocoaPollEvents;
  88. begin
  89.   TCocoaApp(TCocoaApp.sharedApplication).poll;
  90. end;
  91.  
  92.  
  93. procedure CocoaInit;
  94. var
  95.   app: TCocoaApp;
  96.   delegate: TCocoaAppDelegate;
  97. begin
  98.   app := TCocoaApp(TCocoaApp.sharedApplication);
  99.   delegate := TCocoaAppDelegate.alloc.init;
  100.   app.setDelegate(delegate);
  101.  
  102.   NSApp.setActivationPolicy(NSApplicationActivationPolicyRegular);
  103.   NSApp.activateIgnoringOtherApps(true);
  104.   NSApp.finishLaunching;
  105. end;
  106.  
  107.  
  108. procedure CocoaClose;
  109. begin
  110.  window.close;
  111.  CocoaPollEvents;
  112. end;
  113.  
  114.  
  115.  
  116.  
  117. begin
  118.  CocoaInit;
  119.  CocoaCreateWindow(640,480,'test');
  120.  
  121.  repeat
  122.   CocoaPollEvents;
  123.  until done;
  124.  
  125.  CocoaClose;
  126. end.
  127.  

Key-Real

  • New Member
  • *
  • Posts: 44
Re: menu not accessible after window creation osx
« Reply #3 on: March 10, 2022, 12:13:10 pm »
I tested whis Code on
MacOS 10.13.4 (Intel)
MacOS 11.6 (Aarch64)
MacOS 12.2.1 (Intel)
All Same behaviour.

Is this an Apple Bug?
Or is the code wrong?

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: menu not accessible after window creation osx
« Reply #4 on: March 11, 2022, 11:18:50 pm »
Your program does not compile:

Quote
Free Pascal Compiler version 3.3.1 [2022/01/07] for aarch64
Copyright (c) 1993-2021 by Florian Klaempfl and others
Target OS: Darwin for AArch64
Compiling project1.pas
project1.pas(21,16) Error: Inherited methods can only be overridden in Objective-C and Java, add "override" (inherited method defined in NSWindow)
project1.pas(128) Fatal: There were 1 errors compiling module, stopping
Fatal: Compilation aborted
Error: /usr/local/bin/ppca64 returned an error exitcode
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: menu not accessible after window creation osx
« Reply #5 on: March 11, 2022, 11:27:08 pm »
Ok, I added the override directive and now it compiles. It looks fine to me. There is no menu because you have not coded one :-)

Please go read the Lazarus Wiki article Writing a Cocoa app without the LCL for how to add a menu.
« Last Edit: March 11, 2022, 11:31:52 pm by trev »
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

Key-Real

  • New Member
  • *
  • Posts: 44
Re: menu not accessible after window creation osx
« Reply #6 on: March 12, 2022, 11:16:21 am »
the program in the posted link shows the same behavier.

If I start it, I can not click on the menu (nothing hapens), than I click on another window (my prog looses focus), than I click back on my window app, now I can click on the menu.

macOS 11.6.4


l attach the screen recording as evidence:

http://www.sistavip.com/pub/screen.zip
« Last Edit: March 12, 2022, 11:34:43 am by Key-Real »

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: menu not accessible after window creation osx
« Reply #7 on: March 13, 2022, 12:24:24 am »
If you are creating a GUI executable, then you need to wrap it in an application bundle. You can execute the bundle with:

Code: [Select]
open mybundle.app
or

Code: [Select]
./mybundle.app/Contents/MacOS/mybundle
and  if you do that, then the menu items are accessible.
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

Key-Real

  • New Member
  • *
  • Posts: 44
Re: menu not accessible after window creation osx
« Reply #8 on: March 13, 2022, 02:04:35 pm »
Thx,
now I create a Bundle and everything works well.

But
I toke the Info.plist from the Lazarus link above
Code: XML  [Select][+][-]
  1. <?xml version="1.0" encoding="UTF-8"?>
  2.  <!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">'
  3. <plist version="1.0">
  4. <dict>
  5.   <key>CFBundleDevelopmentRegion</key>
  6.   <string>English</string>
  7.   <key>CFBundleExecutable</key>
  8.   <string>test</string>
  9.   <key>CFBundleIconFile</key>
  10.   <string>macicon.icns</string>
  11.   <key>CFBundleIdentifier</key>
  12.   <string>org.magnifier.magnifier</string>
  13.   <key>CFBundleInfoDictionaryVersion</key>
  14.   <string>6.0</string>
  15.   <key>CFBundlePackageType</key>
  16.   <string>APPL</string>
  17.   <key>CFBundleSignature</key>
  18.   <string>MAG#</string>
  19.   <key>CFBundleVersion</key>
  20.   <string>1.0</string>
  21. </dict>
  22. </plist>
  23.  

he trows my a parsing error.
I removed this file from the bundle, everything works

Do I need this file?

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: menu not accessible after window creation osx
« Reply #9 on: March 13, 2022, 11:59:52 pm »
I just used the script to create an Info.plist file and then checked it by using the property list utility thus:

Code: Bash  [Select][+][-]
  1. trev@macmini7 [/Users/trev] $ cd Magnifier.app/
  2. trev@macmini7 [/Users/trev/Magnifier.app] $ cd Contents/
  3. trev@macmini7 [/Users/trev/Magnifier.app/Contents] $ plutil Info.plist
  4. Info.plist: OK

and as you can see it is parsed as OK. I also opened it in Xcode's PlistEditor plugin and no parsing error was detected.

Looking at the file you pasted into your post, the error is on line 2 where you have a trailing ' (single quotation mark) character.

Yes, the Info.plist file is a required application bundle file.
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

Key-Real

  • New Member
  • *
  • Posts: 44
Re: menu not accessible after window creation osx
« Reply #10 on: March 14, 2022, 08:47:09 am »
yes, thx

and sorry for my lameness

trev

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 1988
  • Former Delphi 1-7, 10.2 user
Re: [Solved] menu not accessible after window creation osx
« Reply #11 on: March 14, 2022, 10:49:37 am »
No worries, we have all had to start at the beginning of the journey of knowledge. I'm glad I've been able to help you on your way.
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 x86_64 Xcode 13.4
Lazarus 2.3, FPC 3.3.1 macOS 12.3.1 aarch64 Xcode 13.4

 

TinyPortal © 2005-2018