「入力の取り消し」はどのように動作する必要がありますか?


12

Undo / Redoスタックを含むJavaアプリを実装しています。一部のアプリ(Mac OS XのTextEditなど)では、テキストを入力した後、[編集]メニューから[入力を元に戻す]を選択できます。私も自分のアプリにそのようなことを実装したいと思いますが、それがどのように振る舞うべきかについてのガイドラインを見つけるのに本当に苦労しています。

試行錯誤を繰り返して、TextEditのUndo Typingの動作についての私の推測は次のとおりです。

  • ユーザーが新しい文字を入力する(または削除キーを入力する)ときに、次のいずれかの状況が発生しない限り、元の[元に戻す]項目が元に戻すスタックの最上位にある場合、それをマージします
  • 少なくとも15秒間非アクティブな状態が続いた後にユーザーが入力を続けた後は、常に新しい[元に戻す]項目を作成します。
  • ユーザーが長時間入力し、何らかの条件が満たされた後は、常に新しい[元に戻す]項目を作成します(これが時間ベースであるか文字数ベースであるかはわかりません)。
  • テキストを選択してから削除または上書きする場合は、常に新しい[元に戻す]項目を作成します(テキストを選択し、変更を加えずに元の挿入ポイントに戻って入力し続けても、トリガーされません)

実際には、Appleの戦略は機能しているように見えます(少なくとも私がタイプするときは機能します)が、最後のポイントで述べたように、私は実際にルールを理解することができませんでした。また、他のプログラムはMicrosoft Wordなどの異なる規則に従っているようです。Googleは、Undo Typingの実装に関するルールの定義済みリストを公開しておらず、その動作方法に関するベストプラクティスに遭遇していません。それで、それはどのように振る舞うべきですか?それとも、プログラマーの気まぐれ次第ですか?

編集:明確にするために、今は実装の詳細には興味がありません。特に、これを説明する信頼できる参照(ベストプラクティスやユーザーインターフェイスドキュメントなど)が存在するかどうか、または複数の製品にまたがってどのように実装されているかの説明について興味があります。


私の提案:元に戻す情報から押されたキーの正確なシーケンスを再構築することが可能なポイントまで修正を圧縮し、それ以上はしません。たとえば、これは、ユーザーが何かを入力し、すぐにバックスペースを使用してそれを削除する場合、間に取り消しポイントがあるはずであることを意味します。
アンブロズビズジャック

また、ユーザーが新しい行を作成するたびに、または文字入力の直後にスペースバーが使用されるたびに、新しい「入力を元に戻す」項目を追加することもできます。新しい「入力を元に戻す」項目までのIMOの15秒の待ち時間は少し長くなる可能性がありますが、それは私だけです。(約5秒間行きます)
-user82529

または、「押されたキーの正確なシーケンス」を「各変更後のテキストの状態」に緩和する必要があります。アイデアは、圧縮によりテキストが失われないようにすることです。
アンブロズビズジャク

他の条件が満たされない場合、TextEditはスペースをマージして最後の入力取り消し項目と削除するように思えます。それで124<delete>3、それを元に戻し、やり直します123。これの利点は、上記の提案のように、ユーザーのテキストの最終状態が得られることだと思います。
サンダーフォージ

特許を検索しようとしましたか?(通常、ルールはライブラリレイヤーにエンコードされ、ユーザーコードには公開されません。)
ドナルフェローズ

回答:


5

信頼できるソースを探しているなら、最高のMac関連の資料はAppleのUndo Architectureドキュメントにあると思います。

ただし、元に戻すイベントを合体させるべき、または合体させるべきでない場合のルールのリストを見つけるとは思わない。あるアプリケーションにとって正しいと感じることは、別のアプリケーションにとって必ずしも意味をなさない。たとえば、テキストエディターでは、キーストロークの合体は理にかなっています。ユーザーが段落を入力するのはおそらく個別のアクションとしてではなく、単一のアクションとして表示されるからです。彼らがその段落をタイプする前の時点まで。しかし、描画プログラムのシェイプに対する移動操作はどうでしょうか?または塗りつぶしの色を順番に調整しますか?プログラムの性質に応じて、これらが合体するかしないかの良いケースを作ることができます。

ユーザーが長時間入力し、何らかの条件が満たされた後は、常に新しい[元に戻す]項目を作成します(これが時間ベースであるか文字数ベースであるかはわかりません)。

自動保存に基づいています。幸運なことに、TextEditのソースコードは入手可能で、コメントも豊富です。ご覧になれば、何が起こっているのか、なぜ起こっているのかがよくわかると思います。例えば:

- (void)saveToURL:(NSURL *)absoluteURL ofType:(NSString *)typeName forSaveOperation:(NSSaveOperationType)saveOperation completionHandler:(void (^)(NSError *error))handler {
    // Note that we do the breakUndoCoalescing call even during autosave, which 
    // means the user's undo of long typing will take them back to the last spot an 
    // autosave occured. This might seem confusing, and a more elaborate solution may 
    // be possible (cause an autosave without having to breakUndoCoalescing), but since 
    // this change is coming late in Leopard, we decided to go with the lower risk fix.
    [[self windowControllers] makeObjectsPerformSelector:@selector(breakUndoCoalescing)];
 ...

実装の詳細にはまだ興味がないと言っていましたが、AppleがTextEditを実装した方法を見ると、自分のアプリケーションに対して行った決定を知ることができます。


1
これが最善の答えだと思います。Appleの実装へのリンクと、私が提供した特定の例のコードを提供してくれたことに感謝します。あなたは正しいと思いますが、それは一般的にアプリケーションのニーズに基づいており、それらのニーズが何であり、どのように対処するかを標準化する努力をしている人は誰もいません。
サンダーフォージ

1

キーダウン時 ->アイドルスタートを表すタイマー

キーダウン/タイマー実行時 ->タイマーのリセット

キーダウン時/タイマー実行なし ->セルブロックを再調整して、位置が変化したときに新しい保存状態を準備する

アイドルタイマーがダウンする ->新しい取り消し状態を確立する

キーを押した場合のIDは追跡しません。セルのテキストブロック(文字数)に分割して、最も近いセルの開始位置からのオフセットによって位置を追跡できるようにし、アイドルタイマーが切れるたびにトルストイ小説の状態全体を保存する必要がないようにしました。他のセルが編集される前のセルのオフセットを再調整するのは難しい部分です。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.