From 45c5a16c770929da58ee7e8870244625e8c48beb Mon Sep 17 00:00:00 2001 From: Adam Kovari Date: Thu, 10 Jun 2021 16:15:13 +0200 Subject: [PATCH] Added ability to configure parser/lexer class names. --- README.md | 3 +- .../plugin/ANTLRv4PluginController.java | 19 ++++++--- .../ANTLRv4GrammarProperties.java | 16 +++++++ .../configdialogs/ConfigANTLRDialogPanel.form | 42 +++++++++++++++++-- .../configdialogs/ConfigANTLRPerGrammar.java | 36 +++++++++++++++- 5 files changed, 104 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 074b4ebe..0c63cdd8 100644 --- a/README.md +++ b/README.md @@ -67,7 +67,8 @@ base parser/lexer classes, your custom code will *not* be run during live previe As of 1.17, this limitation is partially not true. The configuration window of a grammar has a new option that allows using the generated parser code in the preview. In this case, the grammar must be compiled into a Java class (just to be on Project's target classpath). Any changes made to such grammar are not immediately -reflected in the preview and the project must be recompiled instead. +reflected in the preview and the project must be recompiled instead. It is also possible to specify the name of the +compiler parser/lexer class. By default the name of the grammar is used (parser and lexer grammar). ## History diff --git a/src/main/java/org/antlr/intellij/plugin/ANTLRv4PluginController.java b/src/main/java/org/antlr/intellij/plugin/ANTLRv4PluginController.java index 88b050ab..3ba2e165 100644 --- a/src/main/java/org/antlr/intellij/plugin/ANTLRv4PluginController.java +++ b/src/main/java/org/antlr/intellij/plugin/ANTLRv4PluginController.java @@ -101,6 +101,9 @@ public class ANTLRv4PluginController implements ProjectComponent { private ProgressIndicator parsingProgressIndicator; private UrlClassLoader projectClassLoader; + private Class tokenStreamClass; + private Class charStreamClass; + public ANTLRv4PluginController(Project project) { this.project = project; } @@ -217,12 +220,19 @@ private void initClassLoader() { for (String path : compiledClassUrls) { try { urls.add(new File(FileUtil.toSystemIndependentName(path)).toURI().toURL()); - } catch (MalformedURLException e1) { + } catch (MalformedURLException e1) { LOG.error(e1); } } this.projectClassLoader = UrlClassLoader.build().parent(TokenStream.class.getClassLoader()).urls(urls).get(); + + try { + this.tokenStreamClass = Class.forName(TokenStream.class.getName(), true, this.projectClassLoader); + this.charStreamClass = Class.forName(CharStream.class.getName(), true, this.projectClassLoader); + } catch (ClassNotFoundException e) { + LOG.error(e); + } } // ------------------------------ @@ -426,13 +436,10 @@ private String updateGrammarObjectsFromFile_(VirtualFile grammarFile) { ANTLRv4GrammarProperties grammarProperties = ANTLRv4GrammarPropertiesStore.getGrammarProperties(project, grammarFile); if (grammarProperties.isUseGeneratedParserCodeCheckBox()) { - String parserClassName = grammarFile.getNameWithoutExtension(); - String lexerClassName = lg.name; + String parserClassName = grammarProperties.getGeneratedParserClassName() != null ? grammarProperties.getGeneratedParserClassName() : grammarFile.getNameWithoutExtension(); + String lexerClassName = grammarProperties.getGeneratedLexerClassName() != null ? grammarProperties.getGeneratedLexerClassName() : lg.name; try { - Class tokenStreamClass = Class.forName(TokenStream.class.getName(), true, this.projectClassLoader); - Class charStreamClass = Class.forName(CharStream.class.getName(), true, this.projectClassLoader); - Class parserClass = (Class) Class.forName(parserClassName, true, this.projectClassLoader); Class lexerClass = (Class) Class.forName(lexerClassName, true, this.projectClassLoader); diff --git a/src/main/java/org/antlr/intellij/plugin/configdialogs/ANTLRv4GrammarProperties.java b/src/main/java/org/antlr/intellij/plugin/configdialogs/ANTLRv4GrammarProperties.java index bfdc2a9d..f89cac57 100644 --- a/src/main/java/org/antlr/intellij/plugin/configdialogs/ANTLRv4GrammarProperties.java +++ b/src/main/java/org/antlr/intellij/plugin/configdialogs/ANTLRv4GrammarProperties.java @@ -81,6 +81,12 @@ public class ANTLRv4GrammarProperties implements Cloneable { @Property boolean useGeneratedParserCodeCheckBox = false; + @Property + String generatedParserClassName; + + @Property + String generatedLexerClassName; + public ANTLRv4GrammarProperties() { } @@ -96,6 +102,8 @@ public ANTLRv4GrammarProperties(ANTLRv4GrammarProperties source) { this.generateVisitor = source.generateVisitor; this.caseChangingStrategy = source.caseChangingStrategy; this.useGeneratedParserCodeCheckBox = source.useGeneratedParserCodeCheckBox; + this.generatedParserClassName = source.generatedParserClassName; + this.generatedLexerClassName = source.generatedLexerClassName; } public boolean shouldAutoGenerateParser() { @@ -134,6 +142,14 @@ public boolean isUseGeneratedParserCodeCheckBox() { return useGeneratedParserCodeCheckBox; } + public String getGeneratedParserClassName() { + return generatedParserClassName; + } + + public String getGeneratedLexerClassName() { + return generatedLexerClassName; + } + public CaseChangingStrategy getCaseChangingStrategy() { return caseChangingStrategy; } diff --git a/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRDialogPanel.form b/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRDialogPanel.form index 7b6ac33d..c7f7a6a5 100644 --- a/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRDialogPanel.form +++ b/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRDialogPanel.form @@ -1,9 +1,9 @@
- + - + @@ -134,9 +134,45 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRPerGrammar.java b/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRPerGrammar.java index 611e4400..ffe65ef8 100644 --- a/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRPerGrammar.java +++ b/src/main/java/org/antlr/intellij/plugin/configdialogs/ConfigANTLRPerGrammar.java @@ -33,8 +33,10 @@ public class ConfigANTLRPerGrammar extends DialogWrapper { protected JTextField languageField; private JComboBox caseTransformation; private JCheckBox useGeneratedParserCodeCheckBox; + private JTextField generatedParserClassName; + private JTextField generatedLexerClassName; - private ConfigANTLRPerGrammar(final Project project) { + private ConfigANTLRPerGrammar(final Project project) { super(project, false); } @@ -66,6 +68,15 @@ private void initAntlrFields(Project project, String qualFileName) { libDirField.setTextFieldPreferredWidth(50); loadValues(project, qualFileName); + + useGeneratedParserCodeCheckBox.addActionListener(e -> toggleGeneratedClassNames()); + toggleGeneratedClassNames(); + } + + private void toggleGeneratedClassNames() { + boolean enabled = useGeneratedParserCodeCheckBox.isSelected(); + generatedParserClassName.setEnabled(enabled); + generatedLexerClassName.setEnabled(enabled); } public void loadValues(Project project, String qualFileName) { @@ -81,6 +92,8 @@ public void loadValues(Project project, String qualFileName) { generateParseTreeListenerCheckBox.setSelected(grammarProperties.shouldGenerateParseTreeListener()); generateParseTreeVisitorCheckBox.setSelected(grammarProperties.shouldGenerateParseTreeVisitor()); useGeneratedParserCodeCheckBox.setSelected(grammarProperties.isUseGeneratedParserCodeCheckBox()); + generatedParserClassName.setText(grammarProperties.generatedParserClassName); + generatedLexerClassName.setText(grammarProperties.generatedLexerClassName); } public void saveValues(Project project, String qualFileName) { @@ -96,6 +109,8 @@ public void saveValues(Project project, String qualFileName) { grammarProperties.generateListener = generateParseTreeListenerCheckBox.isSelected(); grammarProperties.generateVisitor = generateParseTreeVisitorCheckBox.isSelected(); grammarProperties.useGeneratedParserCodeCheckBox = useGeneratedParserCodeCheckBox.isSelected(); + grammarProperties.generatedParserClassName = getGeneratedParserClassName(); + grammarProperties.generatedLexerClassName = getGeneratedLexerClassName(); } boolean isModified(ANTLRv4GrammarProperties originalProperties) { @@ -104,7 +119,10 @@ boolean isModified(ANTLRv4GrammarProperties originalProperties) { || !Objects.equals(originalProperties.getEncoding(), getFileEncodingText()) || !Objects.equals(originalProperties.getPackage(), getPackageFieldText()) || !Objects.equals(originalProperties.getLanguage(), getLanguageText()) - || !Objects.equals(originalProperties.caseChangingStrategy, getCaseChangingStrategy()); + || !Objects.equals(originalProperties.caseChangingStrategy, getCaseChangingStrategy()) + || !Objects.equals(originalProperties.isUseGeneratedParserCodeCheckBox(), isUseGeneratedParserCode()) + || !Objects.equals(originalProperties.generatedParserClassName, getGeneratedParserClassName()) + || !Objects.equals(originalProperties.generatedLexerClassName, getGeneratedLexerClassName()); } String getLanguageText() { @@ -127,6 +145,18 @@ String getOutputDirText() { return outputDirField.getText(); } + boolean isUseGeneratedParserCode() { + return useGeneratedParserCodeCheckBox.isSelected(); + } + + String getGeneratedParserClassName() { + return generatedParserClassName.getText(); + } + + String getGeneratedLexerClassName() { + return generatedLexerClassName.getText(); + } + private CaseChangingStrategy getCaseChangingStrategy() { return (CaseChangingStrategy) caseTransformation.getSelectedItem(); } @@ -146,6 +176,8 @@ public String toString() { ", packageField=" + packageField + ", outputDirField=" + outputDirField + ", libDirField=" + libDirField + + ", generatedParserClassName=" + generatedParserClassName + + ", generatedLexerClassName=" + generatedLexerClassName + '}'; }