122 lines
4.1 KiB
Dart
122 lines
4.1 KiB
Dart
import 'dart:html' as html;
|
|
import 'dart:math';
|
|
import 'package:stagexl/stagexl.dart' as sxl;
|
|
|
|
class ColorScheme {
|
|
//TODO make iterable (perhaps through backing list which gets accesses by the variables)
|
|
final int ON;
|
|
final int EXPANSION;
|
|
final int CORE;
|
|
final int OFF;
|
|
|
|
const ColorScheme(this.ON, this.EXPANSION, this.CORE,
|
|
[this.OFF = sxl.Color.Transparent]);
|
|
}
|
|
|
|
class Render {
|
|
final sxl.Stage _stage;
|
|
final sxl.RenderLoop _renderLoop = sxl.RenderLoop();
|
|
Map<int, sxl.BitmapData> _colorMap;
|
|
final sxl.BitmapContainer _renderContainer = sxl.BitmapContainer();
|
|
|
|
bool transparentBG = false;
|
|
bool _renderEdges = false;
|
|
bool get renderEdges => _renderEdges;
|
|
void set renderEdges(bool value) {
|
|
_renderEdges = value;
|
|
_colorMap = _getColorMap(_cellSize, _colorScheme);
|
|
}
|
|
|
|
Point<int> _gridSize;
|
|
Point<int> get _cellSize => Point(
|
|
_stage.stageWidth ~/ _gridSize.x, _stage.stageHeight ~/ _gridSize.y);
|
|
|
|
final ColorScheme _colorScheme;
|
|
//TODO replace with scheme data structure to enable different color scheme injection
|
|
static const defaultScheme =
|
|
ColorScheme(sxl.Color.Blue, 1, 1, sxl.Color.Black);
|
|
|
|
// TODO gridSize rendering can only be scaled uniformly currently - switch to Point(w,h)?
|
|
Render(html.CanvasElement canvas, Point<int> gridSize,
|
|
[ColorScheme colorScheme = defaultScheme])
|
|
: _stage = _createStage(canvas),
|
|
_colorScheme = colorScheme,
|
|
_gridSize = gridSize {
|
|
_colorMap = _getColorMap(_cellSize, colorScheme);
|
|
_initRenderGrid(_cellSize, gridSize).forEach((sxl.Bitmap bm) {
|
|
_renderContainer.addChild(bm);
|
|
});
|
|
_renderLoop.addStage(_stage);
|
|
_stage.addChild(_renderContainer);
|
|
setDirty();
|
|
}
|
|
|
|
static sxl.Stage _createStage(html.CanvasElement canvas) {
|
|
sxl.StageXL.stageOptions.renderEngine = sxl.RenderEngine.WebGL;
|
|
sxl.StageXL.stageOptions.stageRenderMode = sxl.StageRenderMode.AUTO_INVALID;
|
|
// sxl.StageXL.stageOptions.backgroundColor = sxl.Color.Yellow;
|
|
return sxl.Stage(canvas);
|
|
}
|
|
|
|
Map<int, sxl.BitmapData> _getColorMap(Point<int> size, ColorScheme scheme) {
|
|
print("${size.toString()}, ${scheme.toString()}");
|
|
|
|
// Creates a shape with color of each quad in scheme
|
|
sxl.Shape shape = sxl.Shape();
|
|
// ON
|
|
shape.graphics.beginPath();
|
|
shape.graphics.rect(0 * size.x, 0, size.x, size.y);
|
|
shape.graphics.fillColor(scheme.ON ?? sxl.Color.Transparent);
|
|
shape.graphics
|
|
.strokeColor(renderEdges ? sxl.Color.DarkGray : sxl.Color.Transparent);
|
|
shape.graphics.closePath();
|
|
// OFF
|
|
shape.graphics.beginPath();
|
|
shape.graphics.rect(1 * size.x, 0, size.x, size.y);
|
|
shape.graphics.fillColor(scheme.OFF ?? sxl.Color.Transparent);
|
|
shape.graphics
|
|
.strokeColor(renderEdges ? sxl.Color.DarkGray : sxl.Color.Transparent);
|
|
shape.graphics.closePath();
|
|
|
|
// creates one texture out of shape
|
|
sxl.BitmapData texture = sxl.BitmapData(2 * size.x, size.y);
|
|
texture.draw(shape);
|
|
// re-slice texture into individual BitmapDatas
|
|
Map<int, sxl.BitmapData> colorMap = Map();
|
|
List<sxl.BitmapData> colorBitmaps = texture.sliceIntoFrames(size.x, size.y);
|
|
print("Found ${colorBitmaps.length} colors.");
|
|
// TODO more elegant way through iterables etc; also include EXPANSION, CORE functionality
|
|
colorMap[scheme.ON] = colorBitmaps[0];
|
|
colorMap[scheme.OFF] = colorBitmaps[1];
|
|
|
|
return colorMap;
|
|
}
|
|
|
|
List<sxl.Bitmap> _initRenderGrid(Point<int> cellSize, Point<int> gridSize) {
|
|
List<sxl.Bitmap> grid = List();
|
|
for (int y = 0; y < gridSize.y; y++) {
|
|
for (int x = 0; x < gridSize.x; x++) {
|
|
sxl.Bitmap bm = sxl.Bitmap();
|
|
|
|
bm.bitmapData = _colorMap[_colorScheme.OFF];
|
|
bm.x = x * cellSize.x;
|
|
bm.y = y * cellSize.y;
|
|
grid.add(bm);
|
|
}
|
|
}
|
|
|
|
return grid;
|
|
}
|
|
|
|
void setDirty() => _stage.invalidate();
|
|
|
|
void mergeChanges(Map<int, bool> stateChanges) {
|
|
if (stateChanges.length == 0) return;
|
|
stateChanges.forEach((int i, bool state) {
|
|
_renderContainer.getChildAt(i).bitmapData =
|
|
(state ? _colorMap[_colorScheme.ON] : _colorMap[_colorScheme.OFF]);
|
|
});
|
|
setDirty();
|
|
}
|
|
}
|