Cocoa NSView frame通过-setFrame以外的方式设置:自动调整大小后
我的应用程序通过Cocoa NSView frame通过-setFrame以外的方式设置:自动调整大小后,cocoa,nsview,autoresizingmask,Cocoa,Nsview,Autoresizingmask,我的应用程序通过NSWindowController从XIB文件加载窗口和窗口内的按钮。在-windowDidLoad中,我根据窗口的大小以编程方式设置按钮的框架,窗口的大小可以根据可见的按钮而变化)。在XIB中为这些按钮适当设置自动调整大小的遮罩。问题是,当窗口实际出现时,按钮似乎没有应用自动调整大小 在调试这个问题时,我在调用super的-setFrame:后,将NSButton子类化并重写-setFrame:以打印帧([self frame])。使用此方法,我观察到框架设置了两次:首先是通
NSWindowController
从XIB文件加载窗口和窗口内的按钮。在-windowDidLoad
中,我根据窗口的大小以编程方式设置按钮的框架,窗口的大小可以根据可见的按钮而变化)。在XIB中为这些按钮适当设置自动调整大小的遮罩。问题是,当窗口实际出现时,按钮似乎没有应用自动调整大小
在调试这个问题时,我在调用super的-setFrame:
后,将NSButton子类化并重写-setFrame:
以打印帧([self frame]
)。使用此方法,我观察到框架设置了两次:首先是通过编程布局代码(称为框架A),然后是Cocoa根据用户偏好调整窗口大小(应用自动调整大小掩码,将框架设置为B)。这些框架看起来都是正确的
但是,当窗口出现时,就好像后一个-setFrame:
调用没有持久的效果-按钮的帧现在返回到A。这可以通过中断调试器并打印帧来验证-自动调整帧更新已恢复,但从未再次调用-setFrame:
关于我为什么会看到这种行为,有什么想法吗?当superview
通过setFrameSize:
调整大小时,它首先会发生,但更常见的情况是调用superview
的layoutSubtreeIfNeeded
方法,该方法反过来调用视图的resizeWithOldSuperviewSize:
。您可以通过子类化NSView
(在本例中为NSButton
)并使用空方法覆盖resizeWithOldSuperviewSize:
)来覆盖此项
- (void)resizeWithOldSuperviewSize:(NSSize)oldSize {}
但是,您也可以通过声明不希望自动布局系统调整NSView
的大小来更优雅地解决问题。您可以通过以下方式完成此操作:
[<id> setAutoresizingMask:NSViewNotSizable];
[<id> setTranslatesAutoresizingMaskIntoConstraints:YES];
然后你就可以开始了
[self.myButton setAutoresizingMask:NSViewNotSizable];
[self.myButton setTranslatesAutoresizingMaskIntoConstraints:YES];
然后使用所需的帧调用setFrame:
。第一行表示视图不可缩放,而第二行表示遮罩应被自动布局系统视为约束。希望有帮助
编辑:
抱歉,由于某种原因,我认为您的问题与我的建议相反,即自动布局正在覆盖您的更改。然而,你想知道的恰恰相反。如果您使用的是setAutoresizingMask:
您是否尝试过setTranslatesAutoresizingMaskIntoConstraints:YES
?如果您可以发布一个最小的工作示例,这也会很有帮助。当superview
通过setFrameSize:
调整大小时,最初会发生这种情况,但在调用superview
的layoutSubtreeifneed
方法时,这种情况更常见,它依次调用视图的resizeWithOldSuperviewSize:
。您可以通过子类化NSView
(在本例中为NSButton
)并使用空方法覆盖resizeWithOldSuperviewSize:
)来覆盖此项
- (void)resizeWithOldSuperviewSize:(NSSize)oldSize {}
但是,您也可以通过声明不希望自动布局系统调整NSView
的大小来更优雅地解决问题。您可以通过以下方式完成此操作:
[<id> setAutoresizingMask:NSViewNotSizable];
[<id> setTranslatesAutoresizingMaskIntoConstraints:YES];
然后你就可以开始了
[self.myButton setAutoresizingMask:NSViewNotSizable];
[self.myButton setTranslatesAutoresizingMaskIntoConstraints:YES];
然后使用所需的帧调用setFrame:
。第一行表示视图不可缩放,而第二行表示遮罩应被自动布局系统视为约束。希望有帮助
编辑:
抱歉,由于某种原因,我认为您的问题与我的建议相反,即自动布局正在覆盖您的更改。然而,你想知道的恰恰相反。如果您使用的是setAutoresizingMask:
您是否尝试过setTranslatesAutoresizingMaskIntoConstraints:YES
?如果您能发布一个简单的工作示例,这也会很有帮助