All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.netbeans.modules.project.ui.SimpleTargetChooserPanel Maven / Gradle / Ivy

There is a newer version: RELEASE240
Show newest version
/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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.netbeans.modules.project.ui;

import java.awt.Component;
import java.io.File;
import java.io.IOException;
import javax.swing.JPanel;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import org.netbeans.api.annotations.common.NonNull;
import org.netbeans.api.annotations.common.NullAllowed;
import org.netbeans.api.project.Project;
import org.netbeans.api.project.SourceGroup;
import static org.netbeans.modules.project.ui.Bundle.*;
import org.netbeans.modules.project.uiapi.ProjectChooserFactory;
import org.netbeans.spi.project.ui.templates.support.Templates;
import org.openide.WizardDescriptor;
import org.openide.filesystems.FileObject;
import org.openide.filesystems.FileStateInvalidException;
import org.openide.filesystems.FileSystem;
import org.openide.filesystems.FileUtil;
import org.openide.util.ChangeSupport;
import org.openide.util.HelpCtx;
import org.openide.util.NbBundle.Messages;

/**
 *
 * @author  Petr Hrebejk
 */
final class SimpleTargetChooserPanel implements WizardDescriptor.Panel, ChangeListener {

    private final ChangeSupport changeSupport = new ChangeSupport(this);
    private SimpleTargetChooserPanelGUI gui;
    private boolean includesTemplatesWithProject = true;

    @NullAllowed
    private Project project;
    @NonNull
    private SourceGroup[] folders;
    private WizardDescriptor.Panel bottomPanel;
    private WizardDescriptor wizard;
    private boolean isFolder;
    private boolean freeFileExtension;
    private FileSystem fs;

    
    @SuppressWarnings("LeakingThisInConstructor")
    SimpleTargetChooserPanel(@NullAllowed Project project, @NonNull SourceGroup[] folders,
            WizardDescriptor.Panel bottomPanel, boolean isFolder, boolean freeFileExtension) {
        this.folders = folders;
        this.project = project;
        this.bottomPanel = bottomPanel;
        if ( bottomPanel != null ) {
            bottomPanel.addChangeListener( this );
        }
        this.isFolder = isFolder;
        this.freeFileExtension = freeFileExtension;
        this.gui = null;
    }

    public @Override Component getComponent() {
        if (noProjectFolders()) {
            return new JPanel();
        }
        if (gui == null) {
            gui = new SimpleTargetChooserPanelGUI(project, folders, bottomPanel == null ? null : bottomPanel.getComponent(), isFolder, freeFileExtension);
            gui.addChangeListener(this);
        }
        return gui;
    }

    private boolean noProjectFolders() { // #202410
        // if the project is null then any folder on the system is available
        return project != null && folders != null && folders.length == 0;
    }

    public @Override HelpCtx getHelp() {
        if ( bottomPanel != null ) {
            HelpCtx bottomHelp = bottomPanel.getHelp();
            if ( bottomHelp != null ) {
                return bottomHelp;
            }
        }
        
        //XXX
        return null;
        
    }

    public @Override boolean isValid() {
        if (noProjectFolders()) {
            return false;
        }

        boolean ok = ( gui != null && gui.getTargetName() != null &&
               ( bottomPanel == null || bottomPanel.isValid() ) );
        
        if (!ok) {
            return false;
        }
        
        // check if the file name can be created
        FileObject template = Templates.getTemplate( wizard );
        assert template != null : "Null template in wizard:" + wizard.getClass().getName() + ", prop WIZARD_KEY_TEMPLATE:" + wizard.getProperty( ProjectChooserFactory.WIZARD_KEY_TEMPLATE ) + ", thread:" + Thread.currentThread().getName();
        FileObject rootFolder;
        String targetFolder;
        if (gui.getTargetGroup() != null) {
            rootFolder = gui.getTargetGroup().getRootFolder();
            targetFolder = gui.getTargetFolder();
        }
        else if (gui.getTargetFolder() != null) {
            //this line will return null for non-existing folders
            //FileUtil.toFileObject(FileUtil.normalizeFile(new File(gui.getTargetFolder())))
            //that's suboptimal but makes the handling of the "outside of project" case easier.
            //ideally we would traverse the file structure up until we find an existing folder and then compute the non-existing part
            rootFolder =  fs == null ? FileUtil.toFileObject(FileUtil.normalizeFile(new File(gui.getTargetFolder()))) : fs.getRoot(); // NOI18N
            targetFolder = fs == null ? "" : gui.getTargetFolder();
        }
        else {
            rootFolder = null;
            targetFolder = null;
        }

        String errorMessage = ProjectUtilities.canUseFileName(rootFolder,
                targetFolder, gui.getTargetName(), template.getExt(), isFolder, freeFileExtension);
        wizard.putProperty(WizardDescriptor.PROP_ERROR_MESSAGE, errorMessage);

        return errorMessage == null;
    }

    public @Override void addChangeListener(ChangeListener l) {
        changeSupport.addChangeListener(l);
    }

    public @Override void removeChangeListener(ChangeListener l) {
        changeSupport.removeChangeListener(l);
    }

