WEB Flex : 4コマ動画作成ツール( 自分で描いたものを FLV 化する ) / SimpleFlvWriter

  BitmapData を flv 化するコード



探してたら、以下のようなのを見つけました
http://www.zeropointnine.com/blog/simpleflvwriteras-as3-class-to-create-flvs

これは、ローカル用に書かれたものですが、FileStream を ByteArray に書き換えると WEB で使えます。
↓オリジナル
http://www.zeropointnine.com/blog/assets_code/SimpleFlvWriter.as.txt


↓WEB 用に書き換えたもの
http://winofsql.jp/php/codeget/flex3/createFlv/SimpleFlvWriter.as.txt

とは言っても、
private var fs:FileStream = new FileStream();

public var fs:ByteArray = new ByteArray();
に変更してつじつま合わせただけで、オリジナルコードはそのままです。

以下がバグを修正した部分です
  
public function saveFrame(pBitmapData:BitmapData):void
{
	// bitmap dimensions should of course match parameters passed to createFile()
	bmp = pBitmapData;
	fs.writeUnsignedInt( previousTagSize );
	fs.writeBytes( flvTagVideo() );	
}

public function closeFile():void
{
	fs.writeUnsignedInt( previousTagSize );  // これが無いと、最後のフレームが無視される
	fs.close();	
}		
  


SimpleFlvWriter.as は
Lee Felarca さんによって作られたものです
以下は彼のサイトの URL です
http://www.zeropointnine.com/blog

Source code licensed under a Creative Commons Attribution 3.0 License.
http://creativecommons.org/licenses/by/3.0/
Some Rights Reserved.



  とにかく実行



左上、右上、左下、右下の順にキャンバスを適当に4分割して絵を書いて、
保存してから、表示してみてください。うまくいけば作成された FLV が再生可能な状態で表示されます




  使い道

きちんと作れば、パラパラ漫画ジェネレータにはなりますね。
( サウンドはもともとサポートされていません )



  flex コード

  
<?xml version="1.0" encoding="utf-8"?>
<mx:Application
	xmlns:mx="http://www.adobe.com/2006/mxml"
	initialize="initData();"
	mouseUp="Mouse_Up(event)"
>

<mx:Script>
<![CDATA[

	import mx.controls.*;
	import mx.events.*; 
	import mx.formatters.*;
	import mx.graphics.codec.*;
	import flash.external.*;
	import SimpleFlvWriter;

	private var m_status:Boolean = false;
	private var cvs_thickness:Number = 4;
	private var bmp:BitmapData = null;
	private var cmd_cnt:Number = 0;
	private var img_name:String = "";

	private var post:URLLoader;

	// *********************************************************
	// ログ表示
	// *********************************************************
	public function firebug(data:Object):void {
	
		var fmt:DateFormatter = new DateFormatter();
	
		fmt.formatString = "YYYY/MM/DD HH:NN:SS";
		var logdt:String = fmt.format( new Date );
	
		ExternalInterface.call(
			"console.log", logdt,
			data+""
		);
	
	}

	// *********************************************************
	// アプリケーションの初期化
	// *********************************************************
	public function initData():void {

		post = new URLLoader();

		// IO エラー
		post.addEventListener(IOErrorEvent.IO_ERROR, systemError);

		// 処理終了
		post.addEventListener(Event.COMPLETE, completeUpload);

		// 初期色
		cp.selectedColor = 0x000000;

		// 右クリックメニュー
		var cMenu:ContextMenu = new ContextMenu();
		cMenu.hideBuiltInItems();

		var cMenuItem2:ContextMenuItem =
			new ContextMenuItem("描画エリア拡大");
		cMenuItem2.addEventListener(
			ContextMenuEvent.MENU_ITEM_SELECT, Button_A2
		);
		cMenu.customItems.push(cMenuItem2);

		var cMenuItem1:ContextMenuItem =
			new ContextMenuItem("描画エリア縮小");
		cMenuItem1.addEventListener(
			ContextMenuEvent.MENU_ITEM_SELECT, Button_B2
		);
		cMenu.customItems.push(cMenuItem1);

		this.contextMenu = cMenu;
	}

	// *********************************************************
	// 拡大
	// *********************************************************
	public function Button_A(e:MouseEvent):void {

		cvs.scaleX = 2;
		cvs.scaleY = 2;

	}
	// *********************************************************
	// メニューから拡大
	// *********************************************************
	private function Button_A2(event:ContextMenuEvent):void {

		cvs.scaleX = 2;
		cvs.scaleY = 2;

	}

	// *********************************************************
	// 縮小
	// *********************************************************
	public function Button_B(e:MouseEvent):void {

		cvs.scaleX = 1;
		cvs.scaleY = 1;

	}
	// *********************************************************
	// メニューから縮小
	// *********************************************************
	private function Button_B2(event:ContextMenuEvent):void {

		cvs.scaleX = 1;
		cvs.scaleY = 1;

	}

	// *********************************************************
	// マウスダウン
	// *********************************************************
	public function Mouse_Down(e:flash.events.MouseEvent):void {

		m_status = true;
		e.currentTarget.graphics.moveTo(
			e.localX,
			e.localY
		);

	}

	// *********************************************************
	// マウスアップ
	// *********************************************************
	public function Mouse_Up(e:flash.events.MouseEvent):void {

		m_status = false;

	}

	// *********************************************************
	// 変換
	// *********************************************************
	public function Convert_bmp():void {

		if ( bmp == null ) {
			bmp = new BitmapData(480, 640);
		}

		bmp.draw(cvs);
		cvs.graphics.clear();
		cvs.graphics.beginBitmapFill(bmp); 
		cvs.graphics.drawRect(0, 0, bmp.width, bmp.height); 
		cvs.graphics.endFill(); 

	}

	// *********************************************************
	// マウス移動
	// *********************************************************
	public function Mouse_Move(e:flash.events.MouseEvent):void {

		if ( m_status ) {
			cvs_thickness = Number(lw.selectedItem.data);
			e.currentTarget.graphics.lineStyle(
				cvs_thickness,
				cp.selectedColor,
				100
			);
			e.currentTarget.graphics.lineTo(
				e.localX,
				e.localY
			);
			cmd_cnt++;
			if ( cmd_cnt > 20 ) {
				cmd_cnt = 0;
				Convert_bmp();
			}
			e.currentTarget.graphics.moveTo(
				e.localX,
				e.localY
			);
		}
	}

	// *****************************************************
	// Canvas を画像化してアップロード
	// *****************************************************
	private function uploadImage():void
	{


		var myWriter:SimpleFlvWriter = SimpleFlvWriter.getInstance();
		// 新規
		myWriter.fs = new ByteArray();
		myWriter.createFile(cvs.width/2, cvs.height/2, 3);

		// キャンバスの 1/4 のビットマップを作成
		var bmp:BitmapData = new BitmapData(cvs.width/2, cvs.height/2);
		// 1/4 の Rectangleを作成
		var area:Rectangle = new Rectangle(0,0,cvs.width/2,cvs.height/2);

		// 位置の並行移動用
		var cnv:Matrix = new Matrix();

		// 左上隅を作成
		cnv.tx = 0;
		cnv.ty = 0;
		bmp.draw(cvs,cnv,null,null,area);
		myWriter.saveFrame( bmp );

		// 右上隅を作成
		cnv.tx = cvs.width/2 * -1;
		cnv.ty = 0;
		bmp.draw(cvs,cnv,null,null,area);
		myWriter.saveFrame( bmp );

		// 左下隅を作成
		cnv.tx = 0;
		cnv.ty = cvs.height/2 * -1;
		bmp.draw(cvs,cnv,null,null,area);
		myWriter.saveFrame( bmp );

		// 右下隅を作成
		cnv.tx = cvs.width/2 * -1;
		cnv.ty = cvs.height/2 * -1;
		bmp.draw(cvs,cnv,null,null,area);
		myWriter.saveFrame( bmp );

		// 終了(最後の previoustagsize の書き込み) 
		myWriter.closeFile()

		// アップロード
		var req:URLRequest = new URLRequest("./savePng.php");
		req.data = myWriter.fs;
		req.method = URLRequestMethod.POST;

		post.load(req);

		bmp.dispose();

	}

	// *************************************************
	// 処理終了
	// *************************************************
	private function completeUpload(event:Event):void {

		var result:Array = (post.data).split(/\s/);

		Alert.show(post.data);

		img_name = result[0];
	}
			
	// *************************************************
	// IO エラー
	// *************************************************
	private function systemError(event:IOErrorEvent):void{
		Alert.show("IOError:" + event.text);
	}

	// *************************************************
	// 指定 URL でブラウザを開く
	// *************************************************
	public function OpenUrl(url:String):void {

		if ( url == 'image/' ) {
			Alert.show( "画像は保存されていません" );
		}
		else {
			var req:URLRequest = new URLRequest(url);
			navigateToURL(req, "_blank");
		}
	}

]]>
</mx:Script>

