Skip to content

Commit 4b0e47f

Browse files
committed
2 parents 1371407 + a9b149a commit 4b0e47f

File tree

5 files changed

+189
-39
lines changed

5 files changed

+189
-39
lines changed

LICENSE

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
The MIT License (MIT)
2+
3+
Copyright (c) 2016 Xaver Hellauer
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.

README.md

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,12 @@
22

33
## Release history
44

5+
### v 0.9.0
6+
* add protobuf support (work with https://marketplace.visualstudio.com/items?itemName=peterj.proto)
7+
* add javascript/typescript support
8+
* allow different style & fallback style option for different languages
9+
* format on save is available now (just like https://github.com/Microsoft/vscode-go/blob/master/src/goMain.ts)
10+
511
### v 0.6.1
612
* clean up dependencies #9
713

@@ -28,5 +34,4 @@
2834
If clang-format is installed and in PATH, C/C++ etc source files can be formatted with Visual Studio Code's built-in formatter (Usually: Ctrl+Shift+F).
2935

3036
## Source code
31-
3237
Available on github: https://github.com/xaverh/vscode-clang-format-provider

package.json

Lines changed: 86 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,13 @@
22
"name": "clang-format",
33
"displayName": "Clang-Format",
44
"description": "Use Clang-Format in Visual Studio Code",
5-
"version": "0.6.1",
5+
"version": "0.9.0",
66
"publisher": "xaver",
77
"engines": {
88
"vscode": "^1.0.0"
99
},
1010
"dependencies": {
11-
"sax" : "^1.1.5"
11+
"sax": "^1.1.5"
1212
},
1313
"categories": [
1414
"Other"
@@ -20,7 +20,8 @@
2020
"onLanguage:objective-c",
2121
"onLanguage:java",
2222
"onLanguage:javascript",
23-
"onLanguage:typescript"
23+
"onLanguage:typescript",
24+
"onLanguage:proto"
2425
],
2526
"contributes": {
2627
"configuration": {
@@ -33,20 +34,90 @@
3334
"description": "Run 'clang-format' on save."
3435
},
3536
"clang-format.executable": {
36-
"type": "string",
37-
"default": "clang-format",
38-
"description": "clang-format executable path"
39-
},
37+
"type": "string",
38+
"default": "clang-format",
39+
"description": "clang-format executable path"
40+
},
4041
"clang-format.style": {
41-
"type": "string",
42-
"default": "file",
43-
"description": "clang-format style.(-style=value, value can be file, LLVM, Google, Chromium, Mozilla, WebKit or json configure)"
44-
},
42+
"type": "string",
43+
"default": "file",
44+
"description": "clang-format style.(-style=value, value can be file, LLVM, Google, Chromium, Mozilla, WebKit or json configure)"
45+
},
4546
"clang-format.fallbackStyle": {
46-
"type": "string",
47-
"default": "LLVM",
48-
"description": "clang-format fallback style.(-fallback-style=value, value can be none, LLVM, Google, Chromium, Mozilla, WebKit)"
49-
}
47+
"type": "string",
48+
"default": "LLVM",
49+
"description": "clang-format fallback style.(-fallback-style=value, value can be none, LLVM, Google, Chromium, Mozilla, WebKit)"
50+
},
51+
"clang-format.language.cpp.style": {
52+
"type": "string",
53+
"default": "",
54+
"description": "clang-format fallback style for c++, left empty to use clang-format.style"
55+
},
56+
"clang-format.language.cpp.fallbackStyle": {
57+
"type": "string",
58+
"default": "",
59+
"description": "clang-format fallback style for c++, left empty to use clang-format.fallbackStyle"
60+
},
61+
"clang-format.language.c.style": {
62+
"type": "string",
63+
"default": "",
64+
"description": "clang-format fallback style for c, left empty to use clang-format.style"
65+
},
66+
"clang-format.language.c.fallbackStyle": {
67+
"type": "string",
68+
"default": "",
69+
"description": "clang-format fallback style for c, left empty to use clang-format.fallbackStyle"
70+
},
71+
"clang-format.language.objective-c.style": {
72+
"type": "string",
73+
"default": "",
74+
"description": "clang-format fallback style for objective-c, left empty to use clang-format.style"
75+
},
76+
"clang-format.language.objective-c.fallbackStyle": {
77+
"type": "string",
78+
"default": "",
79+
"description": "clang-format fallback style for objective-c, left empty to use clang-format.fallbackStyle"
80+
},
81+
"clang-format.language.java.style": {
82+
"type": "string",
83+
"default": "",
84+
"description": "clang-format fallback style for java, left empty to use clang-format.style"
85+
},
86+
"clang-format.language.java.fallbackStyle": {
87+
"type": "string",
88+
"default": "",
89+
"description": "clang-format fallback style for java, left empty to use clang-format.fallbackStyle"
90+
},
91+
"clang-format.language.javascript.style": {
92+
"type": "string",
93+
"default": "",
94+
"description": "clang-format fallback style for javascript, left empty to use clang-format.style"
95+
},
96+
"clang-format.language.javascript.fallbackStyle": {
97+
"type": "string",
98+
"default": "",
99+
"description": "clang-format fallback style for javascript, left empty to use clang-format.fallbackStyle"
100+
},
101+
"clang-format.language.typescript.style": {
102+
"type": "string",
103+
"default": "",
104+
"description": "clang-format fallback style for typescript, left empty to use clang-format.style"
105+
},
106+
"clang-format.language.typescript.fallbackStyle": {
107+
"type": "string",
108+
"default": "",
109+
"description": "clang-format fallback style for typescript, left empty to use clang-format.fallbackStyle"
110+
},
111+
"clang-format.language.proto.style": {
112+
"type": "string",
113+
"default": "",
114+
"description": "clang-format fallback style for proto, left empty to use clang-format.style"
115+
},
116+
"clang-format.language.proto.fallbackStyle": {
117+
"type": "string",
118+
"default": "",
119+
"description": "clang-format fallback style for proto, left empty to use clang-format.fallbackStyle"
120+
}
50121
}
51122
}
52123
},

