diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/NewProjectWizardModuleBuilder.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/NewProjectWizardModuleBuilder.kt index 02d6abfd11e..36b119c1981 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/NewProjectWizardModuleBuilder.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/NewProjectWizardModuleBuilder.kt @@ -1,7 +1,6 @@ package org.jetbrains.kotlin.tools.projectWizard.wizard import com.intellij.ide.RecentProjectsManager -import com.intellij.ide.projectWizard.ProjectSettingsStep import com.intellij.ide.util.projectWizard.* import com.intellij.openapi.Disposable import com.intellij.openapi.application.ApplicationNamesInfo @@ -15,13 +14,11 @@ import com.intellij.openapi.roots.ui.configuration.ModulesProvider import com.intellij.openapi.ui.Messages import com.intellij.util.SystemProperties import org.jetbrains.kotlin.idea.configuration.ExperimentalFeatures -import org.jetbrains.kotlin.idea.framework.KotlinModuleSettingStep import org.jetbrains.kotlin.idea.framework.KotlinTemplatesFactory import org.jetbrains.kotlin.idea.projectWizard.ProjectCreationStats import org.jetbrains.kotlin.idea.projectWizard.UiEditorUsageStats import org.jetbrains.kotlin.idea.projectWizard.WizardStatsService import org.jetbrains.kotlin.idea.util.application.runWriteAction -import org.jetbrains.kotlin.platform.jvm.JvmPlatforms import org.jetbrains.kotlin.tools.projectWizard.core.* import org.jetbrains.kotlin.tools.projectWizard.core.entity.StringValidators import org.jetbrains.kotlin.tools.projectWizard.core.entity.ValidationResult @@ -30,16 +27,14 @@ import org.jetbrains.kotlin.tools.projectWizard.phases.GenerationPhase import org.jetbrains.kotlin.tools.projectWizard.plugins.Plugins import org.jetbrains.kotlin.tools.projectWizard.plugins.StructurePlugin import org.jetbrains.kotlin.tools.projectWizard.plugins.buildSystem.BuildSystemType -import org.jetbrains.kotlin.tools.projectWizard.plugins.projectTemplates.ProjectTemplatesPlugin import org.jetbrains.kotlin.tools.projectWizard.wizard.service.IdeaServices -import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.PomWizardStepComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.asHtml import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.firstStep.FirstWizardStepComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.runWithProgressBar import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.secondStep.SecondStepWizardComponent import org.jetbrains.kotlin.utils.addToStdlib.safeAs import java.io.File -import java.nio.file.Paths +import javax.swing.JButton import javax.swing.JComponent import com.intellij.openapi.module.Module as IdeaModule @@ -60,7 +55,6 @@ class NewProjectWizardModuleBuilder : EmptyModuleBuilder() { companion object { const val MODULE_BUILDER_ID = "kotlin.newProjectWizard.builder" - private const val DEFAULT_GROUP_ID = "me.user" private val projectNameValidator = StringValidators.shouldBeValidIdentifier("Project name", setOf('-', '_')) private const val INVALID_PROJECT_NAME_MESSAGE = "Invalid project name" } @@ -68,7 +62,7 @@ class NewProjectWizardModuleBuilder : EmptyModuleBuilder() { override fun isAvailable(): Boolean = ExperimentalFeatures.NewWizard.isEnabled private var wizardContext: WizardContext? = null - private var pomValuesAreSet: Boolean = false + private var finishButtonClicked: Boolean = false override fun getModuleType(): ModuleType<*> = NewProjectWizardModuleType() override fun getParentGroup(): String = KotlinTemplatesFactory.KOTLIN_PARENT_GROUP_NAME @@ -78,7 +72,7 @@ class NewProjectWizardModuleBuilder : EmptyModuleBuilder() { modulesProvider: ModulesProvider ): Array { this.wizardContext = wizardContext - return arrayOf(ModuleNewWizardSecondStep(wizard, uiEditorUsagesStats)) + return arrayOf(ModuleNewWizardSecondStep(wizard, uiEditorUsagesStats, wizardContext)) } override fun commit( @@ -114,19 +108,15 @@ class NewProjectWizardModuleBuilder : EmptyModuleBuilder() { } } - override fun modifySettingsStep(settingsStep: SettingsStep): ModuleWizardStep { - updateProjectNameAndPomDate(settingsStep) - return when (wizard.buildSystemType) { - BuildSystemType.Jps -> { - KotlinModuleSettingStep( - JvmPlatforms.defaultJvmPlatform, - this, - settingsStep, - wizardContext - ) - } - else -> PomWizardStep(settingsStep, wizard) - } + private fun clickFinishButton() { + if (finishButtonClicked) return + finishButtonClicked = true + wizardContext?.getActionButtonWithText("Finish", "Next")?.doClick() + } + + override fun modifySettingsStep(settingsStep: SettingsStep): ModuleWizardStep? { + clickFinishButton() + return null } override fun validateModuleName(moduleName: String): Boolean { @@ -141,42 +131,10 @@ class NewProjectWizardModuleBuilder : EmptyModuleBuilder() { } } - private fun updateProjectNameAndPomDate(settingsStep: SettingsStep) { - if (pomValuesAreSet) return - val suggestedProjectName = wizard.context.read { - ProjectTemplatesPlugin::template.settingValue.suggestedProjectName.decapitalize() - } - settingsStep.moduleNameLocationSettings?.apply { - moduleName = wizard.projectName!! - moduleContentRoot = wizard.projectPath!!.toString() - } - - settingsStep.safeAs()?.bindModuleSettings() - - wizard.artifactId = suggestedProjectName - wizard.groupId = suggestGroupId() - pomValuesAreSet = true - } - - private fun suggestGroupId(): String { - val username = SystemProperties.getUserName() ?: return DEFAULT_GROUP_ID - if (!username.matches("[\\w\\s]+".toRegex())) return DEFAULT_GROUP_ID - val usernameAsGroupId = username.trim().toLowerCase().split("\\s+".toRegex()).joinToString(separator = ".") - return "me.$usernameAsGroupId" - } - override fun getCustomOptionsStep(context: WizardContext?, parentDisposable: Disposable?) = ModuleNewWizardFirstStep(wizard) - override fun setName(name: String) { - wizard.projectName = name - } - override fun setModuleFilePath(path: String) = Unit - - override fun setContentEntryPath(moduleRootPath: String) { - wizard.projectPath = Paths.get(moduleRootPath) - } } abstract class WizardStep(protected val wizard: IdeWizard, private val phase: GenerationPhase) : ModuleWizardStep() { @@ -195,29 +153,13 @@ abstract class WizardStep(protected val wizard: IdeWizard, private val phase: Ge } } -private class PomWizardStep( - originalSettingStep: SettingsStep, - wizard: IdeWizard -) : WizardStep(wizard, GenerationPhase.PROJECT_GENERATION) { - private val pomWizardStepComponent = PomWizardStepComponent(wizard.context) - - init { - originalSettingStep.addSettingsComponent(component) - pomWizardStepComponent.onInit() - - } - - override fun getComponent(): JComponent = pomWizardStepComponent.component -} - - class ModuleNewWizardFirstStep(wizard: IdeWizard) : WizardStep(wizard, GenerationPhase.FIRST_STEP) { private val component = FirstWizardStepComponent(wizard) override fun getComponent(): JComponent = component.component init { runPreparePhase() - initDefaultProjectNameAndPathValues() + initDefaultValues() component.onInit() } @@ -227,15 +169,31 @@ class ModuleNewWizardFirstStep(wizard: IdeWizard) : WizardStep(wizard, Generatio } } - private fun initDefaultProjectNameAndPathValues() { + override fun handleErrors(error: ValidationResult.ValidationError) { + component.navigateTo(error) + } + + private fun initDefaultValues() { val suggestedProjectParentLocation = suggestProjectLocation() val suggestedProjectName = ProjectWizardUtil.findNonExistingFileName(suggestedProjectParentLocation, "untitled", "") wizard.context.writeSettings { StructurePlugin::name.reference.setValue(suggestedProjectName) StructurePlugin::projectPath.reference.setValue(suggestedProjectParentLocation / suggestedProjectName) + StructurePlugin::artifactId.reference.setValue(suggestedProjectName) + + if (StructurePlugin::groupId.reference.notRequiredSettingValue == null) { + StructurePlugin::groupId.reference.setValue(suggestGroupId()) + } } } + private fun suggestGroupId(): String { + val username = SystemProperties.getUserName() ?: return DEFAULT_GROUP_ID + if (!username.matches("[\\w\\s]+".toRegex())) return DEFAULT_GROUP_ID + val usernameAsGroupId = username.trim().toLowerCase().split("\\s+".toRegex()).joinToString(separator = ".") + return "me.$usernameAsGroupId" + } + // copied from com.intellij.ide.util.projectWizard.WizardContext.getProjectFileDirectory private fun suggestProjectLocation(): String { val lastProjectLocation = RecentProjectsManager.getInstance().lastProjectCreationLocation @@ -246,11 +204,16 @@ class ModuleNewWizardFirstStep(wizard: IdeWizard) : WizardStep(wizard, Generatio val productName = ApplicationNamesInfo.getInstance().lowercaseProductName return userHome.replace('/', File.separatorChar) + File.separator + productName.replace(" ", "") + "Projects" } + + companion object { + private const val DEFAULT_GROUP_ID = "me.user" + } } class ModuleNewWizardSecondStep( wizard: IdeWizard, - uiEditorUsagesStats: UiEditorUsageStats + uiEditorUsagesStats: UiEditorUsageStats, + private val wizardContext: WizardContext ) : WizardStep(wizard, GenerationPhase.SECOND_STEP) { private val component = SecondStepWizardComponent(wizard, uiEditorUsagesStats) override fun getComponent(): JComponent = component.component @@ -259,7 +222,22 @@ class ModuleNewWizardSecondStep( component.onInit() } + override fun getPreferredFocusedComponent(): JComponent? { + wizardContext.getActionButtonWithText("Next")?.apply { + text = "Finish" + updateUI() + } + return super.getPreferredFocusedComponent() + } + override fun handleErrors(error: ValidationResult.ValidationError) { component.navigateTo(error) } -} \ No newline at end of file +} + +private fun WizardContext.getActionButtonWithText(text: String, alternativeText: String? = null): JButton? = + wizard?.cancelButton?.parent?.components?.find { child -> + child.safeAs()?.let { button -> + button.text == text || alternativeText != null && button.text == alternativeText + } == true + } as? JButton \ No newline at end of file diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/Component.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/Component.kt index 4ffe40af2eb..1d2ca0f0620 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/Component.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/Component.kt @@ -22,6 +22,10 @@ abstract class Component : Displayable, ErrorNavigatable { this@Component.subComponents += it } + protected fun clearSubComponents() { + subComponents.clear() + } + override fun navigateTo(error: ValidationResult.ValidationError) { subComponents.forEach { it.navigateTo(error) } } diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/PomWizardStepComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/PomWizardStepComponent.kt deleted file mode 100644 index c49165eeb31..00000000000 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/PomWizardStepComponent.kt +++ /dev/null @@ -1,40 +0,0 @@ -package org.jetbrains.kotlin.tools.projectWizard.wizard.ui - -import com.intellij.ui.components.panels.VerticalLayout -import org.jetbrains.kotlin.tools.projectWizard.core.Context -import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.reference -import org.jetbrains.kotlin.tools.projectWizard.plugins.StructurePlugin -import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.StringSettingComponent -import javax.swing.Box -import javax.swing.JSeparator -import javax.swing.SwingConstants - -class PomWizardStepComponent(context: Context) : WizardStepComponent(context) { - private val groupIdComponent = StringSettingComponent( - StructurePlugin::groupId.reference, - context, - needLabel = true - ).asSubComponent() - - private val artifactIdComponent = StringSettingComponent( - StructurePlugin::artifactId.reference, - context, - needLabel = true - ).asSubComponent() - - private val versionComponent = StringSettingComponent( - StructurePlugin::version.reference, - context, - needLabel = true - ).asSubComponent() - - - override val component = panel(VerticalLayout(0)) { - add(Box.createVerticalStrut(10)) - add(JSeparator(SwingConstants.HORIZONTAL)) - add(Box.createVerticalStrut(10)) - add(groupIdComponent.component) - add(artifactIdComponent.component) - add(versionComponent.component) - } -} \ No newline at end of file diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/SubStep.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/SubStep.kt index 47910fe52f0..6d3f549992b 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/SubStep.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/SubStep.kt @@ -11,7 +11,7 @@ abstract class SubStep( protected abstract fun buildContent(): JComponent final override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { - panel { + customPanel { add(buildContent(), BorderLayout.CENTER) } } diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/components/UIComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/components/UIComponent.kt index a050b21ec06..f370533ecd1 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/components/UIComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/components/UIComponent.kt @@ -16,7 +16,7 @@ import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.SettingType import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.DynamicComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.FocusableComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.label -import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.panel +import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.customPanel import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.IdeaBasedComponentValidator import java.awt.BorderLayout import javax.swing.JComponent @@ -57,7 +57,7 @@ abstract class UIComponent( } final override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { - panel { + customPanel { labelText?.let { add(label("$it:"), BorderLayout.NORTH) } add(uiComponent, BorderLayout.CENTER) } diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/firstStep/FirstWizardStepComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/firstStep/FirstWizardStepComponent.kt index dfa2b2dc289..3f899db5d5b 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/firstStep/FirstWizardStepComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/firstStep/FirstWizardStepComponent.kt @@ -1,8 +1,14 @@ package org.jetbrains.kotlin.tools.projectWizard.wizard.ui.firstStep +import com.intellij.icons.AllIcons import com.intellij.ui.JBColor +import com.intellij.ui.TitledSeparator +import com.intellij.ui.layout.panel +import com.intellij.util.io.size import com.intellij.util.ui.JBUI +import com.intellij.util.ui.components.BorderLayoutPanel import org.jetbrains.kotlin.tools.projectWizard.core.Context +import org.jetbrains.kotlin.tools.projectWizard.core.entity.path import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.SettingReference import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.reference import org.jetbrains.kotlin.tools.projectWizard.plugins.StructurePlugin @@ -12,6 +18,8 @@ import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.* import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.secondStep.modulesEditor.ModulesEditorComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.TitledComponentsList import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.createSettingComponent +import java.awt.event.MouseAdapter +import java.awt.event.MouseEvent import javax.swing.JComponent class FirstWizardStepComponent(wizard: IdeWizard) : WizardStepComponent(wizard.context) { @@ -28,6 +36,7 @@ class FirstWizardStepComponent(wizard: IdeWizard) : WizardStepComponent(wizard.c class ProjectSettingsComponent(context: Context) : DynamicComponent(context) { private val projectTemplateComponent = ProjectTemplateSettingComponent(context).asSubComponent() private val buildSystemSetting = BuildSystemTypeSettingComponent(context).asSubComponent() + private val buildSystemAdditionalSettingsComponent = BuildSystemAdditionalSettingsComponent(context).asSubComponent() private val nameAndLocationComponent = TitledComponentsList( listOf( @@ -40,12 +49,89 @@ class ProjectSettingsComponent(context: Context) : DynamicComponent(context) { ).asSubComponent() override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { - nameAndLocationComponent.component.apply { + panel { + row { + nameAndLocationComponent.component(growX) + } + row { + buildSystemAdditionalSettingsComponent.component(growX) + } + }.apply { border = JBUI.Borders.empty(10) } } + + private var locationWasUpdatedByHand: Boolean = false + private var artifactIdWasUpdatedByHand: Boolean = false + + override fun onValueUpdated(reference: SettingReference<*, *>?) { + super.onValueUpdated(reference) + when (reference?.path) { + StructurePlugin::name.path -> { + tryUpdateLocationByProjectName() + tryArtifactIdByProjectName() + } + StructurePlugin::artifactId.path -> { + artifactIdWasUpdatedByHand = true + } + StructurePlugin::projectPath.path -> { + locationWasUpdatedByHand = true + } + } + } + + private fun tryUpdateLocationByProjectName() { + if (!locationWasUpdatedByHand) { + val location = read { StructurePlugin::projectPath.settingValue } + if (location.parent != null) modify { + StructurePlugin::projectPath.reference.setValue(location.parent.resolve(StructurePlugin::name.settingValue)) + locationWasUpdatedByHand = false + } + } + } + + private fun tryArtifactIdByProjectName() { + if (!artifactIdWasUpdatedByHand) modify { + StructurePlugin::artifactId.reference.setValue(StructurePlugin::name.settingValue) + artifactIdWasUpdatedByHand = false + } + } } +class BuildSystemAdditionalSettingsComponent(context: Context) : DynamicComponent(context) { + private val settingsList = TitledComponentsList( + listOf( + StructurePlugin::groupId.reference.createSettingComponent(context), + StructurePlugin::artifactId.reference.createSettingComponent(context), + StructurePlugin::version.reference.createSettingComponent(context) + ), + context + ).asSubComponent() + + override val component: JComponent = HideableSection("Artifact Coordinates", settingsList.component) +} + +@Suppress("SpellCheckingInspection") +private class HideableSection(text: String, private val component: JComponent) : BorderLayoutPanel() { + private val titledSeparator = TitledSeparator(text) + private var isExpanded = false + + init { + addToTop(titledSeparator) + addToCenter(component) + update(isExpanded) + + addMouseListener(object : MouseAdapter() { + override fun mouseReleased(e: MouseEvent) = update(!isExpanded) + }) + } + + private fun update(isExpanded: Boolean) { + this.isExpanded = isExpanded + component.isVisible = this.isExpanded + titledSeparator.label.icon = if (this.isExpanded) AllIcons.General.ArrowDown else AllIcons.General.ArrowRight + } +} class ProjectPreviewComponent(context: Context) : DynamicComponent(context) { private val modulesEditorComponent = ModulesEditorComponent( diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SecondStepWizardComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SecondStepWizardComponent.kt index 69ce4c0d8d9..cf824516d88 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SecondStepWizardComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SecondStepWizardComponent.kt @@ -5,7 +5,6 @@ import org.jetbrains.kotlin.tools.projectWizard.core.Context import org.jetbrains.kotlin.tools.projectWizard.core.entity.ValidationResult import org.jetbrains.kotlin.tools.projectWizard.settings.DisplayableSettingItem import org.jetbrains.kotlin.tools.projectWizard.settings.buildsystem.Module -import org.jetbrains.kotlin.tools.projectWizard.settings.buildsystem.Sourceset import org.jetbrains.kotlin.tools.projectWizard.wizard.IdeWizard import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.* import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.secondStep.modulesEditor.ModulesEditorComponent @@ -62,7 +61,7 @@ class ModuleSettingsSubStep( ModuleSettingsComponent(wizard.context, uiEditorUsagesStats).asSubComponent() private val nothingSelectedComponent = NothingSelectedComponent().asSubComponent() - private val panel = panel { + private val panel = customPanel { add(nothingSelectedComponent.component, BorderLayout.CENTER) } diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SourcesetDependenciesSettingsComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SourcesetDependenciesSettingsComponent.kt index 6c952f316ec..65c478be465 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SourcesetDependenciesSettingsComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/SourcesetDependenciesSettingsComponent.kt @@ -62,7 +62,7 @@ class SourcesetDependenciesSettingsComponent( } } - override val component = panel { + override val component = customPanel { add(toolbarDecorator.createPanelWithPopupHandler(sourcesetDependenciesList), BorderLayout.CENTER) } } @@ -76,7 +76,7 @@ private class ChooseModuleDialog(modules: List, parent: JComponent) : Di } ).bordered(needTopEmptyBorder = false, needBottomEmptyBorder = false) - override fun createCenterPanel() = panel { + override fun createCenterPanel() = customPanel { preferredSize = Dimension(preferredSize.width, 300) add( label("Please select the modules to add as dependencies:") diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/modulesEditor/ModulesEditorComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/modulesEditor/ModulesEditorComponent.kt index 15c17fde164..840991f4a1a 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/modulesEditor/ModulesEditorComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/secondStep/modulesEditor/ModulesEditorComponent.kt @@ -11,7 +11,7 @@ import org.jetbrains.kotlin.tools.projectWizard.plugins.kotlin.KotlinPlugin import org.jetbrains.kotlin.tools.projectWizard.plugins.kotlin.ProjectKind import org.jetbrains.kotlin.tools.projectWizard.settings.DisplayableSettingItem import org.jetbrains.kotlin.tools.projectWizard.settings.buildsystem.Module -import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.panel +import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.customPanel import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.SettingComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting.ValidationIndicator import java.awt.BorderLayout @@ -74,7 +74,7 @@ class ModulesEditorComponent( ) else null override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { - panel { + customPanel { if (needBorder) { border = BorderFactory.createLineBorder(JBColor.border()) } diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/DefaultSettingComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/DefaultSettingComponent.kt index 61e8314bd71..ab90290594d 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/DefaultSettingComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/DefaultSettingComponent.kt @@ -11,7 +11,7 @@ import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.components.DropDownCom import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.components.PathFieldComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.components.TextFieldComponent import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.label -import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.panel +import org.jetbrains.kotlin.tools.projectWizard.wizard.ui.customPanel import java.awt.BorderLayout import java.awt.event.ItemEvent import java.nio.file.Path @@ -87,9 +87,9 @@ class VersionSettingComponent( override val validationIndicator = null override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { - panel { + customPanel { add( - panel { + customPanel { add(settingLabel, BorderLayout.CENTER) }, BorderLayout.WEST diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/UIComponentDelegatingSettingComponent.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/UIComponentDelegatingSettingComponent.kt index 93811d4546a..e0f52ddeef9 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/UIComponentDelegatingSettingComponent.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/setting/UIComponentDelegatingSettingComponent.kt @@ -5,6 +5,7 @@ package org.jetbrains.kotlin.tools.projectWizard.wizard.ui.setting +import com.intellij.openapi.application.ApplicationManager import org.jetbrains.kotlin.tools.projectWizard.core.Context import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.SettingReference import org.jetbrains.kotlin.tools.projectWizard.core.entity.settings.SettingType @@ -33,5 +34,16 @@ abstract class UIComponentDelegatingSettingComponent uiComponent.focusOn() } + override fun onValueUpdated(reference: SettingReference<*, *>?) { + super.onValueUpdated(reference) + if (reference == this.reference) { + ApplicationManager.getApplication().invokeLater { + if (uiComponent.getUiValue() != value) { + value?.let(uiComponent::updateUiValue) + } + } + } + } + override val component: JComponent by lazy(LazyThreadSafetyMode.NONE) { uiComponent.component } } \ No newline at end of file diff --git a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/ui.kt b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/ui.kt index bfdbda180e9..504a19615e4 100644 --- a/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/ui.kt +++ b/idea/idea-new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/wizard/ui/ui.kt @@ -40,7 +40,7 @@ internal inline fun label(text: String, bold: Boolean = false, init: JBLabel.() init() } -inline fun panel(layout: LayoutManager = BorderLayout(), init: JPanel.() -> Unit = {}) = JPanel(layout).apply(init) +inline fun customPanel(layout: LayoutManager = BorderLayout(), init: JPanel.() -> Unit = {}) = JPanel(layout).apply(init) inline fun borderPanel(init: BorderLayoutPanel.() -> Unit = {}) = BorderLayoutPanel().apply(init) diff --git a/libraries/tools/new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/plugins/StructurePlugin.kt b/libraries/tools/new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/plugins/StructurePlugin.kt index 27bc88d3228..4d7e46bc474 100644 --- a/libraries/tools/new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/plugins/StructurePlugin.kt +++ b/libraries/tools/new-project-wizard/src/org/jetbrains/kotlin/tools/projectWizard/plugins/StructurePlugin.kt @@ -13,24 +13,24 @@ import org.jetbrains.kotlin.tools.projectWizard.settings.version.Version import java.nio.file.Paths class StructurePlugin(context: Context) : Plugin(context) { - val projectPath by pathSetting("Location", GenerationPhase.PROJECT_GENERATION) { + val projectPath by pathSetting("Location", GenerationPhase.FIRST_STEP) { defaultValue = value(Paths.get(".")) } - val name by stringSetting("Name", GenerationPhase.PROJECT_GENERATION) { + val name by stringSetting("Name", GenerationPhase.FIRST_STEP) { shouldNotBeBlank() validate(StringValidators.shouldBeValidIdentifier("Name", Module.ALLOWED_SPECIAL_CHARS_IN_MODULE_NAMES)) } - val groupId by stringSetting("Group ID", GenerationPhase.PROJECT_GENERATION) { + val groupId by stringSetting("Group ID", GenerationPhase.FIRST_STEP) { isSavable = true shouldNotBeBlank() validate(StringValidators.shouldBeValidIdentifier("Group ID", setOf('.', '_'))) } - val artifactId by stringSetting("Artifact ID", GenerationPhase.PROJECT_GENERATION) { + val artifactId by stringSetting("Artifact ID", GenerationPhase.FIRST_STEP) { shouldNotBeBlank() validate(StringValidators.shouldBeValidIdentifier("Artifact ID", setOf('_'))) } - val version by stringSetting("Version", GenerationPhase.PROJECT_GENERATION) { + val version by stringSetting("Version", GenerationPhase.FIRST_STEP) { shouldNotBeBlank() validate(StringValidators.shouldBeValidIdentifier("Version", setOf('_', '-', '.'))) defaultValue = value("1.0-SNAPSHOT")