私は現在、このCocoa with Loveの記事に示されているメソッドを使用して、カスタムNSWindowサブクラスを作成しています。例のように、矢印を描画するには、ウィンドウのコンテンツの周囲に約10pxのマージンが必要でした(ポップオーバースタイルのウィンドウを作成しています)。コンテンツを再配置せずに矢印の位置を変更できるようにしたかったので、矢印のある側だけでなく、ウィンドウ全体の周りにマージンを持たせる必要がありました。
要約すると、これを行うために使用している方法は次のとおりです(関連するコードは下部にあります)。
- NSWindowのメソッド
contentRectForFrameRect:
とメソッドをオーバーライドして、コンテンツの周囲にパディングを追加します。frameRectForContentRect:styleMask:
- ウィンドウのカスタム描画フレームビューをとして設定し
contentView
、次にのセッターとゲッターをオーバーライドして、渡されたビューがフレームビューのサブビューcontentView
として追加されるようにします。
問題は、ウィンドウの実際のコンテンツビュー内のビューの自動サイズ変更マスクが完全に台無しになっていることです。インターフェイスビルダーでコンテンツを設定する方法は次のとおりです。
テーブルビュースクロールビューの自動サイズ変更マスクの設定方法は次のとおりです。
また、テキストラベルの自動サイズ変更マスクの設定方法は次のとおりです。
そして、結果はアプリ内で次のようになります。
関連コード(前述の記事から派生)
#define CONTENT_MARGIN 10.0
- (NSRect)contentRectForFrameRect:(NSRect)windowFrame
{
windowFrame.origin = NSZeroPoint;
return NSInsetRect(windowFrame, CONTENT_MARGIN, ICONTENT_MARGIN);
}
- (NSRect)frameRectForContentRect:(NSRect)contentRect
{
return NSInsetRect(contentRect, -CONTENT_MARGINT, -CONTENT_MARGIN);
}
+ (NSRect)frameRectForContentRect:(NSRect)contentRect
styleMask:(NSUInteger)windowStyle
{
return NSInsetRect(contentRect, -CONTENT_MARGIN, -CONTENT_MARGIN);
}
- (NSView*)contentView
{
return _popoverContentView;
}
- (void)setContentView:(NSView *)aView
{
if ([_popoverContentView isEqualTo:aView]) { return; }
NSRect bounds = [self frame];
bounds.origin = NSZeroPoint;
SearchPopoverWindowFrame *frameView = [super contentView];
if (!frameView) {
frameView = [[[SearchPopoverWindowFrame alloc] initWithFrame:bounds] autorelease];
[super setContentView:frameView];
}
if (_popoverContentView) {
[_popoverContentView removeFromSuperview];
}
_popoverContentView = aView;
[_popoverContentView setFrame:[self contentRectForFrameRect:bounds]];
[_popoverContentView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
[frameView addSubview:_popoverContentView];
}
ポップオーバーのコンテンツがどういうわけか余白を超えているのではないかと思ったので、コンテンツビューの周りに境界線を引きましたが、いや、すべてがそうあるべきです。唯一の問題は、コンテンツビュー内のラベルビューとテーブルビューの自動サイズ変更マスクが正常に機能しないことです。アドバイスをいただければ幸いです。
編集:誰かが興味を持っているなら、私はgithub上のこのポップオーバーウィンドウ/コントローラーの完全なコードをINPopoverControllerとしてオープンソース化しました。問題を再現してみたい場合に備えて、サンプルプロジェクトが含まれています。