Repository navigation
AUv2: initialize the Cocoa view before creating the plugin's GUI - #594
Merged
Merged
Conversation
initWithAUv2: registered self as the CLAP window and ran gui->create() before
[super initWithFrame:], so a plugin that called request_resize from inside
create() - which the GUI extension allows - reached -setFrame: on a view AppKit
had not finished building. NSView threw NSInternalInconsistencyException
("_trackingAreaHelper not allocated yet!") and the host aborted: GarageBand, and
pluginval's editor test (#582).
The view is now initialized first, with the size the host offered, and the
plugin's GUI is created into a view that is ready for it. A request_resize
during create() lands on the frame like any other resize, and the frame it
leaves behind becomes the initial size. get_size() is only asked when create()
did not ask for a size of its own, so the plugin's own request wins.
canary moves to after _createWindow(). It says the view is connected to a live
plugin GUI - which is what every other reader of it means - and it should not
say so while create() is still running: the set_size() echo that -setFrame:
normally hands back to the plugin would re-enter create().
Registering the window after [super initWithFrame:] is also the ordering the
registration wanted anyway: self and &canary were handed to the wrapper from an
object that super init had not returned yet.
|
ah, yeah that's much nicer - thanks 🙏👍 confirmed this fixes #582 for me. here's how i repro'ed things: a
NOTE: I applied the commit to i'll close #591 in favor of this. thanks again for working on this stuff. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #582. An alternative to #591 — thanks @busticated for the report, the stack trace and the patch; this takes the first option you suggested in the issue.
What happens today
initWithAUv2:registersselfas the CLAP window and runsgui->create()before[super initWithFrame:]. A plugin that callsrequest_resizefrom insidecreate()— whichclap/ext/gui.hallows — therefore reaches-setFrame:on a view AppKit has not finished building, and NSView throwsNSInternalInconsistencyException: '_trackingAreaHelper not allocated yet!'.What this does
Initializes the view first, with the size the host offered, and creates the plugin's GUI into a view that is ready for it. A
request_resizeduringcreate()then lands on the frame like any other resize, and the frame it leaves behind becomes the initial size;get_size()is only asked whencreate()did not ask for a size of its own, so the plugin's own request still wins.canarymoves to after_createWindow(). It says the view is connected to a live plugin GUI — which is what every other reader of it means (viewDidMoveToWindow,dealloc,-setFrame:, and_destroyWindowinwrapasauv2.cpp) — and it should not say so whilecreate()is still running: theset_size()echo that-setFrame:normally hands back to the plugin would re-entercreate(). That is the same reentrancy #591 avoids with its earlyreturn.So no new state on the view: "may
-setFrame:talk to the plugin yet" iscanary, and "didcreate()ask for a size" is the frame having moved. Registering the window after[super initWithFrame:]also fixes a latent wrinkle —selfand&canarywere handed to the wrapper from an objectsuper inithad not returned yet.Open question
Does the requested size really need to beat
get_size()? After arequest_resizeincreate(), a conforming plugin'sget_size()should return the new size, in which case theNSEqualSizesbranch can go and the fix is purely the reordering. @busticated — doesnice-plug-egui'sget_size()disagree with what it asked for? If it does, that reason should be written into the comment.Testing
Builds all three AUv2 targets. Not yet verified in a host —
auvalcannot open an editor, so this wants the pluginval editor test from #582 and a look in Logic, where the host follows the view's frame-change notification.