0

Applescriptを使用してXcodeでMac Appをコーディングしています。
ずっと止まらない機能を作ったのですが、止められません。
ウィンドウにあるボタンを押すと起動します。
この機能は停止しないため、ボタンはずっと押されたままになります。
そして、「Command + Option + Escape」で強制終了する必要があります。(この操作をしてもアプリが停止しない場合があります。)
機能が始まる前にボタンを離したいので、別のボタンを押して安全に機能を停止したい。
これは私の例です。これを停止するには、Xcode の「停止」ボタンを押します。

property parent : class "NSObject"
property mylabel : missing value

on applicationWillFinishLaunching_(aNotification)
    -- Insert code here to initialize your application before any files are opened
end applicationWillFinishLaunching_

on myStartButtonHandler_(sender)
    my myForeverFunction()
end myStartButtonHandler_

on myStopButtonHandler_(sender)
    --How can I stop "myForeverFunction"?
end myStopButtonHandler_

on myForeverFunction()
    set a to 0
    repeat 100 times
        set a to a+1
        mylabel's setStringValue_(a)
        delay 1
    end repeat
end myForeverFunction

on applicationShouldTerminate_(sender)
    -- Insert code here to do any housekeeping before your application quits 
return current application's NSTerminateNow
end applicationShouldTerminate_

これがプロジェクトファイルです --> https://dl.dropboxusercontent.com/u/97497395/test.zip
私は日本人で、英語がうまく書けません。

4

2 に答える 2

2

基本的に、アプリケーションのインターフェイスは、アプリのメイン スレッドで制御および更新されます。したがって、メイン スレッドを結び付けるコードを実行すると、そのコードが完了するまで、インターフェイスはそれ自体を更新する機会がありません。そのため、コードをバックグラウンド スレッドで実行することを修正すると、インターフェイスはそれ自体を更新できるようになります。

私はあまり慣れていないので、AppleScriptObjC でこれを行うことができるかどうかはわかりません。これがobjective-cでのやり方です。ハンドラー (someHandler) を作成してから、このコードを実行します。このハンドラーは、自動的に生成されたリリース プールを持つメイン スレッドで実行されないため、ハンドラーでリリース プールを作成してドレインする必要があることに注意してください。

[NSThread detachNewThreadSelector:@selector(someHandler) toTarget:self withObject:nil];

編集:これがあなたが尋ねた自動解放プールです。参照カウント環境では、このようにします...

-(void)someHandler {
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];

    // do your stuff here

    [pool drain];
}

自動参照カウント (ARC) を使用すると、次のようになります...

-(void)someHandler {
    @autoreleasepool {
        // do your stuff here
    }
}

したがって、どれが AppleScriptObjC に当てはまるかわかりません。簡単なグーグル検索でこの投稿が見つかりました。

于 2013-08-10T20:23:59.870 に答える
1

現在、あなたのコードはループとループを繰り返しており、インターフェースなどの重要なものは決して更新されていません。doEventFetchキューに入れられたすべてのプロセスを実行する関数を呼び出すと、問題が解決するはずです。ループごとに 1 回呼び出すだけです。

on doEventFetch()
    repeat
        tell current application's NSApp to set theEvent to nextEventMatchingMask_untilDate_inMode_dequeue_(((current application's NSLeftMouseDownMask) as integer) + ((current application's NSKeyDownMask) as integer), missing value, current application's NSEventTrackingRunLoopMode, true)
        if theEvent is missing value then
            exit repeat
        else
            tell current application's NSApp to sendEvent_(theEvent)
        end if
    end repeat
end doEventFetch

on loopFunc()
    repeat
        #Repeat stuff here...
        doEventFetch()
    end repeat
end loopFunc
于 2013-08-11T01:27:00.553 に答える