コンテキストを超えた値の共有[TitaniumMobile]

sxchu_308383_titanium.jpg

TitaniumMobileプログラミングの話。
Windowを生成する時、urlパラメータを使うと、そのWindowは副コンテキストに分割されて動くことになるので、親コンテキストの変数を参照することは出来ません。

Window – titanium-mobile-doc-ja – UIカタログ – Window – Project Hosting on Google blockquote

これを乗り越えるための対策は、上記ドキュメントに書いてあるのですけど、微妙にいろいろ罠があって、実験して分かったことまとめ。

例えば、親コンテキスト(win1)の変数hogeがあって、副コンテキスト(win2)でボタンを押したらhogeをインクリメントしたい、というような場合。

main.jpg
sub.jpg

まず、親コンテキストの変数を子コンテキストで参照するには、こういう風にする。

var hoge = 1;
win2.hoge = hoge;

すると、子コンテキスト側からは、

var win2    = Titanium.UI.currentWindow;
Ti.API.debug("hoge:"+win2.hoge);

みたいにして参照することが出来る。
ただし、変数はby value渡しになるので、副コンテキストで値を変更してもメインコンテキストのhogeには反映されません。
なので、

button1.addEventListener('click',function(e){
win2.hoge = win2.hoge+1;
label.text = 'hoge:'+ win2.hoge;
});

こういうふうに書いても、main側ではhogeの変更は全く無視されてしまいます。

メインコンテキストに値を反映したい時は、

function update_hoge(value){
hoge = value;
}

という具合にセッターを用意してあげて、副コンテキストの方から

win2.update_hoge( Titanium.UI.currentWindow.hoge + 1);

という具合にして呼び出してあげると、メインコンテキストで実行されるので、値を反映することが出来ます。

button1.addEventListener('click',function(e){
win2.update_hoge(win.hoge+1);
label.text = 'hoge:'+ win.hoge;
});

ただしここにはさらに罠があって。update_hogeを呼んだからといって、副コンテキストが見ているwin2.hogeが勝手にアップデートされたりはしません。
なので、上記コードも、ボタンをクリックしても副コンテキストのhogeの値はちっとも増えないように見える。実際には、メインコンテキスト側のhogeが増えているので、いったんウインドウを閉じて開けば反映されるのですけど。

副コンテキスト側に値を戻してあげるには、update_hogeで反映してあげるしかないみたい。

function update_hoge(value){
hoge = value;
win2.hoge = hoge;
}

という具合にして書き戻すようにするか、get_hoge();を作るのがよいみたい。

コンテキストというのがスレッドのことなのかなんなのかによっては、意図しない順番で処理が実行されたりしそうで怖いのですけど、その辺は明日えらい人たちに聞いて勉強してこようと思います。

おまけ

というわけで明日(あ、今日になっちゃった)は
はてな技術勉強会 Hackathonです。@masuidriveをはじめ、TitaniumMobile関係えらい人がいっぱい集まるのにもかかわらず、まだ席が空いています!もったいないお化けが出ますので、空いている人ははてなにGO!