2018を編集:この目的のためにBroadcastChannelを使用することをお勧めします。以下の他の回答を参照してください。それでも、タブ間の通信にlocalstorageを使用したい場合は、次のようにします。
タブが他のタブにメッセージを送信したときに通知を受けるには、単に「ストレージ」イベントにバインドする必要があります。すべてのタブで、次の操作を行います。
$(window).on('storage', message_receive);
この関数message_receive
は、他のタブでlocalStorageの値を設定するたびに呼び出されます。イベントリスナーには、localStorageに新しく設定されたデータも含まれているため、localStorageオブジェクト自体を解析する必要もありません。値を設定した直後にリセットして、トレースを効果的にクリーンアップできるため、これは非常に便利です。メッセージングの機能は次のとおりです。
// use local storage for messaging. Set message in local storage and clear it right away
// This is a safe way how to communicate with other tabs while not leaving any traces
//
function message_broadcast(message)
{
localStorage.setItem('message',JSON.stringify(message));
localStorage.removeItem('message');
}
// receive message
//
function message_receive(ev)
{
if (ev.originalEvent.key!='message') return; // ignore other keys
var message=JSON.parse(ev.originalEvent.newValue);
if (!message) return; // ignore empty msg or msg reset
// here you act on messages.
// you can send objects like { 'command': 'doit', 'data': 'abcd' }
if (message.command == 'doit') alert(message.data);
// etc.
}
したがって、タブがonstorageイベントにバインドし、これらの2つの関数を実装したら、次のように、他のタブ呼び出しにメッセージをブロードキャストするだけです。
message_broadcast({'command':'reset'})
まったく同じメッセージを2回送信すると1回だけ伝播されるため、メッセージを繰り返す必要がある場合は、次のように一意の識別子を追加してください。
message_broadcast({'command':'reset', 'uid': (new Date).getTime()+Math.random()})
また、メッセージをブロードキャストする現在のタブは実際には受信せず、同じドメインの他のタブまたはウィンドウのみを受信することも覚えておいてください。
removeItem()の前のsetItem()呼び出しの直後にユーザーが別のWebページをロードしたり、タブを閉じたりした場合にどうなるかを尋ねることがあります。まあ、私自身のテストから、ブラウザは関数全体message_broadcast()
が終了するまでアンロードを保留します。私はいくつかの非常に長いfor()サイクルを入れるようにテストしましたが、それでも、閉じる前にサイクルが完了するのを待っていました。ユーザーがその間のタブを強制終了すると、ブラウザーにはメッセージをディスクに保存する十分な時間がなくなるため、このアプローチは、トレースなしでメッセージを送信する安全な方法のように思えます。コメントを歓迎します。