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

de.schlichtherle.io.swing.FileComboBoxBrowser Maven / Gradle / Ivy

/*
 * Copyright (C) 2006-2010 Schlichtherle IT Services
 *
 * 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 de.schlichtherle.io.swing;

import de.schlichtherle.io.*;
import de.schlichtherle.io.File;
import de.schlichtherle.key.*;
import de.schlichtherle.swing.*;

import java.io.*;
import java.text.*;
import java.util.*;

import javax.swing.*;

/**
 * Subclasses {@code AbstractComboBoxBrowser} to complete relative and
 * absolute path names of files and directories.
 * This class uses instances of TrueZIP's custom {@link File} class in
 * order to support the browsing of archive files for auto completion.
 * 

* To use it, use something like this: *

    JComboBox box = new JComboBox();
    new FileComboBoxBrowser(box);
    box.setEditable(true);
 * 
* * @author Christian Schlichtherle * @since TrueZIP 6.2 * @version $Id: FileComboBoxBrowser.java,v 1.4 2010/08/20 13:09:46 christian_schlichtherle Exp $ */ public class FileComboBoxBrowser extends AbstractComboBoxBrowser { private static final long serialVersionUID = -6878885832542209810L; private java.io.File directory = new File("."); /** * Creates a new combo box auto completion browser. * {@link #setComboBox} must be called in order to use this object. */ public FileComboBoxBrowser() { } /** * Creates a new combo box auto completion browser. * * @param comboBox The combo box to enable browsing for auto completions. * May be {@code null}. */ public FileComboBoxBrowser(final JComboBox comboBox) { super(comboBox); if (comboBox != null) { final Object item = comboBox.getSelectedItem(); if (item == null || item instanceof String) update( (DefaultComboBoxModel) comboBox.getModel(), directory, (String) item); } } /** * Returns the directory which is used to complete relative path names. * This defaults to the current directory; {@code null} is never * returned. */ public java.io.File getDirectory() { return directory; } /** * Returns the directory which is used to complete relative path names. * * @param directory The directory to use for completion. * If this is {@code null}, the directory is reset to the * current directory. */ public void setDirectory(final java.io.File directory) { this.directory = directory != null ? directory : new File("."); } /** * Interpretes the specified {@code initials} as the initial * characters of an absolute or relative path name of a node in the file * system and updates the contents of the combo box model with possible * completions. * The elements in the combo box model are sorted according to their * natural comparison order. * * @param initials The initial characters of a file or directory path name. * May be {@code null}. * @return {@code true} if and only if the file system contains a * node with {@code initials} as its initial characters and * hence the popup window with the completions should be shown. * @throws NullPointerException If the {@code comboBox} property is * {@code null}. */ protected boolean update(final String initials) { return update( (DefaultComboBoxModel) getComboBox().getModel(), getDirectory(), initials); } private static boolean update( final DefaultComboBoxModel model, java.io.File dir, String initials) { // This is actually a pretty ugly piece of code, but I don't know // of any other way to implement this so that a user can use his // platform specific file separator (e.g. '\\' on Windows) // AND the standard Internet file name separator '/' in a file path // name. if (initials == null) initials = ""; // Identify the directory to list, the prefix of the elements we want // to find and the base string which prepends the elements we will find. final String prefix, base; if ("".equals(initials)) { prefix = base = ""; } else { final ArchiveDetector detector; if (dir instanceof File) detector = ((File) dir).getArchiveDetector(); else detector = ArchiveDetector.NULL; File node = new File(initials, detector); if (node.isAbsolute()) { final boolean dirPath = node.getPath().length() < initials.length(); if (dirPath) PromptingKeyManager.resetCancelledPrompts(); // The test order is important here because isDirectory() may // actually prompt the user for a key if node is an RAES // encrypted ZIP file! if (dirPath && node.isDirectory()) { dir = node; prefix = ""; } else { dir = (File) node.getParentFile(); if (dir == null) { dir = node; prefix = ""; } else { prefix = node.getName(); } } if (dir.getPath().endsWith(File.separator)) { // dir is the root of a file system. base = initials.substring(0, dir.getPath().length()); } else { // Otherwise keep the user provided file separator. base = initials.substring(0, dir.getPath().length() + 1); } } else { final java.io.File directory = dir; node = new File(directory, initials); // inherits archive detector from directory final boolean dirPath = node.getPath().length() < (directory.getPath() + File.separator + initials).length(); if (dirPath) PromptingKeyManager.resetCancelledPrompts(); // The test order is important here because isDirectory() may // actually prompt the user! if (dirPath && node.isDirectory()) { dir = node; prefix = ""; } else { dir = (File) node.getParentFile(); prefix = node.getName(); } // Keep the user provided file separator. base = initials.substring(0, dir.getPath().length() - directory.getPath().length()); } } final FilenameFilter filter; /*if (File.separatorChar != '\\') { // Consider case (Unix). filter = new FilenameFilter() { public boolean accept(java.io.File d, String child) { return child.startsWith(prefix); } }; } else {*/ // Ignore case (Windows). filter = new FilenameFilter() { final int pl = prefix.length(); public boolean accept(java.io.File d, String child) { if (child.length() >= pl) return prefix.equalsIgnoreCase(child.substring(0, pl)); else return false; } }; //} final String[] children = dir.list(filter); // Update combo box model. // Note that the list MUST be cleared and repopulated because its // current content does not need to reflect the status of the edited // initials. try { model.removeAllElements(); final int l = children != null ? children.length : 0; if (l > 0) { Arrays.sort(children, Collator.getInstance()); // get nice sorting order for (int i = 0; i < l; i++) model.addElement(base + children[i]); return true; // show popup } else { // Leave initials als sole content of the list. model.addElement(initials); return false; // hide popup } } finally { if (!initials.equals(model.getSelectedItem())) // check required! model.setSelectedItem(initials); } } }




© 2015 - 2025 Weber Informatics LLC | Privacy Policy