src/clangMode.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,5 @@
22

33
import vscode = require('vscode');
44

5-
const LANGUAGES: string[] = ['cpp', 'c', 'objective-c', 'java', 'javascript', 'typescript'];
5+
const LANGUAGES: string[] = ['cpp', 'c', 'objective-c', 'java', 'javascript', 'typescript', 'proto'];
66
export const MODES: vscode.DocumentFilter[] = LANGUAGES.map(language => ({ language, scheme: 'file' }));

src/extension.ts

Lines changed: 75 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,9 @@ export class ClangDocumentFormattingEditProvider implements vscode.DocumentForma
5959

6060

6161
parser.onopentag = (tag) => {
62-
if (currentEdit) { reject("Malformed output"); }
62+
if (currentEdit) {
63+
reject("Malformed output");
64+
}
6365

6466
switch (tag.name) {
6567
case "replacements":
@@ -120,24 +122,27 @@ export class ClangDocumentFormattingEditProvider implements vscode.DocumentForma
120122
return this.defaultConfigure.executable;
121123
}
122124

123-
private getStyle() {
124-
let ret = vscode.workspace.getConfiguration('clang-format').get<string>('style');
125+
private getStyle(document: vscode.TextDocument) {
126+
let ret = vscode.workspace.getConfiguration('clang-format').get<string>(`language.${document.languageId}.style`);
125127
if (ret.trim()) {
126-
ret = ret.trim();
128+
return ret.trim();
129+
}
130+
131+
ret = vscode.workspace.getConfiguration('clang-format').get<string>('style');
132+
if (ret && ret.trim()) {
133+
return ret.trim();
127134
} else {
128-
ret = this.defaultConfigure.style;
135+
return this.defaultConfigure.style;
129136
}
130-
131-
// Custom style
132-
// if (ret.match(/[\\\{\" ]/)) {
133-
// return `"${ret.replace(/([\\\"])/g, "\\$1")}"`
134-
// }
135-
136-
return ret;
137137
}
138138

139-
private getFallbackStyle() {
140-
let strConf = vscode.workspace.getConfiguration('clang-format').get<string>('fallbackStyle');
139+
private getFallbackStyle(document: vscode.TextDocument) {
140+
let strConf = vscode.workspace.getConfiguration('clang-format').get<string>(`language.${document.languageId}.fallbackStyle`);
141+
if (strConf.trim()) {
142+
return strConf;
143+
}
144+
145+
strConf = vscode.workspace.getConfiguration('clang-format').get<string>('fallbackStyle');
141146
if (strConf.trim()) {
142147
return strConf;
143148
}
@@ -158,7 +163,9 @@ export class ClangDocumentFormattingEditProvider implements vscode.DocumentForma
158163
vscode.window.showInformationMessage("The '" + formatCommandBinPath + "' command is not available. Please check your clang.formatTool user setting and ensure it is installed.");
159164
return resolve(null);
160165
}
161-
if (err) return reject("Cannot format due to syntax errors.");
166+
if (err) {
167+
return reject("Cannot format due to syntax errors.");
168+
}
162169

163170
var dummyProcessor = (value: string) => {
164171
debugger;
@@ -173,8 +180,8 @@ export class ClangDocumentFormattingEditProvider implements vscode.DocumentForma
173180

174181
var formatArgs = [
175182
'-output-replacements-xml',
176-
`-style=${this.getStyle()}`,
177-
`-fallback-style=${this.getFallbackStyle()}`,
183+
`-style=${this.getStyle(document)}`,
184+
`-fallback-style=${this.getFallbackStyle(document)}`,
178185
`-assume-filename=${document.fileName}`,
179186
];
180187

@@ -198,23 +205,69 @@ export class ClangDocumentFormattingEditProvider implements vscode.DocumentForma
198205
var child = cp.execFile(formatCommandBinPath, formatArgs, { cwd: workingPath }, childCompleted);
199206
child.stdin.end(codeContent);
200207

201-
token.onCancellationRequested(() => {
202-
child.kill();
203-
reject("Cancelation requested");
204-
});
208+
if(token) {
209+
token.onCancellationRequested(() => {
210+
child.kill();
211+
reject("Cancelation requested");
212+
});
213+
}
205214
});
206215
}
207216

217+
public formatDocument(document: vscode.TextDocument): Thenable<vscode.TextEdit[]>{
218+
return this.doFormatDocument(document, null, null, null);
219+
}
220+
208221
}
209222

