Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 18 additions & 7 deletions localtypings/pxtarget.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -906,13 +906,7 @@ declare namespace ts.pxtc {
icon?: string;
jresURL?: string;
iconURL?: string;
imageLiteral?: number;
gridLiteral?: number;
gridLiteralOnColor?: string;
gridLiteralOffColor?: string;
imageLiteralColumns?: number; // optional number of columns
imageLiteralRows?: number; // optional number of rows
imageLiteralScale?: number; // button sizing between 0.6 and 2, default is 1

weight?: number;
parts?: string;
hiddenParts?: string; // allows an extesion to declaratively hide a part
Expand Down Expand Up @@ -989,6 +983,23 @@ declare namespace ts.pxtc {

/* end enum-only attributes */

/* led matrix field editor attributes */

imageLiteral?: number;
gridLiteral?: number;
colorGridLiteral?: number;
gridLiteralPalette?: string;
gridLiteralPaletteNames?: string;
gridLiteralUseProjectPalette?: boolean;
gridLiteralOnColor?: string;
gridLiteralOffColor?: string;
gridLiteralVerticalSpacing?: number; // optional spacing between pixels, default is 5
gridLiteralHorizontalSpacing?: number; // optional spacing between pixels, default is 7
gridLiteralBorderRadius?: number; // optional border radius for pixels, default is 5
imageLiteralColumns?: number; // optional number of columns
imageLiteralRows?: number; // optional number of rows
imageLiteralScale?: number; // button sizing between 0.6 and 2, default is 1


isKind?: boolean; // annotation for built-in kinds in library code
kindMemberName?: string; // The name a member of the kind as it will appear in the blocks editor. If the kind was "Colors" this would be "color"
Expand Down
2 changes: 1 addition & 1 deletion pxtblocks/compiler/compiler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -809,7 +809,7 @@ function compileImage(e: Environment, b: Blockly.Block, frames: number, columns:
for (let j = 0; j < columns; ++j) {
if (j > 0)
state += ' ';
state += (leds[(i * columns) + j] === '#') ? "#" : ".";
Comment thread
srietkerk marked this conversation as resolved.
state += leds[(i * columns) + j];
}
state += '\n';
}
Expand Down
2 changes: 1 addition & 1 deletion pxtblocks/compiler/environment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,7 @@ export function mkEnv(w: Blockly.Workspace, blockInfo?: pxtc.BlocksInfo, options
attrs: fn.attributes,
isExtensionMethod: instance,
isExpression: fn.retType && fn.retType !== "void",
imageLiteral: fn.attributes.imageLiteral || fn.attributes.gridLiteral,
imageLiteral: fn.attributes.imageLiteral || fn.attributes.gridLiteral || fn.attributes.colorGridLiteral,
imageLiteralColumns: fn.attributes.imageLiteralColumns,
imageLiteralRows: fn.attributes.imageLiteralRows,
hasHandler: pxt.blocks.hasHandler(fn),
Expand Down
128 changes: 92 additions & 36 deletions pxtblocks/fields/field_ledmatrix.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
/// <reference path="../../built/pxtsim.d.ts" />

import * as Blockly from "blockly";
import { DEFAULT_LED_COLORS } from "./field_ledmatrix_colorPicker";
import { FieldMatrix } from "./field_matrix";
import { FieldCustom } from "./field_utils";

Expand All @@ -27,9 +28,12 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
public SERIALIZABLE = true;

private params: any;
private onColor = "#FFFFFF";
private offColor: string;

private palette: string[];

private static DEFAULT_OFF_COLOR = "#000000";
private static DEFAULT_ON_COLOR = "#FFFFFF";
private offOpacity = 0.2;

private scale = 1;

Expand All @@ -39,13 +43,18 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
private yAxisLabel: LabelMode = LabelMode.None;
private xAxisLabel: LabelMode = LabelMode.None;

private cellState: boolean[][] = [];
private cellState: number[][] = [];

private currentDragState_: boolean;

protected clearSelectionOnBlur = true;
protected forceFocusVisible = true;

protected isColorMatrix = false;
protected colorNames: string[];

private activeColor = 1;

constructor(text: string, params: any, validator?: Blockly.FieldValidator) {
super(text, validator);
this.params = params;
Expand All @@ -64,12 +73,37 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
}
}

if (this.params.onColor !== undefined) {
this.onColor = this.params.onColor;
this.isColorMatrix = !!this.params.isColorMatrix;

if (this.params.colors) {
this.palette = this.params.colors;
}
else {
this.palette = [
FieldLedMatrix.DEFAULT_OFF_COLOR,
...DEFAULT_LED_COLORS
];
}

if (this.params.colorNames) {
this.colorNames = this.params.colorNames;
}
else {
this.colorNames = [
lf("off"),
...DEFAULT_LED_COLORS
];
}

if (this.params.hasOffColor) {
this.offOpacity = 1.0;
}

if (this.params.offColor !== undefined) {
this.offColor = this.params.offColor;
if (this.params.offOpacity) {
const val = parseFloat(this.params.offOpacity);
if (!isNaN(val) && val >= 0 && val <= 1) {
this.offOpacity = val;
}
}

if (this.params.scale !== undefined)
Expand All @@ -79,18 +113,27 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
else if (Math.max(this.numMatrixCols, this.numMatrixRows) > 10)
this.scale = 0.9;

this.size_.height = this.scale * Number(this.numMatrixRows) * (FieldLedMatrix.CELL_WIDTH + FieldLedMatrix.CELL_VERTICAL_MARGIN) + FieldLedMatrix.CELL_VERTICAL_MARGIN * 2 + FieldLedMatrix.BOTTOM_MARGIN + this.getXAxisHeight()
this.size_.width = this.scale * Number(this.numMatrixCols) * (FieldLedMatrix.CELL_WIDTH + FieldLedMatrix.CELL_HORIZONTAL_MARGIN) + FieldLedMatrix.CELL_HORIZONTAL_MARGIN + this.getYAxisWidth();
const verticalMargin = isNaN(this.params.verticalSpacing) ? FieldLedMatrix.CELL_VERTICAL_MARGIN : this.params.verticalSpacing;
const horizontalMargin = isNaN(this.params.horizontalSpacing) ? FieldLedMatrix.CELL_HORIZONTAL_MARGIN : this.params.horizontalSpacing;

this.size_.height = this.scale * Number(this.numMatrixRows) * (FieldLedMatrix.CELL_WIDTH + verticalMargin) + verticalMargin * 2 + FieldLedMatrix.BOTTOM_MARGIN + this.getXAxisHeight()
this.size_.width = this.scale * Number(this.numMatrixCols) * (FieldLedMatrix.CELL_WIDTH + horizontalMargin) + horizontalMargin + this.getYAxisWidth();
}

protected getCellToggled(x: number, y: number): boolean {
return this.cellState[x][y];
return !!this.cellState[x][y];
}

protected useTwoToneFocusIndicator(x: number, y: number): boolean {
return this.getCellToggled(x, y);
}

setActiveColorIndex(index: number) {
if (index >= 0 && index < this.palette.length) {
this.activeColor = index;
}
}

/**
* Show the inline free-text editor on top of the text.
* @private
Expand Down Expand Up @@ -136,31 +179,34 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
for (let i = 0; i < this.numMatrixCols; i++) {
this.cellState.push([])
for (let j = 0; j < this.numMatrixRows; j++) {
this.cellState[i].push(false);
this.cellState[i].push(0);
}
}

this.restoreStateFromString();

const verticalMargin = isNaN(this.params.verticalSpacing) ? FieldLedMatrix.CELL_VERTICAL_MARGIN : this.params.verticalSpacing;
const horizontalMargin = isNaN(this.params.horizontalSpacing) ? FieldLedMatrix.CELL_HORIZONTAL_MARGIN : this.params.horizontalSpacing;

this.createMatrixDisplay({
cellWidth: FieldLedMatrix.CELL_WIDTH,
cellHeight: FieldLedMatrix.CELL_WIDTH,
cellLabel: lf("LED"),
cellHorizontalMargin: FieldLedMatrix.CELL_HORIZONTAL_MARGIN,
cellVerticalMargin: FieldLedMatrix.CELL_VERTICAL_MARGIN,
cornerRadius: FieldLedMatrix.CELL_CORNER_RADIUS,
cellFill: this.offColor,
cellHorizontalMargin: horizontalMargin,
cellVerticalMargin: verticalMargin,
cornerRadius: isNaN(this.params.borderRadius) ? FieldLedMatrix.CELL_CORNER_RADIUS : this.params.borderRadius,
cellFill: this.palette[0],
padLeft: this.getYAxisWidth(),
scale: this.scale
});

this.updateValue();

if (this.xAxisLabel !== LabelMode.None) {
const y = this.scale * this.numMatrixRows * (FieldLedMatrix.CELL_WIDTH + FieldLedMatrix.CELL_VERTICAL_MARGIN) + FieldLedMatrix.CELL_VERTICAL_MARGIN * 2 + FieldLedMatrix.BOTTOM_MARGIN
const y = this.scale * this.numMatrixRows * (FieldLedMatrix.CELL_WIDTH + verticalMargin) + verticalMargin * 2 + FieldLedMatrix.BOTTOM_MARGIN
const xAxis = pxsim.svg.child(this.matrixSvg, "g", { transform: `translate(${0} ${y})` });
for (let i = 0; i < this.numMatrixCols; i++) {
const x = this.getYAxisWidth() + this.scale * i * (FieldLedMatrix.CELL_WIDTH + FieldLedMatrix.CELL_HORIZONTAL_MARGIN) + FieldLedMatrix.CELL_WIDTH / 2 + FieldLedMatrix.CELL_HORIZONTAL_MARGIN / 2;
const x = this.getYAxisWidth() + this.scale * i * (FieldLedMatrix.CELL_WIDTH + horizontalMargin) + FieldLedMatrix.CELL_WIDTH / 2 + horizontalMargin / 2;
const lbl = pxsim.svg.child(xAxis, "text", { x, class: "blocklyText" })
lbl.textContent = this.getLabel(i, this.xAxisLabel);
}
Expand All @@ -169,7 +215,7 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
if (this.yAxisLabel !== LabelMode.None) {
const yAxis = pxsim.svg.child(this.matrixSvg, "g", {});
for (let i = 0; i < this.numMatrixRows; i++) {
const y = this.scale * i * (FieldLedMatrix.CELL_WIDTH + FieldLedMatrix.CELL_VERTICAL_MARGIN) + FieldLedMatrix.CELL_WIDTH / 2 + FieldLedMatrix.CELL_VERTICAL_MARGIN * 2;
const y = this.scale * i * (FieldLedMatrix.CELL_WIDTH + verticalMargin) + FieldLedMatrix.CELL_WIDTH / 2 + verticalMargin * 2;
const lbl = pxsim.svg.child(yAxis, "text", { x: 0, y, class: "blocklyText" })
lbl.textContent = this.getLabel(i, this.yAxisLabel);
}
Expand Down Expand Up @@ -265,7 +311,7 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
}

protected toggleCell = (x: number, y: number, value?: boolean) => {
this.cellState[x][y] = value ?? this.currentDragState_;
this.cellState[x][y] = (value ?? this.currentDragState_) ? this.activeColor : 0;
this.updateValue();
}

Expand Down Expand Up @@ -293,11 +339,11 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
}

private getColor(x: number, y: number) {
return this.cellState[x][y] ? this.onColor : (this.offColor || FieldLedMatrix.DEFAULT_OFF_COLOR);
return this.palette[this.cellState[x][y]];
}

private getOpacity(x: number, y: number) {
const offOpacity = this.offColor ? '1.0': '0.2';
const offOpacity = this.offOpacity + "";
return this.cellState[x][y] ? '1.0' : offOpacity;
}

Expand All @@ -306,7 +352,10 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
cellRect.setAttribute("fill", this.getColor(x, y));
cellRect.setAttribute("fill-opacity", this.getOpacity(x, y));
cellRect.setAttribute('class', `blocklyLed${this.cellState[x][y] ? 'On' : 'Off'}`);
cellRect.setAttribute("aria-checked", this.cellState[x][y].toString());
cellRect.setAttribute("aria-checked", (!!this.cellState[x][y]).toString());
if (this.isColorMatrix) {
cellRect.setAttribute("aria-label", this.colorNames[this.cellState[x][y]] || this.palette[this.cellState[x][y]] || lf("color {0}", this.cellState[x][y]));
}
}

setValue(newValue: string | number, restoreState = true) {
Expand Down Expand Up @@ -357,12 +406,10 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
const row = rows[y];

for (let j = 0; j < row.length && x < this.numMatrixCols; j++) {
if (isNegativeCharacter(row[j])) {
this.cellState[x][y] = false;
x++;
}
else if (isPositiveCharacter(row[j])) {
this.cellState[x][y] = true;
const val = parseCharacter(row[j]);

if (val !== -1) {
this.cellState[x][y] = val;
x++;
}
}
Expand All @@ -372,12 +419,13 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {

// Composes the state into a string an updates the field's state
private updateValue() {
const chars = ".#23456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
Comment thread
srietkerk marked this conversation as resolved.
let res = "";
for (let y = 0; y < this.numMatrixRows; y++) {
for (let x = 0; x < this.numMatrixCols; x++) {
res += (this.cellState[x][y] ? "#" : ".") + " "
res += chars.charAt(this.cellState[x][y]) + " ";
}
res += "\n" + FieldLedMatrix.TAB
res += "\n" + FieldLedMatrix.TAB;
}

// Blockly stores the state of the field as a string
Expand All @@ -393,12 +441,20 @@ export class FieldLedMatrix extends FieldMatrix implements FieldCustom {
}
}

function isPositiveCharacter(c: string) {
return c === "#" || c === "*" || c === "1";
}

function isNegativeCharacter(c: string) {
return c === "." || c === "_" || c === "0";
function parseCharacter(c: string): number {
const chars = ".#23456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
switch (c) {
case "#":
case "*":
case "1":
return 1;
case ".":
case "_":
case "0":
return 0;
default:
return chars.indexOf(c.toUpperCase());
}
}


Expand Down
Loading
Loading