    @Messages({
        "SimpleTargetChooserPanelGUI_no_source_folders=No source folders in project; perhaps it has been deleted?",
        "LBL_TemplatesPanel_Name=Choose File Type"
    })
    @Override public void readSettings(WizardDescriptor settings) {
        Boolean b = (Boolean) settings.getProperty(NewFileWizard.INCLUDES_TEMPLATES_WITH_PROJECTS);
        if (b != null && b.equals(Boolean.FALSE)) {
            includesTemplatesWithProject = false;
        }
        wizard = settings;
                
        if (noProjectFolders()) {
            wizard.putProperty(WizardDescriptor.PROP_ERROR_MESSAGE, SimpleTargetChooserPanelGUI_no_source_folders());
            return;
        }

        if ( gui == null ) {
            getComponent();
        }
        
        // Try to preselect a folder            
        FileObject preselectedTarget = Templates.getTargetFolder( wizard );
        if (preselectedTarget == null) {
            if (project != null) {
                preselectedTarget = project.getProjectDirectory();
            }
            else {
                String home = System.getProperty("user.home");
                if (home != null && new File(home).isDirectory()) {
                    preselectedTarget = FileUtil.toFileObject(FileUtil.normalizeFile(new File(home)));
                }
            }
        }
        // Try to preserve the already entered target name
        String targetName = isFolder ? null : Templates.getTargetName( wizard );
        // Init values
        gui.initValues( Templates.getTemplate( wizard ), preselectedTarget, targetName, includesTemplatesWithProject );
        //only when we don't have a file from local filesystem
        if (preselectedTarget != null && FileUtil.toFile(preselectedTarget) == null) {
            try {
                fs = preselectedTarget.getFileSystem();
            } catch (FileStateInvalidException ex) {
                fs = null;
            }
        }        
        // XXX hack, TemplateWizard in final setTemplateImpl() forces new wizard's title
        // this name is used in NewFileWizard to modify the title
        Object substitute = gui.getClientProperty ("NewFileWizard_Title"); // NOI18N
        if (substitute != null) {
            wizard.putProperty ("NewFileWizard_Title", substitute); // NOI18N
        }
        
        wizard.putProperty(WizardDescriptor.PROP_CONTENT_DATA, new String[] {LBL_TemplatesPanel_Name(), LBL_SimpleTargetChooserPanel_Name()});
            
        if ( bottomPanel != null ) {
            bottomPanel.readSettings( settings );
        }
    }
    
    public @Override void storeSettings(WizardDescriptor settings) {
        if (noProjectFolders()) {
            return;
        }

        if (WizardDescriptor.PREVIOUS_OPTION.equals(settings.getValue())) {
            return;
        }
        if(!WizardDescriptor.CANCEL_OPTION.equals(settings.getValue())
                && !WizardDescriptor.CLOSED_OPTION.equals(settings.getValue()) && isValid()) {
            if ( bottomPanel != null ) {
                bottomPanel.storeSettings( settings );
            }
            if ( gui == null ) {
                getComponent();
            }
            String name = gui.getTargetName ();
            if (name != null && name.indexOf ('/') > 0) { // NOI18N
                name = name.substring (name.lastIndexOf ('/') + 1);
            }
            
            Templates.setTargetFolder(settings, getTargetFolderFromGUI());
            Templates.setTargetName(settings, name);
        }
        settings.putProperty("NewFileWizard_Title", null); // NOI18N
    }

    public @Override void stateChanged(ChangeEvent e) {
        changeSupport.fireChange();
    }
    
    private FileObject getTargetFolderFromGUI () {
        FileObject rootFolder;
        String folderName;
        if (gui.getTargetGroup() != null) {
            rootFolder = gui.getTargetGroup().getRootFolder();
            folderName = gui.getTargetFolder();
        }
        else if (gui.getTargetFolder() != null) {
//            rootFolder = FileUtil.toFileObject(FileUtil.normalizeFile(new File(gui.getTargetFolder())));
//            folderName = "";
            rootFolder =  fs == null ? FileUtil.toFileObject(FileUtil.normalizeFile(new File(gui.getTargetFolder()))) : fs.getRoot(); // NOI18N
            folderName = fs == null ? "" : gui.getTargetFolder();
        }
        else {
            rootFolder = null;
            folderName = null;
        }

        String newObject = gui.getTargetName ();
        
        if (newObject.indexOf ('/') > 0) { // NOI18N
            String path = newObject.substring (0, newObject.lastIndexOf ('/')); // NOI18N
            folderName = folderName == null || "".equals (folderName) ? path : folderName + '/' + path; // NOI18N
        }

        FileObject targetFolder;
        if ( folderName == null ) {
            targetFolder = rootFolder;
        }
        else {            
            targetFolder = rootFolder.getFileObject( folderName );
        }

        if ( targetFolder == null ) {
            // XXX add deletion of the file in uninitalize ow the wizard
            try {
                targetFolder = FileUtil.createFolder( rootFolder, folderName );
            } catch (IOException ioe) {
                // Can't create the folder
                throw new IllegalArgumentException(ioe); // ioe already annotated
            }
        }
        
        return targetFolder;
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy