commit 972944b977ba9c126268e60aebbed06cd609d54b Author: Andrew Date: Wed Aug 20 23:45:39 2025 +0300 first commit diff --git a/.vscode/launch.json b/.vscode/launch.json new file mode 100644 index 0000000..44a86ab --- /dev/null +++ b/.vscode/launch.json @@ -0,0 +1,17 @@ +// A launch configuration that launches the extension inside a new window +// Use IntelliSense to learn about possible attributes. +// Hover to view descriptions of existing attributes. +// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 +{ + "version": "0.2.0", + "configurations": [ + { + "name": "Extension", + "type": "extensionHost", + "request": "launch", + "args": [ + "--extensionDevelopmentPath=${workspaceFolder}" + ] + } + ] +} diff --git a/.vscodeignore b/.vscodeignore new file mode 100644 index 0000000..f369b5e --- /dev/null +++ b/.vscodeignore @@ -0,0 +1,4 @@ +.vscode/** +.vscode-test/** +.gitignore +vsc-extension-quickstart.md diff --git a/README.md b/README.md new file mode 100644 index 0000000..e09f03c Binary files /dev/null and b/README.md differ diff --git a/icons/icon192_dark.png b/icons/icon192_dark.png new file mode 100644 index 0000000..c525003 Binary files /dev/null and b/icons/icon192_dark.png differ diff --git a/icons/icon192_light.png b/icons/icon192_light.png new file mode 100644 index 0000000..968c263 Binary files /dev/null and b/icons/icon192_light.png differ diff --git a/language-configuration.json b/language-configuration.json new file mode 100644 index 0000000..2476e4b --- /dev/null +++ b/language-configuration.json @@ -0,0 +1,20 @@ +{ + "comments": { + "lineComment": ";" + }, + "brackets": [ + ["(", ")"], + ["[", "]"], + ["{", "}"] + ], + "autoClosingPairs": [ + { "open": "(", "close": ")" }, + { "open": "[", "close": "]" }, + { "open": "{", "close": "}" } + ], + "surroundingPairs": [ + { "open": "(", "close": ")" }, + { "open": "[", "close": "]" }, + { "open": "{", "close": "}" } + ] +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..6fa2e48 --- /dev/null +++ b/package.json @@ -0,0 +1,272 @@ +{ + "name": "nc310-syntax", + "displayName": "Balt-System PLC Syntax", + "description": "Подсветка, цвета и сниппеты Baltsystem PLC", + "version": "1.0.0", + "publisher": "andrewkydev", + "pricing": "Free", + "engines": { + "vscode": "^1.45.0" + }, + "main": "./src/extension.js", + "activationEvents": [], + "contributes": { + "semanticTokenColors": {}, + "tokenColors": [ + { + "scope": "comment.line.semicolon.bsnc", + "settings": { + "foreground": "#6A9955", + "fontStyle": "italic" + } + }, + { + "scope": "keyword.control.cycle.rpt.start.bsnc", + "settings": { + "foreground": "#FFFFFF", + "background": "#FF4500", + "fontStyle": "bold" + } + }, + { + "scope": "keyword.control.cycle.rpt.end.bsnc", + "settings": { + "foreground": "#FFFFFF", + "background": "#228B22", + "fontStyle": "bold" + } + }, + { + "scope": "punctuation.section.parens.begin.bsnc", + "settings": { + "foreground": "#FFD700" + } + }, + { + "scope": "punctuation.section.parens.end.bsnc", + "settings": { + "foreground": "#FFD700" + } + }, + { + "scope": "entity.name.function.ucg.bsnc", + "settings": { + "foreground": "#FF69B4" + } + }, + { + "scope": "constant.numeric.ucg-main.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "variable.parameter.axis.bsnc", + "settings": { + "foreground": "#1E90FF" + } + }, + { + "scope": "constant.numeric.axis-value.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "constant.numeric.ucg-extra.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "keyword.control.motion.rapid.bsnc", + "settings": { + "foreground": "#FF69B4" + } + }, + { + "scope": "keyword.control.motion.linear.bsnc", + "settings": { + "foreground": "#FF69B4" + } + }, + { + "scope": "variable.other.e-variable.bsnc", + "settings": { + "foreground": "#FFD700" + } + }, + { + "scope": "constant.numeric.e-value.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "variable.parameter.feedrate.bsnc", + "settings": { + "foreground": "#1E90FF" + } + }, + { + "scope": "constant.numeric.feedrate-value.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "entity.name.function.tool-number.bsnc", + "settings": { + "foreground": "#ADFF2F" + } + }, + { + "scope": "constant.numeric.tool-offset.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "support.function.mcode.bsnc", + "settings": { + "foreground": "#FFA500" + } + }, + { + "scope": "entity.name.function.spindle-speed.bsnc", + "settings": { + "foreground": "#00BFFF" + } + }, + { + "scope": "entity.name.function.triplecode.bsnc", + "settings": { + "foreground": "#FF69B4" + } + }, + { + "scope": "punctuation.separator.comma.bsnc", + "settings": { + "foreground": "#FFD700" + } + }, + { + "scope": "constant.numeric.triplecode-arg.bsnc", + "settings": { + "foreground": "#40E0D0" + } + }, + { + "scope": "string.quoted.double.bsnc", + "settings": { + "foreground": "#ADFF2F" + } + }, + { + "scope": "invalid.illegal.gcode.bsnc", + "settings": { + "foreground": "#FFFFFF", + "background": "#FF0000", + "fontStyle": "bold" + } + } + ], + "configurationDefaults": { + "[bsnc]": { + "files.encoding": "cp866", + "editor.glyphMargin": false + }, + "files.associations": { + "[!.]": "bsnc", + "[!.][!.]": "bsnc", + "[!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]": "bsnc" + } + }, + "languages": [ + { + "id": "bsnc", + "aliases": [ + "Balt-System PLC" + ], + "extensions": [ + ".bsnc", + "[!.]", + "[!.][!.]", + "[!.][!.][!.]", + "[!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]", + "[!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.][!.]" + ], + "configuration": "./language-configuration.json", + "icon": { + "light": "./icons/icon192_light.png", + "dark": "./icons/icon192_dark.png" + } + } + ], + "grammars": [ + { + "language": "bsnc", + "scopeName": "source.bsnc", + "path": "./syntaxes/bsnc.tmLanguage.json" + } + ], + "snippets": [ + { + "language": "bsnc", + "path": "./snippets/bsnc.json" + } + ] + } +} \ No newline at end of file diff --git a/snippets/bsnc.json b/snippets/bsnc.json new file mode 100644 index 0000000..789a43b --- /dev/null +++ b/snippets/bsnc.json @@ -0,0 +1,27 @@ +{ + "UCG template": { + "prefix": "ucg", + "body": ["(UCG,2,X-33X33,Y-33Y33,Z-15Z0,1,-3)"], + "description": "Шаблон UCG" + }, + "URT cycle": { + "prefix": "urt", + "body": ["(URT,${1:0})"], + "description": "Цикл URT" + }, + "RPT cycle": { + "prefix": "rpt", + "body": ["(RPT,${1:E0})"], + "description": "Цикл RPT" + }, + "ERP": { + "prefix": "erp", + "body": ["(ERP)"], + "description": "Маркер ERP" + }, + "E variable": { + "prefix": "evar", + "body": ["E${1:30}=${2:0}"], + "description": "Переменная E" + } +} diff --git a/src/extension.js b/src/extension.js new file mode 100644 index 0000000..303e167 --- /dev/null +++ b/src/extension.js @@ -0,0 +1,28 @@ +'use strict'; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.deactivate = exports.activate = void 0; +const vscode = require("vscode"); +function activate(context) { + context.subscriptions.push(vscode.languages.registerDocumentSymbolProvider({ language: "bsnc" }, new FooDocumentSymbolProvider())); +} +exports.activate = activate; +class FooDocumentSymbolProvider { + provideDocumentSymbols(document, token) { + return new Promise((resolve, reject) => { + var symbols = []; + for (var i = 0; i < document.lineCount; i++) { + var line = document.lineAt(i); + if (line.text.startsWith(";*** ")) { + symbols.push({ + name: line.text.substr(4).trim(), + kind: vscode.SymbolKind.Module, + location: new vscode.Location(document.uri, line.range) + }); + } + } + resolve(symbols); + }); + } +} +function deactivate() { } +exports.deactivate = deactivate; \ No newline at end of file diff --git a/syntaxes/bsnc.tmLanguage.json b/syntaxes/bsnc.tmLanguage.json new file mode 100644 index 0000000..7662cc9 --- /dev/null +++ b/syntaxes/bsnc.tmLanguage.json @@ -0,0 +1,425 @@ +{ + "scopeName": "source.bsnc", + "patterns": [ + { + "include": "#lineComments" + }, + { + "include": "#tripleCodes" + }, + { + "include": "#uao" + }, + { + "include": "#ucg" + }, + { + "include": "#variablesE" + }, + { + "include": "#toolChange" + }, + { + "include": "#spindleWithM" + }, + { + "include": "#gMoves" + }, + { + "include": "#coords" + }, + { + "include": "#cycles" + }, + { + "include": "#gArcs" + }, + { + "include": "#arcParams" + }, + { + "include": "#mCodes" + }, + { + "include": "#rptCycle" + }, + { + "include": "#gCodesValid" + }, + { + "include": "#comments" + } + ], + "repository": { + "lineComments": { + "patterns": [ + { + "match": ";.*$", + "name": "comment.line.semicolon.bsnc" + } + ] + }, + "tripleCodes": { + "patterns": [ + { + "begin": "(\\()([A-Z]{3})", + "beginCaptures": { + "1": { + "name": "punctuation.section.parens.begin.nc310" + }, + "2": { + "name": "entity.name.function.triplecode.nc310" + } + }, + "end": "\\)", + "endCaptures": { + "0": { + "name": "punctuation.section.parens.end.nc310" + } + }, + "patterns": [ + { + "match": ",", + "name": "punctuation.separator.comma.nc310" + }, + { + "match": "\"[^\"]*\"", + "name": "string.quoted.double.nc310" + }, + { + "match": "'[^']*'", + "name": "string.quoted.single.nc310" + }, + { + "match": "(E\\d+)", + "name": "variable.other.e-variable.nc310" + }, + { + "match": "([XYZ])([-+]?\\d+(?:\\.\\d+)?)", + "captures": { + "1": { + "name": "variable.parameter.axis.nc310" + }, + "2": { + "name": "constant.numeric.axis-value.nc310" + } + } + }, + { + "match": "([-+]?\\d+(?:\\.\\d+)?)", + "name": "constant.numeric.triplecode-arg.nc310" + } + ] + } + ] + }, + "uao": { + "patterns": [ + { + "match": "\\((UAO),(\\-?\\d+(?:\\.\\d+)?)\\)", + "captures": { + "1": { + "name": "entity.name.function.uao.bsnc" + }, + "2": { + "name": "constant.numeric.uao-value.bsnc" + } + } + } + ] + }, + "ucg": { + "patterns": [ + { + "match": "\\((UCG),(\\-?\\d+(?:\\.\\d+)?),([XYZ])([-+]?\\d+(?:\\.\\d+)?)([XYZ])([-+]?\\d+(?:\\.\\d+)?),([XYZ])([-+]?\\d+(?:\\.\\d+)?),(\\-?\\d+(?:\\.\\d+)?),(\\-?\\d+(?:\\.\\d+)?)\\)", + "captures": { + "1": { + "name": "entity.name.function.ucg.bsnc" + }, + "2": { + "name": "constant.numeric.ucg-main.bsnc" + }, + "3": { + "name": "variable.parameter.axis.bsnc" + }, + "4": { + "name": "constant.numeric.axis-value.bsnc" + }, + "5": { + "name": "variable.parameter.axis.bsnc" + }, + "6": { + "name": "constant.numeric.axis-value.bsnc" + }, + "7": { + "name": "variable.parameter.axis.bsnc" + }, + "8": { + "name": "constant.numeric.axis-value.bsnc" + }, + "9": { + "name": "constant.numeric.ucg-extra.bsnc" + }, + "10": { + "name": "constant.numeric.ucg-extra.bsnc" + } + } + } + ] + }, + "mCodes": { + "patterns": [ + { + "match": "\\b(M)(0?[0-9]{1,2})\\b", + "captures": { + "1": { + "name": "support.function.mcode.bsnc" + }, + "2": { + "name": "constant.numeric.mcode-value.bsnc" + } + } + } + ] + }, + "variablesE": { + "patterns": [ + { + "match": "\\b(E\\d+)(=)([-+]?[0-9]+(?:\\.[0-9]+)?)\\b", + "captures": { + "1": { + "name": "variable.other.e-variable.bsnc" + }, + "2": { + "name": "keyword.operator.assignment.bsnc" + }, + "3": { + "name": "constant.numeric.e-value.bsnc" + } + } + }, + { + "match": "\\b(E\\d+)\\b", + "captures": { + "1": { + "name": "variable.other.e-variable.bsnc" + } + } + } + ] + }, + "toolChange": { + "patterns": [ + { + "match": "\\b(T\\d+)(\\.\\d+)?(M6)\\b", + "captures": { + "1": { + "name": "entity.name.function.tool-number.bsnc" + }, + "2": { + "name": "constant.numeric.tool-offset.bsnc" + }, + "3": { + "name": "support.function.mcode.bsnc" + } + } + } + ] + }, + "spindleWithM": { + "patterns": [ + { + "match": "\\b(S)([0-9]+(?:\\.[0-9]+)?)(?:\\s*|)(M)(0?[0-9]{1,2})\\b", + "captures": { + "1": { + "name": "entity.name.function.spindle-speed.bsnc" + }, + "2": { + "name": "constant.numeric.spindle-speed-value.bsnc" + }, + "3": { + "name": "support.function.mcode.bsnc" + }, + "4": { + "name": "constant.numeric.mcode-value.bsnc" + } + } + } + ] + }, + "gMoves": { + "patterns": [ + { + "match": "(G0)(?=[XYZF]|$)", + "captures": { + "1": { + "name": "keyword.control.motion.rapid.bsnc" + } + } + }, + { + "match": "(G1)(?=[XYZEF]|$)", + "captures": { + "1": { + "name": "keyword.control.motion.linear.bsnc" + } + } + } + ] + }, + "gArcs": { + "patterns": [ + { + "match": "(G2)(?=[XYZRIJEF]|$)", + "captures": { + "1": { + "name": "keyword.control.motion.arc.cw.bsnc" + } + } + }, + { + "match": "(G3)(?=[XYZRIJEF]|$)", + "captures": { + "1": { + "name": "keyword.control.motion.arc.ccw.bsnc" + } + } + } + ] + }, + "arcParams": { + "patterns": [ + { + "match": "([XYZ])([-+]?[0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.axis.bsnc" + }, + "2": { + "name": "constant.numeric.axis-value.bsnc" + } + } + }, + { + "match": "([IJ])([-+]?[0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.arc-center.bsnc" + }, + "2": { + "name": "constant.numeric.arc-center-value.bsnc" + } + } + }, + { + "match": "(R)([-+]?[0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.arc-radius.bsnc" + }, + "2": { + "name": "constant.numeric.arc-radius-value.bsnc" + } + } + }, + { + "match": "(F)([0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.feedrate.bsnc" + }, + "2": { + "name": "constant.numeric.feedrate-value.bsnc" + } + } + }, + { + "match": "(E\\d+)", + "captures": { + "1": { + "name": "variable.other.e-variable.bsnc" + } + } + } + ] + }, + "coords": { + "patterns": [ + { + "match": "([XYZ])([-+]?[0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.axis.bsnc" + }, + "2": { + "name": "constant.numeric.axis-value.bsnc" + } + } + }, + { + "match": "(F)([0-9]+(?:\\.[0-9]+)?)", + "captures": { + "1": { + "name": "variable.parameter.feedrate.bsnc" + }, + "2": { + "name": "constant.numeric.feedrate-value.bsnc" + } + } + }, + { + "match": "(E\\d+)", + "captures": { + "1": { + "name": "variable.other.e-variable.bsnc" + } + } + } + ] + }, + "cycles": { + "patterns": [ + { + "name": "keyword.control.cycle.rpt.bsnc", + "match": "\\(RPT\\s*,?\\s*E?\\d*\\)" + }, + { + "name": "keyword.control.cycle.urt.bsnc", + "match": "\\(URT\\s*,?\\s*\\d*\\)" + }, + { + "name": "keyword.control.cycle.erp.bsnc", + "match": "\\(ERP\\)" + } + ] + }, + "rptCycle": { + "patterns": [ + { + "match": "\\(RPT\\s*,?\\s*E?\\d*\\)", + "name": "keyword.control.cycle.rpt.start.bsnc" + }, + { + "match": "\\(ERP\\)", + "name": "keyword.control.cycle.rpt.end.bsnc" + } + ] + }, + "gCodesValid": { + "patterns": [ + { + "match": "\\b(G(?:0[0-9]|1|2|3|4|6|9|17|18|19|20|21|27|28|29|33|34|35|40|41|42|70|71|72|73|74|79|80|81|82|83|84|85|86|89|90|91|93|94|95|96|97))\\b", + "name": "keyword.control.gcode.valid.bsnc" + } + ] + }, + "comments": { + "patterns": [ + { + "match": "\\([^A-Z]{3}.*?\\)", + "name": "comment.block.bsnc" + } + ] + } + } +} \ No newline at end of file diff --git a/themes/bsnc-colors.json b/themes/bsnc-colors.json new file mode 100644 index 0000000..5f3b36f --- /dev/null +++ b/themes/bsnc-colors.json @@ -0,0 +1,14 @@ +{ + "$schema": "vscode://schemas/color-theme", + "name": "BSNC Embedded Colors", + "type": "dark", + "tokenColors": [ + { "scope": "entity.name.function.triplecode.bsnc", "settings": { "foreground": "#FF69B4" } }, + { "scope": "constant.numeric.triplecode-arg.bsnc", "settings": { "foreground": "#40E0D0" } }, + { "scope": "variable.other.e-variable.bsnc", "settings": { "foreground": "#FFD700" } }, + { "scope": "support.function.mcode.bsnc", "settings": { "foreground": "#FFA500" } }, + { "scope": "constant.numeric.mcode-value.bsnc", "settings": { "foreground": "#40E0D0" } }, + { "scope": "keyword.control.cycle.rpt.start.bsnc", "settings": { "foreground": "#FFFFFF", "background": "#FF4500", "fontStyle": "bold" } }, + { "scope": "keyword.control.cycle.rpt.end.bsnc", "settings": { "foreground": "#FFFFFF", "background": "#228B22", "fontStyle": "bold" } } + ] +} diff --git a/vsc-extension-quickstart.md b/vsc-extension-quickstart.md new file mode 100644 index 0000000..17f0a68 --- /dev/null +++ b/vsc-extension-quickstart.md @@ -0,0 +1,50 @@ +# BSNC Syntax & Highlighting + +Расширение для Visual Studio Code, добавляющее полноценную подсветку синтаксиса, автодополнение и цветовые схемы для программ ЧПУ в формате **BSNC / NC-310**. + +## ✨ Возможности + +- **Подсветка G/M-кодов** + Разделение кода и числовой части, поддержка слитной и раздельной записи (`G1X0Y0F500`, `S600 M3` и т.д.). +- **Подсветка трёхбуквенных кодов в скобках** + (`UCG`, `UAO`, `URT`, `RPT`, `ERP` и др.) с разбором аргументов по типам: числа, переменные, строки. +- **Подсветка переменных E** + (`E30=0`, `ZE30`) с раздельным цветом для имени и значения. +- **Выделение начала и конца циклов** + `(RPT,...)` и `(ERP)` — яркие цвета для мгновенного поиска в коде. +- **Подсветка допустимых и недопустимых G-кодов** + Валидные коды из документации — обычный цвет, неизвестные — выделяются как ошибка. +- **Подсветка комментариев** + Однострочные (`; ...`) и блочные в скобках. +- **Встроенная цветовая схема** + Все цвета для токенов уже встроены в расширение, интерфейс VS Code не меняется. + +## 📦 Установка + +1. Скачайте `.vsix` или установите из [Visual Studio Marketplace](#) (ссылка после публикации). +2. В VS Code: `Ctrl+Shift+P` → **Extensions: Install from VSIX** → выберите файл. +3. Расширение активируется автоматически для файлов с кодом BSNC. + +## 🚀 Использование + +- Откройте файл программы ЧПУ (с расширением или без). +- Подсветка и цвета применяются автоматически. +- Сниппеты: + - `ucg` → `(UCG,2,X-33X33,Y-33Y33,Z-15Z0,1,-3)` + - `urt` → `(URT,0)` + - `rpt` → `(RPT,E0)` +- Недопустимые G-коды будут выделены красным фоном. + +## ⚙️ Кастомизация + +Если хотите изменить цвета: +1. Откройте `settings.json`. +2. Добавьте свои правила в `editor.tokenColorCustomizations.textMateRules` — они перекроют встроенные. + +## 📄 Лицензия + +MIT — используйте, модифицируйте и делитесь. + +--- + +💡 **Совет:** Расширение можно использовать вместе с любыми тёмными или светлыми темами — встроенные цвета будут работать поверх.