- because the main event loop is not called if initialization fails, it is presently impossible for MsgBoxError() to work if UI initialization fails; this basically means we cannot allow initializiation to fail on Mac OS X if we want to be able to report UI init failures to the user with one (which would be desirable, maybe (would violate Windows HIG?))
- make sure GTK+ documentation version point differences (x in 4.3.x) don't matter
- I found a GTK+ version number meaning page somewhere; have to find it again (TODO)
twists of fate:
- listboxes spanning the vertical height of the window don't always align with the bottom border of the edit control attached to the bottom of the window...
- this specifically only happens when the window has an odd height; I don't think this can be fixed unless we explicitly ignore the extra pixel everywhere
- need a way to get ideal size for all controls on Windows, not just push buttons (Microsoft...)
- make passing of parameters and type conversions of parameters to uitask on Windows consistent: explicit _WPARAM(xxx)/_LPARAM(xxx)/uintptr(xxx), for example
- do this for type signatures in exported functions: (err error) or just error?
- do this for the names of GTK+ helper functions (gtkXXX or gXXX)
- areaView -> goArea (or change the class name to be like the delegate name?) in area_darwin.go?
- make sure every sysData function only performs a single invocation to uitask; see http://blogs.msdn.com/b/oldnewthing/archive/2005/10/10/479124.aspx#479182
- windows: this requires major restructuring
- gtk, mac: this just requires checking
- steamroll ALL errors, especially on windows
- gtk: no way to catch errors
- cocoa: discouraged
- make fully lock free
- prerequisite is the above two
- locks are used because of initial state; we can override by creating controls at construct time
- cocoa, gtk: no real issues
- windows: now required to specify no parent window at create time and set both the parent window AND the child window ID later
- preferred sizes in general are awkward: on Windows, no text-based size calculation is performed, so we have weird things like Labels always having the same width (so if you place a Label in a Stack by itself and forget to make it stretchy, it'll be truncated on Windows (but not on GTK+ or OS X?!))
- for our two custom window classes on Windows, we should allocate extra space in the window class's info structure and then use SetWindowLongPtrW() during WM_CREATE to store the sysData and not have to make a new window class each time; this might also fix the s != nil && s.hwnd != 0 special cases in the Area WndProc if done right
- this is a bit flakier as SetWindowLongPtr() can fail, and it can also succeed in such a way that the last error is unreliable
- and doesn't exist on 32-bit windows; we will need special code for detecting 32-bit/64-bit (see http://bugs.winehq.org/show_bug.cgi?id=30556 and GerbilSoft in irc.badnik.net/#retro)
- also CreateWindow() and CreateWindowEx() docs differ in indicating which messages are sent but ultimately send the same set; WM_GETMINMAXINFO is sent first so that throws a wrench in the whole point, AND we'll need a way to properly differentiate between custom classes and controls...
- tl;dr what started as a somewhat quick change was really way too much effort for only potential/theoretical gain; approach if someone actually DOES hit Go's syscall.NewCallback() limit
- raymond chen does it here: http://blogs.msdn.com/b/oldnewthing/archive/2005/04/22/410773.aspx (check the implementation of Window::s_WndProc())
- ...and suggests we do it here http://blogs.msdn.com/b/oldnewthing/archive/2014/02/03/10496248.aspx (**NOTE THE DATE**) - the comments on this one provide some potential ideas, including IIntrospect's comment about HCBT_CREATEWND; later Raymond says we should not worry about SetWindowLongPtr() failing
- and raymond suggests GWL_USERDATA here: http://blogs.msdn.com/b/oldnewthing/archive/2005/03/03/384285.aspx
- window sizes need to not include the window decoration; while Mac OS X and GTK+ both obey this, I've only had issues with Windows; check the experiments/ folder
- don't use ES_NUMBER for number-only text boxes, as "it is still possible to paste non-digits into the edit control." (though a commenter on MSDN says that's wrong?)
- might want to just have spinners and not numeric text boxes???
- http://stackoverflow.com/questions/3815806/gtk-and-opengl-bindings suggest GtkGLArea is better but that seems to be a Mono thing? also indicates Clutter (with its Cogl) is not an option because it locks you out of using the OpenGL API directly
- er no, the Mono thing is just the homepage... but it doesn't say if this targets GTK+ 2 or GTK+ 3, hm. (also it appears to not have been updated since Precise; in Ubuntu it's libgtkgl)
- and gtkglext doesn't support GTK+ 3 officially anyway
- and cairo doesn't seem to support OpenGL explicitly so it looks like I will need to communicate with glx directly: http://stackoverflow.com/questions/17628241/how-can-i-use-gtk3-and-opengl-together
being able to use comctl32.dll version 6 now that win2k support is gone is a good thing, isn't it?
- GTK+: TODO
- Cocoa: TODO
OTHER NOTES
- on webpage controls: http://blogs.msdn.com/b/oldnewthing/archive/2005/02/11/371042.aspx
THOUGHTS
- privilege escalation requests
- windows vista and up use a button with a shield icon and osme other API that I don't know before performing the privileged action
- typically graphical unix programs nowadays use a graphical sudo prompt provided by the desktop environment (gksu or kdesudo or what not) either before the program even runs or after clicking a button to start the process with elevated privileges
- however, GTK+ also provides https://developer.gnome.org/gtk3/3.4/GtkLockButton.html, which is similar to the Cocoa one below:
- Cocoa uses a button with a lock on it that will disable the entire form when unlocked, then ask for permission when clicked
Mouse Step Snap | 1, fixed | something; likely 0.1 but not sure | yes (`setAllowsTickMarkValuesOnly:`); caveat: must specify an exact number of ticks (see below)
Keyboard Step Snap | configurable | configurable | TODO (same as mouse?)
Directories | no (separate facility provided by the shell) | open and save | open only
Network vs. local only (URI vs. filename) | Network button enabled by default; can be switched off (**TODO** how are network filenames returned?) | yes (default local only; if local only, changing to, say, smb://127.0.0.1/ will pop up an error box; if nonlocal allowed, filename can be null) | xxx
Multiple selection | yes | yes | open only
Hidden files | user-specified; can be switched on in code (but is a no-op?) | hidden by default; can be switched on in code (but is a no-op?) and also by the user | xxx
Overwrite confirmation | available; must be explicitly enabled | available; must be explicitly enabled | xxx
New Folder button | xxx | optional (I think enabled by default? should do it explicitly to be safe, anyway) | optional
File filters | Specified by "patterns" (consisting of filename characters and * but not space; I assume the only safe ones are *.ext and *.*); multiple patterns separated by semicolons; can have custom labels | Specified by MIME type (handles subtypes; has wildcards) or pattern ("shell-style glob", so I assume over whole basename) or by custom function; can have multiple of the above; can have custom labels; also has a shortcut to add all gdk-pixbuf-supported formats | Specified by "UTI"s or by individual filename extensions (format not documented but appears to be just the extension without embellishments); cannot have labels; 1:1 filter:extension mapping.
File filter list format | `"Label\0Filter-list\0Label\0Filter-list\0...Label\0FIlter-list\0\0"`; filter for all files is canonically `"All Files\0*.*\0\0"` in the docs (specifically this due to handling of shortcut links); also provides a way for users to write in their own filters | Add or remove individual GtkFileFIlter objects; can select one specified in the list to show by default; default behavior is all files; if selected one when none has been specified, filter selection disabled; filter for all files specified in docs under gtk_file_filter_new() (except doesn't set a name) | NSArray of filter strings, or nil for All Files. There is no provision to have an "all files" option: you either specify a set of filters or you don't. (See filename extension auto-append below.). All filters are applied at once; there is no way to select. We might need to introduce an accessory panel (extra widget) to fake the filtering rules of other platforms...
Default file name | settable | settable | settable (as the filename label)
Initial directory | complex rules that have changed over time; we can pass an absolute filename (the previous filename or a default filename) and have its path used (if we specify just a path it will either be used as the filename or the program will crash); or we can give it a directory; or Windows will remember for us for some time, or... | pass previous filename or URI to show; overrides default file name; intended only for saving files (so I don't know if it's possible to remember current directory for opening??????); effect of passing containing directory undocumented(???? in my tests the given folder itself is selected) | has some rules; there is a way to specify a custom one; seems to have the undocumented effect that it selects the file if a file is named
Confirmation and cancel buttons | xxx | GTK_STOCK_OPEN, GTK_STOCK_SAVE, GTK_STOCK_SAVE_AS / GTK_STOCK_CANCEL | cancel button predefined; confirmation button can be changed (setPrompt:) but **TODO** the docs imply prompt is actually a global property?
Returned filename rules | xxxx | memory provided by GTK+ itself (so no need to worry about size limits); can return a single filename or URI or a GSList of filenames or URIs | xxx
Window title | optional; defaults to either Open or Save As | required(?) | optional for save (defaults to Save); unknown (**TODO**) for Open
Prompt to create new files | available; must be explicitly enabled; seems to only apply to Open File dialogs (**TODO**) | xxx | xxx
Adds file to a Recent Documents list | available; must be explicitly disabled | xxx | xxx
Allows nonexistent files to be created in Open dialogs | yes; can be switched off | xxx | xxx
"Open as read-only"/"Save as read-only" checkbox | provided; default; can be switched off | xxx | xxx
Navigating changes the current working directory of the program | yes; can be switched off for Save dialogs only (????) | xxx | xxx
Link following | For .lnk files, enabled by default iff a filter is specified; the All Files filter above is listed as being necessary to follow links; can be shut off with a flag in all cases | xxx | For Finder aliases, setResolvesAliases:
Help button | Available; old-style dialog boxes need a parent window (Explorer-style ones don't; they just need a hook function) | xxx | xxx
Extension auto-appending | Optional; three-character maximum; doesn't seem to be available on a per-filter basis | xxx | **NOT OPTIONAL.** The only way to avoid this is to not specify any filters. You can't even circumvent this with a delegate. If the user specifies another extension, they are asked to choose one if setAllowsOtherFileTypes: is set. (**TODO** could we use nameFieldStringValue to circumvent?)
Other labels | xxx | xxx | field before filename entry can be changed; also can provide an additional optional message
* Windows: OFN_NOTESTFILECREATE might be necessary
* Windows: OFN_NOVALIDATE - see what happens without a hook
* Windows: OFN_SHAREAWARE - this is a weird one but it's network related
* Windows: templates seem to be how to provide extra parameters, but their usage isn't documented on the OPENFILENAME struct help page; check the rest of MSDN
* Mac OS X: turn on both setExtensionHidden: and setCanSelectHiddenExtension: to show the extnesion in the dialog
* Mac OS X: turn on setTreatsFilePackagesAsDirectories: since file packages (bundles) are an OS X-specific concept
This actually turns out to be one of the very first things that Raymond ever blogged about, so if you just go to the last page of posts on The Old New Thing, it'll be there. But for my own convenience:
- http://blogs.msdn.com/b/oldnewthing/archive/2004/08/26/220873.aspx (on arrays of size 1 in various data structures; will need to double-check alignments)
- http://blogs.msdn.com/b/oldnewthing/archive/2004/12/14/300204.aspx **VALID DIALOG IDS** holy shit why didn't this come up when I was searching for it
- http://blogs.msdn.com/b/oldnewthing/archive/2005/01/10/349894.aspx some info on notification bubbles
- http://blogs.msdn.com/b/oldnewthing/archive/2005/01/31/363790.aspx 64-bit type equivalency
- http://blogs.msdn.com/b/oldnewthing/archive/2005/03/09/390706.aspx on SystemParametersInfo(); includes icon label font (not part of the non-client metrics)
- passing data to child processes (is this useful for detecting multiple instances?) http://blogs.msdn.com/b/oldnewthing/archive/2003/12/11/56043.aspx
- on the need for cbSize fields http://blogs.msdn.com/b/oldnewthing/archive/2003/12/12/56061.aspx
- notes on critical sections http://blogs.msdn.com/b/oldnewthing/archive/2003/12/18/44425.aspx http://blogs.msdn.com/b/oldnewthing/archive/2003/12/22/45152.aspx
- on COM interfaces and control panels (also uses activation contexts for SxS manifests) http://blogs.msdn.com/b/oldnewthing/archive/2003/12/26/45979.aspx
- version numbers http://blogs.msdn.com/b/oldnewthing/archive/2004/02/13/72476.aspx
- RECT endpoint-exclusivity (everything does this, not just Windows, so it's useful to point people to) http://blogs.msdn.com/b/oldnewthing/archive/2004/02/18/75652.aspx
- on fixing a problem everywhere (see RECT above) http://blogs.msdn.com/b/oldnewthing/archive/2004/02/19/76368.aspx
- proper use of COM http://blogs.msdn.com/b/oldnewthing/archive/2004/02/20/77120.aspx
- invalid thread and process IDs http://blogs.msdn.com/b/oldnewthing/archive/2004/02/23/78395.aspx
- on GetDesktopWindow() http://blogs.msdn.com/b/oldnewthing/archive/2004/02/24/79212.aspx
- links in notification bubbles http://blogs.msdn.com/b/oldnewthing/archive/2004/02/25/79842.aspx
- HWND_BROADCAST is not for multiple instances http://blogs.msdn.com/b/oldnewthing/archive/2004/05/05/126427.aspx
- COM threading http://blogs.msdn.com/b/oldnewthing/archive/2004/05/11/129760.aspx
- disabling vs hiding http://blogs.msdn.com/b/oldnewthing/archive/2004/05/14/131881.aspx
- when to put ... after a command name http://blogs.msdn.com/b/oldnewthing/archive/2004/05/17/133181.aspx
- COM destructors http://blogs.msdn.com/b/oldnewthing/archive/2004/05/20/135841.aspx http://blogs.msdn.com/b/oldnewthing/archive/2004/05/21/136701.aspx
- high performance multithreading http://blogs.msdn.com/b/oldnewthing/archive/2004/05/28/143769.aspx
- getting icons for known file types http://blogs.msdn.com/b/oldnewthing/archive/2004/06/01/145428.aspx
- COM threading models http://blogs.msdn.com/b/oldnewthing/archive/2004/06/02/146671.aspx
- why am I posting so much on COM? in case I need to use shell functions in the future that aren't flat functions...
- thread messages and message reentrancy (and some DDE for good measure) http://blogs.msdn.com/b/oldnewthing/archive/2004/06/08/150929.aspx
- windows language IDs http://blogs.msdn.com/b/oldnewthing/archive/2004/06/09/151689.aspx
- more info on shell interop http://blogs.msdn.com/b/oldnewthing/archive/2004/07/20/188696.aspx
- proof about WM_CLOSE for GUI windows from the task manager (see also our AppQuit channel) http://blogs.msdn.com/b/oldnewthing/archive/2004/07/22/191123.aspx
- on command line password security (useful for showing anyone who asks a similar question) http://blogs.msdn.com/b/oldnewthing/archive/2004/11/29/271551.aspx
- dangers of filtering messages http://blogs.msdn.com/b/oldnewthing/archive/2005/02/09/369804.aspx
- the shell Animation control (is this the same as the one in common controls version 6?) is limited (might be needed for the above) http://blogs.msdn.com/b/oldnewthing/archive/2005/02/16/374397.aspx
- MsgWaitForMultipleObjects() requires care http://blogs.msdn.com/b/oldnewthing/archive/2005/02/17/375307.aspx
- danger of setting parameter info http://blogs.msdn.com/b/oldnewthing/archive/2005/03/10/392118.aspx
- danger of startup helpers and other misleading "performance boosts" http://blogs.msdn.com/b/oldnewthing/archive/2005/03/11/394249.aspx
- danger of saving/restoring window coordinates http://blogs.msdn.com/b/oldnewthing/archive/2005/03/14/395271.aspx
- on the cost of creating and maintaining windows http://blogs.msdn.com/b/oldnewthing/archive/2005/03/15/395866.aspx