Skip to content
This repository was archived by the owner on Oct 1, 2024. It is now read-only.

Commit 10e6466

Browse files
authored
Switch to C++ extension for language service. (#167)
* Update activation events. * Switch to C++ extension for language service.
1 parent 8aafc87 commit 10e6466

File tree

6 files changed

+102
-44
lines changed

6 files changed

+102
-44
lines changed

package.json

+13-21
Original file line numberDiff line numberDiff line change
@@ -30,11 +30,11 @@
3030
"contributes": {
3131
"snippets": [
3232
{
33-
"language": "arduino",
33+
"language": "cpp",
3434
"path": "./snippets/arduino.json"
3535
},
3636
{
37-
"language": "cpp",
37+
"language": "c",
3838
"path": "./snippets/arduino.json"
3939
}
4040
],
@@ -138,19 +138,15 @@
138138
}
139139
}
140140
},
141-
"languages": [
142-
{
143-
"id": "arduino",
144-
"extensions": [
145-
".ino"
146-
],
147-
"aliases": [
148-
"Arduino",
149-
"arduino",
150-
"ino"
151-
],
152-
"configuration": "./syntaxes/arduino.configuration.json"
141+
"configurationDefaults": {
142+
"[cpp]": {
143+
"editor.quickSuggestions": true
153144
},
145+
"[c]": {
146+
"editor.quickSuggestions": true
147+
}
148+
},
149+
"languages": [
154150
{
155151
"id": "arduino-output",
156152
"mimetypes": [
@@ -160,7 +156,7 @@
160156
],
161157
"grammars": [
162158
{
163-
"language": "arduino",
159+
"language": "cpp",
164160
"path": "./syntaxes/arduino.tmLanguage",
165161
"scopeName": "source.cpp.arduino"
166162
},
@@ -169,11 +165,7 @@
169165
"scopeName": "arduino.output",
170166
"path": "./syntaxes/arduino.output.tmLanguage"
171167
}
172-
],
173-
"explorer": {
174-
"treeLabel": "Arduino Examples",
175-
"treeExplorerNodeProviderId": "arduinoExampleTree"
176-
}
168+
]
177169
},
178170
"scripts": {
179171
"vscode:prepublish": "gulp build",
@@ -207,4 +199,4 @@
207199
"winreg": "^1.2.3",
208200
"winston": "^2.3.1"
209201
}
210-
}
202+
}

src/arduino/arduino.ts

+9-5
Original file line numberDiff line numberDiff line change
@@ -126,9 +126,10 @@ export class ArduinoApp {
126126
libPaths = this.getDefaultPackageLibPaths();
127127
}
128128

