选择';计算机&x27;或';图书馆';在Java中';s JFileChooser生成一个奇怪的文件对象

选择';计算机&x27;或';图书馆';在Java中';s JFileChooser生成一个奇怪的文件对象,java,jfilechooser,Java,Jfilechooser,我在非常标准的“另存为”情况下使用JFileChooser。我正在生成一个文件,用户正在选择保存它的位置 令人困惑的是,用户可以选择“非真实”文件夹的数量。在Windows7中,它们是:计算机、网络、图书馆、家庭组。当我调用chooser.getSelectedFile()时;我得到一个文件对象,但它非常奇怪。这可能是一个奇怪的文件对象,因为它与实际存在的文件不对应。如果我尝试使用该文件,例如调用getCanonicalPath,我会得到一个IOException。但作为一名程序员,我缺乏关于这

我在非常标准的“另存为”情况下使用JFileChooser。我正在生成一个文件,用户正在选择保存它的位置

令人困惑的是,用户可以选择“非真实”文件夹的数量。在Windows7中,它们是:计算机、网络、图书馆、家庭组。当我调用chooser.getSelectedFile()时;我得到一个文件对象,但它非常奇怪。这可能是一个奇怪的文件对象,因为它与实际存在的文件不对应。如果我尝试使用该文件,例如调用getCanonicalPath,我会得到一个IOException。但作为一名程序员,我缺乏关于这个文件对象或其父对象的信息是没有意义的

我想配置JFileChooser,使其不允许用户进行这样的选择。到目前为止,我发现使用这种方法是有效的:

setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
但是,用户随后选择的是新文件的目录,而不是名称

或者,我想至少解释一下为什么他们不能保存在那个位置。我所有获取名称的尝试,例如“计算机”、“网络”或“库”都失败了。在Windows7上使用Java6,像isComputerNode和isFileSystem这样的文件系统视图方法(应该解决这个问题)没有帮助

import java.awt.Component;
import java.io.File;
import java.io.IOException;

import javax.swing.JFileChooser;
import javax.swing.filechooser.FileSystemView;

public class JChooserTest {

public static void main(String[] args) {

    JFileChooser chooser = new JFileChooser();
    chooser.setSelectedFile(new File("C:/foo.txt"));
    chooser.setDialogTitle("Save As");
    chooser.setFileHidingEnabled(true);
    chooser.setMultiSelectionEnabled(false);
    chooser.setFileSelectionMode(javax.swing.JFileChooser.FILES_AND_DIRECTORIES);
    chooser.setDialogType(JFileChooser.SAVE_DIALOG);
    Component parentComponent = null; // is not null in the real world 
    int state=chooser.showDialog(parentComponent, "Save As");
    if (state == JFileChooser.CANCEL_OPTION) return;

    File dest = chooser.getSelectedFile();

    try {
        System.out.println("Valid Destination: " + dest.getCanonicalPath());

    } catch (IOException ex) { // getCanonicalPath() threw IOException

        File parent = dest.getParentFile();

        FileSystemView fsv = FileSystemView.getFileSystemView();

        //log.error("Error determining the CanonicalPath of " + dest, ex);
        System.out.println("dest.getName: " + dest.getName());
        System.out.println("parent.getName: " + parent.getName());          
        System.out.println("getSystemDisplayName of dest: " + fsv.getSystemDisplayName(dest));
        System.out.println("getSystemDisplayName of parent: " + fsv.getSystemDisplayName(parent));          
        System.out.println("getSystemTypeDescription of dest: " + fsv.getSystemTypeDescription(dest));
        System.out.println("getSystemTypeDescription of parent: " + fsv.getSystemTypeDescription(parent));
        System.out.println("isFileSystem of dest: " + fsv.isFileSystem(dest));
        System.out.println("isFileSystem of parent: " + fsv.isFileSystem(parent));
        System.out.println("isComputerNode of dest: " + fsv.isComputerNode(dest));
        System.out.println("isComputerNode of parent: " + fsv.isComputerNode(parent));          
        System.out.println("dest" + dest.isDirectory());
        System.out.println("parent" + parent.isDirectory());
    }
}

}

返回的
文件
对象的名称为
:{031E4825-7B94-4DC3-B131-E946B44C8DD5}
。不幸的是,这实际上是libraries文件夹的名称,它只存在于浏览器的想象中,不存在于其他任何人

例如,在某处(例如,在桌面上)创建一个名为
foo.{031E4825-7B94-4DC3-B131-E946B44C8DD5}
,然后打开它。Explorer会认为它是Libraries文件夹,但其他所有内容都会非常混乱:

 Directory of C:\Users\Faux\Desktop\lol.{031E4825-7B94-4DC3-B131-E946B44C8DD5}

17/02/2012  08:06 pm    <DIR>          .
17/02/2012  08:06 pm    <DIR>          ..
               0 File(s)              0 bytes
               2 Dir(s)  794,214,469,632 bytes free
C:\Users\Faux\Desktop\lol.{031E4825-7B94-4DC3-B131-E946B44C8DD5} 2012年2月17日下午8:06。 2012年2月17日08:06下午。。 0个文件0个字节 2个目录794214469632个可用字节
至于如何说服文件选择器不显示它们,我不知道。我建议尝试
getCanonicalPath()
,捕获异常(如您所愿)并将其返回给用户;建议他们选择其他地方。

正如您所发现的那样,
目录(实际的物理文件目录)和
文件夹之间存在差异,它们可能根本不代表磁盘上的任何内容(如
打印机
)或多个磁盘目录(如
我的照片
)。微软的雷蒙德·陈(Raymond Chen)不久前写了一篇短文,解释了基本区别。你可以找到它;这可能有助于形象化事物。有趣。所以“计算机”、“网络”和“库”都是“虚拟文件夹”,也就是“不是目录的文件夹”,这是有道理的。从Java的角度来看,除了调用getCanonicalPath()并捕获异常之外,我仍然不知道如何识别这些异常。令人沮丧的是,FileSystemView似乎是设计用来做这类事情的,但实际上并没有这样做,在Windows的JRE库存中。是的。很抱歉,我无法帮助您了解Java透视图,因为我不是Java人。:)我熟悉WinAPI和Windows Shell,这就是为什么我知道您遇到了什么问题(并且想到了Raymond的文章,这篇文章又花了一点时间才找到)。是的,我可能只是发现了异常并要求他们选择不同的文件夹。我希望说“你选择了库,但那不是一个有效的目的地”,而不是更一般的“你选择了一个无效的目的地”