210223
let diagnosticCollection: vscode.DiagnosticCollection;
211224

212225
export function activate(ctx: vscode.ExtensionContext): void {
213226

214227
var formatter = new ClangDocumentFormattingEditProvider();
228+
var availableLanguages = {};
215229

216230
MODES.forEach(mode => {
217231
ctx.subscriptions.push(vscode.languages.registerDocumentRangeFormattingEditProvider(mode, formatter));
218232
ctx.subscriptions.push(vscode.languages.registerDocumentFormattingEditProvider(mode, formatter));
219-
})
233+
availableLanguages[mode.language] = true;
234+
});
235+
236+
// TODO: This is really ugly. I'm not sure we can do better until
237+
// Code supports a pre-save event where we can do the formatting before
238+
// the file is written to disk.
239+
// @see https://github.com/Microsoft/vscode-go/blob/master/src/goMain.ts
240+
let ignoreNextSave = new WeakSet<vscode.TextDocument>();
241+
242+
vscode.workspace.onDidSaveTextDocument(document => {
243+
try {
244+
let formatOnSave = vscode.workspace.getConfiguration('clang-format').get<boolean>('formatOnSave');
245+
if (!formatOnSave) {
246+
return;
247+
}
248+
249+
if (!availableLanguages[document.languageId] || ignoreNextSave.has(document)) {
250+
return;
251+
}
252+
253+
let textEditor = vscode.window.activeTextEditor;
254+
formatter.formatDocument(document).then(edits => {
255+
return textEditor.edit(editBuilder => {
256+
edits.forEach(edit => editBuilder.replace(edit.range, edit.newText))
257+
});
258+
}).then(applied => {
259+
ignoreNextSave.add(document);
260+
return document.save();
261+
}).then(
262+
() => {
263+
ignoreNextSave.delete(document);
264+
}, () => {
265+
// Catch any errors and ignore so that we still trigger
266+
// the file save.
267+
}
268+
);
269+
} catch(e) {
270+
console.error('formate when save file failed.' + e.toString());
271+
}
272+
});
220273
}

0 commit comments

Comments
 (0)