129-
const configFilePath = path.join(vscode.workspace.rootPath, constants.ARDUINO_CONFIG_FILE);
129+
const configFilePath = path.join(vscode.workspace.rootPath, constants.CPP_CONFIG_FILE);
130130
let deviceContext = null;
131131
if (!util.fileExistsSync(configFilePath)) {
132+
util.mkdirRecursivelySync(configFilePath);
132133
deviceContext = {};
133134
} else {
134135
deviceContext = util.tryParseJSON(fs.readFileSync(configFilePath, "utf8"));
@@ -142,13 +143,16 @@ export class ArduinoApp {
142143
deviceContext.configurations.forEach((section) => {
143144
if (section.name === util.getCppConfigPlatform()) {
144145
configSection = section;
146+
configSection.browse = configSection.browse || {};
147+
configSection.browse.limitSymbolsToIncludedHeaders = false;
145148
}
146149
});
147150

148151
if (!configSection) {
149152
configSection = {
150153
name: util.getCppConfigPlatform(),
151154
includePath: [],
155+
browse: { limitSymbolsToIncludedHeaders: false },
152156
};
153157
deviceContext.configurations.push(configSection);
154158
}
@@ -179,13 +183,13 @@ export class ArduinoApp {
179183
await util.spawn(this._settings.commandPath,
180184
showOutput ? arduinoChannel.channel : null,
181185
["--install-boards", `${packageName}:${arch}${version && ":" + version}`]);
182-
arduinoChannel.end(`Installed board package - ${packageName}`);
186+
arduinoChannel.end(`Installed board package - ${packageName}${os.EOL}`);
183187
}
184188

185189
public uninstallBoard(boardName: string, packagePath: string) {
186190
arduinoChannel.start(`Uninstall board package - ${boardName}...`);
187191
util.rmdirRecursivelySync(packagePath);
188-
arduinoChannel.end(`Installed board package - ${boardName}`);
192+
arduinoChannel.end(`Uninstalled board package - ${boardName}${os.EOL}`);
189193
}
190194

191195
public async installLibrary(libName: string, version: string = "", showOutput: boolean = true) {
@@ -195,13 +199,13 @@ export class ArduinoApp {
195199
showOutput ? arduinoChannel.channel : null,
196200
["--install-library", `${libName}${version && ":" + version}`]);
197201

198-
arduinoChannel.end(`Installed libarray - ${libName}`);
202+
arduinoChannel.end(`Installed libarray - ${libName}${os.EOL}`);
199203
}
200204

201205
public uninstallLibrary(libName: string, libPath: string) {
202206
arduinoChannel.start(`Remove library - ${libName}`);
203207
util.rmdirRecursivelySync(libPath);
204-
arduinoChannel.end(`Removed library - ${libName}`);
208+
arduinoChannel.end(`Removed library - ${libName}${os.EOL}`);
205209
}
206210

207211
public getDefaultPackageLibPaths(): string[] {

src/arduino/boardManager.ts

+1
Original file line numberDiff line numberDiff line change
@@ -244,6 +244,7 @@ export class BoardManager {
244244
dc.board = this.getBoardKey((<any>chosen).entry);
245245
this._currentBoard = (<any>chosen).entry;
246246
this._boardStatusBar.text = chosen.label;
247+
this._arduinoApp.addLibPath(null);
247248
}
248249
}
249250

src/common/constants.ts

+2
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@ import * as vscode from "vscode";
88

99
export const ARDUINO_CONFIG_FILE = path.join(".vscode", "arduino.json");
1010

11+
export const CPP_CONFIG_FILE = path.join(".vscode", "c_cpp_properties.json");
12+
1113
export const ARDUINO_MODE: vscode.DocumentSelector = [
1214
{ language: "cpp", scheme: "file" },
1315
{ language: "arduino", scheme: "file" },

src/extension.ts

+1-13
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,7 @@ import { ArduinoSettings } from "./arduino/settings";
1313
import { ARDUINO_MANAGER_PROTOCOL, ARDUINO_MODE, BOARD_MANAGER_URI, LIBRARY_MANAGER_URI } from "./common/constants";
1414
import { DeviceContext } from "./deviceContext";
1515
import { ClangProvider } from "./langService/clang";
16-
import { ClangFormatter } from "./langService/clangFormatter";
1716
import { CompletionProvider } from "./langService/completionProvider";
18-
import { DefinitionProvider } from "./langService/definitionProvider";
19-
import { FormatterProvider } from "./langService/formatterProvider";
2017
import * as Logger from "./logger/logger";
2118
import { SerialMonitor } from "./serialmonitor/serialMonitor";
2219

@@ -102,17 +99,8 @@ export async function activate(context: vscode.ExtensionContext) {
10299
context.subscriptions.push(registerCommand("arduino.sendMessageToSerialPort", () => monitor.sendMessageToSerialPort()));
103100
context.subscriptions.push(registerCommand("arduino.closeSerialMonitor", (port) => monitor.closeSerialMonitor(port)));
104101

105-
// Add arduino specific language suport.
106-
const clangProvider = new ClangProvider(arduinoApp);
107-
clangProvider.initialize();
108-
const completionProvider = new CompletionProvider(clangProvider);
109-
context.subscriptions.push(clangProvider);
102+
const completionProvider = new CompletionProvider(arduinoApp);
110103
context.subscriptions.push(vscode.languages.registerCompletionItemProvider(ARDUINO_MODE, completionProvider, "<", '"', "."));
111-
const definitionProvider = new DefinitionProvider(clangProvider);
112-
context.subscriptions.push(vscode.languages.registerDefinitionProvider(ARDUINO_MODE, definitionProvider));
113-
const clangFormatter = new ClangFormatter(arduinoSettings);
114-
const formatterProvider = new FormatterProvider(clangFormatter);
115-
context.subscriptions.push(vscode.languages.registerDocumentFormattingEditProvider(ARDUINO_MODE, formatterProvider));
116104

117105
// Example explorer, only work under VSCode insider version.
118106
if (typeof vscode.window.registerTreeExplorerNodeProvider === "function"

src/langService/completionProvider.ts

+76-5
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,32 @@
33
* Licensed under the MIT License. See License.txt in the project root for license information.
44
*-------------------------------------------------------------------------------------------*/
55

6+
import * as childProcess from "child_process";
7+
import * as fs from "fs";
8+
import * as path from "path";
69
import * as vscode from "vscode";
7-
import { ClangProvider } from "./clang";
10+
import * as constants from "../common/constants";
11+
import * as platform from "../common/platform";
12+
import * as util from "../common/util";
13+
14+
import { ArduinoApp } from "../arduino/arduino";
815

916
export class CompletionProvider implements vscode.CompletionItemProvider {
10-
public constructor(private _clangProvider: ClangProvider) {
17+
18+
private _headerFiles = new Set<string>();
19+
20+
private _libPaths = new Set<string>();
21+
22+
private _watcher: vscode.FileSystemWatcher;
23+
24+
private _cppConfigFile: string = path.join(vscode.workspace.rootPath, constants.CPP_CONFIG_FILE);
25+
26+
constructor(private _arduinoApp: ArduinoApp) {
27+
this.updateLibList();
28+
this._watcher = vscode.workspace.createFileSystemWatcher(this._cppConfigFile);
29+
this._watcher.onDidCreate(() => this.updateLibList());
30+
this._watcher.onDidChange(() => this.updateLibList());
31+
this._watcher.onDidDelete(() => this.updateLibList());
1132
}
1233

1334
public provideCompletionItems(document: vscode.TextDocument, position: vscode.Position, token: vscode.CancellationToken):
@@ -18,13 +39,63 @@ export class CompletionProvider implements vscode.CompletionItemProvider {
1839

1940
if (match) {
2041
let result = [];
21-
this._clangProvider.headerFiles.forEach((headerFile) => {
42+
this._headerFiles.forEach((headerFile) => {
2243
result.push(new vscode.CompletionItem(headerFile, vscode.CompletionItemKind.File));
2344
});
2445
return result;
25-
} else {
26-
return this._clangProvider.provideCompletionItems(document, position, token);
2746
}
2847
}
2948

49+
private updateLibList(): void {
50+
this._libPaths.clear();
51+
this._headerFiles.clear();
52+
this._arduinoApp.getDefaultPackageLibPaths().forEach((defaultPath) => {
53+
this._libPaths.add(defaultPath);
54+
});
55+
56+
if (fs.existsSync(this._cppConfigFile)) {
57+
58+
const deviceConfig = util.tryParseJSON(fs.readFileSync(this._cppConfigFile, "utf8"));
59+
if (deviceConfig) {
60+
if (deviceConfig.sketch) {
61+
const appFolder = path.dirname(deviceConfig.sketch);
62+
if (util.directoryExistsSync(appFolder)) {
63+
this._libPaths.add(path.normalize(appFolder));
64+
}
65+
}
66+
if (deviceConfig.configurations) {
67+
const plat = util.getCppConfigPlatform();
68+
deviceConfig.configurations.forEach((configSection) => {
69+
if (configSection.name === plat && Array.isArray(configSection.includePath)) {
70+
configSection.includePath.forEach((includePath) => {
71+
this._libPaths.add(path.normalize(includePath));
72+
});
73+
}
74+
});
75+
}
76+
}
77+
}
78+
79+
this._libPaths.forEach((includePath) => {
80+
this.addLibFiles(includePath);
81+
});
82+
}
83+
84+
private addLibFiles(libPath: string): void {
85+
if (!util.directoryExistsSync(libPath)) {
86+
return;
87+
}
88+
const subItems = fs.readdirSync(libPath);
89+
subItems.forEach((item) => {
90+
try {
91+
let state = fs.statSync(path.join(libPath, item));
92+
if (state.isFile() && item.endsWith(".h")) {
93+
this._headerFiles.add(item);
94+
} else if (state.isDirectory()) {
95+
this.addLibFiles(path.join(libPath, item));
96+
}
97+
} catch (ex) {
98+
}
99+
});
100+
}
30101
}

0 commit comments

Comments
 (0)