http { sendfile on; include /etc/nginx/mime.types; default_type audio/flac; server { listen *:80; server_name as.iostd.ru; root /var/mcs/storage; location / { rewrite "^\/(([a-z0-9]{2})([a-z0-9]{2})([a-z0-9]{2})([a-z0-9]{2})[a-z0-9]{56}).flac$" /$2/$3/$4/$5/$1.flac last; if ($http_origin ~* (https?://([^/]*\.)?.?iostd\.ru(:[0-9]+)?)) { set $cors "true"; } if ($request_method = 'OPTIONS') { set $cors "${cors}options"; } if ($request_method = 'GET') { set $cors "${cors}get"; } if ($request_method = 'POST') { set $cors "${cors}post"; } if ($request_method = 'HEAD') { set $cors "${cors}head"; } if ($cors = "trueget") { add_header 'Access-Control-Allow-Origin' "$http_origin"; add_header 'Access-Control-Allow-Credentials' 'true'; } if ($cors = "truepost") { add_header 'Access-Control-Allow-Origin' "$http_origin"; add_header 'Access-Control-Allow-Credentials' 'true'; } if ($cors = "truehead") { add_header 'Access-Control-Allow-Origin' "$http_origin"; add_header 'Access-Control-Allow-Credentials' 'true'; add_header 'Access-Control-Max-Age' 1728000; add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS'; add_header 'Access-Control-Allow-Headers' 'Authorization,Content-Type,Accept,Origin,User-Agent,DNT,Cache-Control,Range,X-Mx-ReqToken,Keep-Alive,X-Requested-With,If-Modified-Since'; add_header 'Access-Control-Expose-Headers' 'Accept-Ranges,Content-Encoding,Content-Length,Content-Range'; } if ($cors = "trueoptions") { add_header 'Access-Control-Allow-Origin' "$http_origin"; add_header 'Access-Control-Allow-Credentials' 'true'; add_header 'Access-Control-Max-Age' 1728000; add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS'; add_header 'Access-Control-Allow-Headers' 'Authorization,Content-Type,Accept,Origin,User-Agent,DNT,Cache-Control,Range,X-Mx-ReqToken,Keep-Alive,X-Requested-With,If-Modified-Since'; add_header 'Access-Control-Expose-Headers' 'Accept-Ranges,Content-Encoding,Content-Length,Content-Range'; add_header 'Content-Length' 0; add_header 'Content-Type' 'text/plain charset=UTF-8'; return 204; } try_files $uri $uri/; } } }
<?php error_reporting(E_ALL); ini_set('display_errors', '1'); require_once('MysqliDb.php'); // https://github.com/joshcam/PHP-MySQLi-Database-Class function cors() { if (isset($_SERVER['HTTP_ORIGIN'])) { header("Access-Control-Allow-Origin: {$_SERVER['HTTP_ORIGIN']}"); header('Access-Control-Allow-Credentials: true'); header('Access-Control-Max-Age: 86400'); } if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') { if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_METHOD'])) header("Access-Control-Allow-Methods: GET, POST, OPTIONS"); if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS'])) header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}"); exit(0); } } function answer($data = array(), $status = "OK", $message = "") { if(!is_array($data)) return; $rcode = array(); $rcode["status"] = $status; if($status == "ERROR" && $message != "" ) $rcode["message"] = $message; header('Content-Type: application/json'); echo json_encode(array_merge($rcode, array("result" => $data))); exit(); } function error($message) { answer(array(), "ERROR", $message); } cors(); $db = new MysqliDb ('localhost', 'root', 'hackme', 'audio'); // https://github.com/joshcam/PHP-MySQLi-Database-Class if(!isset($_REQUEST["c"])) error("Bad request"); if($_REQUEST["c"] == "tracks") { $tracks = $db->rawQuery('SELECT title, a.artist, audio FROM tracks INNER JOIN artists a ON (tracks.artistid = a.id) LIMIT 20'); answer($tracks); } error("Bad request");
<div class="player"> <div class="info"> <div class="tackinfo"><span id="artist"></span> - <span id="title"></span></div> <div class="timer"><span id="time">00:00</span></div> </div> <div class="seekbar" id="seek"> <div class="wrap"> <div id="buffer"></div> <div id="progress"></div> </div> </div> <div class="controls"> <div class="playback"> <div id="play" class="fa fa-play"></div> <div class="fb"> <div id="backward" class="fa fa-backward"></div> <div id="forward" class="fa fa-forward"></div> </div> </div> <div class="volumebar" id="volume"> <div class="wrap"> <div id="volumevalue"></div> </div> </div> </div> </div>
.player { border: 1px solid #D0D0D0; background-color: #F0F0F0; height: 67px; border-radius: 2px; padding: 5px;} .player .tackinfo { float: left; margin-left: 0px; } .player .tackinfo #artist { color: #0474C0; font-weight: bold; } .player .tackinfo #title { color: #787878; } .player .timer { float: right; cursor: pointer; } .player .seekbar { clear: both; cursor: pointer; padding: 5px 0;} .player .seekbar .wrap { background-color: #D0D0D0; overflow:hidden; height:5px; border-radius: 2px;} .player #buffer, .player #progress { height:100%; width:0%; } .player #buffer { background-color:#909090; } .player #progress { background-color: #0474C0; margin-top:-5px; } .controls .playback { float: left; } .controls .playback .fb { float: left; } .playback #play, .playback #backward, .playback #forward { color: #0474C0; cursor: pointer; border-radius: 2px; text-align: center; vertical-align: middle; float:left; margin-right: 2px;} .playback #play:hover, .playback #backward:hover, .playback #forward:hover { background-color: #D8D8D8; } .playback #play { font-size: 24px; height: 32px; width: 32px; line-height: 32px;} .playback #backward { font-size: 16px; height: 32px; width: 32px; line-height: 32px;} .playback #forward { font-size: 16px; height: 32px; width: 32px; line-height: 32px;} .volumebar { float: right; cursor: pointer; padding: 15px 0; width:80px;} .volumebar .wrap { background-color:#D8D8D8; overflow:hidden; height:5px; border-radius: 2px; } .volumebar #volumevalue { height:100%; width:0%; background-color: #0474C0; }
Playlist = function() { this.list = []; this.current = 0; this.repeatmode = 0; };
Playlist.prototype.add = function(track) { this.list.push(track); };
Playlist.prototype.getCurrent = function() { return this.list[this.current]; };
Playlist.prototype.next = function() { if(this.repeatmode == 2) { return this.current; } if(this.current >= this.list.length - 1) { if(this.repeatmode == 0) { return -1; } else if(this.repeatmode == 1) { return (this.current = 0); } } return ++this.current; }; Playlist.prototype.prev = function() { if(this.current == 0) return this.current; return --this.current; };
Playlist.prototype.shuffle = function(){ for(var j, x, i = this.list.length; i; j = Math.floor(Math.random() * i), x = this.list[--i], this.list[i] = this.list[j], this.list[j] = x); };
Musica = function(params) { this.ui = { artist: params.artist, title: params.title, seekbar: params.seekbar, bufferbar: params.bufferbar, progressbar: params.progressbar, timer: params.timer, playbtn: params.playbtn, backwardbtn: params.backwardbtn, forwardbtn: params.forwardbtn, volumebar: params.volumebar, volume: params.volume }; this.pstate = 0; this.seekstate = 0; this.timetype = 0; this.aurora; this.volume = 100; this.playlist = new Playlist(); this.ui.timer.click((function (_this) { return function(e) { _this.timetype = _this.timetype == 0 ? 1 : 0; _this.setTimer(_this.aurora.currentTime); }; })(this)); this.ui.playbtn.click((function (_this) { return function(e) { if(_this.pstate == 0) _this.play(); else _this.pause(); }; })(this)); this.ui.backwardbtn.click((function (_this) { return function(e) { _this.prev(); }; })(this)); this.ui.forwardbtn.click((function (_this) { return function(e) { _this.next(); }; })(this)); };
Musica.prototype.open = function() { if(this.aurora) this.aurora.stop(); this.aurora = AV.Player.fromURL('http://as.iostd.ru/' + this.playlist.getCurrent().audio + '.flac'); this.aurora.volume = this.volume; this.ui.volume.css('width', ((this.volume * 100 ) / this.ui.volumebar.width())+'%'); this.pstate = 0; this.ui.playbtn.removeClass("fa-play fa-pause").addClass("fa-play"); this.ui.artist.html(this.playlist.getCurrent().artist); this.ui.title.html(this.playlist.getCurrent().title); this.ui.bufferbar.css('width', '0%'); this.ui.progressbar.css('width', '0%'); this.aurora.on('buffer', (function (_this) { return function(percent) { _this.ui.bufferbar.css('width', percent+'%'); }; })(this)); this.aurora.on('progress', (function (_this) { return function(time) { if(_this.seekstate == 0) _this.ui.progressbar.css('width', ((time * 100 ) / _this.aurora.duration)+'%'); _this._setTimer(time); }; })(this)); this.aurora.on('end', (function (_this) { return function() { _this.next(); }; })(this)); this.aurora.preload(); };
this.ui.seekbar.off(); this.ui.seekbar.mousedown((function (_this) { return function(e) { var offsetx = e.offsetX; var origin = $(this); _this.seekstate = 1; _this.ui.progressbar.css('width', ((offsetx * 100 ) / $(this).width())+'%'); $(document).mousemove(function(e) { offsetx = e.pageX - origin.offset().left; offsetx = offsetx < 0 ? 0 : (offsetx > origin.width() ? origin.width() : offsetx); _this.ui.progressbar.css('width', ((offsetx * 100 ) / origin.width())+'%'); }); $(document).mouseup(function(e) { $(document).off("mousemove"); $(document).off("mouseup"); _this.aurora.seek(Math.floor((offsetx * _this.aurora.duration) / origin.width())); _this.seekstate = 0; }); }; })(this));
this.ui.volumebar.off(); this.ui.volumebar.mousedown((function (_this) { return function(e) { var offsetx = e.offsetX; var origin = $(this); _this.ui.volume.css('width', ((offsetx * 100 ) / origin.width())+'%'); _this.volume = Math.floor((offsetx * 100) / origin.width()); _this.aurora.volume = _this.volume; $(document).mousemove(function(e) { offsetx = e.pageX - origin.offset().left; offsetx = offsetx < 0 ? 0 : (offsetx > origin.width() ? origin.width() : offsetx); _this.ui.volume.css('width', ((offsetx * 100 ) / origin.width())+'%'); _this.volume = Math.floor((offsetx * 100) / origin.width()); _this.aurora.volume = _this.volume }); $(document).mouseup(function(e) { $(document).off("mousemove"); $(document).off("mouseup"); _this.volume = Math.floor((offsetx * 100) / origin.width()); _this.aurora.volume = _this.volume; }); }; })(this));
Musica.prototype.play = function() { this.aurora.play(); this.pstate = 1; this.ui.playbtn.removeClass("fa-play fa-pause").addClass("fa-pause"); }; Musica.prototype.pause = function() { this.aurora.pause(); this.pstate = 0; this.ui.playbtn.removeClass("fa-play fa-pause").addClass("fa-play"); }; Musica.prototype.next = function() { if(this.playlist.next() !== -1) { var pss = this.pstate; this.pause(); this.open(); if(pss == 1) { this.play(); } } }; Musica.prototype.prev = function() { if(this.playlist.prev() !== -1) { var pss = this.pstate; this.pause(); this.open(); if(pss == 1) { this.play(); } } };
$(function() { var params = { artist: $('#artist'), title: $('#title'), seekbar: $('#seek'), bufferbar: $("#buffer"), progressbar: $("#progress"), timer: $("#time"), playbtn: $("#play"), backwardbtn: $("#backward"), forwardbtn: $("#forward"), volumebar: $("#volume"), volume: $("#volumevalue") }; var mplayer = new Musica(params); $.get( "http://iostd.ru/audioapi.php?c=tracks", function( data ) { for (var i = 0; i < data.result.length; i++) { mplayer.playlist.add(data.result[i]); } mplayer.open(); mplayer.play(); }); });
Source: https://habr.com/ru/post/235741/
All Articles