Created
October 4, 2010 04:53
-
-
Save snikch/609262 to your computer and use it in GitHub Desktop.
JWPlayer 5 Captions Plugin, with y axis margin variable.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| package { | |
| import com.longtailvideo.jwplayer.events.ViewEvent; | |
| import com.longtailvideo.jwplayer.events.MediaEvent; | |
| import com.longtailvideo.jwplayer.events.PlayerStateEvent; | |
| import com.longtailvideo.jwplayer.events.PlaylistEvent; | |
| import com.longtailvideo.jwplayer.player.IPlayer; | |
| import com.longtailvideo.jwplayer.player.PlayerState; | |
| import com.longtailvideo.jwplayer.plugins.IPlugin; | |
| import com.longtailvideo.jwplayer.plugins.PluginConfig; | |
| import com.longtailvideo.jwplayer.utils.Logger; | |
| import com.longtailvideo.jwplayer.utils.Configger; | |
| import com.jeroenwijering.parsers.*; | |
| import flash.display.MovieClip; | |
| import flash.display.Bitmap; | |
| import flash.events.MouseEvent; | |
| import flash.events.Event; | |
| import flash.text.TextField; | |
| import flash.text.TextFormat; | |
| import flash.net.*; | |
| import flash.filters.DropShadowFilter; | |
| public class Captions2 extends MovieClip implements IPlugin { | |
| [Embed(source="controlbar.png")] | |
| private const ControlbarIcon:Class; | |
| [Embed(source="dock.png")] | |
| private const DockIcon:Class; | |
| /** Configuration list of the plugin. **/ | |
| private var pluginConf:PluginConfig; | |
| /** Reference to the JW Player API. **/ | |
| private var api:IPlayer; | |
| /** List with configuration settings. **/ | |
| public var config:Object = { | |
| back:false, | |
| file:undefined, | |
| fontsize:20, | |
| state:true, | |
| margin:0 | |
| }; | |
| /** XML connect and parse object. **/ | |
| private var loader:URLLoader; | |
| /** Icon for the controlbar. **/ | |
| private var icon:Bitmap; | |
| /** Reference to the textfield. **/ | |
| public var field:TextField; | |
| /** Reference to the background graphic. **/ | |
| private var back:MovieClip; | |
| /** The array the captions are loaded into. **/ | |
| private var captions:Array; | |
| /** Textformat entry for the captions. **/ | |
| private var format:TextFormat; | |
| /** Currently active caption. **/ | |
| private var current:Number; | |
| /** Reference to the dock button. **/ | |
| private var button:MovieClip; | |
| public function Captions2() { | |
| loader = new URLLoader(); | |
| loader.addEventListener(Event.COMPLETE,loaderHandler); | |
| }; | |
| /** This function is automatically called by the player after the plugin has loaded. **/ | |
| public function initPlugin(player:IPlayer, conf:PluginConfig):void { | |
| api = player; | |
| pluginConf = conf; | |
| if(conf['file']) | |
| config['file'] = conf['file']; | |
| if(conf['margin']) | |
| config['margin'] = conf['margin']; | |
| if(conf['fontsize']) | |
| config['fontsize'] = conf['fontsize']; | |
| if(conf['state'] == true) | |
| config['state'] = true; | |
| else | |
| config['state'] = false; | |
| drawClip(); | |
| api.addEventListener(PlaylistEvent.JWPLAYER_PLAYLIST_ITEM,itemHandler); | |
| api.addEventListener(ViewEvent.JWPLAYER_VIEW_REDRAW, resizeHandler); | |
| api.addEventListener(MediaEvent.JWPLAYER_MEDIA_TIME,timeHandler); | |
| api.addEventListener(PlayerStateEvent.JWPLAYER_PLAYER_STATE,stateHandler); | |
| api.addEventListener(MediaEvent.JWPLAYER_MEDIA_META,metaHandler); | |
| mouseEnabled = false; | |
| mouseChildren = false; | |
| Logger.log('initializing','captions2'); | |
| if(api.config.dock) { | |
| button = api.controls.dock.addButton(new DockIcon(),'is on',clickHandler); | |
| } else { | |
| icon = new ControlbarIcon(); | |
| api.controls.controlbar.addButton(icon,'captions',clickHandler); | |
| } | |
| hide(config['state']); | |
| } | |
| /** Clicking the hide button. **/ | |
| private function clickHandler(evt:MouseEvent):void { | |
| hide(!config['state']); | |
| Configger.saveCookie("captions2.state", config.state); | |
| }; | |
| /** Show/hide the captions **/ | |
| public function hide(stt:Boolean):void { | |
| config['state'] = stt; | |
| visible = config['state']; | |
| if(config['state']) { | |
| if(button) { | |
| button.field.text = 'is on'; | |
| } else { | |
| icon.alpha = 1; | |
| } | |
| } else { | |
| if(button) { | |
| button.field.text = 'is off'; | |
| } else { | |
| icon.alpha = 0.3; | |
| } | |
| } | |
| }; | |
| /** This should be a unique, lower-case identifier (e.g. "myplugin") **/ | |
| public function get id():String { | |
| return "captions2"; | |
| } | |
| /** Called when the player has resized. The dimensions of the plugin are passed in here. **/ | |
| public function resizeHandler(evt:ViewEvent=undefined):void { | |
| // Lay out plugin here, if necessary. | |
| field.y = (api.config['height']-field.height)-config['margin']; | |
| //back.y = (view.config['height']-height)-config['margin']; | |
| field.x = (api.config['width']-field.width)/2; | |
| } | |
| public function resize(wid:Number, hei:Number):void | |
| { | |
| } | |
| private function drawClip():void { | |
| back = new MovieClip(); | |
| back.graphics.beginFill(0x000000,0.75); | |
| back.graphics.drawRect(0,0,400,20); | |
| addChild(back); | |
| format = new TextFormat(); | |
| format.color = 0xFFFFFF; | |
| format.size = config['fontsize']; | |
| format.align = "center"; | |
| format.font = "_sans"; | |
| format.leading = 4; | |
| field = new TextField(); | |
| field.width = 400; | |
| field.height = 10; | |
| field.y = 5; | |
| field.autoSize = "center"; | |
| field.selectable = false; | |
| field.multiline = true; | |
| field.wordWrap = true; | |
| field.defaultTextFormat = format; | |
| addChild(field); | |
| if(config['back'] == false) { | |
| back.alpha = 0; | |
| field.filters = new Array(new DropShadowFilter(0,45,0,1,2,2,10,3)); | |
| } | |
| }; | |
| /** Captions are loaded; now display them. **/ | |
| private function loaderHandler(evt:Event):void { | |
| Logger.log('Loader Handler called', 'captions2'); | |
| var ext:String = config['file'].substr(-3); | |
| if(ext == 'srt' || ext == 'txt') { | |
| captions = SRTParser.parseCaptions(String(evt.target.data)); | |
| } else { | |
| captions = TTParser.parseCaptions(XML(evt.target.data)); | |
| } | |
| if(captions.length == 0) { | |
| Logger.log('Not a valid TimedText or SRT file.','captions'); | |
| } | |
| }; | |
| /** Check for captions with a new item. **/ | |
| private function itemHandler(evt:PlaylistEvent=null):void { | |
| Logger.log('Item Handler called','captions2'); | |
| current = 0; | |
| captions = new Array(); | |
| pluginConf['file'] = undefined; | |
| field.htmlText = ''; | |
| // drop metadata caption support | |
| var file:String; | |
| if (api.playlist.currentItem['captions.file']) { | |
| file = api.playlist.currentItem['captions.file']; | |
| } else if (api.playlist.currentItem['captions']) { | |
| file = api.playlist.currentItem['captions']; | |
| } else if (config['file']) { | |
| file = config['file']; | |
| } | |
| Logger.log('Attempting to load file' , 'captions2'); | |
| Logger.log(pluginConf['file'] , 'captions2'); | |
| if(file) { | |
| pluginConf['file'] = file; | |
| try { | |
| loader.load(new URLRequest(pluginConf['file'])); | |
| } catch (err:Error) { | |
| Logger.log(err.message,'captions2'); | |
| } | |
| } | |
| }; | |
| /** Check timing of the player to sync captions. **/ | |
| private function timeHandler(evt:MediaEvent):void { | |
| var pos:Number = evt.position; | |
| if(captions && captions.length > 0 && ( | |
| captions[current]['begin'] > pos || | |
| (captions[current+1] && captions[current+1]['begin'] < pos))) { | |
| setCaption(pos); | |
| } | |
| }; | |
| /** Check timing of the player to sync captions. **/ | |
| private function stateHandler(evt:PlayerStateEvent):void { | |
| if((evt.newstate == 'PLAYING' || | |
| evt.newstate == 'PAUSED') && config['state']) { | |
| visible = true; | |
| } else { | |
| visible = false; | |
| } | |
| }; | |
| /** Check for captions in metadata. **/ | |
| private function metaHandler(evt:MediaEvent):void { | |
| var txt:String; | |
| var fnd:Boolean = false; | |
| if (evt.metadata.type == 'caption') { | |
| txt = evt.metadata.captions; | |
| fnd = true; | |
| } else if (evt.metadata.type == 'textdata') { | |
| txt = evt.metadata.text; | |
| fnd = true; | |
| } | |
| if (fnd == true) { | |
| field.htmlText = txt+' '; | |
| resizeHandler(); | |
| } | |
| }; | |
| /** Set a caption on screen. **/ | |
| private function setCaption(pos:Number):void { | |
| for(var i:Number=0; i<captions.length; i++) { | |
| if(captions[i]['begin'] < pos && (i == captions.length - 1 || captions[i+1]['begin'] > pos)) { | |
| current = i; | |
| field.htmlText = captions[i]['text']; | |
| resizeHandler(); | |
| Logger.log(captions[i]['text'],'caption'); | |
| return; | |
| } | |
| } | |
| }; | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment