forked from: Pixel isometric cube
forked from Pixel Isometric Cube (diff: 86)
@author max.huang @see http://code.google.com/p/pixas/ trying to get shadow
ActionScript3 source code
/**
* Copyright kevinlin ( http://wonderfl.net/user/kevinlin )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/6iUn
*/
// forked from max.huang's Pixel isometric cube
package
{
import com.bit101.components.*;
import flash.display.Sprite;
import flash.events.Event;
/**
* @author max.huang
* @see http://code.google.com/p/pixas/
*/
public class Main extends Sprite
{
private var cubeContainer:Sprite;
private var vBox:VBox;
private var vBoxColor:VBox;
private var vBoxBorder:VBox;
private var sliX:HUISlider;
private var sliY:HUISlider;
private var sliZ:HUISlider;
private var colorChooser:ColorChooser;
private var cb:CheckBox;
public function Main():void
{
cubeContainer = new Sprite();
cubeContainer.x = Math.floor(stage.stageWidth / 2);
cubeContainer.y = Math.floor(stage.stageHeight / 2);
addChild(cubeContainer);
//control menu
vBox = new VBox(this , 5, 4);
var lableA:Label = new Label(vBox, 0, 0, "Cube dimension:");
sliX = new HUISlider(vBox, 0, 0, "X", updateCube);
sliY = new HUISlider(vBox, 0, 0, "Y", updateCube);
sliZ = new HUISlider(vBox, 0, 0, "Z", updateCube);
var s:HUISlider;
for each(s in [sliX, sliY, sliZ])
{
s.setSliderParams( 6, 220, 100);
s.tick = 2;
s.labelPrecision = 0;
}
sliZ.tick = 1;
vBoxColor = new VBox(this , 5, 110);
var lableB:Label = new Label(vBoxColor, 0, 0, "Cube top side color:");
colorChooser = new ColorChooser(vBoxColor, 0, 0, 0xE6E8E9, updateCube);
vBoxBorder = new VBox(this , 5, 180);
cb = new CheckBox(vBoxBorder, 0, 0, "Cube border", updateCube);
cb.selected = true;
updateCube();
}
private function updateCube(e:Event = null):void
{
while (cubeContainer.numChildren > 0)
{
cubeContainer.removeChildAt(0);
}
var cube:Cube = new Cube({ xAxis:sliX.value, yAxis:sliY.value, zAxis:sliZ.value }, CubeColor.getByHorizontalColor(colorChooser.value),cb.selected);
cubeContainer.addChild(cube.generate());
}
}
}
import flash.display.Bitmap;
import flash.display.BitmapData;
import flash.geom.Matrix;
import flash.display.Sprite;
class CubeColor
{
public var inner:uint;
public var border:uint;
public var borderHighlight:uint;
public var left:uint;
public var right:uint;
public var horizontal : uint;
public var shadow : uint;
private static const BRIGHTNESS_GAIN : int = - 20;
public function CubeColor
(
_border:uint = 0x949698,
_borderHighlight:uint = 0xFFFFFF,
_left:uint = 0xC9CFD0,
_right:uint = 0xE6E8E9,
_horizontal:uint = 0xEEEFF0,
_shadow:uint = 0xA9AFB0
)
{
border = get32(_border);
borderHighlight = get32(_borderHighlight);
left = get32(_left);
right = get32(_right);
horizontal = get32(_horizontal);
shadow = get32(_shadow);
}
public static function getByHorizontalColor(_horizontal:uint):CubeColor
{
return new CubeColor
(
CubeColor.applyBrightness(_horizontal, BRIGHTNESS_GAIN * 4),
CubeColor.applyBrightness(_horizontal, 0, true),
CubeColor.applyBrightness(_horizontal, BRIGHTNESS_GAIN * 2),
CubeColor.applyBrightness(_horizontal, BRIGHTNESS_GAIN),
_horizontal,
CubeColor.applyBrightness(_horizontal, BRIGHTNESS_GAIN / 2)
);
}
private function get32(_color:uint):uint
{
var color:uint = _color < 0xFF000000 ? (_color + 0xFF000000) : _color;
return color;
}
private static function applyBrightness (color : uint, brightness : int,highlight:Boolean = false) :uint
{
var r : int = ((color>>>16) & 0x000000FF);
var g : int = ((color>>> 8) & 0x000000FF);
var b : int = ((color) & 0x000000FF);
var y : int;
var v : int;
var u : int;
y = ((r*313524)>>20) + ((g*615514)>>20) + ((b*119538)>>20);
u = -((155189*r)>>20) - ((303038*g)>>20) + ((458227*b)>>20);
v = ((644874*r)>>20) - ((540016*g)>>20) - ((104857*b)>>20);
if (!highlight)
{
y += brightness;
}
else
{
y = 60 + Math.pow( y , 1.2);
}
r = y + ((1195376*v)>>20);
g = y - ((408944*u)>>20) - ((608174*v)>>20);
b = y + ((2128609*u)>>20);
r = Math.max (0,Math.min (r,255));
g = Math.max (0,Math.min (g,255));
b = Math.max (0,Math.min (b,255));
return (r << 16) | (g << 8) | b;
}
}
class AbstractPrimitive
{
protected var matrix:Matrix;
protected var w:uint;
protected var h:uint;
protected var dms:Object;
protected var color:Object;
protected var src_bmd:BitmapData;
public function AbstractPrimitive()
{
w = h = 0;
matrix = new Matrix();
}
public function generate():Bitmap
{
var bm : Bitmap = new Bitmap(src_bmd.clone());
bm.x = matrix.tx;
bm.y = matrix.ty;
return bm;
}
protected function initBmd():void
{
if (w == 0 || h == 0 )
{
throw new Error("BitmapData has not been initilized.");
}
src_bmd = new BitmapData(w, h , true , 0x00FFFFFF);
}
}
class Cube extends AbstractPrimitive
{
private var border:Boolean;
public function Cube(_dms: Object, _color:CubeColor, _border:Boolean = true)
{
super();
border = _border;
initRender(_dms, _color);
initRectangle();
initBmd();
build();
}
private function initRender(_dms:Object,_color:CubeColor):void
{
dms = _dms;
color = _color;
}
private function initRectangle():void
{
w = dms.xAxis + dms.yAxis*2;
h = dms.zAxis + (dms.xAxis*2 + dms.yAxis) / 2;
//22.6 degrees implementation
w -= 2;
h -= 1;
//the matrix offset between the bitmap and the 3d pixel coordinate ZERO point
matrix.tx = - dms.yAxis*2 + 2;
matrix.ty = - dms.zAxis;
}
private function build():void
{
//horizontal layer
var brick:Brick = new Brick
(
{xAxis:dms.xAxis, yAxis:dms.yAxis},
{border:color.border, inner:color.horizontal },
border
);
//left side
var sideX:SideX = new SideX
(
{xAxis:dms.xAxis, zAxis:dms.zAxis},
{border:color.border, inner:color.left },
border
);
//right side
var sideY:SideY = new SideY
(
{yAxis:dms.yAxis, zAxis:dms.zAxis},
{border:color.border, inner:color.right },
border
);
//lower shadow
var shadowX:ShadowX = new ShadowX
(
{xAxis:dms.xAxis, yAxis:dms.yAxis},
{border:color.border, inner:color.shadow },
border
);
var light_bm:Bitmap = generateHighLight();
var po:Sprite = new Sprite();
var po_sx:Sprite = new Sprite();
po_sx.addChild(shadowX.generate());
var po_brick:Sprite = new Sprite();
po_brick.addChild(brick.generate());
var po_x:Sprite = new Sprite();
po_x.addChild(sideX.generate());
var po_y:Sprite = new Sprite();
po_y.addChild(sideY.generate());
po_brick.x = dms.yAxis*2 - 2;
po_x.x = dms.yAxis;
po_x.y = dms.zAxis + dms.yAxis / 2 - 1;
po_y.x = w - 2;
po_y.y = dms.zAxis + dms.xAxis / 2 - 1;
po_sx.x = dms.yAxis;
po_sx.y = dms.zAxis + dms.yAxis / 2 - 1;
po.addChild(po_sx);
po.addChild(po_x);
po.addChild(po_y);
po.addChild(po_brick);
if (border)
{
po.addChild(light_bm);
}
src_bmd.draw(po);
//fix the middle light
if (!border)
{
for (var i:uint = 0; i < dms.zAxis; i++ )
{
src_bmd.setPixel32(dms.xAxis - 2, (dms.xAxis + dms.yAxis) / 2 - 1 + i, color.left);
}
}
}
private function generateHighLight():Bitmap
{
var bmd:BitmapData = new BitmapData(w, h , true , 0x00FFFFFF);
var offsetX : uint = dms.xAxis*2 - 2;
var offsetY : uint = (dms.xAxis + dms.yAxis) / 2 - 2;
//the 2px in bounding without hightlight
for (var i:uint = 0; i < dms.xAxis - 2; i++ )
{
bmd.setPixel32(offsetX + 1 - i, offsetY - Math.floor(i / 2), color.borderHighlight);
}
//the 2px in bounding without hightlight
for (var j:uint = 0; j < dms.yAxis - 2; j++ )
{
bmd.setPixel32(offsetX + j, offsetY - Math.floor(j / 2), color.borderHighlight);
}
for (var k:uint = 0; k < dms.zAxis; k++ )
{
bmd.setPixel32(offsetX, offsetY + k, color.borderHighlight);
}
return new Bitmap(bmd);
}
}
class SideY extends AbstractPrimitive
{
private var border:Boolean;
public function SideY(_dms:Object,_color:Object,_border: Boolean = true)
{
super();
border = _border;
initRender(_dms, _color);
initRectangle();
initBmd();
build();
}
private function initRender(_dms:Object,_color:Object):void
{
dms = _dms;
color = _color;
if (!border)
{
color.border = color.inner;
}
}
private function initRectangle():void
{
w = dms.yAxis;
h = dms.zAxis + dms.yAxis / 2;
//the matrix offset between the bitmap and the 3d pixel coordinate ZERO point
matrix.tx = - dms.yAxis + 2;
matrix.ty = - dms.zAxis;
}
private function build():void
{
var xOffsetInner:int = 0;
var yOffsetInner:int = h - dms.zAxis - 1
var xOffsetOut:int = dms.yAxis - 1;
var yOffsetOut:int = dms.zAxis;
src_bmd.lock();
//y axis
for (var i:uint = 0; i < dms.yAxis ; i++)
{
src_bmd.setPixel32(xOffsetInner + i, yOffsetInner - Math.floor(i / 2), color.border);
src_bmd.setPixel32(xOffsetOut - i, yOffsetOut + Math.floor(i / 2), color.border);
}
//z axis
for (var j:uint = 0; j < dms.zAxis ; j++)
{
src_bmd.setPixel32(xOffsetInner, yOffsetInner + j, color.border);
src_bmd.setPixel32(xOffsetOut , yOffsetOut - j, color.border);
}
//fill an pixel graphic enclosed
src_bmd.floodFill(Math.floor(w / 2), Math.floor(h / 2), color.inner);
src_bmd.unlock();
}
}
class SideX extends AbstractPrimitive
{
private var border:Boolean;
public function SideX(_dms:Object,_color:Object,_border:Boolean = true)
{
super();
border = _border;
initRender(_dms, _color);
initRectangle();
initBmd();
build();
}
private function initRender(_dms:Object,_color:Object):void
{
dms = _dms;
color = _color;
if (!border)
{
color.border = color.inner;
}
}
private function initRectangle():void
{
w = dms.xAxis;
h = dms.zAxis + dms.xAxis / 2;
//the matrix offset between the bitmap and the 3d pixel coordinate ZERO point
matrix.tx = 0;
matrix.ty = - dms.zAxis;
}
private function build():void
{
var xOffsetInner:int = 0;
var yOffsetInner:int = dms.zAxis;
var xOffsetOut:int = dms.xAxis - 1;
var yOffsetOut:int = h - dms.zAxis - 1;
src_bmd.lock();
//x axis
for (var i:uint = 0; i < dms.xAxis ; i++)
{
src_bmd.setPixel32(xOffsetInner + i, yOffsetInner + Math.floor(i / 2), color.border);
src_bmd.setPixel32(xOffsetOut - i, yOffsetOut - Math.floor(i / 2), color.border);
}
//z axis
for (var j:uint = 0; j < dms.zAxis ; j++)
{
src_bmd.setPixel32(xOffsetInner, yOffsetInner - j, color.border);
src_bmd.setPixel32(xOffsetOut , yOffsetOut +j, color.border);
}
//fill an pixel graphic enclosed
src_bmd.floodFill(Math.floor(w / 2), Math.floor(h / 2), color.inner);
src_bmd.unlock();
}
}
class Brick extends AbstractPrimitive
{
private var border:Boolean;
public function Brick(_dms: Object,_color:Object,_border:Boolean = true)
{
super();
border = _border;
initRender(_dms, _color);
initRectangle();
initBmd();
build();
}
private function initRender(_dms:Object,_color:Object):void
{
dms = _dms;
color = _color;
if (!border)
{
color.border = color.inner;
}
}
private function initRectangle():void
{
w = dms.xAxis + dms.yAxis;
h = (dms.xAxis + dms.yAxis) / 2;
// 22.6 degrees implementation
w -= 2;
h -= 1;
//the matrix offset between the bitmap and the 3d pixel coordinate ZERO point
matrix.tx = - dms.yAxis + 2;
matrix.ty = 0;
}
private function build():void
{
var xOffsetInner:int = dms.yAxis - 2;
var yOffsetInner:int = 0;
var xOffsetOut:int = dms.xAxis - 1;
var yOffsetOut:int = h - 1;
src_bmd.lock();
//x axis
for (var i:uint = 0; i < dms.xAxis ; i++)
{
src_bmd.setPixel32(xOffsetInner + i, yOffsetInner + Math.floor(i / 2), color.border);
src_bmd.setPixel32(xOffsetOut - i, yOffsetOut - Math.floor(i / 2), color.border);
}
//z axis
for (var j:uint = 0; j < dms.yAxis ; j++)
{
src_bmd.setPixel32(xOffsetInner + 1 - j, yOffsetInner + Math.floor(j / 2), color.border);
src_bmd.setPixel32(xOffsetOut - 1 + j, yOffsetOut - Math.floor(j / 2), color.border);
}
//fill an pixel graphic enclosed
src_bmd.floodFill(Math.floor(w / 2), Math.floor(h / 2), color.inner);
src_bmd.unlock();
}
}
class ShadowX extends AbstractPrimitive
{
private var border:Boolean;
public function ShadowX(_dms: Object,_color:Object,_border:Boolean = true)
{
super();
border = _border;
initRender(_dms, _color);
initRectangle();
initBmd();
build();
}
private function initRender(_dms:Object,_color:Object):void
{
dms = _dms;
color = _color;
if (!border)
{
color.border = color.inner;
}
}
private function initRectangle():void
{
w = dms.xAxis + dms.yAxis;
h = (dms.xAxis + dms.yAxis) / 2;
// 22.6 degrees implementation
w -= 2;
h -= 1;
//the matrix offset between the bitmap and the 3d pixel coordinate ZERO point
matrix.tx = - dms.yAxis + 2;
matrix.ty = 0;
}
private function build():void
{
var xOffsetInner:int = dms.yAxis - 2;
var yOffsetInner:int = 0;
var xOffsetOut:int = dms.xAxis - 1;
var yOffsetOut:int = h - 1;
src_bmd.lock();
//x axis
for (var i:uint = 0; i < dms.xAxis ; i++)
{
src_bmd.setPixel32(xOffsetInner + i, yOffsetInner + Math.floor(i / 2), color.inner);
src_bmd.setPixel32(xOffsetOut - i, yOffsetOut/2 - Math.floor(i / 2), color.inner);
}
//z axis
for (var j:uint = 0; j < dms.yAxis ; j++)
{
src_bmd.setPixel32(xOffsetInner + 1 - j, 0, color.inner);
src_bmd.setPixel32(xOffsetOut - 1 + j, yOffsetOut/2, color.inner);
}
//fill an pixel graphic enclosed
src_bmd.floodFill(Math.floor(w/2 + 1), Math.floor(h/2 - 1), color.inner);
src_bmd.unlock();
}
}