Drafting TeaVM module settings dialog

This commit is contained in:
Alexey Andreev 2016-02-10 00:00:53 +03:00
parent 78d6917a23
commit c744cd3644
7 changed files with 356 additions and 13 deletions

View File

@ -5,17 +5,21 @@
<value> <value>
<option name="CLASS_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99" /> <option name="CLASS_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99" />
<option name="NAMES_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99" /> <option name="NAMES_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99" />
<option name="PACKAGES_TO_USE_IMPORT_ON_DEMAND">
<value />
</option>
<option name="IMPORT_LAYOUT_TABLE"> <option name="IMPORT_LAYOUT_TABLE">
<value> <value>
<package name="javax" withSubpackages="true" static="false" />
<package name="java" withSubpackages="true" static="false" />
<package name="" withSubpackages="true" static="false" />
<package name="" withSubpackages="true" static="true" /> <package name="" withSubpackages="true" static="true" />
<package name="" withSubpackages="true" static="false" />
</value> </value>
</option> </option>
<JavaCodeStyleSettings> <JavaCodeStyleSettings>
<option name="ANNOTATION_PARAMETER_WRAP" value="1" /> <option name="ANNOTATION_PARAMETER_WRAP" value="1" />
</JavaCodeStyleSettings> </JavaCodeStyleSettings>
<XML>
<option name="XML_LEGACY_SETTINGS_IMPORTED" value="true" />
</XML>
<codeStyleSettings language="JAVA"> <codeStyleSettings language="JAVA">
<option name="KEEP_BLANK_LINES_IN_DECLARATIONS" value="1" /> <option name="KEEP_BLANK_LINES_IN_DECLARATIONS" value="1" />
<option name="KEEP_BLANK_LINES_IN_CODE" value="1" /> <option name="KEEP_BLANK_LINES_IN_CODE" value="1" />
@ -264,6 +268,13 @@
</rules> </rules>
</arrangement> </arrangement>
</codeStyleSettings> </codeStyleSettings>
<codeStyleSettings language="XML">
<indentOptions>
<option name="INDENT_SIZE" value="2" />
<option name="CONTINUATION_INDENT_SIZE" value="4" />
<option name="TAB_SIZE" value="2" />
</indentOptions>
</codeStyleSettings>
</value> </value>
</option> </option>
<option name="USE_PER_PROJECT_SETTINGS" value="true" /> <option name="USE_PER_PROJECT_SETTINGS" value="true" />

View File

