R&Dトレンドレポート

第19回マッシュアップ開発のススメその5:PC版フロントエンドの構成②]

前回に続いて、今回もPCのフロントエンドの説明となります。今回はこのアプリのメインコンテンツである、コメント表示機能について説明します。

コメント表示機能について

コメントの表示形式は、いろいろなパターンが考えられます。

  • 縦スクロール
  • 横スクロール
  • ランダム

などなど。

今回のアプリの狙い所は実用的なものではなく、楽しいか楽しくないかというのがポイントです。実際に動作させた場合にどのように表示すると楽しいか、という点で考えるとランダムが一番適当と思われます。コメント1つ1つの可読性が高いことが重要なわけではなく、盛り上がってるかどうかがわかること、の方が重要です。

ニコニコ動画と同じですね。

ニコニコ動画も画面上に大量のコメントが流れるのを見ることで、コメントしていない閲覧者も盛り上がることができます。あのコメントを1つ1つ読むなんてことは不可能ですよね?

ですので、ここでは

  • 表示位置はランダム
  • 表示方法はフェードインフェードアウト
  • オブジェクトは半透明

という表示形式を採用しました。

閲覧者がコメントエリア内でわいわいがやがや盛り上がっているようなイメージとなります。また、半透明にしたことで、コメントが重なってもある程度読むことが可能となります。

ここで使用したのは、jQueryのプラグインである、Beauty Tipsです。このプラグインは、基本的にはインフォメーションバルーンを提供するモノですが、動きやできることが相当凝っていて、Webページのインターフェースがよりリッチに、そして高いユーザビリティを提供することが可能となります。その割に使い方が非常に簡単という親切設計となっています。

詳しくはデモのページを参照してください。感動します。

コメント表示の流れ

動画再生からの流れをおさらいしておくと、

  • 動画再生
  •    ↓
  • 動画の再生時間変更イベント発生
  •    ↓
  • 再生時間をチェックして、コメントをサーバに取りに行く(getRes()関数起動)

ここでは、getRes()で取得したコメントを画面に表示する部分の説明となります。

コメントの取得について

それではさっそくソースを見てみましょう。

リスト1 BeautyTipsのソースの読み込み
<script src="js/jquery.bt.min.js" type="text/javascript"></script>

getRes()の関数は以下のようになります。

リスト2 getRes()関数
basetime = 1284724805; //動画開始時のunixtime。
function getRes()
{
    var t =  myvid.currentTime; //動画の再生位置の経過時間(秒)を取得
    var _t = basetime + t; // 開始時にプラスしコメント取得時刻のパラメータとする

      // クッキーに当該動画の再生位置を保存する。
    $.cookie("time_"+id, t, {path:"/jikkyou", expires: 3650});

    var URL="./getRes.cgi";

      // getJSON関数でコメントを取得する。
    $.getJSON( 
            URL,
            {
                "time": _t,
                "id": id,
                "sec": updateSec,
            },
            function(data, status){ //JSON取得時にコールバックされる。

                var len = data.bodies.length; //コメント数
                var updmSec = updateSec * 1000; //ミリ秒にする
                // コメントを1件ずつshowRandom()関数に渡す。
                $.each(data.bodies, function(i, d){
                // 引数:コメント番号、コメントデータ、全体の数、再生unixtime、コメント取得間隔ミリ秒
                    showRandom(i,d, len, _t, updmSec);
                });
            });
}

ここでは、動画開始時刻をunixtimeで保持し、動画再生位置の経過時間(秒)を足し込むことでコメント取得時の時刻パラメータとしています。

コメントはJSONで取得しますが、取得したコメントデータを1件ずつshowRandom()関数に渡すことで、コメントを表示させています。

ちなみにコメントのJSONは以下のようなフォーマットとなります。

リスト3 コメントの例
{
    "bodies":
    [
        [" ふぅー間に合った。行ったかと思ったよ ", "間に合ってよかったね!"],
        [" いわゆる実況向き? "],
        [" キタ━━━━━━(゚∀゚)━━━━━━!!!! "],
        [" キター! "]
    ]
}

コメントの表示について

それではshowRandom()を見てみましょう。