<mx:Panel
	title="超シンプル お絵かきコンテンツ"
	horizontalAlign="center"
>

	<mx:HBox>

	<mx:Canvas
		id="cvs"
		borderStyle="solid"
		width="480"
		height="640"
		top="0"
		mouseDown="Mouse_Down(event)"
		mouseUp="Mouse_Up(event)"
		mouseMove="Mouse_Move(event)"
		mouseOut="Mouse_Move(event)"
	>
	</mx:Canvas>

	<mx:VBox>
	<mx:ColorPicker id="cp" showTextField="true" />
	<mx:Button
		id="btn_A"
		label="拡大"
		click="Button_A(event)"
	/>
	<mx:Button
		id="btn_B"
		label="縮小"
		click="Button_B(event)"
	/>

	<mx:List id="lw" selectedIndex="2" width="50" height="400">
		<mx:dataProvider>
			<mx:Array>
				<mx:Object label="極細" data="0" />
				<mx:Object label="2" data="2" />
				<mx:Object label="4" data="4" />
				<mx:Object label="6" data="6" />
				<mx:Object label="8" data="8" />
				<mx:Object label="10" data="10" />
				<mx:Object label="12" data="12" />
				<mx:Object label="14" data="14" />
				<mx:Object label="16" data="16" />
				<mx:Object label="18" data="18" />
				<mx:Object label="20" data="20" />
				<mx:Object label="22" data="22" />
				<mx:Object label="24" data="24" />
			</mx:Array>
		</mx:dataProvider>
	</mx:List>

	<mx:Button
		id="btn_C"
		label="保存"
		click="uploadImage()"
	/>

	<mx:Button
		id="btn_D"
		label="表示"
		click="OpenUrl( 'Example_www.swf?source=' + img_name )"
	/>

	</mx:VBox>

	</mx:HBox>


</mx:Panel>
</mx:Application>
  



  PHP コード

  
<?
session_start();
$id = session_id();


$fp = fopen( "php://input", "rb" );
$wfp = fopen( "$id.flv", "wb" );

while( $ret = fread( $fp, 4096 ) ) {

	fwrite( $wfp, $ret );

}

fclose($wfp);
fclose($fp);


print $id . ".flv\n";
?>
で画像が保存されました
  










  infoboard   管理者用   
このエントリーをはてなブックマークに追加





フリーフォントWEBサービス
SQLの窓WEBサービス

SQLの窓フリーソフト

素材

一般WEBツールリンク

SQLの窓

フリーソフト

JSライブラリ