|
- Application Kit-
NSView
Application Kit - NSView
View にカーソルを対応付ける
Keywords: resetCursorRects, addCursorRect
ある View とカーソルを対応付けられたら、便利だと思わないかい?View にマウスが入ったら、カーソルが変わる、出たら戻る、って感じの動作。
そのための機構が用意されている。Tracking Rect ってやつだ。Tracking Rect として、ある rect をセットしてやると、そこへマウスが入る時と、出る時が監視されるんだ。Tracking Rect の詳しい話は他に譲るとして、NSView にはカーソルと Tracking Rect を結び付けるための便利なメソッドが用意されているんだ。
まず、resetCurosorRects というメソッドだ。
Application Kit/NSView.h
- (void)resetCursorRects;
このメソッドは NSView がカーソル用の Tracking Rect を設定する時に使われるんだ。ユーザがオーバーライドする。カーソル用 Tracking Rect は、View の大きさが変わったり、ウィンドウの大きさが変わったりした時に、リセットされる。その度にこのメソッドが呼び出されるわけ。
resetCursorRects の中では、addCursorRect:cursor: を使おう。
Application Kit/NSView.h
- (void)addCursorRect:(NSRect)aRect
cursor:(NSCursor*)aCursor;
addCurosrRect:: で、カーソル用 Tracking Rect を追加できる。aRect の領域に入ったら、aCursor のカーソルに変わるんだ。
CursorView.m (sample)
- (void)resetCursorRects
{
NSRect rect = [self bounds];
NSCursor* cursor = [NSCursor IBeamCursor];
[self addCursorRect:rect cursor:cursor];
}
これで、この View の領域に入った時、カーソルが I ビームカーソルに変わるぞ。
Application Kit - NSView
drawRect 以外で描画する
Keywords: displayIfNeeded
View になにかを描くときは、drawRect: メソッドをオーバーライドして、その中でいろいろやるのが普通だ。でも、それ以外のタイミングでやりたくなるときもあるよね。そんなときは、displayIfNeeded を使う。
Application Kit/NSView.h
- (void)displayIfNeeded;
View に対してなんらかの描画をしたあと、displayIfNeeded を呼べば、システムがよきにはからってくれるわけ。
DisplayView.m (sample)
- (void)initWithFrame:(NSRect)rect
{
self = [super initWithFrameRect:rect];
if(self) {
NSArray* array =
[NSArray arrayWithObject:NSFilenamesPboardType];
[self registerForDraggedTypes:array];
}
return self;
}
- (unsigned int)draggingEntered:(id <NSDraggingInfo>)sender
{
NSFrameRect([self visibleRect]);
[self dispalyIfNeeded];
return NSDragOperationNone;
}
- (void)draggingExited:(id <NSDraggingInfo>)sender
{
NSEraseRect([self visibleRect]);
[self dispalyIfNeeded];
}
上のサンプルは、Finder からファイルをドラッグしてきたときに、View をハイライト表示させる例だ。draggingEntered: の中で、NSFrameRect を使って枠を描いてる。その後に displayIfNeeded を呼んで、システムにアップデートをお願いしているんだ。draggingExited: の方も同様だね。
Application Kit - NSView
コンテキストメニューを動的に変化させる
Keywords: menuForEvent
NSResponder で解説した通り、コンテキストメニューを設定できるんだ。そのメニューを、状況に応じて動的に変化させたい場合には?その場合には NSView のメソッドである menuForEvent: を使うんだ。
Application Kit/NSView.h
- (NSMenu *)menuForEvent:(NSEvent *)event;
ctrl + クリックなど、コンテキストメニューを表示させようとすると、このメソッドが呼び出される。で、好きなメニューを作って、返してやればいいんだ。そうすれば、それが表示される。引数として NSEvent が渡されるので、マウスの位置とか、好きな情報を取り出して使えばいいんだ。
■関連リンク:
コンテキストメニューを設定する (NSResponder)
Application Kit - NSView
フォーカスリングのスタイルを変える
Keywords: NSFocusRingType
Mac OS X 10.3 からは、NSView と NSCell に、フォーカスリングのタイプを設定できるようになった。フォーカスリングっていうのは、テキストビューとかにフォーカスがあたったときに、周りに描かれるあれね。
フォーカスリングのタイプは、NSFocusRingType 定数として定義されている。次の 3 つがあるんだ。
Application Kit/NSGraphics.h
typedef enum _NSFocusRingType {
NSFocusRingTypeDefault = 0,
NSFocusRingTypeNone = 1,
NSFocusRingTypeExterior = 2
} NSFocusRingType;
NSFocusRingTypeDefault は、NSView か NSCell で定義されているデフォルトのタイプを使う。NSFocusRingTypeNone は、フォーカスリング無し。NSFocusRingTypeExterior は、標準のフォーカスリングで、外側に描くやつだ。ま、実質 NSFocusRingTypeExterior しかないようなもんだ。
このフォーカスリングを取得、設定するには、NSView か NSCell の focusRingType、setFocusRingType を使う。
Application Kit/NSView.h
- (NSFocusRingType)focusRingType;
- (void)setFocusRingType:(NSFocusRingType)focusRingType;
ここでフォーカスリングとしてデフォルト(NSFocusRingTypeDefault)が設定されると、NSView か NSCell の defaultFocusRingType が呼ばれる。ここで得られる値がデフォルトとして使われるんだ。
Application Kit/NSView.h
+ (NSFocusRingType)defaultFocusRingType;
だから、これを上書きすれば、デフォルトのフォーカスリングを変更できる。たとえば、こんな感じで。
(sample)
@interface NSView (DefaultFocusRingType)
+ (NSFocusRingType)defaultFocusRingType;
@end
@implementation NSView (DefaultFocusRingType)
+ (NSFocusRingType)defaultFocusRingType
{
return NSFocusRingTypeNone;
}
@end
これはカテゴリを使って、NSView の defaultFocusRingType を書き換えてみた例だ。NSFocusRingTypeNone を返すようにしてみた。これで、デフォルトの挙動を変更できるぜ。
|