リスト4 showRandom()関数
function showRandom(i, d, len, _t, updmSec)
{
    i++;
    var t = updmSec / len * i;
    var idx = Math.floor(_t) + "_" + i; // コメントにユニークなIDを付与

    var di = $("<div>").attr("id", "comment_"+idx); // コメントのDIV要素を作成

    di.css("position", "absolute");

    // コメントエリアを3x3の9分割し、
    // エリア全体になんとなく散らばるように配置する。CSSで座標を指定する。
    di.css("top", Math.random() * spDisp[ i % 9 ]["topRange"] + spDisp[ i % 9 ]["topOffset"]);
    di.css("left",Math.random() * spDisp[ i % 9 ]["leftRange"] + spDisp[ i % 9 ]["leftOffset"]);
    $("#myBody").append(di); // エリアに要素を配置。

    var dat = d.join("<br>>>"); //配列の場合は引用のため>>を付与して連結する。

    // $(selecter).bt()でBeautyTipsを設定する。
    $("#comment_"+idx).bt( 
        dat.replace(/\n/, "<br>"), // バルーン内に表示させたいHTML。改行を<BR>に。
        {
            // 表示の仕方 500msecでフェードイン
            showTip: function(box){
                $(box).fadeIn(500);
            },
            // 非表示の仕方 500msecでフェードアウト
            hideTip: function(box, callback){
                $(box).animate({opacity: 0}, 500, callback);
            },
            trigger: "none", // noneはbtOn, btOffで外部から制御
            positions: "top",
            padding: 10, //文字の間隔
            width: 200, //全体幅
            spikeLength: 5, //噴出し矢印の長さ
            spikeGirth: 10, //噴出し矢印の幅
            cornerRadius: 10, //角の丸さ
            fill: "rgba(0, 0, 0, 0.5)", //背景の色、透明度
            strokeWidth: 3, //枠線の太さ 
            strokeStyle: "#CC0", //枠線の色
            cssStyles: {color: "#FFF", fontWeight: "bold"}//fontスタイル
        });

        // t秒後にbtOn()を実行する(バルーンを表示する)
        setTimeout(function(){$("#comment_"+idx).btOn()}, t);

             // t+updmSec後にbtOff()を実行(バルーンの非表示)
             // あとで要素を削除するためにdelQue配列に現在時刻とDIVのIDを保存する。
        setTimeout(function(){
            $("#comment_"+idx).btOff();
            delQue.push({"id":"#comment_"+idx, "time": new Date().getTime()});
        }, t + updmSec);
}

最初の方ではコメントのDIV要素を作成し、その表示位置をランダム関数と9分割の区分けに従って、散らばるように設定をしています。

その後、作成したDIV要素にBeauty Tipsの設定を行います。

Beauty Tipsのサンプルを見るとわかると思いますが、ほとんどが何かの要素に付随するイベントによって表示非表示が制御されています。画像の上にポインターが乗ったら説明をバルーン表示する、といった具合です。

しかし、今回の場合は何らかの意味のある要素に対するバルーンでありません。ただバルーンのみを表示非表示させたいということになります。そのような場合には、triggerパラメータに⁠none⁠を渡すことで、ユーザの任意のタイミングで制御することが可能となります(赤字の部分がポイントです⁠⁠。

また、非表示となったDIVは見えないだけでHTMLとしては存在していますので、放っておくとブラウザがどんどん重たくなっていきます。メモリの無駄遣いでもありますので、DIV要素そのものを削除する必要があります。delQue配列にDIVのIDと保存時間を記録しておき、数分後にdelQueを走査し、DIVを削除します。ガベージコレクションのような動きです。

以上が、コメント表示の部分になりますが、jQueryの多彩なプラグインにはいつも驚かされますね。Beauty Tipsのおかげで、半透明なバルーンチップを、フェードインフェードアウトで表示が可能となりました。

こんな風に動きます。

コメント表示機能の実際
コメント表示機能の実際

これは映画アルマゲドンのワンシーン、松田聖子が出てくるシーン付近です(個人的にはどこに出てるのかよくわからなかったけど…⁠⁠。静止画ですみませんが、半透明+フェードインフェードアウトという動きの雰囲気が伝わりますでしょうか。

ちょっと長くなりましたので、グラフ機能については次回にします。

おすすめ記事

記事・ニュース一覧