2

特に XUL でprefwindowメカニズムを使用する場合、Firefox 拡張機能で設定値を検証する一般的に受け入れられている方法は何ですか?

設定ウィンドウを閉じる前に検証したい拡張機能の 1 つにいくつかの新しい設定を導入しています。エラーが発生した場合は、ユーザーが問題を修正してから続行できるようにする必要があります。prefwindowこの要素には、この点で役立つ可能性のある 2 つの機能があることがわかります。

前者には関連するバグ ( Bug 474527 ) があり、その関数からprefwindow戻るときに が開いたままになるのを妨げているようです。falseこれは、ユーザーが間違いをすぐに修正する機会を与えないという点で悪いことです。

後者には、終了する前に設定が保存され、設定が内部的に悪い状態のままになるという問題があるようです。

さらに、このprefwindowメカニズムはbrowser.preferences.instantApply、関連付けられたコントロールを更新するとすぐに設定値が書き込まれるオプションをサポートします。これにより、検証がさらに難しくなります。ユーザーが潜在的な間違いを修正できるように、Firefox 拡張機能のカスタム設定を検証するクリーンな方法はありますか?

4

2 に答える 2

2

通常、設定が変更されたときに設定を検証する必要があります。これは、onchange属性(および対応するchangeイベント) が適しているものです。

<preference name="preference.name" onchange="validate(this);"/>

このイベントは、設定値が変更された後に発生します。2 つの欠点があります。

  • 新しい設定値がすでに保存されている場合、instantApply検証して拒否するには遅すぎます。
  • テキスト フィールドの場合、新しい文字が入力されるたびに設定が保存されます。ユーザーがまだ入力している間に検証の失敗を報告すると、これは見苦しくなります。

最初の問題は、実際の入力フィールドの変更イベントをインターセプトすることで解決できます。たとえば、テキスト フィールドの場合は次のようにします。

<input preference="preference.name"
    oninput="if (!validate(this)) event.stopPropagation();"
    onchange="if (!validate(this)) { event.stopPropagation(); this.focus(); }"/>

そのため、正しく検証されない変更は<prefpane>要素に反映されず、保存されません。リッスンするイベントはinputchangeテキスト フィールド、commandボタンとチェックボックス、select要素<colorpicker>です。

2番目の問題はトリッキーです。入力が発生したときに入力を検証する必要がありますが、メッセージをすぐに表示するのは悪い UI です。最良の解決策は、最初は各入力フィールドがまだ「進行中」であると想定することだと思います。blurフィールドで最初にイベントが表示されたときにのみ、値が完了したというフラグを設定します。このとき、必要に応じて検証メッセージを表示できます (モーダル プロンプトではなく、設定ページに表示される赤いテキストが理想的です)。

したがって、最終的なソリューションがどのように見えるかを示すために(テストされていないコードですが、過去にそのようなものを使用しました):

<description id="error" hidden="true">Invalid preference value</description>

<input preference="preference.name"
    _errorText="error"
    onblur="validate(event);"
    oninput="validate(event);"
    onchange="validate(event);/>

<script>
  function validate(event)
  {
    // Perform actual validation
    var field = event.target;
    var valid = isValid(field);

    // If this is the blur event then the element is no longer "in progress"
    if (event.type == "blur")
    {
      field._inputDone = true;
      if (!valid)
        field.focus();
    }

    // Prevent preferences changing to invalid value
    if (!valid)
      event.stopPropagation();

    // Show or hide error text
    var errorText = document.getElementById(field.getAttribute("_errorText"));
    errorText.hidden = valid || !field._inputDone;
  }
</script>
于 2012-10-10T11:58:40.493 に答える
1

フィールドが変更されたらすぐに値を検証してinstantApplyケースを処理できるようにする場合は、個々のフィールドの変更イベントにフックすることができます(例oninput:)textbox。エラーメッセージを表示し、値が無効な場合はフォーカスをフィールドに戻します。自動的に有効な値に戻すか、修正されるまでユーザーがダイアログを閉じるのをブロックすることができます。

于 2012-10-10T07:29:26.427 に答える