srs.player.js 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382
  1. /**
  2. * the SrsPlayer object.
  3. * @param container the html container id.
  4. * @param width a float value specifies the width of player.
  5. * @param height a float value specifies the height of player.
  6. * @param private_object [optional] an object that used as private object,
  7. * for example, the logic chat object which owner this player.
  8. * Usage:
  9. <script type="text/javascript" src="js/swfobject.js"></script>
  10. <script type="text/javascript" src="js/srs.player.js"></script>
  11. <div id="player"></div>
  12. var p = new SrsPlayer("player", 640, 480);
  13. p.set_srs_player_url("srs_player.swf?v=1.0.0");
  14. p.on_player_ready = function() {
  15. p.set_bt(0.8);
  16. p.set_mbt(1.2);
  17. p.play("rtmp://ossrs.net/live/livestream");
  18. };
  19. p.on_player_metadata = function(metadata) {
  20. console.log(metadata);
  21. console.log(p.dump_log());
  22. };
  23. p.start();
  24. */
  25. function SrsPlayer(container, width, height, private_object) {
  26. if (!SrsPlayer.__id) {
  27. SrsPlayer.__id = 100;
  28. }
  29. if (!SrsPlayer.__players) {
  30. SrsPlayer.__players = [];
  31. }
  32. SrsPlayer.__players.push(this);
  33. this.private_object = private_object;
  34. this.container = container;
  35. this.width = width;
  36. this.height = height;
  37. this.id = SrsPlayer.__id++;
  38. this.stream_url = null;
  39. this.buffer_time = 0.3; // default to 0.3
  40. this.max_buffer_time = this.buffer_time * 3; // default to 3 x bufferTime.
  41. this.volume = 1.0; // default to 100%
  42. this.callbackObj = null;
  43. this.srs_player_url = "srs_player/release/srs_player.swf?_version="+srs_get_version_code();
  44. // callback set the following values.
  45. this.meatadata = {}; // for on_player_metadata
  46. this.time = 0; // current stream time.
  47. this.buffer_length = 0; // current stream buffer length.
  48. this.kbps = 0; // current stream bitrate(video+audio) in kbps.
  49. this.fps = 0; // current stream video fps.
  50. this.rtime = 0; // flash relative time in ms.
  51. this.__fluency = {
  52. total_empty_count: 0,
  53. total_empty_time: 0,
  54. current_empty_time: 0
  55. };
  56. this.__fluency.on_stream_empty = function(time) {
  57. this.total_empty_count++;
  58. this.current_empty_time = time;
  59. };
  60. this.__fluency.on_stream_full = function(time) {
  61. if (this.current_empty_time > 0) {
  62. this.total_empty_time += time - this.current_empty_time;
  63. this.current_empty_time = 0;
  64. }
  65. };
  66. this.__fluency.calc = function(time) {
  67. var den = this.total_empty_count * 4 + this.total_empty_time * 2 + time;
  68. if (den > 0) {
  69. return time * 100 / den;
  70. }
  71. return 0;
  72. };
  73. }
  74. /**
  75. * user can set some callback, then start the player.
  76. * @param url the default url.
  77. * callbacks:
  78. * on_player_ready():int, when srs player ready, user can play().
  79. * on_player_metadata(metadata:Object):int, when srs player get metadata.
  80. * methods:
  81. * set_bt(t:Number):void, set the buffer time in seconds.
  82. * set_mbt(t:Number):void, set the max buffer time in seconds.
  83. * dump_log():String, get all logs of player.
  84. */
  85. SrsPlayer.prototype.start = function(url) {
  86. if (url) {
  87. this.stream_url = url;
  88. }
  89. // embed the flash.
  90. var flashvars = {};
  91. flashvars.id = this.id;
  92. flashvars.on_player_ready = "__srs_on_player_ready";
  93. flashvars.on_player_metadata = "__srs_on_player_metadata";
  94. flashvars.on_player_timer = "__srs_on_player_timer";
  95. flashvars.on_player_empty = "__srs_on_player_empty";
  96. flashvars.on_player_full = "__srs_on_player_full";
  97. flashvars.on_player_status = "__srs_on_player_status";
  98. var params = {};
  99. params.wmode = "opaque";
  100. params.allowFullScreen = "true";
  101. params.allowScriptAccess = "always";
  102. var attributes = {};
  103. var self = this;
  104. swfobject.embedSWF(
  105. this.srs_player_url,
  106. this.container,
  107. this.width, this.height,
  108. "11.1.0", "js/AdobeFlashPlayerInstall.swf",
  109. flashvars, params, attributes,
  110. function(callbackObj){
  111. self.callbackObj = callbackObj;
  112. if (!callbackObj.success) {
  113. console.error('Initialize player failed:'); console.error(callbackObj);
  114. }
  115. }
  116. );
  117. return this;
  118. }
  119. /**
  120. * play the stream.
  121. * @param stream_url the url of stream, rtmp or http.
  122. * @param volume the volume, 0 is mute, 1 is 100%, 2 is 200%.
  123. */
  124. SrsPlayer.prototype.play = function(url, volume) {
  125. this.stop();
  126. SrsPlayer.__players.push(this);
  127. if (url) {
  128. this.stream_url = url;
  129. }
  130. // volume maybe 0, so never use if(volume) to check its value.
  131. if (volume != null && volume != undefined) {
  132. this.volume = volume;
  133. }
  134. this.callbackObj.ref.__play(this.stream_url, this.width, this.height, this.buffer_time, this.max_buffer_time, this.volume);
  135. }
  136. /**
  137. * stop play stream.
  138. */
  139. SrsPlayer.prototype.stop = function() {
  140. this.callbackObj.ref.__stop();
  141. }
  142. /**
  143. * pause the play.
  144. */
  145. SrsPlayer.prototype.pause = function() {
  146. this.callbackObj.ref.__pause();
  147. }
  148. /**
  149. * resume the play.
  150. */
  151. SrsPlayer.prototype.resume = function() {
  152. this.callbackObj.ref.__resume();
  153. }
  154. /**
  155. * get the stream fluency, where 100 is 100%.
  156. */
  157. SrsPlayer.prototype.fluency = function() {
  158. return this.__fluency.calc(this.rtime);
  159. }
  160. /**
  161. * get the stream empty count.
  162. */
  163. SrsPlayer.prototype.empty_count = function() {
  164. return this.__fluency.total_empty_count;
  165. }
  166. /**
  167. * get all log data.
  168. */
  169. SrsPlayer.prototype.dump_log = function() {
  170. return this.callbackObj.ref.__dump_log();
  171. }
  172. /**
  173. * to set the DAR, for example, DAR=16:9 where num=16,den=9.
  174. * @param num, for example, 16.
  175. * use metadata width if 0.
  176. * use user specified width if -1.
  177. * @param den, for example, 9.
  178. * use metadata height if 0.
  179. * use user specified height if -1.
  180. */
  181. SrsPlayer.prototype.set_dar = function(num, den) {
  182. this.callbackObj.ref.__set_dar(num, den);
  183. }
  184. /**
  185. * set the fullscreen size data.
  186. * @refer the refer fullscreen mode. it can be:
  187. * video: use video orignal size.
  188. * screen: use screen size to rescale video.
  189. * @param percent, the rescale percent, where
  190. * 100 means 100%.
  191. */
  192. SrsPlayer.prototype.set_fs = function(refer, percent) {
  193. this.callbackObj.ref.__set_fs(refer, percent);
  194. }
  195. /**
  196. * set the stream buffer time in seconds.
  197. * @buffer_time the buffer time in seconds.
  198. */
  199. SrsPlayer.prototype.set_bt = function(buffer_time) {
  200. if (this.buffer_time == buffer_time) {
  201. return;
  202. }
  203. this.buffer_time = buffer_time;
  204. this.callbackObj.ref.__set_bt(buffer_time);
  205. // reset the max buffer time to 3 x buffer_time.
  206. this.set_mbt(buffer_time * 3);
  207. }
  208. /**
  209. * set the stream max buffer time in seconds.
  210. * @param max_buffer_time the max buffer time in seconds.
  211. * @remark this is the key feature for realtime communication by flash.
  212. */
  213. SrsPlayer.prototype.set_mbt = function(max_buffer_time) {
  214. // we must atleast set the max buffer time to 0.6s.
  215. max_buffer_time = Math.max(0.6, max_buffer_time);
  216. // max buffer time always greater than buffer time.
  217. max_buffer_time = Math.max(this.buffer_time, max_buffer_time);
  218. if (parseInt(this.max_buffer_time * 10) == parseInt(max_buffer_time * 10)) {
  219. return;
  220. }
  221. this.max_buffer_time = max_buffer_time;
  222. this.callbackObj.ref.__set_mbt(max_buffer_time);
  223. }
  224. /**
  225. * set the srs_player.swf url
  226. * @param url, srs_player.swf's url.
  227. * @param params, object.
  228. */
  229. SrsPlayer.prototype.set_srs_player_url = function(url, params) {
  230. var query_array = [],
  231. query_string = "",
  232. p;
  233. params = params || {};
  234. params._version = srs_get_version_code();
  235. for (p in params) {
  236. if (params.hasOwnProperty(p)) {
  237. query_array.push(p + "=" + encodeURIComponent(params[p]));
  238. }
  239. }
  240. query_string = query_array.join("&");
  241. this.srs_player_url = url + "?" + query_string;
  242. }
  243. /**
  244. * the callback when player is ready.
  245. */
  246. SrsPlayer.prototype.on_player_ready = function() {
  247. }
  248. /**
  249. * the callback when player got metadata.
  250. * @param metadata the metadata which player got.
  251. */
  252. SrsPlayer.prototype.on_player_metadata = function(metadata) {
  253. // ignore.
  254. }
  255. /**
  256. * the callback when player timer event.
  257. * @param time current stream time.
  258. * @param buffer_length current buffer length.
  259. * @param kbps current video plus audio bitrate in kbps.
  260. * @param fps current video fps.
  261. * @param rtime current relative time by flash.util.getTimer().
  262. */
  263. SrsPlayer.prototype.on_player_timer = function(time, buffer_length, kbps, fps, rtime) {
  264. // ignore.
  265. }
  266. /**
  267. * the callback when player got NetStream.Buffer.Empty
  268. * @param time current relative time by flash.util.getTimer().
  269. */
  270. SrsPlayer.prototype.on_player_empty = function(time) {
  271. // ignore.
  272. }
  273. /**
  274. * the callback when player got NetStream.Buffer.Full
  275. * @param time current relative time by flash.util.getTimer().
  276. */
  277. SrsPlayer.prototype.on_player_full = function(time) {
  278. // ignore.
  279. }
  280. /**
  281. * the callback when player status change.
  282. * @param code the status code, "init", "connected", "play", "closed", "rejected", "failed".
  283. * init => connected/rejected/failed
  284. * connected => play/rejected => closed
  285. * @param desc the description for the status.
  286. */
  287. SrsPlayer.prototype.on_player_status = function(code, desc) {
  288. // ignore.
  289. }
  290. /**
  291. * helpers.
  292. */
  293. function __srs_find_player(id) {
  294. for (var i = 0; i < SrsPlayer.__players.length; i++) {
  295. var player = SrsPlayer.__players[i];
  296. if (player.id != id) {
  297. continue;
  298. }
  299. return player;
  300. }
  301. throw new Error("player not found. id=" + id);
  302. }
  303. function __srs_on_player_ready(id) {
  304. var player = __srs_find_player(id);
  305. player.on_player_ready();
  306. }
  307. function __srs_on_player_metadata(id, metadata) {
  308. var player = __srs_find_player(id);
  309. // user may override the on_player_metadata,
  310. // so set the data before invoke it.
  311. player.metadata = metadata;
  312. player.on_player_metadata(metadata);
  313. }
  314. function __srs_on_player_timer(id, time, buffer_length, kbps, fps, rtime) {
  315. var player = __srs_find_player(id);
  316. buffer_length = Math.max(0, buffer_length);
  317. buffer_length = Math.min(player.buffer_time, buffer_length);
  318. time = Math.max(0, time);
  319. // user may override the on_player_timer,
  320. // so set the data before invoke it.
  321. player.time = time;
  322. player.buffer_length = buffer_length;
  323. player.kbps = kbps;
  324. player.fps = fps;
  325. player.rtime = rtime;
  326. player.on_player_timer(time, buffer_length, kbps, fps, rtime);
  327. }
  328. function __srs_on_player_empty(id, time) {
  329. var player = __srs_find_player(id);
  330. player.__fluency.on_stream_empty(time);
  331. player.on_player_empty(time);
  332. }
  333. function __srs_on_player_full(id, time) {
  334. var player = __srs_find_player(id);
  335. player.__fluency.on_stream_full(time);
  336. player.on_player_full(time);
  337. }
  338. function __srs_on_player_status(id, code, desc) {
  339. var player = __srs_find_player(id);
  340. player.on_player_status(code, desc);
  341. if (code != "closed") {
  342. return;
  343. }
  344. for (var i = 0; i < SrsPlayer.__players.length; i++) {
  345. var player = SrsPlayer.__players[i];
  346. if (player.id != this.id) {
  347. continue;
  348. }
  349. SrsPlayer.__players.splice(i, 1);
  350. break;
  351. }
  352. }