/src/away3d/materials/VideoMaterial.as
ActionScript | 208 lines | 115 code | 54 blank | 39 comment | 11 complexity | ab078e1fc0156507f486de125f4c1bd3 MD5 | raw file
1package away3d.materials 2{ 3 4 5 import away3d.materials.utils.IVideoPlayer; 6 import away3d.materials.utils.SimpleVideoPlayer; 7 8 import flash.display.BitmapData; 9 import flash.display.Sprite; 10 import flash.events.Event; 11 import flash.geom.Rectangle; 12 13 public class VideoMaterial extends BitmapMaterial 14 { 15 16 private var _broadcaster:Sprite; 17 private var _autoPlay:Boolean; 18 private var _autoUpdate:Boolean; 19 private var _materialSize:int; 20 private var _player:IVideoPlayer; 21 private var _clippingRect:Rectangle; 22 23 24 public function VideoMaterial(source:String, materialSize:int = 256, loop:Boolean = true, autoPlay:Boolean = false, player:IVideoPlayer = null) 25 { 26 27 // used to capture the onEnterFrame event 28 _broadcaster = new Sprite(); 29 30 // validates the size of the video 31 _materialSize = materialSize; 32 33 // this clipping ensures the bimapdata size is valid. 34 _clippingRect = new Rectangle(0, 0, _materialSize, _materialSize); 35 36 // assigns the provided player or creates a simple player if null. 37 _player = player || new SimpleVideoPlayer(); 38 _player.loop = loop; 39 _player.source = source; 40 _player.width = _player.height = _materialSize; 41 42 // sets autplay 43 _autoPlay = autoPlay; 44 45 // Sets up the bitmap material 46 super( new BitmapData(_materialSize, _materialSize, true, 0x00ffffff), true, false, false); 47 48 // if autoplay start video 49 if(autoPlay) 50 _player.play(); 51 52 // auto update is true by default 53 autoUpdate = true; 54 } 55 56 57 58 /** 59 * Draws the video and updates the bitmap material 60 * If this function is not called the bitmap material will not update! 61 */ 62 public function update():void 63 { 64 65 if(_player.playing && !_player.paused) 66 { 67 68 bitmapData.lock(); 69 bitmapData.draw( _player.container, null, null, null, _clippingRect); 70 updateTexture(); 71 bitmapData.unlock(); 72 73 } 74 75 } 76 77 78 override public function dispose(deep:Boolean):void 79 { 80 81 autoUpdate = false; 82 _player.dispose(); 83 _player = null; 84 _broadcaster = null; 85 _clippingRect = null; 86 87 super.dispose(deep); 88 } 89 90 private function autoUpdateHandler( e:Event ):void 91 { 92 update(); 93 } 94 95 ////////////////////////////////////////////////////// 96 // private class methods (static) 97 ////////////////////////////////////////////////////// 98 99 100 /** 101 * Validates the size of the BitmapMaterial. 102 * Supported size are 2, 4, 8, 16, 32, 64, 128, 512, 1024, 2048. 103 * Example: 145 would return 128. 104 * @param size 105 * @return int A valid size. 106 * 107 */ 108 109 public static function validateMaterialSize( size:int ):int 110 { 111 112 var sizes:Array = [2, 4, 8, 16, 32, 64, 128, 512, 1024, 2048]; 113 var validSize:int = Math.abs( size ); 114 115 if( sizes.indexOf( validSize ) == -1 ) 116 { 117 118 for(var i:uint = 1; i < sizes.length; ++i) 119 { 120 if( sizes[i] > validSize ) 121 { 122 // finds the closest match 123 validSize = ( Math.abs( sizes[i] - validSize ) < Math.abs( sizes[i-1] - validSize ) )? sizes[i] : sizes[i - 1]; 124 break; 125 } 126 } 127 128 validSize = (validSize > 2048)? 2048 : validSize; 129 130 trace("Warning: "+ size + " is not a valid material size. Updating to the closest supported resolution: " + validSize); 131 132 } 133 134 135 return validSize; 136 137 } 138 139 140 141 ////////////////////////////////////////////////////// 142 // get / set functions 143 ////////////////////////////////////////////////////// 144 145 146 /** 147 * Indicates whether the video will start playing on initialisation. 148 * If false, only the first frame is displayed. 149 */ 150 public function set autoPlay(b:Boolean):void 151 { 152 _autoPlay = b; 153 } 154 public function get autoPlay():Boolean 155 { 156 return _autoPlay; 157 } 158 159 160 /** 161 * Size of the bitmap used to render the video. This must be a supported resolution 162 * [2, 4, 8, 16, 32, 64, 128, 512, 1024, 2048] 163 * The size will be adjusted if an invalid value is passed 164 */ 165 public function set materialSize(value:int):void 166 { 167 _materialSize = validateMaterialSize( value ); 168 _player.width = _player.height = _materialSize; 169 _clippingRect = new Rectangle(0, 0, _materialSize, _materialSize); 170 } 171 172 public function get materialSize():int 173 { 174 return _materialSize; 175 } 176 177 178 /** 179 * Indicates whether the material will redraw onEnterFrame 180 */ 181 public function set autoUpdate(value:Boolean):void 182 { 183 _autoUpdate = value; 184 185 if(value) 186 { 187 if(!_broadcaster.hasEventListener(Event.ENTER_FRAME)) 188 _broadcaster.addEventListener(Event.ENTER_FRAME, autoUpdateHandler, false, 0, true); 189 } 190 else 191 { 192 if(_broadcaster.hasEventListener(Event.ENTER_FRAME)) 193 _broadcaster.removeEventListener(Event.ENTER_FRAME, autoUpdateHandler); 194 } 195 } 196 197 public function get autoUpdate():Boolean 198 { 199 return _autoUpdate; 200 } 201 202 public function get player():IVideoPlayer 203 { 204 return _player; 205 } 206 207 } 208}