Ascii Webcam

Generating ASCII art from webcam data

Ascii Webcam

src/main.as


/*
	    _____    __________________ .___.___ 
	   /  _  \  /   _____/\_   ___ \|   |   |
	  /  /_\  \ \_____  \ /    \  \/|   |   |
	 /    |    \/        \     \___|   |   |
	 \____|__  /_______  / \______  /___|___|
	         \/   ___. \/         \/            
	__  _  __ ____\_ |__   ____ _____    _____  
	\ \/ \/ // __ \| __ \_/ ___\__  \  /     \ 
	 \     /\  ___/| \_\ \  \___ / __ \|  Y Y  \
	  \/\_/  \___  >___  /\___  >____  /__|_|  /
	             \/    \/     \/     \/      \/ 
	                                             */
package { 	
//______________________________________________________________________________
//                                                                       imports
	import com.bit101.components.*;
	
	import flash.display.*;
	import flash.events.*;
	import flash.geom.*;
	import flash.media.*;
	import flash.text.*;
	import flash.ui.*;
	import flash.utils.*;
	
	import nu.xero.gfx.*;
//______________________________________________________________________________
//                                                                        export	
	[SWF(backgroundColor="0xffffff", 
		 heightPercent="100%", 
		 widthPercent="100%",
		 pageTitle="ascii webcam")]
//______________________________________________________________________________
//                                                                         class
	public class main extends Sprite {
//______________________________________________________________________________
//                                                                          vars
		private var webcam			:Video;
		private var camera			:Camera;
		private var webcamData		:Bitmap
		private var tempData		:BitmapData;
		private var converter		:bitmap2ascii;
		private var format			:TextFormat;
		private var canvas			:TextField;
		private var form			:Sprite;
		private var fontSlider		:Slider;
		private var resSlider		:Slider;
		private var blackSlider		:Slider;
		private var whiteSlider		:Slider;
		private var fontColor		:ColorChooser;
		private var bgColor			:ColorChooser;
		private var chkPreview		:CheckBox;
		private var preview			:Sprite;
		private var shrink			:Matrix;
//______________________________________________________________________________
//                                                                   constructor
		public function main() {
			stage.scaleMode = StageScaleMode.NO_SCALE;
			stage.align = StageAlign.TOP_LEFT;
			stage.quality = StageQuality.MEDIUM;
			stage.frameRate = 100;
						
			createUI();
			createMenu();
			initCams();
		}
//______________________________________________________________________________
//                                                               setup interface		
		private function createUI():void {
			format = new TextFormat("Courier New", 6);
			
			Style.setStyle('dark');
			
			canvas = new TextField();
			canvas.autoSize = TextFieldAutoSize.LEFT;
			canvas.x = 80;
			canvas.y = 0 
			canvas.wordWrap = false;
			canvas.selectable = false;
			canvas.defaultTextFormat = format;
			addChild(canvas);
			
			form = new Sprite();
			form.x = form.y = 0;
			form.graphics.beginFill(0x222222);
			form.graphics.drawRect(0, 0, 80, stage.stageHeight);
			addChild(form);
			
			var lblFont:Label = new Label();
			lblFont.x = 0;
			lblFont.y = 20;
			lblFont.text = "font size";
			form.addChild(lblFont);
			
			fontSlider = new Slider(Slider.HORIZONTAL);
			fontSlider.scaleX = fontSlider.scaleY = 0.75;
			fontSlider.x = 2;
			fontSlider.y = 40;
			fontSlider.minimum = 4;
			fontSlider.maximum = 10;
			fontSlider.value   = 6;
			fontSlider.addEventListener(Event.CHANGE, fontChange);
			form.addChild(fontSlider);

			var lblRes:Label = new Label();
			lblRes.x = 0;
			lblRes.y = 50;
			lblRes.text = "resolution";
			form.addChild(lblRes);
 
			resSlider = new Slider(Slider.HORIZONTAL);
			resSlider.scaleX = resSlider.scaleY = 0.75;
			resSlider.x = 2;
			resSlider.y = 70;
			resSlider.minimum = 0.01;
			resSlider.maximum = 0.05;
			resSlider.value   = 0.025;
			resSlider.addEventListener(Event.CHANGE, formChange);
			form.addChild(resSlider);

			var lblBlack:Label = new Label();
			lblBlack.x = 0;
			lblBlack.y = 80;
			lblBlack.text = "black threshold";
			form.addChild(lblBlack);
			
			blackSlider = new Slider(Slider.HORIZONTAL);
			blackSlider.scaleX = blackSlider.scaleY = 0.75;
			blackSlider.x = 2;
			blackSlider.y = 100;
			blackSlider.minimum = 0;
			blackSlider.maximum = 40;
			blackSlider.value   = 40;
			blackSlider.addEventListener(Event.CHANGE, formChange);
			form.addChild(blackSlider);

			var lblWhite:Label = new Label();
			lblWhite.x = 0;
			lblWhite.y = 110;
			lblWhite.text = "white threshold";
			form.addChild(lblWhite);
			
			whiteSlider = new Slider(Slider.HORIZONTAL);
			whiteSlider.scaleX = whiteSlider.scaleY = 0.75;
			whiteSlider.x = 2;
			whiteSlider.y = 130;
			whiteSlider.minimum = 10;
			whiteSlider.maximum = 255;
			whiteSlider.value   = 200;
			whiteSlider.addEventListener(Event.CHANGE, formChange);
			form.addChild(whiteSlider);
			
			var lblBgColor:Label = new Label();
			lblBgColor.x = 0;
			lblBgColor.y = 140;
			lblBgColor.text = "background color";
			form.addChild(lblBgColor);
						
			bgColor = new ColorChooser();
			bgColor.value = 0xffffff;
			bgColor.x = 5;
			bgColor.y = 160;
			bgColor.usePopup = true;
			bgColor.addEventListener(Event.CHANGE, colorChange);
			form.addChild(bgColor);						
			
			var lblFontColor:Label = new Label();
			lblFontColor.x = 0;
			lblFontColor.y = 180;
			lblFontColor.text = "font color";
			form.addChild(lblFontColor);
			
			fontColor = new ColorChooser();
			fontColor.value = 0x000000;
			fontColor.x = 5;
			fontColor.y = 200;
			fontColor.usePopup = true;
			fontColor.addEventListener(Event.CHANGE, fontChange);
			form.addChild(fontColor);			
						
			var lblPreview:Label = new Label();
			lblPreview.x = 0;
			lblPreview.y = 220;
			lblPreview.text = "preview";
			form.addChild(lblPreview);	
			
			chkPreview = new CheckBox();
			chkPreview.x = 45;
			chkPreview.y = 225;
			chkPreview.selected = true;
			chkPreview.addEventListener(Event.CHANGE, formChange);
			form.addChild(chkPreview);
			
			shrink = new Matrix(); 
			shrink.scale(0.25, 0.25);
			preview = new Sprite();
			preview.x = 0;
			preview.y = 240;
			addChild(preview);			
			

			
		}
		private function colorChange(e:Event):void {
			graphics.beginFill(bgColor.value);
			graphics.drawRect(0, 0, stage.stageWidth, stage.stageHeight);
			graphics.endFill();
		}
		private function fontChange(e:Event):void {
			format = new TextFormat("Courier New", fontSlider.value, fontColor.value);
			canvas.defaultTextFormat = format;
		}
		private function formChange(e:Event):void {
			converter.resolution = resSlider.value;
			converter.blackThreshold = blackSlider.value;
			converter.whiteThreshold = whiteSlider.value;
		}
//______________________________________________________________________________
//                                                                          menu
		private function createMenu():void {
			var menu:ContextMenu = new ContextMenu();
			menu.addEventListener(ContextMenuEvent.MENU_SELECT, menuHandler);
			menu.hideBuiltInItems();
			
			var menuFullscreen:ContextMenuItem = new ContextMenuItem("go fullscreen");
			menuFullscreen.addEventListener(ContextMenuEvent.MENU_ITEM_SELECT, goFullscreen);
			menu.customItems.push(menuFullscreen);
			
			var menuExitFull:ContextMenuItem = new ContextMenuItem("exit fullscreen");
			menuExitFull.addEventListener(ContextMenuEvent.MENU_ITEM_SELECT, exitFullscreen);
			menu.customItems.push(menuExitFull);
			
			this.contextMenu = menu;
		}
		private function menuHandler(e:ContextMenuEvent):void {
			if (stage.displayState == StageDisplayState.NORMAL) {
				e.target.customItems[0].enabled = true;
				e.target.customItems[1].enabled = false;
			} else {
				e.target.customItems[0].enabled = false;
				e.target.customItems[1].enabled = true;
			}
		}
		private function goFullscreen(e:ContextMenuEvent):void {
			stage.displayState = StageDisplayState.FULL_SCREEN;	
		}
		private function exitFullscreen(e:ContextMenuEvent):void {
			stage.displayState = StageDisplayState.NORMAL;
		}
//______________________________________________________________________________
//                                                                        webcam
		private function initCams():void {
			camera = Camera.getCamera();
			camera.addEventListener(StatusEvent.STATUS, onCamStatus);
			
			webcam = new Video(320, 240);
			webcam.attachCamera(camera);
			
			tempData = new BitmapData(320, 240, false, 0xff0000);
			webcamData = new Bitmap(tempData);
			webcamData.x = 320;
						
			converter = new bitmap2ascii(0.025, 200, 40);
			converter.resolution = 0.01;
		}
		private function onCamStatus(e:StatusEvent):void {
			if (e.code.indexOf("unmuted")) {
				var chronos:Timer;
				chronos = new Timer(30);
				chronos.addEventListener(TimerEvent.TIMER, update);
				chronos.start();
			}
		}
		private function update(e:TimerEvent):void {
			tempData.draw(webcam);
			webcamData.bitmapData = tempData;
			canvas.text = converter.convert(tempData);
			preview.graphics.clear();
			if(chkPreview.selected) {
				preview.graphics.beginBitmapFill(webcamData.bitmapData, shrink);
				preview.graphics.drawRect(0, 0, 80, 60);
				preview.graphics.endFill();
			}
			return;
		}		
	}
}
//______________________________________________________________________________
//                                                                   end of file

Download

raw zip tar