/* * Copyright 2000-2015 JetBrains s.r.o. * * 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 com.intellij.formatting.contextConfiguration; import com.intellij.application.options.TabbedLanguageCodeStylePanel; import com.intellij.lang.Language; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.options.ConfigurationException; import com.intellij.openapi.util.Disposer; import com.intellij.psi.codeStyle.CodeStyleSettings; import com.intellij.psi.codeStyle.CodeStyleSettingsCodeFragmentFilter; import com.intellij.psi.codeStyle.LanguageCodeStyleSettingsProvider; import com.intellij.ui.components.JBScrollPane; import com.intellij.util.containers.ContainerUtil; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import javax.swing.*; import java.awt.*; import java.util.Collection; import java.util.List; import java.util.Set; import static com.intellij.psi.codeStyle.LanguageCodeStyleSettingsProvider.SettingsType.SPACING_SETTINGS; import static com.intellij.psi.codeStyle.LanguageCodeStyleSettingsProvider.SettingsType.WRAPPING_AND_BRACES_SETTINGS; class CodeFragmentCodeStyleSettingsPanel extends TabbedLanguageCodeStylePanel { private static final Logger LOG = Logger.getInstance(CodeFragmentCodeStyleSettingsPanel.class); private final CodeStyleSettingsCodeFragmentFilter.CodeStyleSettingsToShow mySettingsToShow; private final SelectedTextFormatter mySelectedTextFormatter; private SpacesPanelWithoutPreview mySpacesPanel; private WrappingAndBracesPanelWithoutPreview myWrappingPanel; private Runnable mySomethingChangedCallback; public CodeFragmentCodeStyleSettingsPanel(@NotNull CodeStyleSettings settings, @NotNull CodeStyleSettingsCodeFragmentFilter.CodeStyleSettingsToShow settingsToShow, @NotNull Language language, @NotNull SelectedTextFormatter selectedTextFormatter) { super(language, settings, settings.clone()); mySettingsToShow = settingsToShow; mySelectedTextFormatter = selectedTextFormatter; ensureTabs(); } public void setOnSomethingChangedCallback(Runnable runnable) { mySomethingChangedCallback = runnable; } @Override protected void somethingChanged() { if (mySomethingChangedCallback != null) { mySomethingChangedCallback.run(); } } @Override protected String getPreviewText() { return null; } @Override protected void updatePreview(boolean useDefaultSample) { } @Override protected void initTabs(CodeStyleSettings settings) { SpacesPanelWithoutPreview panel = getSpacesPanel(settings); if (panel != null) { mySpacesPanel = panel; addTab(mySpacesPanel); } myWrappingPanel = new WrappingAndBracesPanelWithoutPreview(settings); addTab(myWrappingPanel); reset(getSettings()); } @Nullable private SpacesPanelWithoutPreview getSpacesPanel(CodeStyleSettings settings) { SpacesPanelWithoutPreview spacesPanel = new SpacesPanelWithoutPreview(settings); if (spacesPanel.hasSomethingToShow()) { return spacesPanel; } Disposer.dispose(spacesPanel); return null; } public JComponent getPreferredFocusedComponent() { return mySpacesPanel != null ? mySpacesPanel.getPreferredFocusedComponent() : myWrappingPanel.getPreferredFocusedComponent(); } public static CodeStyleSettingsCodeFragmentFilter.CodeStyleSettingsToShow calcSettingNamesToShow(CodeStyleSettingsCodeFragmentFilter filter) { return filter.getFieldNamesAffectingCodeFragment(SPACING_SETTINGS, WRAPPING_AND_BRACES_SETTINGS); } public static boolean hasOptionsToShow(LanguageCodeStyleSettingsProvider provider) { LanguageCodeStyleSettingsProvider.SettingsType[] types = { SPACING_SETTINGS, WRAPPING_AND_BRACES_SETTINGS }; for (LanguageCodeStyleSettingsProvider.SettingsType type : types) { if (!provider.getSupportedFields(type).isEmpty()) { return true; } } return !provider.getSupportedFields().isEmpty(); } private void reformatSelectedTextWithNewSettings() { try { apply(getSettings()); } catch (ConfigurationException e) { LOG.debug("Cannot apply code style settings", e); } CodeStyleSettings clonedSettings = getSettings().clone(); mySelectedTextFormatter.reformatSelectedText(clonedSettings); } private class SpacesPanelWithoutPreview extends MySpacesPanel { private JPanel myPanel; public SpacesPanelWithoutPreview(CodeStyleSettings settings) { super(settings); } @Override protected void somethingChanged() { mySelectedTextFormatter.restoreSelectedText(); reformatSelectedTextWithNewSettings(); CodeFragmentCodeStyleSettingsPanel.this.somethingChanged(); } @Override protected void init() { List<String> settingNames = mySettingsToShow.getSettings(getSettingsType()); if (settingNames.isEmpty()) { settingNames = mySettingsToShow.getOtherSetting(); } String[] names = ContainerUtil.toArray(settingNames, new String[settingNames.size()]); showStandardOptions(names); initTables(); myOptionsTree = createOptionsTree(); myOptionsTree.setCellRenderer(new MyTreeCellRenderer()); JBScrollPane pane = new JBScrollPane(myOptionsTree) { @Override public Dimension getMinimumSize() { return super.getPreferredSize(); } }; myPanel = new JPanel(new BorderLayout()); myPanel.add(pane); isFirstUpdate = false; } public boolean hasSomethingToShow() { return !myKeys.isEmpty(); } @Override public JComponent getPanel() { return myPanel; } @Override protected String getPreviewText() { return null; } public JComponent getPreferredFocusedComponent() { return myOptionsTree; } } private class WrappingAndBracesPanelWithoutPreview extends MyWrappingAndBracesPanel { public JPanel myPanel; public WrappingAndBracesPanelWithoutPreview(CodeStyleSettings settings) { super(settings); } @Override protected void init() { Collection<String> settingNames = mySettingsToShow.getSettings(getSettingsType()); if (settingNames.isEmpty()) { settingNames = mySettingsToShow.getOtherSetting(); } initTables(); Collection<String> fields = populateWithAssociatedFields(settingNames); fields.add("KEEP_LINE_BREAKS"); String[] names = ContainerUtil.toArray(fields, new String[fields.size()]); showStandardOptions(names); myTreeTable = createOptionsTree(getSettings()); JBScrollPane scrollPane = new JBScrollPane(myTreeTable) { @Override public Dimension getMinimumSize() { return myTreeTable.getPreferredSize(); } }; myPanel = new JPanel(new BorderLayout()); myPanel.add(scrollPane); showStandardOptions(names); isFirstUpdate = false; } @NotNull private Collection<String> populateWithAssociatedFields(Collection<String> settingNames) { Set<String> commonFields = ContainerUtil.newHashSet(); for (String fieldName : settingNames) { SettingsGroup settingsGroup = getAssociatedSettingsGroup(fieldName); if (settingsGroup == null) { commonFields.add(fieldName); } else if (settingsGroup.title != WRAPPING_KEEP) { commonFields.addAll(settingsGroup.commonCodeStyleSettingFieldNames); } } return commonFields; } @Override public JComponent getPanel() { return myPanel; } @Override protected void somethingChanged() { mySelectedTextFormatter.restoreSelectedText(); reformatSelectedTextWithNewSettings(); CodeFragmentCodeStyleSettingsPanel.this.somethingChanged(); } @Override protected String getPreviewText() { return null; } public JComponent getPreferredFocusedComponent() { return myTreeTable; } } }