RubberBand もずいぶん長くなったが、アプリに必要な検証および機能実装も大分できてきた。後もう少し。
今回はアプリへの組み込みを想定して、初期状態を導入する。今までは初期状態はあらかじめ決まった大きさの RubberBandを表示していたが、アプリで使う場合の初期状態は RubberBandが表示されない状態を想定している。
ここである点をクリックしてドラッグするとRubberBandが現れる。この後はいままでと同じ。
状態を管理する為にメンバ変数に _state を用意する。0 は初期状態(非表示)、1 を表示状態とする。
@interface RubberBandView : NSView {
:
int _state;
}
_state == 0 の時は描画させない。
- (void)drawRect:(NSRect)rect {
if (_state == 0) {
return;
}
:
マウスクリック時の処理を状態によって変える。
- (void)mouseDown:(NSEvent*)event
{
NSPoint pp, cp;
cp = [self convertPoint:[event locationInWindow] fromView:nil];
int knob_type;
switch (_state) {
case 0:
while ([event type] != NSLeftMouseUp) {
event = [[self window] nextEventMatchingMask:(NSLeftMouseDraggedMask | NSLeftMouseUpMask)];
NSPoint cp2 = [self convertPoint:[event locationInWindow] fromView:nil];
if (fabs(cp2.x - cp.x) > KNOB_WIDTH || fabs(cp2.y - cp.y) > KNOB_WIDTH) {
knob_type = 7; // BOTTOM_RIGHT;
_rect = NSMakeRect(cp.x, cp.y, 0, 0);
_state = 1;
break;
}
if ([event type] == NSLeftMouseUp) {
return;
}
}
break;
case 1:
knob_type = [self knobAtPoint:cp];
break;
default:
break;
}
:
(今までのドラッグ処理)
初期状態(_state ==0)の時にマウスクリックがあったらイベントループを作りドラッグとボタン離しを監視する。一定以上(KNOB_WIDTH)以上の移動があったらドラッグ開始とみなしてループを抜ける。この時、初期位置・サイズを決定した上で、右下のKnobを押しているように振る舞わせる。そして状態を 1にする。この後は今まで作ってきた通常のドラッグ処理に合流する。一方、ドラッグ無しでマウスボタンが押された場合は何もせずにその場でメソッド処理を抜ける。
ソース:RubberBand-13.zip