Added (untested; VM issues) code to handle Mac OS X Quit Dock menu items and other related stuff that may happen in the future. Will drop the TODO after I can test it.
This commit is contained in:
parent
af770340c9
commit
f7817f6987
|
@ -20,6 +20,7 @@ though this is not always the case.
|
|||
#include <AppKit/NSGraphics.h>
|
||||
#include <AppKit/NSBitmapImageRep.h>
|
||||
#include <AppKit/NSCell.h>
|
||||
#include <AppKit/NSApplication.h>
|
||||
|
||||
/* used by listbox_darwin.go; requires NSString */
|
||||
id *_NSObservedObjectKey = (id *) (&NSObservedObjectKey);
|
||||
|
@ -241,7 +242,8 @@ static void __areaView_drawRect(id self, SEL sel, NSRect r)
|
|||
|
||||
void *_areaView_drawRect = (void *) __areaView_drawRect;
|
||||
|
||||
/* the only objective-c feature you'll see here
|
||||
/*
|
||||
this and one below it are the only objective-c feature you'll see here
|
||||
|
||||
unfortunately NSRect both varies across architectures and is passed as just a structure, so its encoding has to be computed at compile time
|
||||
because @encode() is NOT A LITERAL, we're going to just stick it all the way back in objc_darwin.go
|
||||
|
@ -327,3 +329,19 @@ void objc_setFont(id what, unsigned int csize)
|
|||
objc_msgSend(what, s_setFont,
|
||||
objc_msgSend(c_NSFont, s_systemFontOfSize, size));
|
||||
}
|
||||
|
||||
/*
|
||||
-[NSApplicationDelegate applicationShouldTerminate] used to return a BOOL, but now returns a NSApplicationTerminateReply, which is a NSUInteger; hence, here.
|
||||
*/
|
||||
|
||||
extern void appDelegate_applicationShouldTerminate();
|
||||
|
||||
static NSApplicationTerminateReply __appDelegate_applicationShouldTerminate(id self, SEL sel)
|
||||
{
|
||||
appDelegate_applicationShouldTerminate();
|
||||
return NSTerminateCancel; // don't quit
|
||||
}
|
||||
|
||||
void *_appDelegate_applicationShouldTerminate = (void *) __appDelegate_applicationShouldTerminate;
|
||||
|
||||
char *encodedTerminateReply = @encode(NSApplicationTerminateReply);
|
||||
|
|
|
@ -12,6 +12,7 @@ This creates a class goAppDelegate that will be used as the delegate for /everyt
|
|||
- handles window close events (windowShouldClose:)
|
||||
- handles window resize events (windowDidResize:)
|
||||
- handles button click events (buttonClicked:)
|
||||
- handles the application-global Quit event (such as from the Dock) (applicationShouldTerminate)
|
||||
*/
|
||||
|
||||
// #cgo LDFLAGS: -lobjc -framework Foundation -framework AppKit
|
||||
|
@ -45,6 +46,8 @@ var appDelegateSels = []selector{
|
|||
"handling window resize events"},
|
||||
selector{"buttonClicked:", uintptr(C.appDelegate_buttonClicked), sel_bool_id,
|
||||
"handling button clicks"},
|
||||
selector{"applicationShouldTerminate", uintptr(C._appDelegate_applicationShouldTerminate), sel_terminatereply,
|
||||
"handling Quit menu items (such as from the Dock)/the AppQuit channel"},
|
||||
}
|
||||
|
||||
func mkAppDelegate() error {
|
||||
|
@ -94,3 +97,12 @@ func appDelegate_buttonClicked(self C.id, sel C.SEL, button C.id) {
|
|||
sysData := getSysData(button)
|
||||
sysData.signal()
|
||||
}
|
||||
|
||||
//export appDelegate_applicationShouldTerminate
|
||||
func appDelegate_applicationShouldTerminate() {
|
||||
// asynchronous so as to return control to the event loop
|
||||
go func() {
|
||||
AppQuit <- struct{}{}
|
||||
}()
|
||||
// xxx in bleh_darwin.m tells Cocoa not to quit
|
||||
}
|
||||
|
|
3
doc.go
3
doc.go
|
@ -20,6 +20,7 @@ Here is a simple, complete program that asks the user for their name and greets
|
|||
|
||||
func myMain() {
|
||||
w := ui.NewWindow("Hello", 400, 100)
|
||||
ui.AppQuit = w.Closing // treat quitting the application like closing the main window
|
||||
nameField := ui.NewLineEdit("Enter Your Name Here")
|
||||
button := ui.NewButton("Click Here For a Greeting")
|
||||
err := w.Open(ui.NewVerticalStack(nameField, button))
|
||||
|
@ -29,7 +30,7 @@ Here is a simple, complete program that asks the user for their name and greets
|
|||
|
||||
for {
|
||||
select {
|
||||
case <-w.Closing: // user tries to close the window
|
||||
case <-w.Closing: // user tries to close the window or quit the program
|
||||
return
|
||||
case <-button.Clicked: // user clicked the button
|
||||
ui.MsgBox("Hello, " + nameField.Text() + "!", "")
|
||||
|
|
11
init.go
11
init.go
|
@ -14,3 +14,14 @@ package ui
|
|||
func Go(main func()) error {
|
||||
return ui(main)
|
||||
}
|
||||
|
||||
// AppQuit is pulsed when the user decides to quit the program if their operating system provides a facility for quitting an entire application, rather than merely close all windows (for instance, Mac OS X via the Dock icon).
|
||||
// You should assign one of your Windows's Closing to this variable so the user choosing to quit the application is treated the same as closing that window.
|
||||
// If you do not respond to this signal, nothing will happen.
|
||||
// Do not merely check this channel alone; it is not guaranteed to be pulsed on all systems or in all conditions.
|
||||
var AppQuit chan struct{}
|
||||
|
||||
func init() {
|
||||
// don't expose this in the documentation
|
||||
AppQuit = newEvent()
|
||||
}
|
||||
|
|
|
@ -71,14 +71,16 @@ const (
|
|||
sel_bool_id
|
||||
sel_bool
|
||||
sel_void_rect
|
||||
sel_terminatereply
|
||||
nitypes
|
||||
)
|
||||
|
||||
var itypes = [nitypes][]C.char{
|
||||
sel_void_id: []C.char{'v', '@', ':', '@', 0},
|
||||
sel_bool_id: []C.char{'c', '@', ':', '@', 0},
|
||||
sel_bool: []C.char{'c', '@', ':', 0},
|
||||
sel_void_rect: nil, // see init() below
|
||||
sel_void_id: []C.char{'v', '@', ':', '@', 0},
|
||||
sel_bool_id: []C.char{'c', '@', ':', '@', 0},
|
||||
sel_bool: []C.char{'c', '@', ':', 0},
|
||||
sel_void_rect: nil, // see init() below
|
||||
sel_terminatereply: nil,
|
||||
}
|
||||
|
||||
func init() {
|
||||
|
@ -91,6 +93,14 @@ func init() {
|
|||
}
|
||||
x = append(x, 0)
|
||||
itypes[sel_void_rect] = x
|
||||
|
||||
x = make([]C.char, 0, 256) // more than enough
|
||||
y = C.GoString(C.encodedTerminateReply)
|
||||
for _, b := range y {
|
||||
x = append(x, C.char(b))
|
||||
}
|
||||
x = append(x, '@', ':', 0)
|
||||
itypes[sel_terminatereply] = x
|
||||
}
|
||||
|
||||
func makeClass(name string, super C.id, sels []selector, desc string) (id C.id, err error) {
|
||||
|
|
|
@ -117,8 +117,12 @@ extern struct xpoint getTranslatedEventPoint(id, id);
|
|||
|
||||
/* for objc_darwin.go */
|
||||
extern char *encodedNSRect;
|
||||
extern char *encodedTerminateReply;
|
||||
|
||||
/* for sysdata_darwin.go */
|
||||
extern void objc_setFont(id, unsigned int);
|
||||
|
||||
/* for delegate_darwin.go */
|
||||
extern void *_appDelegate_applicationShouldTerminate;
|
||||
|
||||
#endif
|
||||
|
|
|
@ -282,6 +282,9 @@ _=curtime
|
|||
case <-w.Closing:
|
||||
println("window closed event received")
|
||||
break mainloop
|
||||
case <-AppQuit:
|
||||
println("application quit event received")
|
||||
break mainloop
|
||||
case <-b.Clicked:
|
||||
w.SetTitle(fmt.Sprintf("%v | %s | %s | %s | %s",
|
||||
c.Checked(),
|
||||
|
|
Loading…
Reference in New Issue