source: trunk/fl5/src/com/longtailvideo/jwplayer/media/VideoMediaProvider.as @ 658

Revision 658, 6.5 KB checked in by zach, 4 years ago (diff)

Fixing VideoMediaProvider time bug

Line 
1package com.longtailvideo.jwplayer.media {
2        import com.longtailvideo.jwplayer.events.MediaEvent;
3        import com.longtailvideo.jwplayer.model.PlayerConfig;
4        import com.longtailvideo.jwplayer.model.PlaylistItem;
5        import com.longtailvideo.jwplayer.player.PlayerState;
6        import com.longtailvideo.jwplayer.utils.Logger;
7        import com.longtailvideo.jwplayer.utils.NetClient;
8        import com.longtailvideo.jwplayer.utils.Strings;
9       
10        import flash.events.*;
11        import flash.media.*;
12        import flash.net.*;
13        import flash.utils.*;
14
15
16        /**
17         * Wrapper for playback of progressively downloaded _video.
18         **/
19        public class VideoMediaProvider extends MediaProvider {
20                /** Video object to be instantiated. **/
21                protected var _video:Video;
22                /** NetConnection object for setup of the video _stream. **/
23                protected var _connection:NetConnection;
24                /** NetStream instance that handles the stream IO. **/
25                protected var _stream:NetStream;
26                /** Sound control object. **/
27                protected var _transformer:SoundTransform;
28                /** ID for the position interval. **/
29                protected var _positionInterval:Number;
30                /** Load offset for bandwidth checking. **/
31                protected var _loadTimer:Number;
32                /** Whether the buffer has filled **/
33                private var _bufferFull:Boolean;
34
35
36                /** Constructor; sets up the connection and display. **/
37                public function VideoMediaProvider() {
38                        super('video');
39                }
40
41
42                public override function initializeMediaProvider(cfg:PlayerConfig):void {
43                        super.initializeMediaProvider(cfg);
44                        _connection = new NetConnection();
45                        _connection.connect(null);
46                        _stream = new NetStream(_connection);
47                        _stream.addEventListener(NetStatusEvent.NET_STATUS, statusHandler);
48                        _stream.addEventListener(IOErrorEvent.IO_ERROR, errorHandler);
49                        _stream.addEventListener(AsyncErrorEvent.ASYNC_ERROR, errorHandler);
50                        _stream.bufferTime = config.bufferlength;
51                        _stream.client = new NetClient(this);
52                        _video = new Video(320, 240);
53                        _video.smoothing = config.smoothing;
54                        _video.attachNetStream(_stream);
55                        _transformer = new SoundTransform();
56                }
57
58
59                /** Catch security errors. **/
60                protected function errorHandler(evt:ErrorEvent):void {
61                        error(evt.text);
62                }
63
64
65                /** Load content. **/
66                override public function load(itm:PlaylistItem):void {
67                        var replay:Boolean;
68                        if (item != itm || _stream.bytesLoaded == 0) {
69                                _item = itm;
70                                media = _video;
71                                _stream.checkPolicyFile = true;
72                                _stream.play(item.file);
73                                _stream.pause();
74                        } else {
75                                replay = true;
76                        }
77
78                        setState(PlayerState.BUFFERING);
79                        if (replay){
80                                seekStream(0, false);
81                        } else {
82                                sendBufferEvent(0);
83                        }
84                        _bufferFull = false;
85                        _positionInterval = setInterval(positionHandler, 200);
86                        _loadTimer = setTimeout(loadTimerComplete, 3000);
87                        sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_LOADED);
88                        config.mute == true ? setVolume(0) : setVolume(config.volume);
89                }
90
91
92                /** timeout for checking the bitrate. **/
93                protected function loadTimerComplete():void {
94                        var obj:Object = new Object();
95                        obj.bandwidth = Math.round(_stream.bytesLoaded / 1024 / 3 * 8);
96                        if (item.duration) {
97                                obj.bitrate = Math.round(_stream.bytesTotal / 1024 * 8 / item.duration);
98                        }
99                        sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_META, {metadata: obj});
100                }
101
102
103                /** Get metadata information from netstream class. **/
104                public function onData(dat:Object):void {
105                        if (dat.width) {
106                                _video.width = dat.width;
107                                _video.height = dat.height;
108                                resize(_width, _height);
109                        }
110                        if (dat.duration && item.duration < 0) {
111                                item.duration = dat.duration;
112                        }
113                        sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_META, {metadata: dat});
114                }
115
116
117                /** Pause playback. **/
118                override public function pause():void {
119                        _stream.pause();
120                        super.pause();
121                }
122
123
124                /** Resume playing. **/
125                override public function play():void {
126                        if (!_positionInterval) {
127                                _positionInterval = setInterval(positionHandler, 100);
128                        }
129                        _stream.resume();
130                        super.play();
131                }
132
133
134                /** Interval for the position progress **/
135                protected function positionHandler():void {
136                        var _streamTime:Number = Math.min(_stream.time, item.duration);
137                        _position = Math.round(_streamTime * 10) / 10;
138                        var bufferPercent:Number = _stream.bytesLoaded / _stream.bytesTotal * 100;
139                        var bufferTime:Number = _stream.bufferTime < (item.duration - _streamTime) ? _stream.bufferTime : Math.floor(Math.abs(item.duration - _streamTime));
140                        var bufferFill:Number = bufferTime == 0 ? 100 : Math.ceil(_stream.bufferLength / bufferTime * 100);
141                       
142                        //Logger.log(Strings.print_r({streamtime: _streamTime, position:position, bufferPercent: bufferPercent, bufferFill: bufferFill, bufferTime:bufferTime}));
143                       
144                        if (bufferFill < 25 && state == PlayerState.PLAYING) {
145                                _stream.pause();
146                                setState(PlayerState.BUFFERING);
147                                _bufferFull = false;
148                        } else if (bufferFill > 95 && state == PlayerState.BUFFERING && _bufferFull == false) {
149                                sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_BUFFER_FULL);
150                                _bufferFull = true;
151                        }
152
153                        if (state == PlayerState.BUFFERING) {
154                                sendBufferEvent(bufferPercent);
155                        } else if (position < item.duration) {
156                                if (state == PlayerState.PLAYING && position >= 0) {
157                                        sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_TIME, {position: position, duration: item.duration, bufferPercent: bufferPercent});
158                                }
159                        } else if (item.duration > 0) {
160                                complete();
161                        }
162                }
163
164
165                /** Seek to a new position. **/
166                override public function seek(pos:Number):void {
167                        seekStream(pos);
168                }
169               
170                private function seekStream(pos:Number, ply:Boolean=true):void {
171                        var bufferLength:Number = _stream.bytesLoaded / _stream.bytesTotal * item.duration;
172                        if (pos <= bufferLength) {
173                                super.seek(pos);
174                                clearInterval(_positionInterval);
175                                _positionInterval = undefined;
176                                _stream.seek(position);
177                                if (ply){
178                                        play();
179                                }
180                        }
181                }
182
183
184                /** Receive NetStream status updates. **/
185                protected function statusHandler(evt:NetStatusEvent):void {
186                        switch (evt.info.code) {
187                                case "NetStream.Play.Stop":
188                                        complete();
189                                        break;
190                                case "NetStream.Play.StreamNotFound":
191                                        error('Video not found or access denied: ' + item.file);
192                                        break;
193                        }
194                        sendMediaEvent(MediaEvent.JWPLAYER_MEDIA_META, {metadata: {status: evt.info.code}});
195                }
196
197
198                /** Destroy the video. **/
199                override public function stop():void {
200                        if (_stream.bytesLoaded < _stream.bytesTotal) {
201                                _stream.close();
202                        } else {
203                                _stream.pause();
204                                _stream.seek(0);
205                        }
206                        _loadTimer = undefined;
207                        clearInterval(_positionInterval);
208                        _positionInterval = undefined;
209                        super.stop();
210                }
211
212
213                /** Set the volume level. **/
214                override public function setVolume(vol:Number):void {
215                        _transformer.volume = vol / 100;
216                        _stream.soundTransform = _transformer;
217                        super.setVolume(vol);
218                }
219        }
220}
Note: See TracBrowser for help on using the repository browser.