こんにちは この記事は、Sailfish OSモバイルプラットフォーム向けのアプリケーション開発に関する一連の記事の続きです。 今回は、QMLで日付とタイムゾーンを操作する機能について説明します。 問題自体の説明から記事を開始し、次にそれを解決する方法に進みます。
問題の説明
Sailfish OSアプリケーションを開発する場合、多くの場合、何らかの形式で日付と時刻を操作する必要があります(ただし、他のプラットフォーム用に開発する場合)。 Sailfish OSアプリケーションは、
DatePickerDialogや
TimePickerDialogなどのコンポーネントを使用して日付と時刻を指定します。 内部的には、日付と時刻を制御するために、標準のJavaScript
Dateオブジェクトから継承された
Date QMLオブジェクトを使用します。これは、UTCまたはローカル以外のタイムゾーンで日付と時刻を作成する機能をサポートしません。
Dateオブジェクトには、このためのコンストラクターとメソッドがありません。
new Date(); new Date(value); new Date(dateString); new Date(year, month[, day[, hour[, minute[, second[, millisecond]]]]]);
UTCからの日付、時刻、オフセットを含む文字列を渡すと、リストの3番目のコンストラクタが役立つはずです。 オブジェクトのタイムゾーンは依然としてローカルであり、オフセットで示されるタイムゾーンではありません。
new Date('Jan 30 2017 10:00:00 GMT+0700')
「タイムゾーンを使用する理由は何ですか?」 UTCの時間でできないのはなぜですか?」と答えます:はい、タイムゾーンが意味をなさない場合があります。 日付と時刻のみを使用すれば十分です。 たとえば、勤務時間が9:00に始まる場合、カムチャッカの同僚が18:00に働くことを期待することはほとんどありません。 ただし、異なるタイムゾーンで同時に発生する定期的なイベントの場合は、タイムゾーンが依然として必要です。 たとえば、プロジェクトの進行中の作業に関する毎日の議論は、カムチャツカの同僚の場合は10:00から、同僚の場合は19:00から始まります。
タイムゾーンを設定して日付と時刻を作成する問題の解決策の1つは、サードパーティライブラリのいずれかを使用することでした:
timezone-jsおよび
moment.js 。 しかし、
DatePickerDialogと
TimePickerDialogはこれらのライブラリについて何も知らないため、不適切であることが判明しましたが、内部では標準の
Dateを積極的に使用しています。これは
timezone-jsおよび
moment.jsを使用して作成されたオブジェクトと互換性がありません その結果、他の2つのソリューションが開発されました。
ソリューションNo. 1
思いついた最初の決定は、日付と時刻を制御する独自のJavaScriptオブジェクトを作成することでした。 そのようなオブジェクトは、日付、時刻、およびタイムゾーン情報の保存を許可する必要があり、最も重要なことは、タイムゾーンに影響を与えることなく、Sailfish OSコンポーネント
DatePickerDialogおよび
TimePickerDialogを使用して日付と時刻を変更することです。
独自のJavaScriptオブジェクトを作成するには、別個のJavaScriptファイルでコンストラクター関数を定義する必要があります。
コンストラクター関数は、「yyyy-MM-ddTHH:mm:ssZ」という形式の文字列を受け入れます。Zは、「[+-] HH:mm」という標準ISO 8601形式のUTCに対するオフセットです。Dateオブジェクトは、文字列の一部から作成され、
dateTimeプロパティに割り当てられます。 このプロパティには、タイムゾーンを除く日付と時刻に関する情報が含まれます。 UTCからのオフセットを含む残りの行は、別の
utcOffsetプロパティに保存されます。 これで、日付、時刻、タイムゾーンに関する情報を含むオブジェクトを作成できます。
var myDateTime = new CustomDateTime("2016-12-22T13:40:00+05:00"); print(myDateTime.dateTime);
日付と時刻を同じ形式「yyyy-MM-ddTHH:mm:ssZ」で返すオブジェクトにメソッドを追加します。
多くの場合、日付と時刻を扱うアプリケーションでは、対応する値を表示する必要があります。 開発者として、すべてのユーザーが現在のロケールに従って日付と時刻が正しく表示されるようにする必要があります。 これを行うために、日付と時刻の言語依存表現で文字列を返すJavaScriptオブジェクトメソッドに追加します。
したがって、特定の形式の文字列を使用して作成され、同じ形式の文字列と現在のロケールの形式設定された文字列を返すことができる、日付、時刻、およびタイムゾーンに関する情報を保存および編集できるオブジェクトがあります。 このようなオブジェクトを使用すると、必要なタイムゾーンで日付と時刻を簡単に操作できます。
CustomDateTimeオブジェクトの使用例を考えてみましょう。
この例には、日付と時刻を編集するための
ValueButtonコンポーネントが含まれています。 1つのコンポーネントをクリックすると、2番目の
TimePickerDialogをクリックして
DatePickerDialogが開きます。 時間を編集するための
ValueButtonコンポーネントについて詳しく説明します。
CustomDateTimeオブジェクトは
Pageコンポーネントのプロパティとして作成され、
valueプロパティを使用して
ValueButtonに日付と時刻を表示するために使用されます。また、
onClickedイベント
ハンドラで説明されているように、
DatePickerDialogおよび
TimePickerDialogに値を渡します。
DatePickerDialogおよび
TimePickerDialogからデータを取得し、
CustomDateTimeオブジェクトの
dateTimeプロパティを更新する
方法についても
説明しています。
そのため、日付、時刻、タイムゾーンに関する情報を保存できるCustomDateTime JavaScriptオブジェクトが作成され、
DatePickerDialogと
TimePickerDialogを使用して日付と時刻を編集することもできます。
このソリューションの欠点は、JavaScriptオブジェクトがプロパティバインディングをサポートしないことです。 この例では、日付または時刻を変更(
CustomDateTimeオブジェクトの
dateTimeプロパティを変更)した後、
ValueButtonオブジェクトの
valueプロパティは更新されません。 視覚的には、
CustomDateTimeオブジェクトが
実際に変更されている
にもかかわらず、画面に変更は発生しません。 これは、
CustomDateTimeオブジェクトの
dateTimeプロパティを
ValueButtonオブジェクトの
valueプロパティに関連付けることができないためです。
プロパティのバインドが重要でない場合は、上記のソリューションを使用できますが、他の場合は、ソリューション番号2を参照する必要があります。
決定番号2
2番目の解決策は、独自のQMLコンポーネント、特に
QtObject型のコンポーネントを作成すること
です 。
QtObjectは最も「軽量」な標準QMLタイプであり、視覚的なコンポーネントがなく、モデルオブジェクトを作成するときに役立ちます。 最も重要なことは、QMLコンポーネントがプロパティバインディングをサポートしていることです。 QMLコンポーネントで上記で定義したJavaScriptオブジェクトを書き換えます。
コードがより簡潔になり、JavaScriptオブジェクトのコンストラクター関数とメソッドが
QtObject内のプロパティに置き換えられ
ました 。 ここで、新しいオブジェクトを作成するには、標準のQML構文を使用して
dateTimeStringToSetプロパティを1つだけ定義する必要があります。他のすべてのプロパティは自動的に計算されます。 プロパティバインディングが機能します。
CustomDateTime { dateTimeStringToSet: "2017-01-15T13:45:00+05:00" }
CustomMLateTime QMLオブジェクトを使用して、上記の例を書き換えます。
それほど多くの変更がないことは簡単にわかります。 プロパティ宣言は
CustomMLateTime QMLコンポーネントの宣言に置き換えられ、
toLocaleDateString()および
toLocaleTimeString() 関数の代わりに
localeDateStringおよび
localeTimeStringプロパティが使用され
ます 。 他のすべての点では、コードはまったく変更されていませんが、プロパティバインディングは機能します。
CustomDateTimeオブジェクトの
dateTimeプロパティを変更すると、すべてのオブジェクトプロパティ、特に
localeTimeStringプロパティが更新され、
ValueButtonオブジェクトの外観が更新されます。
おわりに
その結果、Sailfish OSで日付と時刻を編集するコンポーネントによってサポートされる、日付、時刻、およびタイムゾーン情報を管理するためのソリューションが開発されました。 解決策は、独自のQMLコンポーネントを作成し、モデルとして使用することです。 このようなオブジェクトを使用すると、日付、時間、およびタイムゾーンを保存できます。また、プロパティバインドメカニズムをサポートし、Sailfish OSの
DatePickerDialogおよび
TimePickerDailogコンポーネント内で使用して編集できます。 この例のソースコードは
GitHubで入手でき
ます 。
著者:イヴァン・シトフ