diff --git a/src/components/Blockly/BlocklyComponent.jsx b/src/components/Blockly/BlocklyComponent.jsx
index 3bc97aa..631b25d 100644
--- a/src/components/Blockly/BlocklyComponent.jsx
+++ b/src/components/Blockly/BlocklyComponent.jsx
@@ -27,6 +27,7 @@ import './BlocklyComponent.css';
import Blockly from 'blockly/core';
//import locale from 'blockly/msg/en';
import 'blockly/blocks';
+import Toolbox from './toolbox/Toolbox';
//Blockly.setLocale(locale);
@@ -61,13 +62,11 @@ class BlocklyComponent extends React.Component {
}
render() {
- const { children } = this.props;
+
return
-
- {children}
-
+
;
}
}
diff --git a/src/components/Blockly/blocks/index.js b/src/components/Blockly/blocks/index.js
index 3caa84b..e5c75e7 100644
--- a/src/components/Blockly/blocks/index.js
+++ b/src/components/Blockly/blocks/index.js
@@ -1,4 +1,6 @@
import './loops';
import './sensebox';
import './logic';
-import './sensebox-sensors';
\ No newline at end of file
+import './sensebox-sensors';
+import './sensebox-telegram';
+import './io';
\ No newline at end of file
diff --git a/src/components/Blockly/blocks/io.js b/src/components/Blockly/blocks/io.js
new file mode 100644
index 0000000..f17149d
--- /dev/null
+++ b/src/components/Blockly/blocks/io.js
@@ -0,0 +1,257 @@
+/**
+ * @license Licensed under the Apache License, Version 2.0 (the "License"):
+ * http://www.apache.org/licenses/LICENSE-2.0
+ */
+
+/**
+ * @fileoverview Blocks for Arduino Digital and Analogue input and output
+ * functions. The Arduino function syntax can be found at
+ * http://arduino.cc/en/Reference/HomePage
+ *
+ * TODO: maybe change this to a "PIN" BlocklyType
+ */
+import { defineBlocksWithJsonArray } from 'blockly';
+import Blockly from 'blockly/core';
+import { selectedBoard } from '../helpers/board'
+
+
+Blockly.Blocks['io_digitalwrite'] = {
+ /**
+ * Block for creating a 'set pin' to a state.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/DigitalWrite');
+ this.setColour(250);
+ this.appendValueInput('STATE')
+ .appendField(Blockly.Msg.ARD_DIGITALWRITE)
+ .appendField(new Blockly.FieldDropdown(
+ selectedBoard().digitalPins), 'PIN')
+ .appendField(Blockly.Msg.ARD_WRITE_TO)
+ // .setCheck(Blockly.Types.BOOLEAN.checkList);
+ this.setInputsInline(false);
+ this.setPreviousStatement(true, null);
+ this.setNextStatement(true, null);
+ this.setTooltip(Blockly.Msg.ARD_DIGITALWRITE_TIP);
+ },
+ /**
+ * Updates the content of the the pin related fields.
+ * @this Blockly.Block
+ */
+ updateFields: function () {
+ Blockly.Arduino.Boards.refreshBlockFieldDropdown(
+ this, 'PIN', 'digitalPins');
+ }
+};
+
+Blockly.Blocks['io_digitalread'] = {
+ /**
+ * Block for creating a 'read pin'.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/DigitalRead');
+ this.setColour(250);
+ this.appendDummyInput()
+ .appendField(Blockly.Msg.ARD_DIGITALREAD)
+ .appendField(new Blockly.FieldDropdown(
+ Blockly.Arduino.Boards.selected.digitalPins), 'PIN');
+ this.setOutput(true, Blockly.Types.BOOLEAN.output);
+ this.setTooltip(Blockly.Msg.ARD_DIGITALREAD_TIP);
+ },
+ /** @return {!string} The type of return value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.BOOLEAN;
+ },
+ /**
+ * Updates the content of the the pin related fields.
+ * @this Blockly.Block
+ */
+ updateFields: function () {
+ Blockly.Arduino.Boards.refreshBlockFieldDropdown(
+ this, 'PIN', 'digitalPins');
+ }
+};
+
+Blockly.Blocks['io_builtin_led'] = {
+ /**
+ * Block for setting built-in LED to a state.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/DigitalWrite');
+ this.setColour(250);
+ this.appendValueInput('STATE')
+ .appendField(Blockly.Msg.ARD_BUILTIN_LED)
+ .appendField(new Blockly.FieldDropdown(
+ Blockly.Arduino.Boards.selected.builtinLed), 'BUILT_IN_LED')
+ .appendField(Blockly.Msg.ARD_WRITE_TO)
+ .setCheck(Blockly.Types.BOOLEAN.checkList);
+ this.setInputsInline(false);
+ this.setPreviousStatement(true, null);
+ this.setNextStatement(true, null);
+ this.setTooltip(Blockly.Msg.ARD_BUILTIN_LED_TIP);
+ },
+ /**
+ * Updates the content of the the pin related fields.
+ * @this Blockly.Block
+ */
+ updateFields: function () {
+ Blockly.Arduino.Boards.refreshBlockFieldDropdown(
+ this, 'BUILT_IN_LED', 'builtinLed');
+ },
+ /** @return {!string} The type of input value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.BOOLEAN;
+ },
+};
+
+Blockly.Blocks['io_analogwrite'] = {
+ /**
+ * Block for creating a 'set pin' to an analogue value.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/AnalogWrite');
+ this.setColour(250);
+ this.appendValueInput('NUM')
+ .appendField(Blockly.Msg.ARD_ANALOGWRITE)
+ .appendField(new Blockly.FieldDropdown(
+ Blockly.Arduino.Boards.selected.pwmPins), 'PIN')
+ .appendField(Blockly.Msg.ARD_WRITE_TO)
+ .setCheck(Blockly.Types.NUMBER.output);
+ this.setInputsInline(false);
+ this.setPreviousStatement(true, null);
+ this.setNextStatement(true, null);
+ this.setTooltip(Blockly.Msg.ARD_ANALOGWRITE_TIP);
+ },
+ /**
+ * Updates the content of the the pin related fields.
+ * @this Blockly.Block
+ */
+ updateFields: function () {
+ Blockly.Arduino.Boards.refreshBlockFieldDropdown(this, 'PIN', 'pwmPins');
+ },
+ /** @return {!string} The type of input value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.NUMBER;
+ },
+};
+
+Blockly.Blocks['io_analogread'] = {
+ /**
+ * Block for reading an analogue input.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/AnalogRead');
+ this.setColour(250);
+ this.appendDummyInput()
+ .appendField(Blockly.Msg.ARD_ANALOGREAD)
+ .appendField(new Blockly.FieldDropdown(
+ Blockly.Arduino.Boards.selected.analogPins), 'PIN');
+ this.setOutput(true, Blockly.Types.NUMBER.output);
+ this.setTooltip(Blockly.Msg.ARD_ANALOGREAD_TIP);
+ },
+ /** @return {!string} The type of return value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.NUMBER;
+ },
+ /**
+ * Updates the content of the the pin related fields.
+ * @this Blockly.Block
+ */
+ updateFields: function () {
+ Blockly.Arduino.Boards.refreshBlockFieldDropdown(this, 'PIN', 'analogPins');
+ }
+};
+
+Blockly.Blocks['io_highlow'] = {
+ /**
+ * Block for creating a pin state.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.setHelpUrl('http://arduino.cc/en/Reference/Constants');
+ this.setColour(250);
+ this.appendDummyInput()
+ .appendField(
+ new Blockly.FieldDropdown([[Blockly.Msg.ARD_HIGH, 'HIGH'], [Blockly.Msg.ARD_LOW, 'LOW']]),
+ 'STATE');
+ this.setOutput(true, Blockly.Types.BOOLEAN.output);
+ this.setTooltip(Blockly.Msg.ARD_HIGHLOW_TIP);
+ },
+ /** @return {!string} The type of return value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.BOOLEAN;
+ }
+};
+
+Blockly.Blocks['io_pulsein'] = {
+ /**
+ * Block for measuring the duration of a pulse in an input pin.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.jsonInit({
+ "type": "math_foo",
+ "message0": Blockly.Msg.ARD_PULSE_READ,
+ "args0": [{
+ "type": "input_value",
+ "name": "PULSETYPE",
+ "check": Blockly.Types.BOOLEAN.check
+ }, {
+ "type": "field_dropdown",
+ "name": "PULSEPIN",
+ "options": Blockly.Arduino.Boards.selected.digitalPins
+ }
+ ],
+ "output": Blockly.Types.NUMBER.output,
+ "inputsInline": true,
+ "colour": 250,
+ "tooltip": Blockly.Msg.ARD_PULSE_TIP,
+ "helpUrl": 'https://www.arduino.cc/en/Reference/PulseIn'
+ });
+ },
+ /** @return {!string} The type of input value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.NUMBER;
+ }
+};
+
+Blockly.Blocks['io_pulsetimeout'] = {
+ /**
+ * Block for measuring (with a time-out) the duration of a pulse in an input
+ * pin.
+ * @this Blockly.Block
+ */
+ init: function () {
+ this.jsonInit({
+ "type": "math_foo",
+ "message0": Blockly.Msg.ARD_PULSE_READ_TIMEOUT,
+ "args0": [{
+ "type": "input_value",
+ "name": "PULSETYPE",
+ "check": Blockly.Types.BOOLEAN.check
+ }, {
+ "type": "field_dropdown",
+ "name": "PULSEPIN",
+ "options": Blockly.Arduino.Boards.selected.digitalPins
+ }, {
+ "type": "input_value",
+ "name": "TIMEOUT",
+ "check": Blockly.Types.NUMBER.check
+ }
+ ],
+ "output": Blockly.Types.NUMBER.output,
+ "inputsInline": true,
+ "colour": 250,
+ "tooltip": Blockly.Msg.ARD_PULSETIMEOUT_TIP,
+ "helpUrl": 'https://www.arduino.cc/en/Reference/PulseIn'
+ });
+ },
+ /** @return {!string} The type of input value for the block, an integer. */
+ getBlockType: function () {
+ return Blockly.Types.NUMBER;
+ }
+};
diff --git a/src/components/Blockly/blocks/sensebox-telegram.js b/src/components/Blockly/blocks/sensebox-telegram.js
new file mode 100644
index 0000000..2ba704d
--- /dev/null
+++ b/src/components/Blockly/blocks/sensebox-telegram.js
@@ -0,0 +1,17 @@
+import Blockly from 'blockly';
+
+Blockly.Blocks["sensebox_telegram"] = {
+ init: function () {
+ this.setColour(120);
+ this.appendDummyInput()
+ .appendField(Blockly.Msg.senseBox_telegram_init);
+ this.appendDummyInput()
+ .setAlign(Blockly.ALIGN_LEFT)
+ .appendField("telegram")
+ .appendField(new Blockly.FieldTextInput("token"), "telegram_token");
+ this.setPreviousStatement(true, null);
+ this.setNextStatement(true, null);
+ }
+};
+
+
diff --git a/src/components/Blockly/blocks/sensebox.js b/src/components/Blockly/blocks/sensebox.js
index 18ce462..43ebcbb 100644
--- a/src/components/Blockly/blocks/sensebox.js
+++ b/src/components/Blockly/blocks/sensebox.js
@@ -1,16 +1,4 @@
import Blockly from 'blockly';
-Blockly.Blocks["sensebox_telegram"] = {
- init: function () {
- this.setColour(120);
- this.appendDummyInput()
- .appendField(Blockly.Msg.senseBox_telegram_init);
- this.appendDummyInput()
- .setAlign(Blockly.ALIGN_LEFT)
- .appendField("telegram")
- .appendField(new Blockly.FieldTextInput("token"), "telegram_token");
- this.setPreviousStatement(true, null);
- this.setNextStatement(true, null);
- }
-};
+
diff --git a/src/components/Blockly/generator/index.js b/src/components/Blockly/generator/index.js
index 271af4a..c629df3 100644
--- a/src/components/Blockly/generator/index.js
+++ b/src/components/Blockly/generator/index.js
@@ -2,4 +2,6 @@ import './generator';
import './loops';
import './sensebox';
import './logic';
+import './math';
+import './io';
diff --git a/src/components/Blockly/generator/io.js b/src/components/Blockly/generator/io.js
new file mode 100644
index 0000000..5cef62a
--- /dev/null
+++ b/src/components/Blockly/generator/io.js
@@ -0,0 +1,32 @@
+import * as Blockly from 'blockly/core';
+import { Block } from 'blockly';
+
+/**
+ * Function for 'set pin' (X) to a state (Y).
+ * Arduino code: setup { pinMode(X, OUTPUT); }
+ * loop { digitalWrite(X, Y); }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {string} Completed code.
+ */
+Blockly.Arduino['io_digitalwrite'] = function (block) {
+ var pin = block.getFieldValue('PIN');
+ var stateOutput = Blockly.Arduino.valueToCode(
+ block, 'STATE', Blockly['Arduino'].ORDER_ATOMIC) || 'LOW';
+ Blockly['Arduino'].setupCode_['pinMode'] = 'pinMode(' + pin + ', OUTPUT);';
+ var code = 'digitalWrite(' + pin + ', ' + stateOutput + ');\n';
+ return code;
+};
+
+/**
+ * Function for reading a digital pin (X).
+ * Arduino code: setup { pinMode(X, INPUT); }
+ * loop { digitalRead(X) }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['io_digitalread'] = function (block) {
+ var pin = block.getFieldValue('PIN');
+ Blockly['Arduino'].setupCode_['pinMode' + pin] = 'pinMode(' + pin + ', INPUT);'
+ var code = 'digitalRead(' + pin + ')';
+ return [code, Blockly.Arduino.ORDER_ATOMIC];
+};
diff --git a/src/components/Blockly/generator/math.js b/src/components/Blockly/generator/math.js
new file mode 100644
index 0000000..0832e0c
--- /dev/null
+++ b/src/components/Blockly/generator/math.js
@@ -0,0 +1,344 @@
+
+import * as Blockly from 'blockly/core';
+import { Block } from 'blockly';
+
+/**
+ * @license Licensed under the Apache License, Version 2.0 (the "License"):
+ * http://www.apache.org/licenses/LICENSE-2.0
+ */
+
+/**
+ * @fileoverview Generating Arduino code for the Math blocks.
+ *
+ * TODO: Math on list needs lists to be implemented.
+ * math_constant and math_change needs to be tested in compiler.
+ */
+
+/**
+ * Generator for a numeric value (X).
+ * Arduino code: loop { X }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_number'] = function (block) {
+ // Numeric value.
+ var code = parseFloat(block.getFieldValue('NUM'));
+ if (code == Infinity) {
+ code = 'INFINITY';
+ } else if (code == -Infinity) {
+ code = '-INFINITY';
+ }
+ return [code, Blockly.Arduino.ORDER_ATOMIC];
+};
+
+/**
+ * Generator for a basic arithmetic operators (X and Y) and power function
+ * (X ^ Y).
+ * Arduino code: loop { X operator Y }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_arithmetic'] = function (block) {
+ var OPERATORS = {
+ ADD: [' + ', Blockly.Arduino.ORDER_ADDITIVE],
+ MINUS: [' - ', Blockly.Arduino.ORDER_ADDITIVE],
+ MULTIPLY: [' * ', Blockly.Arduino.ORDER_MULTIPLICATIVE],
+ DIVIDE: [' / ', Blockly.Arduino.ORDER_MULTIPLICATIVE],
+ POWER: [null, Blockly.Arduino.ORDER_NONE] // Handle power separately.
+ };
+ var tuple = OPERATORS[block.getFieldValue('OP')];
+ var operator = tuple[0];
+ var order = tuple[1];
+ var argument0 = Blockly.Arduino.valueToCode(block, 'A', order) || '0';
+ var argument1 = Blockly.Arduino.valueToCode(block, 'B', order) || '0';
+ var code;
+ // Power in C++ requires a special case since it has no operator.
+ if (!operator) {
+ code = 'Math.pow(' + argument0 + ', ' + argument1 + ')';
+ return [code, Blockly.Arduino.ORDER_UNARY_POSTFIX];
+ }
+ code = argument0 + operator + argument1;
+ return [code, order];
+};
+
+/**
+ * Generator for math operators that contain a single operand (X).
+ * Arduino code: loop { operator(X) }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_single'] = function (block) {
+ var operator = block.getFieldValue('OP');
+ var code;
+ var arg;
+ if (operator == 'NEG') {
+ // Negation is a special case given its different operator precedents.
+ arg = Blockly.Arduino.valueToCode(block, 'NUM',
+ Blockly.Arduino.ORDER_UNARY_PREFIX) || '0';
+ if (arg[0] == '-') {
+ // --3 is not legal in C++ in this context.
+ arg = ' ' + arg;
+ }
+ code = '-' + arg;
+ return [code, Blockly.Arduino.ORDER_UNARY_PREFIX];
+ }
+ if (operator == 'ABS' || operator.substring(0, 5) == 'ROUND') {
+ arg = Blockly.Arduino.valueToCode(block, 'NUM',
+ Blockly.Arduino.ORDER_UNARY_POSTFIX) || '0';
+ } else if (operator == 'SIN' || operator == 'COS' || operator == 'TAN') {
+ arg = Blockly.Arduino.valueToCode(block, 'NUM',
+ Blockly.Arduino.ORDER_MULTIPLICATIVE) || '0';
+ } else {
+ arg = Blockly.Arduino.valueToCode(block, 'NUM',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ }
+ // First, handle cases which generate values that don't need parentheses.
+ switch (operator) {
+ case 'ABS':
+ code = 'abs(' + arg + ')';
+ break;
+ case 'ROOT':
+ code = 'sqrt(' + arg + ')';
+ break;
+ case 'LN':
+ code = 'log(' + arg + ')';
+ break;
+ case 'EXP':
+ code = 'exp(' + arg + ')';
+ break;
+ case 'POW10':
+ code = 'pow(10,' + arg + ')';
+ break;
+ case 'ROUND':
+ code = 'round(' + arg + ')';
+ break;
+ case 'ROUNDUP':
+ code = 'ceil(' + arg + ')';
+ break;
+ case 'ROUNDDOWN':
+ code = 'floor(' + arg + ')';
+ break;
+ case 'SIN':
+ code = 'sin(' + arg + ' / 180 * Math.PI)';
+ break;
+ case 'COS':
+ code = 'cos(' + arg + ' / 180 * Math.PI)';
+ break;
+ case 'TAN':
+ code = 'tan(' + arg + ' / 180 * Math.PI)';
+ break;
+ }
+ if (code) {
+ return [code, Blockly.Arduino.ORDER_UNARY_POSTFIX];
+ }
+ // Second, handle cases which generate values that may need parentheses.
+ switch (operator) {
+ case 'LOG10':
+ code = 'log(' + arg + ') / log(10)';
+ break;
+ case 'ASIN':
+ code = 'asin(' + arg + ') / M_PI * 180';
+ break;
+ case 'ACOS':
+ code = 'acos(' + arg + ') / M_PI * 180';
+ break;
+ case 'ATAN':
+ code = 'atan(' + arg + ') / M_PI * 180';
+ break;
+ default:
+ throw 'Unknown math operator: ' + operator;
+ }
+ return [code, Blockly.Arduino.ORDER_MULTIPLICATIVE];
+};
+
+/**
+ * Generator for math constants (PI, E, the Golden Ratio, sqrt(2), 1/sqrt(2),
+ * INFINITY).
+ * Arduino code: loop { constant }
+ * TODO: Might need to include "#define _USE_MATH_DEFINES"
+ * The arduino header file already includes math.h
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {string} Completed code.
+ */
+Blockly.Arduino['math_constant'] = function (block) {
+ var CONSTANTS = {
+ 'PI': ['M_PI', Blockly.Arduino.ORDER_UNARY_POSTFIX],
+ 'E': ['M_E', Blockly.Arduino.ORDER_UNARY_POSTFIX],
+ 'GOLDEN_RATIO': ['(1 + sqrt(5)) / 2', Blockly.Arduino.ORDER_MULTIPLICATIVE],
+ 'SQRT2': ['M_SQRT2', Blockly.Arduino.ORDER_UNARY_POSTFIX],
+ 'SQRT1_2': ['M_SQRT1_2', Blockly.Arduino.ORDER_UNARY_POSTFIX],
+ 'INFINITY': ['INFINITY', Blockly.Arduino.ORDER_ATOMIC]
+ };
+ return CONSTANTS[block.getFieldValue('CONSTANT')];
+};
+
+/**
+ * Generator for math checks: if a number is even, odd, prime, whole, positive,
+ * negative, or if it is divisible by certain number. Returns true or false.
+ * Arduino code: complex code, can create external functions.
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_number_property'] = function (block) {
+ var number_to_check = Blockly.Arduino.valueToCode(block, 'NUMBER_TO_CHECK',
+ Blockly.Arduino.ORDER_MULTIPLICATIVE) || '0';
+ var dropdown_property = block.getFieldValue('PROPERTY');
+ var code;
+ if (dropdown_property == 'PRIME') {
+ var func = [
+ 'boolean ' + Blockly.Arduino.DEF_FUNC_NAME + '(int n) {',
+ ' // https://en.wikipedia.org/wiki/Primality_test#Naive_methods',
+ ' if (n == 2 || n == 3) {',
+ ' return true;',
+ ' }',
+ ' // False if n is NaN, negative, is 1.',
+ ' // And false if n is divisible by 2 or 3.',
+ ' if (isnan(n) || (n <= 1) || (n == 1) || (n % 2 == 0) || ' +
+ '(n % 3 == 0)) {',
+ ' return false;',
+ ' }',
+ ' // Check all the numbers of form 6k +/- 1, up to sqrt(n).',
+ ' for (int x = 6; x <= sqrt(n) + 1; x += 6) {',
+ ' if (n % (x - 1) == 0 || n % (x + 1) == 0) {',
+ ' return false;',
+ ' }',
+ ' }',
+ ' return true;',
+ '}'];
+ var funcName = Blockly.Arduino.addFunction('mathIsPrime', func.join('\n'));
+ Blockly.Arduino.addInclude('math', '#include ');
+ code = funcName + '(' + number_to_check + ')';
+ return [code, Blockly.Arduino.ORDER_UNARY_POSTFIX];
+ }
+ switch (dropdown_property) {
+ case 'EVEN':
+ code = number_to_check + ' % 2 == 0';
+ break;
+ case 'ODD':
+ code = number_to_check + ' % 2 == 1';
+ break;
+ case 'WHOLE':
+ Blockly.Arduino.addInclude('math', '#include ');
+ code = '(floor(' + number_to_check + ') == ' + number_to_check + ')';
+ break;
+ case 'POSITIVE':
+ code = number_to_check + ' > 0';
+ break;
+ case 'NEGATIVE':
+ code = number_to_check + ' < 0';
+ break;
+ case 'DIVISIBLE_BY':
+ var divisor = Blockly.Arduino.valueToCode(block, 'DIVISOR',
+ Blockly.Arduino.ORDER_MULTIPLICATIVE) || '0';
+ code = number_to_check + ' % ' + divisor + ' == 0';
+ break;
+ }
+ return [code, Blockly.Arduino.ORDER_EQUALITY];
+};
+
+/**
+ * Generator to add (Y) to a variable (X).
+ * If variable X has not been declared before this block it will be declared as
+ * a (not initialised) global int, however globals are 0 initialised in C/C++.
+ * Arduino code: loop { X += Y; }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_change'] = function (block) {
+ var argument0 = Blockly.Arduino.valueToCode(block, 'DELTA',
+ Blockly.Arduino.ORDER_ADDITIVE) || '0';
+ var varName = Blockly.Arduino.variableDB_.getName(
+ block.getFieldValue('VAR'), Blockly.Variables.NAME_TYPE);
+ return varName + ' += ' + argument0 + ';\n';
+};
+
+/** Rounding functions have a single operand. */
+Blockly.Arduino['math_round'] = Blockly.Arduino['math_single'];
+
+/** Trigonometry functions have a single operand. */
+Blockly.Arduino['math_trig'] = Blockly.Arduino['math_single'];
+
+/**
+ * Generator for the math function to a list.
+ * Arduino code: ???
+ * TODO: List have to be implemented first. Removed from toolbox for now.
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_on_list'] = Blockly.Arduino.noGeneratorCodeInline;
+
+/**
+ * Generator for the math modulo function (calculates remainder of X/Y).
+ * Arduino code: loop { X % Y }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_modulo'] = function (block) {
+ var argument0 = Blockly.Arduino.valueToCode(block, 'DIVIDEND',
+ Blockly.Arduino.ORDER_MULTIPLICATIVE) || '0';
+ var argument1 = Blockly.Arduino.valueToCode(block, 'DIVISOR',
+ Blockly.Arduino.ORDER_MULTIPLICATIVE) || '0';
+ var code = argument0 + ' % ' + argument1;
+ return [code, Blockly.Arduino.ORDER_MULTIPLICATIVE];
+};
+
+/**
+ * Generator for clipping a number(X) between two limits (Y and Z).
+ * Arduino code: loop { (X < Y ? Y : ( X > Z ? Z : X)) }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_constrain'] = function (block) {
+ // Constrain a number between two limits.
+ var argument0 = Blockly.Arduino.valueToCode(block, 'VALUE',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ var argument1 = Blockly.Arduino.valueToCode(block, 'LOW',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ var argument2 = Blockly.Arduino.valueToCode(block, 'HIGH',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ var code = '(' + argument0 + ' < ' + argument1 + ' ? ' + argument1 +
+ ' : ( ' + argument0 + ' > ' + argument2 + ' ? ' + argument2 + ' : ' +
+ argument0 + '))';
+ return [code, Blockly.Arduino.ORDER_UNARY_POSTFIX];
+};
+
+/**
+ * Generator for a random integer between two numbers (X and Y).
+ * Arduino code: loop { math_random_int(X, Y); }
+ * and an aditional math_random_int function
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {array} Completed code with order of operation.
+ */
+Blockly.Arduino['math_random_int'] = function (block) {
+ var argument0 = Blockly.Arduino.valueToCode(block, 'FROM',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ var argument1 = Blockly.Arduino.valueToCode(block, 'TO',
+ Blockly.Arduino.ORDER_NONE) || '0';
+ var functionName = Blockly.Arduino.variableDB_.getDistinctName(
+ 'math_random_int', Blockly.Generator.NAME_TYPE);
+ Blockly.Arduino.setups_['init_rand'] = 'randomSeed(analogRead(0));';
+ Blockly.Arduino.math_random_int.random_function = functionName;
+ var func = [
+ 'int ' + Blockly.Arduino.DEF_FUNC_NAME + '(int min, int max) {',
+ ' if (min > max) {',
+ ' // Swap min and max to ensure min is smaller.',
+ ' int temp = min;',
+ ' min = max;',
+ ' max = temp;',
+ ' }',
+ ' return min + (rand() % (max - min + 1));',
+ '}'];
+ var funcName = Blockly.Arduino.addFunction('mathRandomInt', func.join('\n'));
+ var code = funcName + '(' + argument0 + ', ' + argument1 + ')';
+ return [code, Blockly.Arduino.ORDER_UNARY_POSTFIX];
+};
+
+/**
+ * Generator for a random float from 0 to 1.
+ * Arduino code: loop { (rand() / RAND_MAX) }
+ * @param {!Blockly.Block} block Block to generate the code from.
+ * @return {string} Completed code.
+ */
+Blockly.Arduino['math_random_float'] = function (block) {
+ return ['(rand() / RAND_MAX)', Blockly.Arduino.ORDER_UNARY_POSTFIX];
+};
diff --git a/src/components/Blockly/helpers/board.js b/src/components/Blockly/helpers/board.js
new file mode 100644
index 0000000..f6fc279
--- /dev/null
+++ b/src/components/Blockly/helpers/board.js
@@ -0,0 +1,44 @@
+/**
+ * Define boards and pins
+ *
+ */
+const sensebox_mcu = {
+ description: 'senseBox Microcontroller Unit based on Microchip SAMD21G18A',
+ compilerFlag: 'arduino:samd',
+ digitalPins: [['D1', '1'], ['D2', '2'], ['D3', '3'], ['D4', '4'], ['D5', '5'], ['D6', '6']],
+ digitalPinsLED: [['BUILTIN_1', '7'], ['BUILTIN_2', '8'], ['D1', '1'], ['D2', '2'], ['D3', '3'], ['D4', '4'], ['D5', '5'], ['D6', '6']],
+ digitalPinsButton: [['on Board', '0'], ['D1', '1'], ['D2', '2'], ['D3', '3'], ['D4', '4'], ['D5', '5'], ['D6', '6']],
+ pwmPins: [['D1', '1'], ['D2', '2'], ['D3', '3'], ['D4', '4'], ['D5', '5'], ['D6', '6']],
+ serial: [['serial', 'SerialUSB'], ['serial_1', 'Serial1'], ['serial_2', 'Serial2']],
+ serialPins: {
+ SerialUSB: [['RX', ''], ['TX', '']],
+ Serial1: [['RX', '11'], ['TX', '10']],
+ Serial2: [['RX', '13'], ['TX', '12']]
+ },
+ serialSpeed: [['300', '300'], ['600', '600'], ['1200', '1200'],
+ ['2400', '2400'], ['4800', '4800'], ['9600', '9600'],
+ ['14400', '14400'], ['19200', '19200'], ['28800', '28800'],
+ ['31250', '31250'], ['38400', '38400'], ['57600', '57600'],
+ ['115200', '115200']],
+ spi: [['SPI', 'SPI']],
+ spiPins: { SPI: [['MOSI', '19'], ['MISO', '21'], ['SCK', '20']] },
+ spiClockDivide: [['2 (8MHz)', 'SPI_CLOCK_DIV2'],
+ ['4 (4MHz)', 'SPI_CLOCK_DIV4'],
+ ['8 (2MHz)', 'SPI_CLOCK_DIV8'],
+ ['16 (1MHz)', 'SPI_CLOCK_DIV16'],
+ ['32 (500KHz)', 'SPI_CLOCK_DIV32'],
+ ['64 (250KHz)', 'SPI_CLOCK_DIV64'],
+ ['128 (125KHz)', 'SPI_CLOCK_DIV128']],
+ i2c: [['I2C', 'Wire']],
+ i2cPins: { Wire: [['SDA', '17'], ['SCL', '16']] },
+ i2cSpeed: [['100kHz', '100000L'], ['400kHz', '400000L']],
+ builtinLed: [['BUILTIN_1', '7'], ['BUILTIN_2', '8']],
+ interrupt: [['interrupt1', '1'], ['interrupt2', '2'], , ['interrupt3', '3'], ['interrupt4', '4'], ['interrupt5', '5'], ['interrupt6', '6']],
+ analogPins: [['A1', 'A1'], ['A2', 'A2'], ['A3', 'A3'], ['A4', 'A4'], ['A5', 'A5'], ['A6', 'A6']],
+ serial_baud_rate: 9600,
+ parseKey: '_*_'
+};
+
+export const selectedBoard = () => {
+ return sensebox_mcu;
+};
diff --git a/src/components/Blockly/toolbox/Toolbox.js b/src/components/Blockly/toolbox/Toolbox.js
new file mode 100644
index 0000000..ccbf34d
--- /dev/null
+++ b/src/components/Blockly/toolbox/Toolbox.js
@@ -0,0 +1,110 @@
+import React, { Component } from 'react';
+import BlocklyComponent, { Block, Value, Field, Shadow, Category } from '../';
+
+
+class Toolbox extends React.Component {
+ constructor(props) {
+ super(props);
+ }
+
+ render() {
+ return (
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 10
+
+
+
+
+
+
+
+ 1
+
+
+
+
+ 10
+
+
+
+
+ 1
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 1
+
+
+
+
+
+
+
+
+ 1
+
+
+
+
+ 100
+
+
+
+
+
+
+ 1
+
+
+
+
+ 100
+
+
+
+
+ {/* */}
+
+
+
+
+
+
+
+ );
+ };
+}
+
+export default Toolbox;
\ No newline at end of file
diff --git a/src/components/Home.js b/src/components/Home.js
index 289b155..64b4237 100644
--- a/src/components/Home.js
+++ b/src/components/Home.js
@@ -7,8 +7,9 @@ import BlocklyComponent, { Block, Value, Field, Shadow, Category } from './Block
import * as Blockly from 'blockly/core';
import * as De from './Blockly/msg/de'; // de locale files
//import * as En from './Blockly/msg/en'; // de locale files
-import './Blockly/blocks/index';
-import './Blockly/generator/index';
+import './Blockly/blocks/';
+import './Blockly/generator/';
+
@@ -43,27 +44,7 @@ class Home extends React.Component {
drag: true,
wheel: true
}}
- initialXml={''}>
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+ initialXml={''} />
);