第4回:twitter の JavaScript Badge をIEで表示するとおかしい件に対応してみる

twitter 流行ってますね。みなさんも使っていますか?
オレはというと…ポツリポツリと呟いています。
friends は2人しかいません orz

twitter は SNS 的な使い方もできるツールなのですが、SNS よりも遥かにゆるく「低機能」なので自分としては本当にその時のステータスをブログパーツとしてこのブログに貼り付けるために使っています。
で、このブログパーツ(アチラでは Badge と呼びますね)なんですが、twitterには標準で4つの Badge が用意されていてブロガー達に重宝されているようです。内2つは Flash バージョンなんですがデザインが気に食わなかったので JavaScript 版にちょっとテコ入れをして使う事にしました。

・・・ってか写真展示に関する Tip's を公開するスペースじゃなかったのか?ここは。
スミマセン。興味の向くままノープランで書いております(苦笑)

1)IE で Badge を見ると「NaN」とかなっている

badge の 中にある relative_time 関数は「about * hours ago」とか表示してくれるんだけど、IE の場合は JavaScript に問題があって、「NaN days ago」とかなっちゃう。
原因は relative_time 関数内1行目の Date.parse だ。

Date.parse は日付文字列を Date 型にパースしてくれるんだけど、引数で渡す文字列によってはうまく日付として扱ってくれない。しかも、ブラウザによって解釈が違う。
この Badge で relative_time 関数に渡される日付文字列はJSONPから返されているのだけど、こんなフォーマットだ。

"Wed Apr 25 12:35:05 +0000 2007"

これを JavaScript で解釈しやすい下記のフォーマットに変換してみる。

"Apr 25, 2007 12:35:05"

修正は Date.parse の前に下記2行を足すだけ。

function relative_time(time_value) {
time_values = time_value.split(" ");
time_value = time_values[1]+" "+time_values[2]+", "+time_values[5]+" "+time_values[3];
var parsed_date = Date.parse(time_value);

1行目では、" "スペースで配列に分解、
2行目では、並び替えをしている。(曜日とミリ秒はいらない)

これで「NaN」は解決しました。


2)9時間ズレてますけど

twitterサーバは米国(?)で UTC 、JavaScriptを動かしているのは日本で JST 、ありがちなネタです。 relative_time 関数で経過秒数である delta 変数の計算のあとに、差分を吸収するためのコードを追加します。

var delta = parseInt((relative_to.getTime() - parsed_date) / 1000);
delta = delta + (relative_to.getTimezoneOffset()*60);

getTimezoneOffset()ってのが差分を出してくれる関数。日本だと9時間だから -540 (分)が返る。単位は秒数だから 60 をかけた。

これで修正は終わりです。
一応完成したコードをのせておきます。

<script type="text/javascript">
function relative_time(time_value) {
time_values = time_value.split(" ");
time_value = time_values[1]+" "+time_values[2]+", "+time_values[5]+" "+time_values[3];
var parsed_date = Date.parse(time_value);
var relative_to = (arguments.length > 1) ? arguments[1] : new Date();
var delta = parseInt((relative_to.getTime() - parsed_date) / 1000);
delta = delta + (relative_to.getTimezoneOffset()*60);
if(delta < 60) {
return 'less than a minute ago';
} else if(delta < 120) {
return 'about a minute ago';
} else if(delta < (45*60)) {
return (parseInt(delta / 60)).toString() + ' minutes ago';
} else if(delta < (90*60)) {
return 'about an hour ago';
} else if(delta < (24*60*60)) {
return 'about ' + (parseInt(delta / 3600)).toString() + ' hours ago';
} else if(delta < (48*60*60)) {
return '1 day ago';
} else {
return (parseInt(delta / 86400)).toString() + ' days ago';
}
}

function twitterCallback(obj) {
var id = obj[0].user.id;
document.getElementById('my_twitter_status').innerHTML = obj[0].text;
document.getElementById('my_twitter_status_time').innerHTML = relative_time(obj[0].created_at);
}
</script>
<span id="my_twitter_status"></span> <span id="my_twitter_status_time"></span>
<script type="text/javascript" src="http://www.twitter.com/statuses/user_timeline/{YourID}.json?callback=twitterCallback&count=1"></script>


関連エントリー

 ・第6回:TinyURL の遷移先が怖くて開けない場合の対処法
 ・第5回:twitter の JavaScript Badge を改造する

ブログランキング←この記事が役に立った場合はクリックで応援して下さい!

同じカテゴリーの記事

このページの一番上に戻る
  • Facebook
  • Twitter
  • Tumblr
  • Instagram
  • miil