1 module dlangide.workspace.idesettings;
2 
3 import dlangui.core.settings;
4 import dlangui.core.i18n;
5 import dlangui.graphics.fonts;
6 
7 import std.algorithm : equal;
8 
9 const AVAILABLE_THEMES = ["ide_theme_default", "ide_theme_dark"];
10 const AVAILABLE_LANGUAGES = ["en", "ru", "es", "cs"];
11 
12 class IDESettings : SettingsFile {
13 
14     this(string filename) {
15         super(filename);
16     }
17 
18     override void updateDefaults() {
19         Setting ed = editorSettings();
20         ed.setBooleanDef("useSpacesForTabs", true);
21         ed.setIntegerDef("tabSize", 4);
22         ed.setBooleanDef("smartIndents", true);
23         ed.setBooleanDef("smartIndentsAfterPaste", true);
24         ed.setBooleanDef("showWhiteSpaceMarks", true);
25         ed.setBooleanDef("showTabPositionMarks", true);
26         ed.setStringDef("fontFace", "Default");
27         ed.setIntegerDef("fontSize", 11);
28         Setting ui = uiSettings();
29         ui.setStringDef("theme", "ide_theme_default");
30         ui.setStringDef("language", "en");
31         ui.setIntegerDef("hintingMode", 1);
32         ui.setIntegerDef("minAntialiasedFontSize", 0);
33         ui.setFloatingDef("fontGamma", 0.8);
34         ui.setStringDef("uiFontFace", "Default");
35         ui.setIntegerDef("uiFontSize", 10);
36         version (Windows) {
37             debuggerSettings.setStringDef("executable", "mago-mi");
38         } else {
39             debuggerSettings.setStringDef("executable", "gdb");
40         }
41         terminalSettings.setStringDef("executable", "xterm");
42         dubSettings.setStringDef("executable", "dub");
43         dubSettings.setStringDef("additional_params", "");
44         rdmdSettings.setStringDef("executable", "rdmd");
45         rdmdSettings.setStringDef("additional_params", "");
46         dmdToolchainSettings.setStringDef("executable", "dmd");
47         dmdToolchainSettings.setStringDef("dub_additional_params", "");
48         ldcToolchainSettings.setStringDef("executable", "ldc2");
49         ldcToolchainSettings.setStringDef("dub_additional_params", "");
50         ldmdToolchainSettings.setStringDef("executable", "ldmd2");
51         ldmdToolchainSettings.setStringDef("dub_additional_params", "");
52         gdcToolchainSettings.setStringDef("executable", "gdc");
53         gdcToolchainSettings.setStringDef("dub_additional_params", "");
54     }
55 
56     /// override to do something after loading - e.g. set defaults
57     override void afterLoad() {
58     }
59     
60     @property Setting editorSettings() {
61         Setting res = _setting.objectByPath("editors/textEditor", true);
62         return res;
63     }
64 
65     @property Setting uiSettings() {
66         Setting res = _setting.objectByPath("interface", true);
67         return res;
68     }
69 
70     @property Setting debuggerSettings() {
71         Setting res = _setting.objectByPath("dlang/debugger", true);
72         return res;
73     }
74 
75     @property Setting terminalSettings() {
76         Setting res = _setting.objectByPath("dlang/terminal", true);
77         return res;
78     }
79 
80     @property Setting dubSettings() {
81         Setting res = _setting.objectByPath("dlang/dub", true);
82         return res;
83     }
84 
85     @property Setting rdmdSettings() {
86         Setting res = _setting.objectByPath("dlang/rdmd", true);
87         return res;
88     }
89 
90     @property Setting dmdToolchainSettings() {
91         Setting res = _setting.objectByPath("dlang/toolchains/dmd", true);
92         return res;
93     }
94 
95     @property Setting ldcToolchainSettings() {
96         Setting res = _setting.objectByPath("dlang/toolchains/ldc", true);
97         return res;
98     }
99 
100     @property Setting ldmdToolchainSettings() {
101         Setting res = _setting.objectByPath("dlang/toolchains/ldmd", true);
102         return res;
103     }
104 
105     @property Setting gdcToolchainSettings() {
106         Setting res = _setting.objectByPath("dlang/toolchains/gdc", true);
107         return res;
108     }
109 
110     /// theme
111     @property string uiTheme() {
112         return limitString(uiSettings.getString("theme", "ide_theme_default"), AVAILABLE_THEMES);
113     }
114     /// theme
115     @property IDESettings uiTheme(string v) {
116         uiSettings.setString("theme", limitString(v, AVAILABLE_THEMES));
117         return this;
118     }
119 
120     /// language
121     @property string uiLanguage() {
122         return limitString(uiSettings.getString("language", "en"), AVAILABLE_LANGUAGES);
123     }
124     /// language
125     @property IDESettings uiLanguage(string v) {
126         uiSettings.setString("language", limitString(v, AVAILABLE_LANGUAGES));
127         return this;
128     }
129 
130     /// UI font face
131     @property string uiFontFace() {
132         return uiSettings.getString("uiFontFace", "Default");
133     }
134 
135     /// UI font size
136     @property int uiFontSize() {
137         return pointsToPixels(cast(int)uiSettings.getInteger("uiFontSize", 10));
138     }
139 
140     /// text editor setting, true if need to insert spaces instead of tabs
141     @property bool useSpacesForTabs() {
142         return editorSettings.getBoolean("useSpacesForTabs", true);
143     }
144     /// text editor setting, true if need to insert spaces instead of tabs
145     @property IDESettings useSpacesForTabs(bool v) {
146         editorSettings.setBoolean("useSpacesForTabs", v);
147         return this;
148     }
149 
150     /// text editor setting, true if need to insert spaces instead of tabs
151     @property int tabSize() {
152         return limitInt(editorSettings.getInteger("tabSize", 4), 1, 16);
153     }
154     /// text editor setting, true if need to insert spaces instead of tabs
155     @property IDESettings tabSize(int v) {
156         editorSettings.setInteger("tabSize", limitInt(v, 1, 16));
157         return this;
158     }
159 
160     /// true if smart indents are enabled
161     @property bool smartIndents() { return editorSettings.getBoolean("smartIndents", true); }
162     /// set smart indents enabled flag
163     @property IDESettings smartIndents(bool enabled) { editorSettings.setBoolean("smartIndents", enabled); return this; }
164 
165     /// true if white space marks are enabled
166     @property bool showWhiteSpaceMarks() { return editorSettings.getBoolean("showWhiteSpaceMarks", true); }
167     /// set white space marks enabled flag
168     @property IDESettings showWhiteSpaceMarks(bool enabled) { editorSettings.setBoolean("showWhiteSpaceMarks", enabled); return this; }
169 
170     /// true if tab position marks are enabled
171     @property bool showTabPositionMarks() { return editorSettings.getBoolean("showTabPositionMarks", true); }
172     /// set tab position marks enabled flag
173     @property IDESettings showTabPositionMarks(bool enabled) { editorSettings.setBoolean("showTabPositionMarks", enabled); return this; }
174     /// string value of font face in text editors
175     @property string editorFontFace() { return editorSettings.getString("fontFace", "Default"); }
176     /// int value of font size in text editors
177     @property int editorFontSize() { return cast(int)editorSettings.getInteger("fontSize", 11); }
178 
179     /// true if smart indents are enabled
180     @property bool smartIndentsAfterPaste() { return editorSettings.getBoolean("smartIndentsAfterPaste", true); }
181     /// set smart indents enabled flag
182     @property IDESettings smartIndentsAfterPaste(bool enabled) { editorSettings.setBoolean("smartIndentsAfterPaste", enabled); return this; }
183 
184     @property double fontGamma() {
185         double gamma = uiSettings.getFloating("fontGamma", 1.0);
186         if (gamma >= 0.5 && gamma <= 2.0)
187             return gamma;
188         return 1.0;
189     }
190 
191     @property HintingMode hintingMode() {
192         long mode = uiSettings.getInteger("hintingMode", HintingMode.Normal);
193         if (mode >= HintingMode.Normal && mode <= HintingMode.Light)
194             return cast(HintingMode)mode;
195         return HintingMode.Normal;
196     }
197 
198     @property int minAntialiasedFontSize() {
199         long sz = uiSettings.getInteger("minAntialiasedFontSize", 0);
200         if (sz >= 0)
201             return cast(int)sz;
202         return 0;
203     }
204 
205     @property string debuggerExecutable() {
206         version (Windows) {
207             return debuggerSettings.getString("executable", "mago-mi");
208         } else {
209             return debuggerSettings.getString("executable", "gdb");
210         }
211     }
212 
213     @property string terminalExecutable() {
214         return terminalSettings.getString("executable", "xterm");
215     }
216 
217     @property string dubExecutable() {
218         return dubSettings.getString("executable", "dub");
219     }
220 
221     @property string dubAdditionalParams() {
222         return dubSettings.getString("additional_params", "");
223     }
224 
225     @property string rdmdExecutable() {
226         return rdmdSettings.getString("executable", "rdmd");
227     }
228 
229     @property string rdmdAdditionalParams() {
230         return rdmdSettings.getString("additional_params", "");
231     }
232 
233     string getToolchainCompilerExecutable(string toolchainName) {
234         if (toolchainName.equal("dmd"))
235             return dmdToolchainSettings.getString("executable", "dmd");
236         if (toolchainName.equal("gdc"))
237             return gdcToolchainSettings.getString("executable", "gdc");
238         if (toolchainName.equal("ldc"))
239             return ldcToolchainSettings.getString("executable", "ldc2");
240         if (toolchainName.equal("ldmd"))
241             return ldmdToolchainSettings.getString("executable", "ldmd2");
242         return null;
243     }
244 
245     string getToolchainAdditionalDubParams(string toolchainName) {
246         if (toolchainName.equal("dmd"))
247             return dmdToolchainSettings.getString("dub_additional_params", "");
248         if (toolchainName.equal("gdc"))
249             return gdcToolchainSettings.getString("dub_additional_params", "");
250         if (toolchainName.equal("ldc"))
251             return ldcToolchainSettings.getString("dub_additional_params", "");
252         if (toolchainName.equal("ldmd"))
253             return ldmdToolchainSettings.getString("dub_additional_params", "");
254         return null;
255     }
256 
257     /// get recent path for category name, returns null if not found
258     @property string getRecentPath(string category = "FILE_OPEN_DLG_PATH") {
259         Setting obj = _setting.objectByPath("pathHistory", true);
260         return obj.getString(category, null);
261     }
262 
263     /// set recent path for category name
264     @property void setRecentPath(string value, string category = "FILE_OPEN_DLG_PATH") {
265         Setting obj = _setting.objectByPath("pathHistory", true);
266         obj.setString(category, value);
267         save();
268     }
269 
270     @property string[] recentWorkspaces() {
271         import std.file;
272         Setting obj = _setting.objectByPath("history", true);
273         string[] list = obj.getStringArray("recentWorkspaces");
274         string[] res;
275         foreach(fn; list) {
276             if (exists(fn) && isFile(fn))
277                 res ~= fn;
278         }
279         return res;
280     }
281 
282     void updateRecentWorkspace(string ws) {
283         import std.file;
284         string[] list;
285         list ~= ws;
286         string[] existing = recentWorkspaces;
287         foreach(fn; existing) {
288             if (exists(fn) && isFile(fn) && !ws.equal(fn))
289                 list ~= fn;
290         }
291         Setting obj = _setting.objectByPath("history", true);
292         obj["recentWorkspaces"] = list;
293         save();
294     }
295     
296     @property bool autoOpenLastProject() {
297         Setting obj =_setting.objectByPath("common", true);
298         return obj.getBoolean("autoOpenLastProject", false);
299     }
300 
301     @property void autoOpenLastProject(bool value) {
302         Setting obj =_setting.objectByPath("common", true);
303         obj.setBoolean("autoOpenLastProject", value);
304     }
305 }
306