From 5b4bb78357fa66475863c591582ba5632afeb20b Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Tue, 12 Jan 2021 14:17:21 -0800 Subject: [PATCH 01/14] Set version to 1.5.7-alpha-2 Disable Sentry during development. --- src/modules/constants.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/modules/constants.js b/src/modules/constants.js index daf92b42..b60a98e5 100644 --- a/src/modules/constants.js +++ b/src/modules/constants.js @@ -24,7 +24,7 @@ * Global flag to enable/disable the Sentry logger * @type {boolean} */ -export const EnableSentry = true; +export const EnableSentry = false; /** * Set the application version string @@ -44,7 +44,7 @@ export const EnableSentry = true; * {b#} is the beta release number. * {rc#} is the release candidate number. */ -export const APP_VERSION = '1.5.6'; +export const APP_VERSION = '1.5.7-a2'; /** * Constant string that represents the base, empty project header From 174e58a9cac9a6731bd959fbce99d191760e5df8 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Tue, 12 Jan 2021 14:20:03 -0800 Subject: [PATCH 02/14] Update Sentry package. --- package-lock.json | 62 +++++++++++++++++++++++------------------------ package.json | 2 +- 2 files changed, 32 insertions(+), 32 deletions(-) diff --git a/package-lock.json b/package-lock.json index 32336909..0383913b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -84,59 +84,59 @@ } }, "@sentry/browser": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/browser/-/browser-5.25.0.tgz", - "integrity": "sha512-QDVUbUuTu58xCdId0eUO4YzpvrPdoUw1ryVy/Yep9Es/HD0fiSyO1Js0eQVkV/EdXtyo2pomc1Bpy7dbn2EJ2w==", + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/browser/-/browser-5.29.2.tgz", + "integrity": "sha512-uxZ7y7rp85tJll+RZtXRhXPbnFnOaxZqJEv05vJlXBtBNLQtlczV5iCtU9mZRLVHDtmZ5VVKUV8IKXntEqqDpQ==", "requires": { - "@sentry/core": "5.25.0", - "@sentry/types": "5.25.0", - "@sentry/utils": "5.25.0", + "@sentry/core": "5.29.2", + "@sentry/types": "5.29.2", + "@sentry/utils": "5.29.2", "tslib": "^1.9.3" } }, "@sentry/core": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/core/-/core-5.25.0.tgz", - "integrity": "sha512-hY6Zmo7t/RV+oZuvXHP6nyAj/QnZr2jW0e7EbL5YKMV8q0vlnjcE0LgqFXme726OJemoLk67z+sQOJic/Ztehg==", - "requires": { - "@sentry/hub": "5.25.0", - "@sentry/minimal": "5.25.0", - "@sentry/types": "5.25.0", - "@sentry/utils": "5.25.0", + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/core/-/core-5.29.2.tgz", + "integrity": "sha512-7WYkoxB5IdlNEbwOwqSU64erUKH4laavPsM0/yQ+jojM76ErxlgEF0u//p5WaLPRzh3iDSt6BH+9TL45oNZeZw==", + "requires": { + "@sentry/hub": "5.29.2", + "@sentry/minimal": "5.29.2", + "@sentry/types": "5.29.2", + "@sentry/utils": "5.29.2", "tslib": "^1.9.3" } }, "@sentry/hub": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/hub/-/hub-5.25.0.tgz", - "integrity": "sha512-kOlOiJV8wMX50lYpzMlOXBoH7MNG0Ho4RTusdZnXZBaASq5/ljngDJkLr6uylNjceZQP21wzipCQajsJMYB7EQ==", + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/hub/-/hub-5.29.2.tgz", + "integrity": "sha512-LaAIo2hwUk9ykeh9RF0cwLy6IRw+DjEee8l1HfEaDFUM6TPGlNNGObMJNXb9/95jzWp7jWwOpQjoIE3jepdQJQ==", "requires": { - "@sentry/types": "5.25.0", - "@sentry/utils": "5.25.0", + "@sentry/types": "5.29.2", + "@sentry/utils": "5.29.2", "tslib": "^1.9.3" } }, "@sentry/minimal": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/minimal/-/minimal-5.25.0.tgz", - "integrity": "sha512-9JFKuW7U+1vPO86k3+XRtJyooiVZsVOsFFO4GulBzepi3a0ckNyPgyjUY1saLH+cEHx18hu8fGgajvI8ANUF2g==", + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/minimal/-/minimal-5.29.2.tgz", + "integrity": "sha512-0aINSm8fGA1KyM7PavOBe1GDZDxrvnKt+oFnU0L+bTcw8Lr+of+v6Kwd97rkLRNOLw621xP076dL/7LSIzMuhw==", "requires": { - "@sentry/hub": "5.25.0", - "@sentry/types": "5.25.0", + "@sentry/hub": "5.29.2", + "@sentry/types": "5.29.2", "tslib": "^1.9.3" } }, "@sentry/types": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/types/-/types-5.25.0.tgz", - "integrity": "sha512-8M4PREbcar+15wrtEqcwfcU33SS+2wBSIOd/NrJPXJPTYxi49VypCN1mZBDyWkaK+I+AuQwI3XlRPCfsId3D1A==" + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/types/-/types-5.29.2.tgz", + "integrity": "sha512-dM9wgt8wy4WRty75QkqQgrw9FV9F+BOMfmc0iaX13Qos7i6Qs2Q0dxtJ83SoR4YGtW8URaHzlDtWlGs5egBiMA==" }, "@sentry/utils": { - "version": "5.25.0", - "resolved": "https://registry.npmjs.org/@sentry/utils/-/utils-5.25.0.tgz", - "integrity": "sha512-Hz5spdIkMSRH5NR1YFOp5qbsY5Ud2lKhEQWlqxcVThMG5YNUc10aYv5ijL19v0YkrC2rqPjCRm7GrVtzOc7bXQ==", + "version": "5.29.2", + "resolved": "https://registry.npmjs.org/@sentry/utils/-/utils-5.29.2.tgz", + "integrity": "sha512-nEwQIDjtFkeE4k6yIk4Ka5XjGRklNLThWLs2xfXlL7uwrYOH2B9UBBOOIRUraBm/g/Xrra3xsam/kRxuiwtXZQ==", "requires": { - "@sentry/types": "5.25.0", + "@sentry/types": "5.29.2", "tslib": "^1.9.3" } }, diff --git a/package.json b/package.json index 81f9b998..be21a3ae 100644 --- a/package.json +++ b/package.json @@ -27,7 +27,7 @@ }, "homepage": "https://github.com/parallaxinc/solo#readme", "dependencies": { - "@sentry/browser": "^5.25.0", + "@sentry/browser": "^5.29.2", "ace-builds": "^1.4.8", "blockly": "^2.20190722.1", "bootbox": "^5.4.0", From 6574ca1a9d499ff6f3145db1dfb9823fe9f844eb Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Tue, 12 Jan 2021 15:01:19 -0800 Subject: [PATCH 03/14] Webpack CopyPlugin now expects an initializer object. --- webpack/dev.config.js | 29 +++------- webpack/prod.config.js | 125 ++++++++++++++++++----------------------- 2 files changed, 65 insertions(+), 89 deletions(-) diff --git a/webpack/dev.config.js b/webpack/dev.config.js index 2e597326..80779199 100644 --- a/webpack/dev.config.js +++ b/webpack/dev.config.js @@ -51,7 +51,8 @@ module.exports = merge(baseConfig, { poll: 1000, }, plugins: [ - new CopyPlugin([ + new CopyPlugin({ + patterns: [ { from: './index.html', to: path.resolve(__dirname, targetPath) @@ -59,27 +60,15 @@ module.exports = merge(baseConfig, { { from: './blocklyc.html', to: path.resolve(__dirname, targetPath) - } - ]), - - // Copy over media resources from the Blockly package - new CopyPlugin([ + }, { from: path.resolve(__dirname, '../node_modules/blockly/media'), to: path.resolve(__dirname, `${targetPath}/media`) - } - ]), - - // Copy over media resources from Solo images tree - new CopyPlugin([ + }, { from: './src/images', to: path.resolve(__dirname, `${targetPath}/images`) - } - ]), - - // Copy over style sheets - new CopyPlugin([ + }, { from: './src/site.css', to: path.resolve(__dirname, targetPath) @@ -96,7 +85,7 @@ module.exports = merge(baseConfig, { from: './src/style-editor.css', to: path.resolve(__dirname, targetPath) } - ]), - ], - } -); + ] + } + )] +}); diff --git a/webpack/prod.config.js b/webpack/prod.config.js index ea659b4d..c73d462d 100644 --- a/webpack/prod.config.js +++ b/webpack/prod.config.js @@ -28,81 +28,68 @@ const baseConfig = require('./base.config'); // const HtmlWebpackPlugin = require('html-webpack-plugin'); module.exports = merge(baseConfig, { - // Use env. here: - // console.log('NODE_ENV: ', env.NODE_ENV); // 'local' - // console.log('Production: ', env.production); // true + // Use env. here: + // console.log('NODE_ENV: ', env.NODE_ENV); // 'local' + // console.log('Production: ', env.production); // true - mode: 'production', - devtool: 'source-map', - output: { - path: path.resolve(__dirname, '../dist'), - filename: '[name].bundle.[chunkhash].js', + mode: 'production', + devtool: 'source-map', + output: { + path: path.resolve(__dirname, '../dist'), + filename: '[name].bundle.[chunkhash].js', // chunkFilename: '[id].bundle.js', // pathinfo: true, - sourceMapFilename: '[name].bundle.[chunkhash].js.map', - }, + sourceMapFilename: '[name].bundle.[chunkhash].js.map', + }, // optimization: { // splitChunks: { // chunks: 'all', // }, // }, - module: { - rules: [ - { - test: /\.css$/, - use: [ - 'style-loader', - 'css-loader' - ] - } + module: { + rules: [ + { + test: /\.css$/, + use: [ + 'style-loader', + 'css-loader' ] - }, - plugins: [ - new CopyPlugin([ - { - from: './index.html', - to: path.resolve(__dirname, '../dist') - }, - { - from: './blocklyc.html', - to: path.resolve(__dirname, '../dist') - } - ]), - - // Copy over media resources from the Blockly package - new CopyPlugin([ - { - from: path.resolve(__dirname, '../node_modules/blockly/media'), - to: path.resolve(__dirname, '../dist/media') - } - ]), - - // Copy over media resources from Solo images tree - new CopyPlugin([ - { - from: './src/images', - to: path.resolve(__dirname, '../dist/images') - } - ]), - - // Copy over style sheets - new CopyPlugin([ - { - from: './src/site.css', - to: path.resolve(__dirname, '../dist') - }, - { - from: './src/style.css', - to: path.resolve(__dirname, '../dist') - }, - { - from: './src/style-clientdownload.css', - to: path.resolve(__dirname, '../dist') - }, - { - from: './src/style-editor.css', - to: path.resolve(__dirname, '../dist') - }, - ]), - ], - }); + } + ]}, + plugins: [ + new CopyPlugin({ + patterns: [ + { + from: './index.html', + to: path.resolve(__dirname, '../dist') + }, + { + from: './blocklyc.html', + to: path.resolve(__dirname, '../dist') + }, + { + // Copy over media resources from the Blockly package + from: path.resolve(__dirname, '../node_modules/blockly/media'), + to: path.resolve(__dirname, '../dist/media') + }, + { + // Copy over style sheets + from: './src/site.css', + to: path.resolve(__dirname, '../dist') + }, + { + from: './src/style.css', + to: path.resolve(__dirname, '../dist') + }, + { + from: './src/style-clientdownload.css', + to: path.resolve(__dirname, '../dist') + }, + { + from: './src/style-editor.css', + to: path.resolve(__dirname, '../dist') + }, + ] + }) + ] +}); From 6852340e3beed1f9211712b599a824b6f8c837fe Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Tue, 12 Jan 2021 15:10:31 -0800 Subject: [PATCH 04/14] Refactor serial_receive_text. Add comments. --- .../blockly/generators/propc/communicate.js | 50 ++++++++++++------- 1 file changed, 32 insertions(+), 18 deletions(-) diff --git a/src/modules/blockly/generators/propc/communicate.js b/src/modules/blockly/generators/propc/communicate.js index 1f4ec3a9..036c04e0 100644 --- a/src/modules/blockly/generators/propc/communicate.js +++ b/src/modules/blockly/generators/propc/communicate.js @@ -1527,46 +1527,60 @@ Blockly.Blocks.serial_receive_text = { onchange: Blockly.Blocks['serial_send_text'].onchange, }; + /** * Serial Receive Text code generator * @return {string} + * @description Generate C source code to scan data from a serial port input. */ Blockly.propc.serial_receive_text = function() { let p = ''; + + /* Is a serial pin defined? */ if (this.ser_pins.length > 0) { - p = this.ser_pins[0].replace(',', '_').replace(/None/g, 'N'); + p = this.ser_pins[0] + .replace(',', '_') // Replace commas with underscores + .replace(/None/g, 'N'); // Replace 'None' with 'N' in all occurrences. } + + /* Get serial pins in use */ if (this.getInput('SERPIN')) { p = this.getFieldValue('SER_PIN') .replace(',', '_') .replace(/None/g, 'N'); } - const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); - if (allBlocks.indexOf('Serial initialize') === -1) { + + if (! Blockly.getMainWorkspace() + .getBlocksByType('Serial initialize', false)) { return '// ERROR: Serial is not initialized!\n'; } else { - const data = Blockly.propc.variableDB_.getName( - this.getFieldValue('VALUE'), - Blockly.VARIABLE_CATEGORY_NAME); + const data = Blockly.propc.variableDB_ + .getName(this.getFieldValue('VALUE'), Blockly.VARIABLE_CATEGORY_NAME); - const type = this.getFieldValue('TYPE'); + switch (this.getFieldValue('TYPE')) { + case 'BYTE': + return data + ' = fdserial_rxChar(fdser' + p + ');\n'; - if (type === 'BYTE') { - return data + ' = fdserial_rxChar(fdser' + p + ');\n'; - } else if (type === 'INT') { - return 'dscan(fdser' + p + ', "%d", &' + data + ');\n'; - } else if (type === 'BIN') { - return 'dscan(fdser' + p + ', "%b", &' + data + ');\n'; - } else if (type === 'HEX') { - return 'dscan(fdser' + p + ', "%x", &' + data + ');\n'; - } else { - Blockly.propc.vartype_[data] = 'char *'; + case 'INT': + return 'dscan(fdser' + p + ', "%d", &' + data + ');\n'; - return 'dscan(fdser' + p + ', "%s", ' + data + ');\n'; + case 'BIN': + return 'dscan(fdser' + p + ', "%b", &' + data + ');\n'; + + case 'HEX': + return 'dscan(fdser' + p + ', "%x", &' + data + ');\n'; + + case 'TEXT': + default: + Blockly.propc.vartype_[data] = 'char *'; } + + // This will return a string up to the first whitespace character. + return 'dscan(fdser' + p + ', "%s", ' + data + ');\n'; } }; + /** * Serial Status block definition * @type {{ From bb52f0147c61ae07d3bda3367af85cb1b1920314 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Tue, 12 Jan 2021 16:20:54 -0800 Subject: [PATCH 05/14] Solo-521. Remove regex expression. Refactor code block. --- .../blockly/generators/propc/communicate.js | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/modules/blockly/generators/propc/communicate.js b/src/modules/blockly/generators/propc/communicate.js index 036c04e0..d8f5c090 100644 --- a/src/modules/blockly/generators/propc/communicate.js +++ b/src/modules/blockly/generators/propc/communicate.js @@ -836,23 +836,23 @@ Blockly.propc.console_print_multiple = function() { orIt = '0'; } + // Get the resulting code from Blockly core + const result = Blockly.propc.valueToCode( + this, 'PRINT' + i, Blockly.propc.ORDER_NONE) || orIt; + if (!this.getFieldValue('TYPE' + i).includes('float point divide by')) { - varList += ', ' + (Blockly.propc.valueToCode( - this, - 'PRINT' + i, - Blockly.propc.ORDER_NONE).replace(/%/g, '%%') || orIt); + varList += ', ' + result; } else { - varList += ', ((float) ' + (Blockly.propc.valueToCode( - this, - 'PRINT' + i, - Blockly.propc.ORDER_NONE) || orIt) + - ') / ' + this.getFieldValue('DIV' + i) + '.0'; + varList += ', ((float) ' + result + ') / ' + + this.getFieldValue('DIV' + i) + '.0'; } i++; } + if (this.getFieldValue('ck_nl') === 'TRUE') { code += '\\r'; } + code += '"' + varList + ');\n'; // TODO: Replace .getAllBlocks() with getAllBlocksByType() From 64bf89ed1b349c362dece24dfbec46c76a2cd9f7 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Fri, 15 Jan 2021 17:48:27 -0800 Subject: [PATCH 06/14] Refactor sd_read code emitter. Correct SD_read number input accepting string text. --- src/modules/blockly/generators/propc/gpio.js | 91 +++++++++++++------- 1 file changed, 58 insertions(+), 33 deletions(-) diff --git a/src/modules/blockly/generators/propc/gpio.js b/src/modules/blockly/generators/propc/gpio.js index 69300839..6d558586 100644 --- a/src/modules/blockly/generators/propc/gpio.js +++ b/src/modules/blockly/generators/propc/gpio.js @@ -2249,7 +2249,9 @@ Blockly.propc.wav_stop = function() { return 'wav_stop();\n'; }; +// ---------------------------------------------------------------- // ----------------- SD Card file blocks -------------------------- +// ---------------------------------------------------------------- /** * SD Card Initialization @@ -2378,15 +2380,15 @@ Blockly.propc.sd_open = function() { } if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');\r'; } - let code = head + 'fp = fopen("' + fp + '","' + mode + '");'; + let code = head + 'fp = fopen("' + fp + '","' + mode + '");\r'; if (project.boardType.name !== 'activity-board' && project.boardType.name !== 'heb-wx' && allBlocks.toString().indexOf('SD initialize') === -1) { code = '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; + ' beginning of your program!\r'; } return code; }; @@ -2438,8 +2440,9 @@ Blockly.Blocks.sd_read = { this.removeInput('VALUE'); } if (mode === 'fwrite') { + // Ensure that the field only receives numeric data this.appendValueInput('SIZE') - .setCheck(null) + .setCheck('Number') .appendField('SD file') .appendField(new Blockly.FieldDropdown([ ['write', 'fwrite'], @@ -2505,15 +2508,55 @@ Blockly.Blocks.sd_read = { }; /** - * SD Card Read C code generator + * SD Card Read/Write/Close C code generator + * + * Generate code to read from an sd card, write to an sd card or to close a + * connection to the sd card reader. + * * @return {string} */ Blockly.propc.sd_read = function() { + // Identify the block action (fread, fwrite, or fclose) + const mode = this.getFieldValue('MODE'); + + // Handle close stright away + if (mode === 'fclose') { + return ` if(fp) ${mode}(fp);`; + } + + // Verify the required SD-Open block is in the project + const block = Blockly.getMainWorkspace().getBlocksByType( + 'sd_open', false); + + if ( block.length === 0 || (!block[0].isEnabled())) { + return '// WARNING: You must use a SD file open block before reading,' + + ' writing, or closing an SD file!'; + } + + /** + * Verify that for boards that do not have a built-in card reader, there is + * an sd_init block in the project + */ const project = getProjectInitialState(); - const profile = getDefaultProfile(); + let initFound = false; + + const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { + initFound = true; + } + + if (project.boardType.name !== 'heb-wx' && + project.boardType.name !== 'activity-board' && + ! initFound) { + return '// WARNING: You must use a SD initialize block at the' + + ' beginning of your program!'; + } + + // Retreive the number of bytes to read/write. Default to one byte const size = Blockly.propc.valueToCode( this, 'SIZE', Blockly.propc.ORDER_NONE) || '1'; - const mode = this.getFieldValue('MODE'); + let value = ''; let code = ''; @@ -2521,6 +2564,7 @@ Blockly.propc.sd_read = function() { value = Blockly.propc.variableDB_.getName( this.getFieldValue('VAR'), Blockly.VARIABLE_CATEGORY_NAME); + value = '&' + value; Blockly.propc.vartype_[value] = 'char *'; } else if (mode === 'fwrite') { @@ -2528,31 +2572,10 @@ Blockly.propc.sd_read = function() { this, 'VALUE', Blockly.propc.ORDER_NONE) || ''; } - if (mode === 'fclose') { - code = mode + '(fp);'; - } else { - code = mode + '(' + value + ', 1, ' + size + ', fp);'; - // code = mode + '(&' + value + ', 1, ' + size + ', fp);'; - } - - const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); - if (allBlocks.indexOf('SD file open') === -1) { - code = '// WARNING: You must use a SD file open block before reading,' + - ' writing, or closing an SD file!'; - } else if (allBlocks.indexOf('SD initialize') === -1 && - project.boardType.name !== 'heb-wx' && - project.boardType.name !== 'activity-board') { - code = '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; - } - - let initFound = false; - for (let x = 0; x < allBlocks.length; x++) { - if (allBlocks[x].type === 'sd_init') { - initFound = true; - } - } + code = ` ${mode}(${value}, 1, ${size}, fp);\r`; + // Silently mount the embedded sd card device + const profile = getDefaultProfile(); if (!this.disabled && !initFound && profile.sd_card) { Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; } @@ -2603,6 +2626,7 @@ Blockly.Blocks.sd_file_pointer = { this.setPreviousStatement(true, 'Block'); this.setNextStatement(true, null); } else { + // mode == get this.appendDummyInput('FP'); this.getInput('FP') .appendField('SD file') @@ -2614,7 +2638,8 @@ Blockly.Blocks.sd_file_pointer = { this.getSourceBlock().setSdMode(blockMode); }), 'MODE') .appendField('pointer'); - this.setPreviousStatement(false, 'Block'); + + this.setPreviousStatement(false); this.setNextStatement(false, null); this.setOutput(true, 'Number'); } @@ -2654,7 +2679,7 @@ Blockly.propc.sd_file_pointer = function() { } else if (this.getFieldValue('MODE') === 'set') { const fp = Blockly.propc.valueToCode( this, 'FP', Blockly.propc.ORDER_NONE) || '0'; - code = 'fp = ' + fp + ';'; + code = 'fp = ' + fp + ';\r'; } else { code = ['fp', Blockly.propc.ORDER_ATOMIC]; } From 790296689ba60d57bfd20c998ae0365aa5277c6b Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Fri, 15 Jan 2021 23:21:37 -0800 Subject: [PATCH 07/14] SD card file handle is now a global. Correct more cases where check for sd_init was ignoring the enabled state. Correct missing line feeds in code emitters. --- src/modules/blockly/generators/propc/gpio.js | 64 +++++++++++--------- 1 file changed, 34 insertions(+), 30 deletions(-) diff --git a/src/modules/blockly/generators/propc/gpio.js b/src/modules/blockly/generators/propc/gpio.js index 6d558586..53495d18 100644 --- a/src/modules/blockly/generators/propc/gpio.js +++ b/src/modules/blockly/generators/propc/gpio.js @@ -2289,12 +2289,19 @@ Blockly.Blocks.sd_init = { * @return {string} */ Blockly.propc.sd_init = function() { + // Global variable for SD file processing + this.myType = 'fp'; + if (!this.disabled) { Blockly.propc.setups_['sd_card'] = 'sd_mount(' + this.getFieldValue('DO') + ', ' + this.getFieldValue('CLK') + ', ' + this.getFieldValue('DI') + ', ' + this.getFieldValue('CS') + ');'; + + // Declare the global variable + Blockly.propc.global_vars_[ + this.myType + 'global'] = 'FILE *' + this.myType + ';'; } return ''; @@ -2338,12 +2345,18 @@ Blockly.Blocks.sd_open = { this.setPreviousStatement(true, 'Block'); this.setNextStatement(true, null); }, + + /** + * Check for an active sd_init block in the project. The block must exist + * and not be disabled. + */ onchange: function() { const project = getProjectInitialState(); if (project.boardType.name !== 'activity-board' && project.boardType.name !== 'heb-wx') { - const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); - if (allBlocks.indexOf('SD initialize') === -1) { + const block = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (block.length === 0 || ! block[0].isEnabled()) { this.setWarningText('WARNING: You must use a SD' + ' initialize\nblock at the beginning of your program!'); } else { @@ -2358,39 +2371,30 @@ Blockly.Blocks.sd_open = { * @return {string} */ Blockly.propc.sd_open = function() { - const profile = getDefaultProfile(); - const project = getProjectInitialState(); - const fp = this.getFieldValue('FILENAME'); + const filename = this.getFieldValue('FILENAME'); const mode = this.getFieldValue('MODE'); - let head = ''; - let i = 0; let initFound = false; - const allBlocks = Blockly.getMainWorkspace().getAllBlocks(); - for (let x = 0; x < allBlocks.length; x++) { - if (allBlocks[x].type === 'sd_open') { - i++; - if (allBlocks[x] === this && i === 1) { - head = 'FILE* '; - } - } - if (allBlocks[x].type === 'sd_init') { - initFound = true; + const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { + initFound = true; + } else { + const project = getProjectInitialState(); + if (project.boardType.name !== 'activity-board' && + project.boardType.name !== 'heb-wx') { + return '/** WARNING: You must use a SD initialize block at the' + + ' beginning of your program! **/\r'; } } + // Quietly mount the sd card filesystem + const profile = getDefaultProfile(); if (!this.disabled && !initFound && profile.sd_card) { Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');\r'; } - let code = head + 'fp = fopen("' + fp + '","' + mode + '");\r'; - if (project.boardType.name !== 'activity-board' && - project.boardType.name !== 'heb-wx' && - allBlocks.toString().indexOf('SD initialize') === -1) { - code = '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!\r'; - } - return code; + return `fp = fopen("${filename}","${mode}");\r`; }; /** @@ -2521,7 +2525,7 @@ Blockly.propc.sd_read = function() { // Handle close stright away if (mode === 'fclose') { - return ` if(fp) ${mode}(fp);`; + return ` if(fp) ${mode}(fp);\r`; } // Verify the required SD-Open block is in the project @@ -2530,7 +2534,7 @@ Blockly.propc.sd_read = function() { if ( block.length === 0 || (!block[0].isEnabled())) { return '// WARNING: You must use a SD file open block before reading,' + - ' writing, or closing an SD file!'; + ' writing, or closing an SD file!\r'; } /** @@ -2549,11 +2553,11 @@ Blockly.propc.sd_read = function() { if (project.boardType.name !== 'heb-wx' && project.boardType.name !== 'activity-board' && ! initFound) { - return '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; + return '/** WARNING: You must use a SD initialize block at the' + + ' beginning of your program! **/\r'; } - // Retreive the number of bytes to read/write. Default to one byte + // Retrieve the number of bytes to read/write. Default to one byte const size = Blockly.propc.valueToCode( this, 'SIZE', Blockly.propc.ORDER_NONE) || '1'; From fbf12941ad4edb9e073ada8a0e932a5317c61f0b Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 07:46:58 -0800 Subject: [PATCH 08/14] Refactor SD card blocks into separate module. --- src/modules/blockly/generators/propc/gpio.js | 440 ----------------- .../blockly/generators/propc/sd_card.js | 467 ++++++++++++++++++ src/modules/editor.js | 1 + 3 files changed, 468 insertions(+), 440 deletions(-) create mode 100644 src/modules/blockly/generators/propc/sd_card.js diff --git a/src/modules/blockly/generators/propc/gpio.js b/src/modules/blockly/generators/propc/gpio.js index 53495d18..269122fb 100644 --- a/src/modules/blockly/generators/propc/gpio.js +++ b/src/modules/blockly/generators/propc/gpio.js @@ -2249,446 +2249,6 @@ Blockly.propc.wav_stop = function() { return 'wav_stop();\n'; }; -// ---------------------------------------------------------------- -// ----------------- SD Card file blocks -------------------------- -// ---------------------------------------------------------------- - -/** - * SD Card Initialization - * @type {{ - * init: Blockly.Blocks.sd_init.init, - * helpUrl: string - * }} - */ -Blockly.Blocks.sd_init = { - helpUrl: Blockly.MSG_SD_HELPURL, - init: function() { - const profile = getDefaultProfile(); - this.setTooltip(Blockly.MSG_SD_INIT_TOOLTIP); - this.setColour(colorPalette.getColor('output')); - this.appendDummyInput() - .appendField('SD initialize DO') - .appendField(new Blockly.FieldDropdown( - profile.digital), 'DO') - .appendField('CLK') - .appendField(new Blockly.FieldDropdown( - profile.digital), 'CLK') - .appendField('DI') - .appendField(new Blockly.FieldDropdown( - profile.digital), 'DI') - .appendField('CS') - .appendField(new Blockly.FieldDropdown( - profile.digital), 'CS'), - this.setPreviousStatement(true, 'Block'); - this.setNextStatement(true, null); - }, -}; - -/** - * - * @return {string} - */ -Blockly.propc.sd_init = function() { - // Global variable for SD file processing - this.myType = 'fp'; - - if (!this.disabled) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + - this.getFieldValue('DO') + ', ' + - this.getFieldValue('CLK') + ', ' + - this.getFieldValue('DI') + ', ' + - this.getFieldValue('CS') + ');'; - - // Declare the global variable - Blockly.propc.global_vars_[ - this.myType + 'global'] = 'FILE *' + this.myType + ';'; - } - - return ''; -}; - -/** - * - * @type {{ - * init: Blockly.Blocks.sd_open.init, - * helpUrl: string, - * onchange: Blockly.Blocks.sd_open.onchange - * }} - */ -Blockly.Blocks.sd_open = { - helpUrl: Blockly.MSG_SD_HELPURL, - init: function() { - this.setTooltip(Blockly.MSG_SD_OPEN_TOOLTIP); - this.setColour(colorPalette.getColor('output')); - this.appendDummyInput('MODE') - .appendField('SD file open') - .appendField(new Blockly.FieldTextInput( - 'filename.txt', - function(filename) { - filename = filename.replace(/[^A-Z0-9a-z_.]/g, '').toLowerCase(); - const filenamePart = filename.split('.'); - if (filenamePart[0].length > 8) { - filenamePart[0].length = 8; - } - if (!filenamePart[1]) { - filenamePart[1] = 'TXT'; - } else if (filenamePart[1].length > 3) { - filenamePart[1].length = 3; - } - return filenamePart[0] + '.' + filenamePart[1]; - }), 'FILENAME') - .appendField(new Blockly.FieldDropdown([ - ['as read-only', 'r'], - ['as read-write', 'w'], - ]), 'MODE'); - this.setInputsInline(false); - this.setPreviousStatement(true, 'Block'); - this.setNextStatement(true, null); - }, - - /** - * Check for an active sd_init block in the project. The block must exist - * and not be disabled. - */ - onchange: function() { - const project = getProjectInitialState(); - if (project.boardType.name !== 'activity-board' && - project.boardType.name !== 'heb-wx') { - const block = Blockly.getMainWorkspace().getBlocksByType( - 'sd_init', false); - if (block.length === 0 || ! block[0].isEnabled()) { - this.setWarningText('WARNING: You must use a SD' + - ' initialize\nblock at the beginning of your program!'); - } else { - this.setWarningText(null); - } - } - }, -}; - -/** - * SD Card Open C code generator - * @return {string} - */ -Blockly.propc.sd_open = function() { - const filename = this.getFieldValue('FILENAME'); - const mode = this.getFieldValue('MODE'); - let initFound = false; - - const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( - 'sd_init', false); - if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { - initFound = true; - } else { - const project = getProjectInitialState(); - if (project.boardType.name !== 'activity-board' && - project.boardType.name !== 'heb-wx') { - return '/** WARNING: You must use a SD initialize block at the' + - ' beginning of your program! **/\r'; - } - } - - // Quietly mount the sd card filesystem - const profile = getDefaultProfile(); - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');\r'; - } - - return `fp = fopen("${filename}","${mode}");\r`; -}; - -/** - * - * @type {{ - * init: Blockly.Blocks.sd_read.init, - * mutationToDom: (function(): HTMLElement), - * helpUrl: string, - * setSdMode: Blockly.Blocks.sd_read.setSdMode, - * onchange: Blockly.Blocks.sd_read.onchange, - * domToMutation: Blockly.Blocks.sd_read.domToMutation - * }} - */ -Blockly.Blocks.sd_read = { - helpUrl: Blockly.MSG_SD_HELPURL, - init: function() { - this.setTooltip(Blockly.MSG_SD_READ_TOOLTIP); - this.setColour(colorPalette.getColor('output')); - this.setSdMode('fwrite'); - this.setInputsInline(true); - this.setPreviousStatement(true, 'Block'); - this.setNextStatement(true, null); - }, - mutationToDom: function() { - const container = document.createElement('mutation'); - container.setAttribute('mode', this.getFieldValue('MODE')); - return container; - }, - domToMutation: function(container) { - const mode = container.getAttribute('mode'); - if (mode) { - this.setFieldValue(mode, 'MODE'); - } - this.setSdMode(mode); - }, - setSdMode: function(mode) { - let connectedBlock = null; - - if (this.getInput('SIZE')) { - const valueConnection = this.getInput('SIZE').connection; - if (valueConnection) { - connectedBlock = valueConnection.targetBlock(); - } - this.removeInput('SIZE'); - } - if (this.getInput('VALUE')) { - this.removeInput('VALUE'); - } - if (mode === 'fwrite') { - // Ensure that the field only receives numeric data - this.appendValueInput('SIZE') - .setCheck('Number') - .appendField('SD file') - .appendField(new Blockly.FieldDropdown([ - ['write', 'fwrite'], - ['read', 'fread'], - ['close', 'fclose'], - ], function(mode) { - // eslint-disable-next-line no-invalid-this - this.getSourceBlock().setSdMode(mode); - }), 'MODE'); - this.appendValueInput('VALUE') - .setCheck('String') - .appendField('bytes of'); - } else if (mode === 'fread') { - this.appendValueInput('SIZE') - .setCheck('Number') - .appendField('SD file') - .appendField(new Blockly.FieldDropdown([ - ['read', 'fread'], - ['write', 'fwrite'], - ['close', 'fclose'], - ], function(mode) { - // eslint-disable-next-line no-invalid-this - this.getSourceBlock().setSdMode(mode); - }), 'MODE'); - this.appendDummyInput('VALUE') - .appendField('bytes store in') - .appendField(new Blockly.FieldVariable( - Blockly.LANG_VARIABLES_SET_ITEM), 'VAR'); - } else { - this.appendDummyInput('SIZE') - .appendField('SD file') - .appendField(new Blockly.FieldDropdown([ - ['close', 'fclose'], - ['read', 'fread'], - ['write', 'fwrite'], - ], function(mode) { - // eslint-disable-next-line no-invalid-this - this.getSourceBlock().setSdMode(mode); - }), 'MODE'); - } - if (connectedBlock) { - connectedBlock.outputConnection.connect(this.getInput('SIZE').connection); - } - }, - onchange: function(event) { - const project = getProjectInitialState(); - if (event.type === Blockly.Events.BLOCK_DELETE || - event.type === Blockly.Events.BLOCK_CREATE) { - let warnTxt = null; - const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); - if (allBlocks.indexOf('SD file open') === -1) { - warnTxt = 'WARNING: You must use a SD file open block\nbefore' + - ' reading, writing, or closing an SD file!'; - } else if (allBlocks.indexOf('SD initialize') === -1 && - project.boardType.name !== 'heb-wx' && - project.boardType.name !== 'activity-board') { - warnTxt = 'WARNING: You must use a SD initialize\nblock at the' + - ' beginning of your program!'; - } - this.setWarningText(warnTxt); - } - }, -}; - -/** - * SD Card Read/Write/Close C code generator - * - * Generate code to read from an sd card, write to an sd card or to close a - * connection to the sd card reader. - * - * @return {string} - */ -Blockly.propc.sd_read = function() { - // Identify the block action (fread, fwrite, or fclose) - const mode = this.getFieldValue('MODE'); - - // Handle close stright away - if (mode === 'fclose') { - return ` if(fp) ${mode}(fp);\r`; - } - - // Verify the required SD-Open block is in the project - const block = Blockly.getMainWorkspace().getBlocksByType( - 'sd_open', false); - - if ( block.length === 0 || (!block[0].isEnabled())) { - return '// WARNING: You must use a SD file open block before reading,' + - ' writing, or closing an SD file!\r'; - } - - /** - * Verify that for boards that do not have a built-in card reader, there is - * an sd_init block in the project - */ - const project = getProjectInitialState(); - let initFound = false; - - const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( - 'sd_init', false); - if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { - initFound = true; - } - - if (project.boardType.name !== 'heb-wx' && - project.boardType.name !== 'activity-board' && - ! initFound) { - return '/** WARNING: You must use a SD initialize block at the' + - ' beginning of your program! **/\r'; - } - - // Retrieve the number of bytes to read/write. Default to one byte - const size = Blockly.propc.valueToCode( - this, 'SIZE', Blockly.propc.ORDER_NONE) || '1'; - - let value = ''; - let code = ''; - - if (mode === 'fread') { - value = Blockly.propc.variableDB_.getName( - this.getFieldValue('VAR'), - Blockly.VARIABLE_CATEGORY_NAME); - - value = '&' + value; - Blockly.propc.vartype_[value] = 'char *'; - } else if (mode === 'fwrite') { - value = Blockly.propc.valueToCode( - this, 'VALUE', Blockly.propc.ORDER_NONE) || ''; - } - - code = ` ${mode}(${value}, 1, ${size}, fp);\r`; - - // Silently mount the embedded sd card device - const profile = getDefaultProfile(); - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; - } - - return code; -}; - -/** - * - * @type {{ - * init: Blockly.Blocks.sd_file_pointer.init, - * mutationToDom: *, - * helpUrl: string, - * setSdMode: Blockly.Blocks.sd_file_pointer.setSdMode, - * onchange: *, - * domToMutation: * - * }} - */ -Blockly.Blocks.sd_file_pointer = { - helpUrl: Blockly.MSG_SD_HELPURL, - init: function() { - this.setTooltip(Blockly.MSG_SD_FILE_POINTER_TOOLTIP); - this.setColour(colorPalette.getColor('output')); - this.setSdMode('set'); - this.setInputsInline(false); - this.setPreviousStatement(true, 'Block'); - this.setNextStatement(true, null); - }, - mutationToDom: Blockly.Blocks['sd_read'].mutationToDom, - domToMutation: Blockly.Blocks['sd_read'].domToMutation, - setSdMode: function(mode) { - if (this.getInput('FP')) { - this.removeInput('FP'); - } - if (mode === 'set') { - this.appendValueInput('FP') - .setCheck('Number') - .appendField('SD file') - .appendField(new Blockly.FieldDropdown([ - ['set', 'set'], - ['get', 'get'], - ], function(blockMode) { - // eslint-disable-next-line no-invalid-this - this.getSourceBlock().setSdMode(blockMode); - }), 'MODE') - .appendField('pointer = '); - this.setOutput(false); - this.setPreviousStatement(true, 'Block'); - this.setNextStatement(true, null); - } else { - // mode == get - this.appendDummyInput('FP'); - this.getInput('FP') - .appendField('SD file') - .appendField(new Blockly.FieldDropdown([ - ['get', 'get'], - ['set', 'set'], - ], function(blockMode) { - // eslint-disable-next-line no-invalid-this - this.getSourceBlock().setSdMode(blockMode); - }), 'MODE') - .appendField('pointer'); - - this.setPreviousStatement(false); - this.setNextStatement(false, null); - this.setOutput(true, 'Number'); - } - }, - onchange: Blockly.Blocks['sd_read'].onchange, -}; - -/** - * SD Card File Pointer - * @return {(string|number)[]|string} - */ -Blockly.propc.sd_file_pointer = function() { - const profile = getDefaultProfile(); - const project = getProjectInitialState(); - // TODO: Refactor getAllBlocks to getAllBlocksByType - const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); - let code = null; - let initFound = false; - for (let x = 0; x < allBlocks.length; x++) { - if (allBlocks[x].type === 'sd_init') { - initFound = true; - } - } - - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; - } - - if (allBlocks.indexOf('SD file open') === -1) { - code = '// WARNING: You must use a SD file open block before' + - ' using the file pointer!'; - } else if (allBlocks.indexOf('SD initialize') === -1 && - project.boardType.name !== 'heb-wx' && - project.boardType.name !== 'activity-board') { - code = '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; - } else if (this.getFieldValue('MODE') === 'set') { - const fp = Blockly.propc.valueToCode( - this, 'FP', Blockly.propc.ORDER_NONE) || '0'; - code = 'fp = ' + fp + ';\r'; - } else { - code = ['fp', Blockly.propc.ORDER_ATOMIC]; - } - return code; -}; // ----------------- Robot (drive) blocks ------------------------------------ diff --git a/src/modules/blockly/generators/propc/sd_card.js b/src/modules/blockly/generators/propc/sd_card.js new file mode 100644 index 00000000..e2972a19 --- /dev/null +++ b/src/modules/blockly/generators/propc/sd_card.js @@ -0,0 +1,467 @@ +/* + * TERMS OF USE: MIT License + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +import Blockly from 'blockly/core'; +import {getDefaultProfile, getProjectInitialState} from '../../../project'; +import {colorPalette} from '../propc'; + +// ---------------------------------------------------------------- +// ----------------- SD Card file blocks -------------------------- +// ---------------------------------------------------------------- + + +/** + * SD Card Initialization + * @type {{ + * init: Blockly.Blocks.sd_init.init, + * helpUrl: string + * }} + */ +Blockly.Blocks.sd_init = { + helpUrl: Blockly.MSG_SD_HELPURL, + init: function() { + const profile = getDefaultProfile(); + this.setTooltip(Blockly.MSG_SD_INIT_TOOLTIP); + this.setColour(colorPalette.getColor('output')); + this.appendDummyInput() + .appendField('SD initialize DO') + .appendField(new Blockly.FieldDropdown( + profile.digital), 'DO') + .appendField('CLK') + .appendField(new Blockly.FieldDropdown( + profile.digital), 'CLK') + .appendField('DI') + .appendField(new Blockly.FieldDropdown( + profile.digital), 'DI') + .appendField('CS') + .appendField(new Blockly.FieldDropdown( + profile.digital), 'CS'), + this.setPreviousStatement(true, 'Block'); + this.setNextStatement(true, null); + }, +}; + +/** + * + * @return {string} + */ +Blockly.propc.sd_init = function() { + // Global variable for SD file processing + this.myType = 'fp'; + + if (!this.disabled) { + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + + this.getFieldValue('DO') + ', ' + + this.getFieldValue('CLK') + ', ' + + this.getFieldValue('DI') + ', ' + + this.getFieldValue('CS') + ');'; + + // Declare the global variable + Blockly.propc.global_vars_[ + this.myType + 'global'] = 'FILE *' + this.myType + ';'; + } + + return ''; +}; + +/** + * + * @type {{ + * init: Blockly.Blocks.sd_open.init, + * helpUrl: string, + * onchange: Blockly.Blocks.sd_open.onchange + * }} + */ +Blockly.Blocks.sd_open = { + helpUrl: Blockly.MSG_SD_HELPURL, + init: function() { + this.setTooltip(Blockly.MSG_SD_OPEN_TOOLTIP); + this.setColour(colorPalette.getColor('output')); + this.appendDummyInput('MODE') + .appendField('SD file open') + .appendField(new Blockly.FieldTextInput( + 'filename.txt', + function(filename) { + filename = filename.replace(/[^A-Z0-9a-z_.]/g, '').toLowerCase(); + const filenamePart = filename.split('.'); + if (filenamePart[0].length > 8) { + filenamePart[0].length = 8; + } + if (!filenamePart[1]) { + filenamePart[1] = 'TXT'; + } else if (filenamePart[1].length > 3) { + filenamePart[1].length = 3; + } + return filenamePart[0] + '.' + filenamePart[1]; + }), 'FILENAME') + .appendField(new Blockly.FieldDropdown([ + ['as read-only', 'r'], + ['as read-write', 'w'], + ]), 'MODE'); + this.setInputsInline(false); + this.setPreviousStatement(true, 'Block'); + this.setNextStatement(true, null); + }, + + /** + * Check for an active sd_init block in the project. The block must exist + * and not be disabled. + */ + onchange: function() { + const project = getProjectInitialState(); + if (project.boardType.name !== 'activity-board' && + project.boardType.name !== 'heb-wx') { + const block = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (block.length === 0 || ! block[0].isEnabled()) { + this.setWarningText('WARNING: You must use a SD' + + ' initialize\nblock at the beginning of your program!'); + } else { + this.setWarningText(null); + } + } + }, +}; + +/** + * SD Card Open C code generator + * @return {string} + */ +Blockly.propc.sd_open = function() { + const filename = this.getFieldValue('FILENAME'); + const mode = this.getFieldValue('MODE'); + let initFound = false; + + const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { + initFound = true; + } else { + const project = getProjectInitialState(); + if (project.boardType.name !== 'activity-board' && + project.boardType.name !== 'heb-wx') { + return '/** WARNING: You must use a SD initialize block at the' + + ' beginning of your program! **/\r'; + } + } + + // Quietly mount the sd card filesystem + const profile = getDefaultProfile(); + if (!this.disabled && !initFound && profile.sd_card) { + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');\r'; + } + + return `fp = fopen("${filename}","${mode}");\r`; +}; + +/** + * + * @type {{ + * init: Blockly.Blocks.sd_read.init, + * mutationToDom: (function(): HTMLElement), + * helpUrl: string, + * setSdMode: Blockly.Blocks.sd_read.setSdMode, + * onchange: Blockly.Blocks.sd_read.onchange, + * domToMutation: Blockly.Blocks.sd_read.domToMutation + * }} + */ +Blockly.Blocks.sd_read = { + helpUrl: Blockly.MSG_SD_HELPURL, + init: function() { + this.setTooltip(Blockly.MSG_SD_READ_TOOLTIP); + this.setColour(colorPalette.getColor('output')); + this.setSdMode('fwrite'); + this.setInputsInline(true); + this.setPreviousStatement(true, 'Block'); + this.setNextStatement(true, null); + }, + mutationToDom: function() { + const container = document.createElement('mutation'); + container.setAttribute('mode', this.getFieldValue('MODE')); + return container; + }, + domToMutation: function(container) { + const mode = container.getAttribute('mode'); + if (mode) { + this.setFieldValue(mode, 'MODE'); + } + this.setSdMode(mode); + }, + setSdMode: function(mode) { + let connectedBlock = null; + + if (this.getInput('SIZE')) { + const valueConnection = this.getInput('SIZE').connection; + if (valueConnection) { + connectedBlock = valueConnection.targetBlock(); + } + this.removeInput('SIZE'); + } + if (this.getInput('VALUE')) { + this.removeInput('VALUE'); + } + if (mode === 'fwrite') { + // Ensure that the field only receives numeric data + this.appendValueInput('SIZE') + .setCheck('Number') + .appendField('SD file') + .appendField(new Blockly.FieldDropdown([ + ['write', 'fwrite'], + ['read', 'fread'], + ['close', 'fclose'], + ], function(mode) { + // eslint-disable-next-line no-invalid-this + this.getSourceBlock().setSdMode(mode); + }), 'MODE'); + this.appendValueInput('VALUE') + .setCheck('String') + .appendField('bytes of'); + } else if (mode === 'fread') { + this.appendValueInput('SIZE') + .setCheck('Number') + .appendField('SD file') + .appendField(new Blockly.FieldDropdown([ + ['read', 'fread'], + ['write', 'fwrite'], + ['close', 'fclose'], + ], function(mode) { + // eslint-disable-next-line no-invalid-this + this.getSourceBlock().setSdMode(mode); + }), 'MODE'); + this.appendDummyInput('VALUE') + .appendField('bytes store in') + .appendField(new Blockly.FieldVariable( + Blockly.LANG_VARIABLES_SET_ITEM), 'VAR'); + } else { + this.appendDummyInput('SIZE') + .appendField('SD file') + .appendField(new Blockly.FieldDropdown([ + ['close', 'fclose'], + ['read', 'fread'], + ['write', 'fwrite'], + ], function(mode) { + // eslint-disable-next-line no-invalid-this + this.getSourceBlock().setSdMode(mode); + }), 'MODE'); + } + if (connectedBlock) { + connectedBlock.outputConnection.connect(this.getInput('SIZE').connection); + } + }, + onchange: function(event) { + const project = getProjectInitialState(); + if (event.type === Blockly.Events.BLOCK_DELETE || + event.type === Blockly.Events.BLOCK_CREATE) { + let warnTxt = null; + const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); + if (allBlocks.indexOf('SD file open') === -1) { + warnTxt = 'WARNING: You must use a SD file open block\nbefore' + + ' reading, writing, or closing an SD file!'; + } else if (allBlocks.indexOf('SD initialize') === -1 && + project.boardType.name !== 'heb-wx' && + project.boardType.name !== 'activity-board') { + warnTxt = 'WARNING: You must use a SD initialize\nblock at the' + + ' beginning of your program!'; + } + this.setWarningText(warnTxt); + } + }, +}; + +/** + * SD Card Read/Write/Close C code generator + * + * Generate code to read from an sd card, write to an sd card or to close a + * connection to the sd card reader. + * + * @return {string} + */ +Blockly.propc.sd_read = function() { + // Identify the block action (fread, fwrite, or fclose) + const mode = this.getFieldValue('MODE'); + + // Handle close stright away + if (mode === 'fclose') { + return ` if(fp) ${mode}(fp);\r`; + } + + // Verify the required SD-Open block is in the project + const block = Blockly.getMainWorkspace().getBlocksByType( + 'sd_open', false); + + if ( block.length === 0 || (!block[0].isEnabled())) { + return '// WARNING: You must use a SD file open block before reading,' + + ' writing, or closing an SD file!\r'; + } + + /** + * Verify that for boards that do not have a built-in card reader, there is + * an sd_init block in the project + */ + const project = getProjectInitialState(); + let initFound = false; + + const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( + 'sd_init', false); + if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { + initFound = true; + } + + if (project.boardType.name !== 'heb-wx' && + project.boardType.name !== 'activity-board' && + ! initFound) { + return '/** WARNING: You must use a SD initialize block at the' + + ' beginning of your program! **/\r'; + } + + // Retrieve the number of bytes to read/write. Default to one byte + const size = Blockly.propc.valueToCode( + this, 'SIZE', Blockly.propc.ORDER_NONE) || '1'; + + let value = ''; + let code = ''; + + if (mode === 'fread') { + value = Blockly.propc.variableDB_.getName( + this.getFieldValue('VAR'), + Blockly.VARIABLE_CATEGORY_NAME); + + value = '&' + value; + Blockly.propc.vartype_[value] = 'char *'; + } else if (mode === 'fwrite') { + value = Blockly.propc.valueToCode( + this, 'VALUE', Blockly.propc.ORDER_NONE) || ''; + } + + code = ` ${mode}(${value}, 1, ${size}, fp);\r`; + + // Silently mount the embedded sd card device + const profile = getDefaultProfile(); + if (!this.disabled && !initFound && profile.sd_card) { + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; + } + + return code; +}; + +/** + * + * @type {{ + * init: Blockly.Blocks.sd_file_pointer.init, + * mutationToDom: *, + * helpUrl: string, + * setSdMode: Blockly.Blocks.sd_file_pointer.setSdMode, + * onchange: *, + * domToMutation: * + * }} + */ +Blockly.Blocks.sd_file_pointer = { + helpUrl: Blockly.MSG_SD_HELPURL, + init: function() { + this.setTooltip(Blockly.MSG_SD_FILE_POINTER_TOOLTIP); + this.setColour(colorPalette.getColor('output')); + this.setSdMode('set'); + this.setInputsInline(false); + this.setPreviousStatement(true, 'Block'); + this.setNextStatement(true, null); + }, + mutationToDom: Blockly.Blocks['sd_read'].mutationToDom, + domToMutation: Blockly.Blocks['sd_read'].domToMutation, + setSdMode: function(mode) { + if (this.getInput('FP')) { + this.removeInput('FP'); + } + if (mode === 'set') { + this.appendValueInput('FP') + .setCheck('Number') + .appendField('SD file') + .appendField(new Blockly.FieldDropdown([ + ['set', 'set'], + ['get', 'get'], + ], function(blockMode) { + // eslint-disable-next-line no-invalid-this + this.getSourceBlock().setSdMode(blockMode); + }), 'MODE') + .appendField('pointer = '); + this.setOutput(false); + this.setPreviousStatement(true, 'Block'); + this.setNextStatement(true, null); + } else { + // mode == get + this.appendDummyInput('FP'); + this.getInput('FP') + .appendField('SD file') + .appendField(new Blockly.FieldDropdown([ + ['get', 'get'], + ['set', 'set'], + ], function(blockMode) { + // eslint-disable-next-line no-invalid-this + this.getSourceBlock().setSdMode(blockMode); + }), 'MODE') + .appendField('pointer'); + + this.setPreviousStatement(false); + this.setNextStatement(false, null); + this.setOutput(true, 'Number'); + } + }, + onchange: Blockly.Blocks['sd_read'].onchange, +}; + +/** + * SD Card File Pointer + * @return {(string|number)[]|string} + */ +Blockly.propc.sd_file_pointer = function() { + const profile = getDefaultProfile(); + const project = getProjectInitialState(); + // TODO: Refactor getAllBlocks to getAllBlocksByType + const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); + let code = null; + let initFound = false; + for (let x = 0; x < allBlocks.length; x++) { + if (allBlocks[x].type === 'sd_init') { + initFound = true; + } + } + + if (!this.disabled && !initFound && profile.sd_card) { + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; + } + + if (allBlocks.indexOf('SD file open') === -1) { + code = '// WARNING: You must use a SD file open block before' + + ' using the file pointer!'; + } else if (allBlocks.indexOf('SD initialize') === -1 && + project.boardType.name !== 'heb-wx' && + project.boardType.name !== 'activity-board') { + code = '// WARNING: You must use a SD initialize block at the' + + ' beginning of your program!'; + } else if (this.getFieldValue('MODE') === 'set') { + const fp = Blockly.propc.valueToCode( + this, 'FP', Blockly.propc.ORDER_NONE) || '0'; + code = 'fp = ' + fp + ';\r'; + } else { + code = ['fp', Blockly.propc.ORDER_ATOMIC]; + } + return code; +}; diff --git a/src/modules/editor.js b/src/modules/editor.js index 8fd3cc58..2d817602 100644 --- a/src/modules/editor.js +++ b/src/modules/editor.js @@ -37,6 +37,7 @@ import './blockly/generators/propc/oled'; import './blockly/generators/propc/heb'; import './blockly/generators/propc/procedures'; import './blockly/generators/propc/s3'; +import './blockly/generators/propc/sd_card'; import './blockly/generators/propc/sensors'; import './blockly/generators/propc/variables'; From 25ea685e6b9d6a125e06c7bc2b0287ec1b31d4db Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 11:35:53 -0800 Subject: [PATCH 09/14] Refactor SD card open. Refactor sd_init into a separate function. --- .../blockly/generators/propc/sd_card.js | 83 ++++++++++--------- 1 file changed, 45 insertions(+), 38 deletions(-) diff --git a/src/modules/blockly/generators/propc/sd_card.js b/src/modules/blockly/generators/propc/sd_card.js index e2972a19..905e5117 100644 --- a/src/modules/blockly/generators/propc/sd_card.js +++ b/src/modules/blockly/generators/propc/sd_card.js @@ -24,10 +24,6 @@ import Blockly from 'blockly/core'; import {getDefaultProfile, getProjectInitialState} from '../../../project'; import {colorPalette} from '../propc'; -// ---------------------------------------------------------------- -// ----------------- SD Card file blocks -------------------------- -// ---------------------------------------------------------------- - /** * SD Card Initialization @@ -61,6 +57,8 @@ Blockly.Blocks.sd_init = { }; /** + * Generate source code for the sd_init block. + * This creates a global file pointer. * * @return {string} */ @@ -147,29 +145,22 @@ Blockly.Blocks.sd_open = { * @return {string} */ Blockly.propc.sd_open = function() { - const filename = this.getFieldValue('FILENAME'); - const mode = this.getFieldValue('MODE'); - let initFound = false; - const initSdBlock = Blockly.getMainWorkspace().getBlocksByType( 'sd_init', false); - if (initSdBlock.length > 0 && initSdBlock[0].isEnabled()) { - initFound = true; - } else { + if (initSdBlock.length === 0 || !initSdBlock[0].isEnabled()) { const project = getProjectInitialState(); if (project.boardType.name !== 'activity-board' && project.boardType.name !== 'heb-wx') { return '/** WARNING: You must use a SD initialize block at the' + ' beginning of your program! **/\r'; + } else { + // Quietly mount the sd card filesystem + setupSdCard(); } } - // Quietly mount the sd card filesystem - const profile = getDefaultProfile(); - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');\r'; - } - + const filename = this.getFieldValue('FILENAME'); + const mode = this.getFieldValue('MODE'); return `fp = fopen("${filename}","${mode}");\r`; }; @@ -333,13 +324,17 @@ Blockly.propc.sd_read = function() { ' beginning of your program! **/\r'; } + // Silently mount the embedded sd card device + if (!this.disabled && !initFound) { + setupSdCard(); + } + // Retrieve the number of bytes to read/write. Default to one byte const size = Blockly.propc.valueToCode( this, 'SIZE', Blockly.propc.ORDER_NONE) || '1'; + // Retrieve the data buffer or variable let value = ''; - let code = ''; - if (mode === 'fread') { value = Blockly.propc.variableDB_.getName( this.getFieldValue('VAR'), @@ -352,15 +347,7 @@ Blockly.propc.sd_read = function() { this, 'VALUE', Blockly.propc.ORDER_NONE) || ''; } - code = ` ${mode}(${value}, 1, ${size}, fp);\r`; - - // Silently mount the embedded sd card device - const profile = getDefaultProfile(); - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; - } - - return code; + return ` ${mode}(${value}, 1, ${size}, fp);\r`; }; /** @@ -432,7 +419,6 @@ Blockly.Blocks.sd_file_pointer = { * @return {(string|number)[]|string} */ Blockly.propc.sd_file_pointer = function() { - const profile = getDefaultProfile(); const project = getProjectInitialState(); // TODO: Refactor getAllBlocks to getAllBlocksByType const allBlocks = Blockly.getMainWorkspace().getAllBlocks().toString(); @@ -444,24 +430,45 @@ Blockly.propc.sd_file_pointer = function() { } } - if (!this.disabled && !initFound && profile.sd_card) { - Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; + // Quietly install setup code + if (!this.disabled && !initFound) { + setupSdCard(); } if (allBlocks.indexOf('SD file open') === -1) { - code = '// WARNING: You must use a SD file open block before' + - ' using the file pointer!'; - } else if (allBlocks.indexOf('SD initialize') === -1 && + return '// WARNING: You must use a SD file open block before' + + ' using the file pointer!'; + } + if (allBlocks.indexOf('SD initialize') === -1 && project.boardType.name !== 'heb-wx' && project.boardType.name !== 'activity-board') { - code = '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; - } else if (this.getFieldValue('MODE') === 'set') { + return '// WARNING: You must use a SD initialize block at the' + + ' beginning of your program!'; + } + + if (this.getFieldValue('MODE') === 'set') { + // Set pointer const fp = Blockly.propc.valueToCode( this, 'FP', Blockly.propc.ORDER_NONE) || '0'; code = 'fp = ' + fp + ';\r'; + // fseek(fp, item, SEEK_CUR) + // code = `fp = (FILE*) fseek(${fp}, item, SEEK_CUR);\r`; } else { - code = ['fp', Blockly.propc.ORDER_ATOMIC]; + // Get pointer + code = ['ftell(fp);', Blockly.propc.ORDER_ATOMIC]; } + return code; }; + + +/** + * Mount SD Card + */ +function setupSdCard() { + const profile = getDefaultProfile(); + if (profile.sd_card) { + Blockly.propc.setups_['sd_card'] = 'sd_mount(' + profile.sd_card + ');'; + Blockly.propc.global_vars_['fpglobal'] = 'FILE *fp;'; + } +} From c169004c28254e733514e70af2f9f4a07820043d Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 11:49:29 -0800 Subject: [PATCH 10/14] Refactor warning messages. --- .../blockly/generators/propc/sd_card.js | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/src/modules/blockly/generators/propc/sd_card.js b/src/modules/blockly/generators/propc/sd_card.js index 905e5117..6676a674 100644 --- a/src/modules/blockly/generators/propc/sd_card.js +++ b/src/modules/blockly/generators/propc/sd_card.js @@ -24,6 +24,13 @@ import Blockly from 'blockly/core'; import {getDefaultProfile, getProjectInitialState} from '../../../project'; import {colorPalette} from '../propc'; +const SdInitMissingMessage = + '/** WARNING: You must use a SD initialize block at the' + + ' beginning of your program! **/\r'; + +const SdOpenMissingMessage = + '/** WARNING: You must use a SD file open block before reading,' + + ' writing, or closing an SD file! **/\r'; /** * SD Card Initialization @@ -151,8 +158,7 @@ Blockly.propc.sd_open = function() { const project = getProjectInitialState(); if (project.boardType.name !== 'activity-board' && project.boardType.name !== 'heb-wx') { - return '/** WARNING: You must use a SD initialize block at the' + - ' beginning of your program! **/\r'; + return SdOpenMissingMessage; } else { // Quietly mount the sd card filesystem setupSdCard(); @@ -300,8 +306,7 @@ Blockly.propc.sd_read = function() { 'sd_open', false); if ( block.length === 0 || (!block[0].isEnabled())) { - return '// WARNING: You must use a SD file open block before reading,' + - ' writing, or closing an SD file!\r'; + return SdOpenMissingMessage; } /** @@ -320,8 +325,7 @@ Blockly.propc.sd_read = function() { if (project.boardType.name !== 'heb-wx' && project.boardType.name !== 'activity-board' && ! initFound) { - return '/** WARNING: You must use a SD initialize block at the' + - ' beginning of your program! **/\r'; + return SdInitMissingMessage; } // Silently mount the embedded sd card device @@ -442,8 +446,7 @@ Blockly.propc.sd_file_pointer = function() { if (allBlocks.indexOf('SD initialize') === -1 && project.boardType.name !== 'heb-wx' && project.boardType.name !== 'activity-board') { - return '// WARNING: You must use a SD initialize block at the' + - ' beginning of your program!'; + return SdInitMissingMessage; } if (this.getFieldValue('MODE') === 'set') { From f40945aeb32687b95444af2de128daff015066b6 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 17:36:30 -0800 Subject: [PATCH 11/14] Replace '\r' with '\n'. Remove semicolon from get file pointer block. --- .../blockly/generators/propc/sd_card.js | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/src/modules/blockly/generators/propc/sd_card.js b/src/modules/blockly/generators/propc/sd_card.js index 6676a674..d7119f9f 100644 --- a/src/modules/blockly/generators/propc/sd_card.js +++ b/src/modules/blockly/generators/propc/sd_card.js @@ -26,11 +26,11 @@ import {colorPalette} from '../propc'; const SdInitMissingMessage = '/** WARNING: You must use a SD initialize block at the' + - ' beginning of your program! **/\r'; + ' beginning of your program! **/\n'; const SdOpenMissingMessage = '/** WARNING: You must use a SD file open block before reading,' + - ' writing, or closing an SD file! **/\r'; + ' writing, or closing an SD file! **/\n'; /** * SD Card Initialization @@ -167,7 +167,7 @@ Blockly.propc.sd_open = function() { const filename = this.getFieldValue('FILENAME'); const mode = this.getFieldValue('MODE'); - return `fp = fopen("${filename}","${mode}");\r`; + return `fp = fopen("${filename}","${mode}");\n`; }; /** @@ -298,7 +298,7 @@ Blockly.propc.sd_read = function() { // Handle close stright away if (mode === 'fclose') { - return ` if(fp) ${mode}(fp);\r`; + return `if(fp) ${mode}(fp);\n`; } // Verify the required SD-Open block is in the project @@ -351,7 +351,7 @@ Blockly.propc.sd_read = function() { this, 'VALUE', Blockly.propc.ORDER_NONE) || ''; } - return ` ${mode}(${value}, 1, ${size}, fp);\r`; + return `${mode}(${value}, 1, ${size}, fp);\n`; }; /** @@ -441,7 +441,7 @@ Blockly.propc.sd_file_pointer = function() { if (allBlocks.indexOf('SD file open') === -1) { return '// WARNING: You must use a SD file open block before' + - ' using the file pointer!'; + ' using the file pointer!\n'; } if (allBlocks.indexOf('SD initialize') === -1 && project.boardType.name !== 'heb-wx' && @@ -453,12 +453,10 @@ Blockly.propc.sd_file_pointer = function() { // Set pointer const fp = Blockly.propc.valueToCode( this, 'FP', Blockly.propc.ORDER_NONE) || '0'; - code = 'fp = ' + fp + ';\r'; - // fseek(fp, item, SEEK_CUR) - // code = `fp = (FILE*) fseek(${fp}, item, SEEK_CUR);\r`; + code = `fp = (FILE*) fseek(fp, ${fp}, SEEK_CUR);\n`; } else { // Get pointer - code = ['ftell(fp);', Blockly.propc.ORDER_ATOMIC]; + code = ['ftell(fp)', Blockly.propc.ORDER_ATOMIC]; } return code; From a59b1017c157a33bf7299c87c4f18654b14662c8 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 17:36:58 -0800 Subject: [PATCH 12/14] Add SD File reserved words. --- src/modules/blockly/generators/propc.js | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/modules/blockly/generators/propc.js b/src/modules/blockly/generators/propc.js index c2958e2a..22deaff3 100644 --- a/src/modules/blockly/generators/propc.js +++ b/src/modules/blockly/generators/propc.js @@ -399,6 +399,12 @@ Blockly.propc.addReservedWords( 'ws2812_set,ws2812_start,ws2812_stop,ws2812_wheel,ws2812_wheel_dim,' + 'ws2812b_open,ws2812b_start'); +/** + * SD File reserved words + */ +Blockly.propc.addReservedWords( + 'fp,fclose,fopen,fread,fseek,ftell,fwrite,sd_init,sd_mount,'); + /** * Order of operation ENUMs. * From 468acb5843652341aae5820ffe3c7f322e4130fd Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 22:09:45 -0800 Subject: [PATCH 13/14] Correct error in set file pointer. --- src/modules/blockly/generators/propc/sd_card.js | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/src/modules/blockly/generators/propc/sd_card.js b/src/modules/blockly/generators/propc/sd_card.js index d7119f9f..65880933 100644 --- a/src/modules/blockly/generators/propc/sd_card.js +++ b/src/modules/blockly/generators/propc/sd_card.js @@ -420,7 +420,16 @@ Blockly.Blocks.sd_file_pointer = { /** * SD Card File Pointer + * Retrieves or sets the file pointer of an open file. + * + * set - Uses the fseek function to position the file pointer to 'n' bytes + * from the beginning of the file. + * + * get - Returns an integer value indicating the current position of the + * file pointer in the file stream. + * * @return {(string|number)[]|string} + * */ Blockly.propc.sd_file_pointer = function() { const project = getProjectInitialState(); @@ -443,6 +452,7 @@ Blockly.propc.sd_file_pointer = function() { return '// WARNING: You must use a SD file open block before' + ' using the file pointer!\n'; } + if (allBlocks.indexOf('SD initialize') === -1 && project.boardType.name !== 'heb-wx' && project.boardType.name !== 'activity-board') { @@ -450,10 +460,9 @@ Blockly.propc.sd_file_pointer = function() { } if (this.getFieldValue('MODE') === 'set') { - // Set pointer const fp = Blockly.propc.valueToCode( this, 'FP', Blockly.propc.ORDER_NONE) || '0'; - code = `fp = (FILE*) fseek(fp, ${fp}, SEEK_CUR);\n`; + code = `fseek(fp, ${fp}, SEEK_SET);\n`; } else { // Get pointer code = ['ftell(fp)', Blockly.propc.ORDER_ATOMIC]; From 0e0a3f838bcfe6c0acde6fdb15b83012fd2c82d4 Mon Sep 17 00:00:00 2001 From: Jim Ewald Date: Sat, 16 Jan 2021 22:38:42 -0800 Subject: [PATCH 14/14] Set release 1.5.7 Enable Sentry. --- src/modules/constants.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/modules/constants.js b/src/modules/constants.js index b60a98e5..676c42a5 100644 --- a/src/modules/constants.js +++ b/src/modules/constants.js @@ -24,7 +24,7 @@ * Global flag to enable/disable the Sentry logger * @type {boolean} */ -export const EnableSentry = false; +export const EnableSentry = true; /** * Set the application version string @@ -44,7 +44,7 @@ export const EnableSentry = false; * {b#} is the beta release number. * {rc#} is the release candidate number. */ -export const APP_VERSION = '1.5.7-a2'; +export const APP_VERSION = '1.5.7'; /** * Constant string that represents the base, empty project header