音楽(MP3)を再生する必要があったので、探していたら「 audio.js」が見つかったのでその使い方のメモ。
以下の「audio.js」のページからダウンロード
http://kolber.github.io/audiojs/
解凍して、「audiojs」フォルダ(audio.min.js, player-graphics.gif audiojs.swf が入っている)を適当なところに配置。
以下のリンクに英語のドキュメントがある
http://kolber.github.io/audiojs/docs/
配置した audio.min.js を読み込む
<script src="../audiojs/audio.min.js"></script>
audio.js を初期化して使用できるようにする。
<script>
audiojs.events.ready(function() {
var as = audiojs.createAll();
});
</script>
プレイヤー(再生バー)を設置したい所(HTML)に audio タグを記述
<audio src="/mp3/juicy.mp3" preload="auto" />
src には再生したい音声ファイルのパスを指定。
preload=”auto” :ページの読み込み時に自動的に音声ファイルも読み込み開始
preload=”none” :再生ボタンを押してから読み込みを開始
基本的にはこれで src に指定した音声ファイルを再生可能。
「audio.min.js」により自動的に CSS(style 要素)が head 要素の先頭に挿入されるので、その後に CSS の値を上書きすると見た目を変更できる。
サンプルの「Customised player」を参考にして変更した例。
<style>
/* プレイヤー(再生バー)の高さ、幅、背景色の指定 */
.audiojs { height: 22px; background: #404040; width: 280px;}
/* 再生・停止ボタンの高さ、幅、パディングの指定 */
.audiojs .play-pause { width: 25px; height: 20px; padding: 0px 8px 0px 0px; }
/* 再生・停止ボタンなどの p 要素 */
.audiojs p { width: 25px; height: 20px; margin: -3px 0px 0px -1px; }
/* 進行状態・ロードの状態を表示する部分 */
.audiojs .scrubber { background: #5a5a5a; width: 150px; height: 10px; margin: 5px; }
/* 進行状態を表示するバーの部分 */
.audiojs .progress { height: 10px; width: 0px; background: #ccc; }
/* ロード状態を表示するバーの部分 */
.audiojs .loaded { height: 10px; background: #000;}
/* 再生時間の部分 */
.audiojs .time { float: left; height: 25px; line-height: 25px; }
.audiojs .error-message { height: 24px;line-height: 24px; }
/* 再生している曲の情報 */
.track-details { clear: both; height: 20px; width: 280px; padding: 1px 6px; background: #eee; color: #222; font-size: 11px; line-height: 20px;}
.track-details:before { content: '♬ Now Playing: '; }
</style>
「audio.min.js」により挿入される HTML 要素の例
<div class="track-details" style="">曲名</div>
<div id="audiojs_wrapper0" class="audiojs " classname="audiojs" style="">
<audio preload="auto" src="xxxx/01.mp3"></audio>
<div class="play-pause">
<p class="play"></p>
<p class="pause"></p>
<p class="loading"></p>
<p class="error"></p>
</div>
<div class="scrubber">
<div class="progress" style="width: 5.4779px;"></div>
<div class="loaded" style="width: 150px;"></div>
</div>
<div class="time">
<em class="played">00:02</em>
/
<strong class="duration">00:58</strong>
</div>
<div class="error-message"></div>
</div>
サンプルの「 Customised playlist player」を参考にプレイリストを作成した例。
概要
・・・省略・・・
<div id="contents">
<h2>CD</h2>
<audio preload="auto"></audio> //プレイヤー(再生バー)
<div class="track-details"></div> //曲名を表示
・・・省略・・・
<div class="cd">
<ol>
<li><a href="#" data-src="01.mp3">Song 1</a></li>
<li><a href="#" data-src="02.mp3">Song 2</a></li>
<li><a href="#" data-src="03.mp3">Song 3</a></li>
......
<li class="last"><a href="#" data-src="03.mp8">Song 8</a></li>
</ol>
</div><!-- end of .cd -->
<div class="cd">
<ol>
<li><a href="#" data-src="a.mp3">Song a</a></li>
<li><a href="#" data-src="b.mp3">Song b</a></li>
<li><a href="#" data-src="c.mp3">Song c</a></li>
......
<li class="last"><a href="#" data-src="h.mp8">Song h</a></li>
</ol>
</div><!-- end of .cd -->
・・・省略・・・
</div><!--end of #contents-->
・・・省略・・・
jQuery
jQuery(function($){
var clicked; //クリックされた li 要素を格納する変数
var a = audiojs.createAll({
//曲が終了した時の処理
trackEnded: function() {
//クリックして再生した曲の li 要素のクラスが「last」の場合、終了して非表示に
if($('ol li.playing', clicked.closest('div.cd')).hasClass('last')){
$('div.audiojs, div.track-details').fadeOut('slow');
$('ol li.playing').removeClass('playing');
return;
}
//次の曲を設定
var next = $('ol li.playing', clicked.closest('div.cd')).next();
if (!next.length) next = $('ol li', clicked.closest('div.cd')).first();
next.addClass('playing').siblings().removeClass('playing');
//曲名を「div.track-details」に表示
$('div.track-details').html(next.closest('li').text());
//プレイヤー(再生バー)をリストの後に追加(appendTo)して表示
$('div.audiojs, div.track-details').appendTo(next.closest('div')).fadeIn('slow');
//プレイヤーをリストの直後に入れる場合はinsertAfterで
//$('div.audiojs, div.track-details').insertAfter(next.closest('div').find('ol')).fadeIn('slow');
//曲を再生
audio.load($('a', next).attr('data-src'));
audio.play();
}
});
// 最初の曲をロード
var audio = a[0];
first = $('ol a').attr('data-src');
$('ol li').first().addClass('playing');
audio.load(first);
// プレイヤー(再生バー)と曲の情報は最初は非表示に
$('div.audiojs, div.track-details').css('display', 'none');
//クリックされた曲をロードして再生
$('ol li').click(function(e) {
clicked = $(this);
e.preventDefault();
$('div.track-details').html($(this).closest('li').text()).appendTo($(this).closest('div')).fadeIn('slow');
$('div.audiojs, div.track-details').appendTo($(this).closest('div')).fadeIn('slow');
//プレイヤーをリストの直後に入れる場合
//$('div.audiojs, div.track-details').insertAfter(next.closest('div').find('ol')).fadeIn('slow');
$(this).addClass('playing').siblings().removeClass('playing');
audio.load($('a', this).attr('data-src'));
audio.play();
});
});
モダンブラウザでは上記で問題なく再生されるが、IE7、IE8 ではプレイヤー(再生バー)は表示されるが、音楽が再生されない。コンソールを確認すると、以下の様なエラーが表示されていた。
SCRIPT16389: 名前が不明です。
xxxxx.html, 行 49 文字5
SCRIPT16389: 未定義のエラーです。
xxxxx.html, 行 49 文字5
「行 49 文字5」を見ても原因はまったくわからない。切り分けてみたところ、「div.audiojs」を「appendTo」する処理があるとこのエラーが出ることがわかったが、原因は不明。
$('div.audiojs').appendTo($(this).closest('div')); //これがエラーの原因?
追加情報
2013年12月15日
エミュレータでは、なんとかなったかのように見えたが、実機で IE8 で試してみると、表示がくずれてしまい、またそもそもエラーで作動しなかったので諦めて、代わりに「jPlayer (2.5.0)」を使うことにしました。
関連ページ:「jPlayer (2.5.0) を使ってみる」
したがって以下の部分は、参考にしないでください(自分用のメモとして残しておきます)。
また、解決策は見つからなかったので、最後の手段としてブラウザ判定して、IE7、IE8 ではそれぞれのリストの下にプレイヤーを表示するのはあきらめて常にページの固定した場所に表示するようにした。
以下は現時点での例。
jQuery(function($){
var _ua = (function(){ //ブラウザ判定
return {
ltIE6:typeof window.addEventListener == "undefined" && typeof document.documentElement.style.maxHeight == "undefined",
ltIE7:typeof window.addEventListener == "undefined" && typeof document.querySelectorAll == "undefined",
ltIE8:typeof window.addEventListener == "undefined" && typeof document.getElementsByClassName == "undefined"
}
})();
if(!_ua.ltIE8){ //モダンブラウザ
var clicked;
var a = audiojs.createAll({
trackEnded: function() {
if($('ol li.playing', clicked.closest('div.cd')).hasClass('last')){
$('div.audiojs, div.track-details').fadeOut('slow');
$('ol li.playing').removeClass('playing');
return;
}
var next = $('ol li.playing', clicked.closest('div.cd')).next();
if (!next.length) next = $('ol li', clicked.closest('div.cd')).first();
next.addClass('playing').siblings().removeClass('playing');
$('div.track-details').html(next.closest('li').text());
$('div.audiojs, div.track-details').appendTo(next.closest('div')).fadeIn('slow');
audio.load($('a', next).attr('data-src'));
audio.play();
}
});
// Load in the first track
var audio = a[0];
first = $('ol a').attr('data-src');
$('ol li').first().addClass('playing');
audio.load(first);
$('div.audiojs, div.track-details').css('display', 'none');
// Load in a track on click
$('ol li').click(function(e) {
clicked = $(this);
e.preventDefault();
$('div.track-details').html($(this).closest('li').text()).appendTo($(this).closest('div')).fadeIn('slow');
$('div.audiojs, div.track-details').appendTo($(this).closest('div')).fadeIn('slow');
$(this).addClass('playing').siblings().removeClass('playing');
audio.load($('a', this).attr('data-src'));
audio.play();
});
}else{
//IE7、IE8
var clicked;
var a = audiojs.createAll({
trackEnded: function() {
if($('ol li.playing', clicked.closest('div.cd')).hasClass('last')){
$('ol li.playing').removeClass('playing');
return;
}
var next = $('ol li.playing', clicked.closest('div.cd')).next();
if (!next.length) next = $('ol li', clicked.closest('div.cd')).first();
next.addClass('playing').siblings().removeClass('playing');
$('div.track-details').html(next.closest('li').text());
audio.load($('a', next).attr('data-src'));
audio.play();
}
});
// Load in the first track
var audio = a[0];
first = $('ol a').attr('data-src');
$('ol li').first().addClass('playing');
$('div.track-details').html($('ol li').first().text());
audio.load(first);
// Load in a track on click
$('ol li').click(function(e) {
clicked = $(this);
e.preventDefault();
$('div.track-details').html($(this).closest('li').text());
$(this).addClass('playing').siblings().removeClass('playing');
audio.load($('a', this).attr('data-src'));
audio.play();
});
}
});
IE7、IE8 用の記述はサンプルの「 Customised playlist player」とほぼ同じ内容。
ブラウザの判別のコードは「JavaScript ユーザエージェント条件分岐便利スニペット(W3G)」を参考にさせていただきました。
以下は上記を変更(改良)した例:
jQuery(function($){
var _ua = (function(){ //ブラウザ判定
return {
ltIE6:typeof window.addEventListener == "undefined" && typeof document.documentElement.style.maxHeight == "undefined",
ltIE7:typeof window.addEventListener == "undefined" && typeof document.querySelectorAll == "undefined",
ltIE8:typeof window.addEventListener == "undefined" && typeof document.getElementsByClassName == "undefined"
}
})();
//閉じるボタンをクリックした際の処理
$(document).on('click', '.close_audio', function() {
audio.pause();
$('div.audiojs, div.track-details').fadeOut('slow');
});
if(!_ua.ltIE8){
var clicked;
var a = audiojs.createAll({
trackEnded: function() {
if($('ol li.playing', clicked.closest('div.cd')).hasClass('last')){
$('div.audiojs, div.track-details').fadeOut('slow');
$('ol li.playing').removeClass('playing');
return;
}
var next = $('ol li.playing', clicked.closest('div.cd')).next();
if (!next.length) next = $('ol li', clicked.closest('div.cd')).first();
next.addClass('playing').siblings().removeClass('playing');
//閉じるボタンを追加
$('div.track-details').html(next.closest('li').text() + '<p class="close_audio"><span class="glyphicon glyphicon-remove-circle"></span> close </p>');
//track-details と audiojs を一定の順序で表示
$('div.track-details').insertAfter($(this).closest('div').find('ol'));
$('div.audiojs').insertAfter($(this).closest('div').find('ol'));
$('div.audiojs, div.track-details').fadeIn('slow');
audio.load($('a', next).attr('data-src'));
audio.play();
}
});
// Load in the first track
var audio = a[0];
first = $('ol a').attr('data-src');
$('ol li').first().addClass('playing');
audio.load(first);
$('div.audiojs, div.track-details').css('display', 'none');
// Load in a track on click
$('ol li').click(function(e) {
$('div.audiojs, div.track-details').css('display', 'none');
clicked = $(this);
e.preventDefault();
//閉じるボタンを追加
$('div.track-details').html($(this).closest('li').text() + '<p class="close_audio"><span class="glyphicon glyphicon-remove-circle"></span> close </p>').appendTo($(this).closest('div'));
//track-details と audiojs を一定の順序で表示
$('div.track-details').insertAfter($(this).closest('div').find('ol'));
$('div.audiojs').insertAfter($(this).closest('div').find('ol'));
$('div.audiojs, div.track-details').fadeIn('slow');
$(this).addClass('playing').siblings().removeClass('playing');
//どの位置でもプレーヤーが見えるように必要であればスクロールして表示
if($('div.audiojs:first').offset().top > ($(window).scrollTop() + $(window).height())) {
var window_bottom_y = $(window).scrollTop() + $(window).height();
var audiojs_offset_y = $('div.audiojs:first').offset().top - window_bottom_y;
var window_top = $(window).scrollTop() + audiojs_offset_y + 80;
$('body,html').animate({
scrollTop: (window_top)
}, 500);
}
audio.load($('a', this).attr('data-src'));
audio.play();
});
}else{
//IE7、IE8
var clicked;
var a = audiojs.createAll({
trackEnded: function() {
if($('ol li.playing', clicked.closest('div.cd')).hasClass('last')){
$('ol li.playing').removeClass('playing');
return;
}
var next = $('ol li.playing', clicked.closest('div.cd')).next();
if (!next.length) next = $('ol li', clicked.closest('div.cd')).first();
next.addClass('playing').siblings().removeClass('playing');
//閉じるボタンを追加
$('div.track-details').html(next.closest('li').text() + '<p class="close_audio"><span class="glyphicon glyphicon-remove-circle"></span> close </p>').appendTo($(this).closest('div'));
audio.load($('a', next).attr('data-src'));
audio.play();
}
});
// Load in the first track
var audio = a[0];
first = $('ol a').attr('data-src');
$('ol li').first().addClass('playing');
$('div.track-details').html($('ol li').first().text());
audio.load(first);
// Load in a track on click
$('ol li').click(function(e) {
clicked = $(this);
e.preventDefault();
//閉じるボタンを追加
$('div.track-details').html($(this).closest('li').text() + '<p class="close_audio"><span class="glyphicon glyphicon-remove-circle"></span> close </p>').appendTo($(this).closest('div'));
$(this).addClass('playing').siblings().removeClass('playing');
audio.load($('a', this).attr('data-src'));
audio.play();
});
}
});
CSSに以下を記述
.close_audio {
cursor: pointer;
}