@ -22,9 +22,12 @@ import org.jetbrains.jps.builders.BuildTargetType;
import org.jetbrains.jps.incremental.BuilderCategory; import org.jetbrains.jps.incremental.BuilderCategory;
import org.jetbrains.jps.incremental.BuilderService; import org.jetbrains.jps.incremental.BuilderService;
import org.jetbrains.jps.incremental.ModuleLevelBuilder; import org.jetbrains.jps.incremental.ModuleLevelBuilder;
import org.jetbrains.jps.incremental.TargetBuilder;
public class TeaVMBuilderService extends BuilderService { public class TeaVMBuilderService extends BuilderService {
TeaVMBuilderService() {
System.out.println("Hello");
}
@NotNull @NotNull
@Override @Override
public List<? extends BuildTargetType<?>> getTargetTypes() { public List<? extends BuildTargetType<?>> getTargetTypes() {

View File

@ -0,0 +1,46 @@
/*
* Copyright 2016 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.idea;
public class TeaVMConfiguration {
private boolean enabled;
private String mainClass;
private String targetDirectory;
public boolean isEnabled() {
return enabled;
}
public void setEnabled(boolean enabled) {
this.enabled = enabled;
}
public String getMainClass() {
return mainClass;
}
public void setMainClass(String mainClass) {
this.mainClass = mainClass;
}
public String getTargetDirectory() {
return targetDirectory;
}
public void setTargetDirectory(String targetDirectory) {
this.targetDirectory = targetDirectory;
}
}

View File

@ -0,0 +1,65 @@
/*
* Copyright 2016 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.idea;
import com.intellij.openapi.components.PersistentStateComponent;
import com.intellij.openapi.components.State;
import com.intellij.openapi.components.Storage;
import com.intellij.openapi.module.ModuleComponent;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@State(name = "teavm", storages = @Storage(id = "other", file = "$MODULE_FILE$"))
public class TeaVMConfigurationStorage implements PersistentStateComponent<TeaVMConfiguration>, ModuleComponent {
private TeaVMConfiguration state;
@Nullable
@Override
public TeaVMConfiguration getState() {
return state;
}
@Override
public void loadState(TeaVMConfiguration state) {
this.state = state;
}
@Override
public void projectOpened() {
}
@Override
public void projectClosed() {
}
@Override
public void moduleAdded() {
}
@Override
public void initComponent() {
}
@Override
public void disposeComponent() {
}
@NotNull
@Override
public String getComponentName() {
return "TeaVM configuration";
}
}

View File

@ -0,0 +1,87 @@
/*
* Copyright 2016 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.idea.ui;
import com.intellij.openapi.module.Module;
import com.intellij.openapi.module.ModuleServiceManager;
import com.intellij.openapi.options.Configurable;
import com.intellij.openapi.options.ConfigurationException;
import javax.swing.JComponent;
import org.jetbrains.annotations.Nls;
import org.jetbrains.annotations.Nullable;
import org.teavm.idea.TeaVMConfiguration;
import org.teavm.idea.TeaVMConfigurationStorage;
public class TeaVMConfigurable implements Configurable {
private final Module module;
private TeaVMConfigurationPanel panel;
public TeaVMConfigurable(Module module) {
this.module = module;
}
@Nls
@Override
public String getDisplayName() {
return "TeaVM";
}
@Nullable
@Override
public String getHelpTopic() {
return null;
}
@Nullable
@Override
public JComponent createComponent() {
if (panel == null) {
panel = new TeaVMConfigurationPanel();
}
return panel;
}
@Override
public boolean isModified() {
return panel != null && panel.isModified();
}
@Override
public void apply() throws ConfigurationException {
TeaVMConfiguration config = new TeaVMConfiguration();
panel.save(config);
TeaVMConfigurationStorage configStorage = ModuleServiceManager.getService(module,
TeaVMConfigurationStorage.class);
assert configStorage != null;
configStorage.loadState(config);
}
@Override
public void reset() {
if (panel == null) {
return;
}
TeaVMConfigurationStorage configStorage = ModuleServiceManager.getService(module,
TeaVMConfigurationStorage.class);
assert configStorage != null;
panel.load(configStorage.getState());
}
@Override
public void disposeUIResources() {
this.panel = null;
}
}

View File

@ -0,0 +1,132 @@
/*
* Copyright 2016 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.idea.ui;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
import javax.swing.JCheckBox;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import org.teavm.idea.TeaVMConfiguration;
class TeaVMConfigurationPanel extends JPanel {
private final JCheckBox enabledCheckBox = new JCheckBox("TeaVM enabled for this module");
private final JTextField mainClassField = new JTextField();
private final JTextField targetDirectoryField = new JTextField();
private final TeaVMConfiguration initialConfiguration = new TeaVMConfiguration();
private final List<JComponent> editComponents = Arrays.asList(mainClassField, targetDirectoryField);
private final List<Field<?>> fields = Arrays.asList(
new Field<>(TeaVMConfiguration::setEnabled, TeaVMConfiguration::isEnabled,
enabledCheckBox::setSelected, enabledCheckBox::isSelected),
new Field<>(TeaVMConfiguration::setMainClass, TeaVMConfiguration::getMainClass,
mainClassField::setText, mainClassField::getText),
new Field<>(TeaVMConfiguration::setTargetDirectory, TeaVMConfiguration::getTargetDirectory,
targetDirectoryField::setText, targetDirectoryField::getText)
);
TeaVMConfigurationPanel() {
enabledCheckBox.addActionListener(event -> updateEnabledState());
setupLayout();
}
private void setupLayout() {
setLayout(new GridBagLayout());
GridBagConstraints constraints = new GridBagConstraints();
constraints.gridwidth = GridBagConstraints.REMAINDER;
add(enabledCheckBox, constraints);
constraints.gridwidth = GridBagConstraints.RELATIVE;
add(new JLabel("Main class:"), constraints);
constraints.gridwidth = GridBagConstraints.REMAINDER;
add(mainClassField, constraints);
constraints.gridwidth = GridBagConstraints.RELATIVE;
add(new JLabel("Target directory:"), constraints);
constraints.gridwidth = GridBagConstraints.REMAINDER;
add(targetDirectoryField, constraints);
}
public void load(TeaVMConfiguration config) {
if (config == null) {
config = new TeaVMConfiguration();
}
updateInitialConfiguration(config);
for (Field<?> field : fields) {
loadField(field, config);
}
updateEnabledState();
}
public void save(TeaVMConfiguration config) {
for (Field<?> field : fields) {
saveField(field, config);
}
updateInitialConfiguration(config);
}
private <T> void loadField(Field<T> field, TeaVMConfiguration config) {
field.editConsumer.accept(field.dataSupplier.apply(config));
}
private <T> void saveField(Field<T> field, TeaVMConfiguration config) {
field.dataConsumer.accept(config, field.editSupplier.get());
}
private void updateEnabledState() {
for (JComponent component : editComponents) {
component.setEnabled(enabledCheckBox.isSelected());
}
}
public boolean isModified() {
return fields.stream().anyMatch(this::isFieldModified);
}
private <T> boolean isFieldModified(Field<T> field) {
return !Objects.equals(field.dataSupplier.apply(initialConfiguration), field.editSupplier.get());
}
private void updateInitialConfiguration(TeaVMConfiguration config) {
initialConfiguration.setEnabled(config.isEnabled());
initialConfiguration.setMainClass(config.getMainClass());
initialConfiguration.setTargetDirectory(config.getTargetDirectory());
}
static class Field<T> {
final BiConsumer<TeaVMConfiguration, T> dataConsumer;
final Function<TeaVMConfiguration, T> dataSupplier;
final Consumer<T> editConsumer;
final Supplier<T> editSupplier;
public Field(BiConsumer<TeaVMConfiguration, T> dataConsumer, Function<TeaVMConfiguration, T> dataSupplier,
Consumer<T> editConsumer, Supplier<T> editSupplier) {
this.dataConsumer = dataConsumer;
this.dataSupplier = dataSupplier;
this.editConsumer = editConsumer;
this.editSupplier = editSupplier;
}
}
}

View File

@ -15,21 +15,20 @@
]]> ]]>
</change-notes> </change-notes>
<!-- please see http://www.jetbrains.org/intellij/sdk/docs/basics/getting_started/build_number_ranges.html for description -->
<idea-version since-build="141.0"/> <idea-version since-build="141.0"/>
<!-- please see http://www.jetbrains.org/intellij/sdk/docs/basics/getting_started/plugin_compatibility.html
on how to target different products -->
<!-- uncomment to enable plugin in all products
<depends>com.intellij.modules.lang</depends>
-->
<extensions defaultExtensionNs="com.intellij"> <extensions defaultExtensionNs="com.intellij">
<!-- Add your extensions here --> <moduleConfigurable instance="org.teavm.idea.ui.TeaVMConfigurable"/>
<moduleService serviceInterface="org.teavm.idea.TeaVMConfigurationStorage"
serviceImplementation="org.teavm.idea.TeaVMConfigurationStorage"/>
</extensions> </extensions>
<actions> <actions>
<!-- Add your actions here -->
</actions> </actions>
<module-components>
<component>
<implementation-class>org.teavm.idea.TeaVMConfigurationStorage</implementation-class>
</component>
</module-components>
</idea-plugin> </idea-plugin>