Java仿文件资源管理器(Java课程设计)

JAVA课设的时候,网上百度没有完全符合以下要求的帖子,在拼凑完成课设后,发出来给大家分享

必做需求:①左侧以树形结构列出本机文件系统,根为“我的电脑”;②点击左侧结点,右侧 以表格展示其下文件/文件夹,包含文件名、大小、修改日期、文件类型等列;③单击右侧表头可按该列升降排序;④右侧文件/文件夹支持右键菜单,以完成常用的文件/文件夹管理功能(复制、粘贴、删除、剪切、重命名等)。选做需求:支持常用文件类型(文本、图片等)的预览

运行截图:


Java仿文件资源管理器(Java课程设计)_第1张图片

Java仿文件资源管理器(Java课程设计)_第2张图片

可以右侧表头升降序排列

Java仿文件资源管理器(Java课程设计)_第3张图片


源代码:

为了方便伙伴们使用,特地截图代码的包目录分布:

Java仿文件资源管理器(Java课程设计)_第4张图片

1、节点渲染器类 FolderRenderer .java
package CLASS;

import java.awt.Component;

import javax.swing.Icon;

import javax.swing.JTree;

import javax.swing.filechooser.FileSystemView;

import javax.swing.tree.DefaultMutableTreeNode;

import javax.swing.tree.DefaultTreeCellRenderer;

public class FolderRenderer extends DefaultTreeCellRenderer {  //自定义渲染器类,以描述节点的显示细节,此处的主要作用是渲染图片

private static FileSystemView fsView;

    private static final long serialVersionUID = 1L;

    //重写父类方法

    public Component getTreeCellRendererComponent(JTree tree, Object value,

           boolean sel, boolean expanded, boolean leaf, int row,

           boolean hasFocus) {//将当前树单元格的值设置为 value。如果 selected 为 true,则将单元格作为已选择的单元格进行绘制。

    	//如果 expanded 为 true,则当前扩展该节点,如果 leaf 为 true,则该节点表示叶节点,如果 hasFocus 为 true,则该节点当前拥有焦点。tree 是为其配置接收者的 JTree。返回渲染器用来绘制值的 Component。

fsView = FileSystemView.getFileSystemView();//获取FileSystemView的实例

DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) value;//获取当前节点

NodeData data = (NodeData) selectedNode.getUserObject();//取得节点的用户对象

Icon icon = fsView.getSystemIcon(data.f);//Icon为图片

        setLeafIcon(icon);//用于显示叶节点的图标

        setOpenIcon(icon);//用于显示扩展的非叶节点的图标

        setClosedIcon(icon);//设置用于显示无扩展的非叶节点的图标      

        return super.getTreeCellRendererComponent(tree, value, sel, expanded,

              leaf, row, hasFocus);

    }

}

 

2、文件节点类

package CLASS;

import java.io.File;

public class NodeData//文件节点类

{

public File f;

public String Name;

    public NodeData(File f,String Name)

{

this.f = f;

this.Name = Name;

}

public String toString()

{

return Name;

}

public void ChangeString(String s)

{

Name = s;

}

public NodeData(File file) {

   this.f = file;

  }

}

3GUI窗口创建和各项处理事件代码

package ui;

 

import java.awt.BorderLayout;

import java.awt.Component;

import java.awt.Dimension;

import java.awt.MenuItem;

import java.awt.Panel;

import java.awt.PopupMenu;

import java.awt.event.ActionEvent;

import java.awt.event.ActionListener;

import java.awt.event.MouseAdapter;

import java.awt.event.MouseEvent;

import java.awt.event.MouseListener;

import java.io.File;

import java.io.FileInputStream;

import java.io.FileOutputStream;

import java.io.IOException;

import java.sql.Date;

import java.text.SimpleDateFormat;

 

//

import javax.swing.Icon;

import javax.swing.JDialog;

import javax.swing.JFrame;

import javax.swing.JOptionPane;

import javax.swing.JScrollPane;

import javax.swing.JTable;

import javax.swing.JTextArea;

import javax.swing.JTree;

import javax.swing.SwingUtilities;

import javax.swing.event.TreeModelEvent;

import javax.swing.event.TreeModelListener;

import javax.swing.event.TreeSelectionEvent;

import javax.swing.event.TreeSelectionListener;

import javax.swing.filechooser.FileSystemView;

import javax.swing.table.DefaultTableModel;

import javax.swing.table.TableModel;

import javax.swing.table.TableRowSorter;

import javax.swing.tree.DefaultMutableTreeNode;

import javax.swing.tree.DefaultTreeCellRenderer;

import javax.swing.tree.DefaultTreeModel;

import javax.swing.tree.MutableTreeNode;

import javax.swing.tree.TreePath;

import javax.swing.tree.TreeSelectionModel;

 

import CLASS.FolderRenderer;

import CLASS.NodeData;

@SuppressWarnings("unused")

public class MyTree

{

TreePath copyPath;

JFrame jf;

JTree tree;//树结构

JTable table;//表格

Object[][] list = { {} };

DefaultTableModel tableModel;//表格模型

DefaultMutableTreeNode parent;

DefaultTreeModel model;//声明树状视图模型  以指定的模型创建一棵树,DefaultTreeModel自行查阅API

PopupMenu pop = new PopupMenu();//右键弹出菜单

MenuItem deleteItem = new MenuItem("删除");

MenuItem renameItem = new MenuItem("重命名");

    MenuItem natrueItem = new MenuItem("属性");

    MenuItem copyItem=new MenuItem("复制");

    MenuItem pasteItem=new MenuItem("粘贴");

DefaultMutableTreeNode root = new DefaultMutableTreeNode(new NodeData(null,"我的电脑"));//自定义一个名为root的节点,后面作为根节点创建一棵树  NodeData是自定义节点类。

//用于重命名时生成一个原节点的克隆体

DefaultMutableTreeNode aClone;

public void init()

{

jf = new JFrame("文件资源管理器");

jf.setSize(600, 600);

File[] roots = File.listRoots();//获得系统根目录文件  需要获取磁盘中所有的盘符路径:jdk6中一个方法搞定

for(int i = 0;i < roots.length;i++)

{

DefaultMutableTreeNode node = new DefaultMutableTreeNode(new NodeData(roots[i],roots[i].getAbsolutePath()));//NodeDate自定义节点类

root.add(node);//从父节点删除 newChild并将其添加到该节点的子数组的末尾,使其成为该节点的子节点

}

tree = new JTree(root);//以指定的自定义的节点(root)作为根节点创建一棵树  

model = (DefaultTreeModel) tree.getModel();//获取Jtree对应的TreeModel的对象,即获取树的数据模型

        tree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);//一次只能选中一个节点先返回树的选择模型才能设置树的选择模型   contiguous连续的

        // getSelectionModel()返回模型进行选择                           setSelectionMode设置树的选择模型 。

        tree.setCellRenderer(new FolderRenderer());//设置使用定制的节点绘制器

  String[] row = { "文件名", "类型","最后修改日期", "大小" };

  tableModel = new DefaultTableModel(list, row);

  table = new JTable(tableModel);

  //表格升降序

  TableRowSorter sorter = new TableRowSorter(tableModel);

  table.setRowSorter(sorter);

          JScrollPane scrollTable = new JScrollPane(table);//显示区为table表格的可滚动面板

  scrollTable.setPreferredSize(new Dimension(500, 500));

  jf.add(BorderLayout.CENTER,scrollTable);//使用边界布局

//e.path() 返回已更改节点的父节点的路径。

//e.childIndices() 返回更改节点的索引。

//当用户完成一个节点的编辑时,这个 model 产生一个 tree model 事件,它会告诉所有监听者(包括 Jtree ):树节点被改变了。注意:尽管 DefaultMutableTreeNode 拥有改变一个节点内容的方法,但是改变还是需要通过 DefaultTreeModel 上面的方法。否则, tree model 事件就不能产生,事件的监听者(例如 tree )就不能知道这些更新。

 

    //为了通知“节点改变”,我们可以实现一个 TreeModelListener 。这里有一个关于 tree model 监听器的例子,当用户为一个树节点输入一个新名字时,事件会被检测到。

        model.addTreeModelListener(new TreeModelListener()

{

public void treeNodesChanged(TreeModelEvent e)//当树的节点改变时就调用这个方法

{

    //获得编辑后的节点的父节点

DefaultMutableTreeNode parent = (DefaultMutableTreeNode)(e.getTreePath().getLastPathComponent());//返回从根节点到该节点的路径,在找到树种最后一个选中的节点

DefaultMutableTreeNode node;

try

{

int []index = e.getChildIndices();//返回目前修改点的索引值

node = (DefaultMutableTreeNode)(parent.getChildAt(index[0]));//getChildAt()方法取得修改的節點對象.

 

//System.out.println(aClone.toString());

//克隆体更新名称,file不变

((NodeData)aClone.getUserObject()).ChangeString(node.toString());

//删除选定节点且要求该节点存在父节点

model.removeNodeFromParent(node);

//添加克隆体

model.insertNodeInto(aClone,parent,index[0]);//在父节点的子节点中的 index 处插入aClone

}

catch (NullPointerException exc) //點選的節點為root node,則getChildIndices()的返回值為null,root node產生的NullPointerException問題.

 

{

System.out.println("model error");

}

//系统实现改名

NodeData data = (NodeData) aClone.getUserObject();

String tt = data.f.getParent() + "//";

tt = tt + aClone.toString();

File newfile = new File(tt);

data.f.renameTo(newfile);//将文件改名为 指定的名字

data.f = newfile;

return;

}

public   void   treeStructureChanged(TreeModelEvent   e){}   //当树的结构改变时就调用这个方法

            public   void   treeNodesRemoved(TreeModelEvent   e){}  // 当属的节点删除时就调用这个方法

            public   void   treeNodesInserted(TreeModelEvent   e){} //当树的节点添加时就调用这个方法  

});

//为pop添加菜单项

pop.add(deleteItem);

pop.addSeparator();

pop.add(renameItem);

pop.addSeparator();

pop.add(copyItem);

pop.addSeparator();

pop.add(pasteItem);

pop.addSeparator();

        pop.add(natrueItem);

  

//属性功能       

        natrueItem.addActionListener(new ActionListener()

        {               //属性功能

                   public void actionPerformed(ActionEvent event){

                   JDialog subDialog;                                                    

                   subDialog=new JDialog(jf,"属性");

                   subDialog.setVisible(true);

                   subDialog.setSize(400,400);                            

                   JTextArea text=new JTextArea();

                   subDialog.getContentPane().add(text);  

                   TreePath tp=tree.getSelectionPath();//得到树状视图的被选择节点路径

           String fullPath="";//得到被选择节点对应文件的完整路径信息

           for(Object obj:tp.getPath())

                   {

          String str=obj.toString();

                  if(str.endsWith("\\"))//处理盘符根目录问题

                          str=str.substring(0,str.length()-1);

                          if(fullPath.equals(""))

                              fullPath+=str;

                      else     

                              fullPath+="\\"+str;

                   }

           int n=fullPath.indexOf("脑");

           String sp=fullPath.substring(n+2);                              

               File currentFile=new File(sp);                           

                   StringBuffer sb=new StringBuffer();                              

                   if(currentFile.isDirectory())

                       sb.append("文件夹路径:"+currentFile.getAbsolutePath()+"\n");                                  

                   else

                       sb.append("文件路径:"+currentFile.getAbsolutePath()+"\n");

                       sb.append("是否可读"+currentFile.canRead()+"\n");

                       sb.append("是否可写"+currentFile.canWrite()+"\n");

                   if(!currentFile.isDirectory())

                       sb.append("文件的长度:"+currentFile.length()/(1024*1024)+"M\n");

                       SimpleDateFormat s=new SimpleDateFormat("yyyy年MM年dd日HH小时mm分钟ss秒");

                       sb.append("文件上次修改的时间:"+s.format(new Date(currentFile.lastModified()))+"\n");

                       sb.append("文件是否被隐藏:"+currentFile.isHidden()+"\n");                        

                       text.setText(sb.toString());

                      }                       

                 });

//菜单项deleteItem的动作侦听器

deleteItem.addActionListener(new ActionListener()

{

public void actionPerformed(ActionEvent event)

{

//获取选中节点

DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) tree.getLastSelectedPathComponent();

if(selectedNode == null)

return;

//获得节点数据

NodeData data = (NodeData) selectedNode.getUserObject();

//显示是否删除的确认对话框

int n = JOptionPane.showConfirmDialog(tree,"确认删除吗?","确认对话框",JOptionPane.YES_NO_OPTION);

if(n == JOptionPane.NO_OPTION)

return;

//如果该节点是文件

if(selectedNode == root)

{

JOptionPane.showMessageDialog(tree,"本地磁盘不能被删除","警告对话框",JOptionPane.WARNING_MESSAGE);

return;

}

else if(data.f.isFile())

{

//删除文件

delFile(data.f.getAbsolutePath());

}

else if(data.f.isDirectory())

{

//删除文件夹

if(selectedNode.getParent() != root)

delFolder(data.f.getAbsolutePath());

else

{

JOptionPane.showMessageDialog(tree,"本地磁盘不能被删除","警告对话框",JOptionPane.WARNING_MESSAGE);

return;

}

}

//处理树节点的删除

model.removeNodeFromParent(selectedNode);

}

});

//菜单项renameItem的动作监控器

renameItem.addActionListener(new ActionListener()

{

public void actionPerformed(ActionEvent event)

{

//设置可编辑

tree.setEditable(true);

//获取选中节点

DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) tree.getLastSelectedPathComponent();

TreePath editPath = tree.getSelectionPath();//得到被选择节点的路径

if(selectedNode == null)

return;

//开始编辑

tree.startEditingAtPath(editPath);//选择路径中的最后一个项并试着编辑它

//修改节点监控器,保存节点新名字

aClone = (DefaultMutableTreeNode) selectedNode.clone();

}

});

//菜单项copyItem的动作监听器

copyItem.addActionListener(new ActionListener() {

@Override

public void actionPerformed(ActionEvent e) {

//设置可编辑

tree.setEditable(true);

//获取选中节点

DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode)tree.getLastSelectedPathComponent();

copyPath = tree.getSelectionPath();//得到被复制节点的路径

}

});

    final Panel p = new Panel();

//向窗口添加PopupMenu对象

jf.add(pop);

//节点的鼠标事件监视器

MouseListener ml = new MouseAdapter()

{

public void mousePressed(MouseEvent e)//单右键单击时,也选中

{

TreePath tp = tree.getPathForLocation(e.getX(),e.getY()); //返回指定节点的完整的信息

if(tp == null)

return;

tree.setSelectionPath(tp); //选中节点选择指定路径标识的节点

//如果是右键点击,则不必考虑展开

if(SwingUtilities.isRightMouseButton(e))

return;

//如果是左键点击,就展开或者合上

                if(tree.isExpanded(tp))//由Path所确定的节点被展开,则返回true

                {   

                    tree.collapsePath(tp);//将Path所确定的节点收缩,并保证可见

                }   

                else   

                {   

                    tree.expandPath(tp);   //将Path所确定的节点展开,并保证可见

                }

}

public void mouseClicked(MouseEvent e)

{

if(e.getClickCount() >= 2)//如果连击

{

TreePath tp = tree.getPathForLocation(e.getX(),e.getY());

if(tp != null)

{

DefaultMutableTreeNode temp = (DefaultMutableTreeNode) tp.getLastPathComponent();//获得选中节点

if(temp == null)

return;

//如果节点名被改变了,节点数据自动被改成String型的,而不再是NodeData型的

if(temp.getUserObject() == temp.getUserObject().toString())

{

System.out.println("Object of getUserObject() has been changed");

return;

}

NodeData data = (NodeData) temp.getUserObject();//获得数据节点

if(tp != null && data.f.isFile())//如果是可执行文件

{

try

{

//调用具体命令行功能的程序,根据命令行格式加上文件名

Runtime ce = Runtime.getRuntime();

String Temp = new String(data.f.getParent());

Temp = Temp + "//";

Temp = Temp + data.f.getName();

String cmdarray = "cmd /c start " + Temp;

ce.exec(cmdarray);

}

catch(Exception ee)

{

System.out.println(ee);

}

}

}

}

}

public void mouseReleased(MouseEvent e)//鼠标松开时,如果是右击,则显示右击菜单

{

if(e.isPopupTrigger())//测试是否这个事件将引起一个弹出式菜单在平台中探出

{

TreePath tp = tree.getPathForLocation(e.getX(),e.getY());

//如果右击节点

if(tp == null)

return;

pop.show(tree,e.getX(),e.getY());

}

}

};

tree.addMouseListener(ml);

//节点选中事件监视器   事件监听器作为匿名内部类

tree.addTreeSelectionListener(new TreeSelectionListener()//节点选中事件监视器 添加 TreeSelection事件的监听器。

{

//重写接口方法valueChanged  每当选择的值更改时调用

    public void valueChanged(TreeSelectionEvent e)

{

        TreePath movepath = (TreePath)e.getNewLeadSelectionPath();//返回当前前导路径

//如果节点被菜单选项deleteItem删除了,就会返回null,此时什么都不做,返回即可

if(movepath == null)

return;

DefaultMutableTreeNode temp = (DefaultMutableTreeNode) movepath.getLastPathComponent();//获得选中节点

if(temp == null)

return;

//---------------------非常关键的一个判断--------------------

//如果节点名被改变了,节点数据自动被改成String型的,而不再是NodeData型的

if(temp.getUserObject() == temp.getUserObject().toString())

{

DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode)tree.getLastSelectedPathComponent();

//测试是否进来

System.out.println(aClone.toString());

DefaultMutableTreeNode parent = (DefaultMutableTreeNode) selectedNode.getParent();

int selectedIndex = parent.getIndex(selectedNode);

System.out.println("Object of getUserObject() has been changed");

//克隆体更新名称,file不变

((NodeData)aClone.getUserObject()).ChangeString(selectedNode.toString());

//删除选定节点

model.removeNodeFromParent(selectedNode);

//添加克隆体

model.insertNodeInto(aClone,parent,selectedIndex + 1);

//系统实现改名

NodeData data = (NodeData) aClone.getUserObject();

String tt = data.f.getParent() + "//";

tt = tt + aClone.toString();

data.f.renameTo(new File(tt));

//设置选中节点,避免重复触发该控制流

tree.setSelectionRow(selectedIndex + 1);

                    return;

}

NodeData data = (NodeData) temp.getUserObject();//获得数据节点

                if(data.f != null)

{

//处理初次选中后快速添加新子节点代表新的文件

if(data.f.isDirectory() && temp.isLeaf())//如果是目录,但目前还是叶节点,那么就添加

{

File[] RRoots = data.f.listFiles();

for(int j = 0;j < RRoots.length;j ++)

{

DefaultMutableTreeNode NNode = new DefaultMutableTreeNode(new NodeData(RRoots[j],RRoots[j].getName()));

model.insertNodeInto(NNode,temp,temp.getChildCount());//添加新节点并自动刷新

}

//实时表格构造

tableModel.setRowCount(0);

list = fu(RRoots);//在fu方法中进行表格list的赋值

    	     for (int i = 0; i < RRoots.length; i++) {

    	      tableModel.addRow(list[i]);

    	     }

}

else if(data.f.isFile())//如果是文件

{}

                }

else

{

System.out.println("无法获得选中的节点");

}

   }	    

});

JScrollPane scrollTree = new JScrollPane(tree);//显示区为table表格的可滚动面板

scrollTree.setPreferredSize(new Dimension(200, 300));

jf.add(BorderLayout.WEST,scrollTree);//显示区为tree的可滚动面板

jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

jf.setVisible(true);

}

//**************************************************************************************************************************************************************************

//读取所选节点,获取子节点

 public void readfiles(File file, DefaultMutableTreeNode node) {

  File list[] = file.listFiles();

  if (list == null)

   return;

  for (int i = 0; i < list.length; i++) {

   File file_inlist = list[i];

   // String filename = file_inlist.getName();

   if (file_inlist.isDirectory()) {

    parent = new DefaultMutableTreeNode(new NodeData(file_inlist));

    // 添加空白文件夹节点 使子节点显示为文件夹

    File stubadd = null;

    DefaultMutableTreeNode stub = new DefaultMutableTreeNode(

      stubadd);

    parent.add(stub);

    node.add(parent);

   } else {

    DefaultMutableTreeNode son = new DefaultMutableTreeNode(

      new NodeData(file_inlist));

    node.add(son);

   }

  }

 }

//读取文件的大小

 public String size(File file) throws IOException {

//	  FileInputStream fileLength = new FileInputStream(file);

  String sizefile = file.length() + "字节";

  return sizefile;

 }

   // 取得最后一次修改的时间

 public Date lastTime(File file) {

  long lastModified = file.lastModified();

  Date date = new Date(lastModified);

  date.setTime(lastModified);

  return date;

 }

public Object[][] fu(File[] file) {

 

  Object[][] m = new Object[file.length][4];

  for (int i = 0; i < file.length; i++) {

   m[i][0] = file[i].getName();

   // 这里有问题,如果是目录,怎么取大小?所以要用if

// m[i][1] = size(file[i]);

if (file[i].isDirectory()) {

 m[i][1] = "文件夹";

} else {

String fileName = file[i].getName();

String fileType = fileName.substring(fileName.lastIndexOf(".") + 1, fileName.length());

 

m[i][1] = fileType;

}

   //文件最后修改时间

   m[i][2] = lastTime(file[i]);

   //文件大小

   try {

    // 这里有问题,如果是目录,怎么取大小?所以要用if

    // m[i][1] = size(file[i]);

    if (file[i].isDirectory()) {

     m[i][3] = "文件夹类型大小待定";

    } else {

     m[i][3] = size(file[i]);

    }

      

   } catch (IOException e) {

    // TODO 自动生成 catch 块

    e.printStackTrace();

   }

   

  }

  return m;

 }

 

public  void  delFile(String  filePathAndName)  {  //删除文件

try  

{  

String  filePath  =  filePathAndName;  

filePath  =  filePath.toString();  

java.io.File  myDelFile  =  new  java.io.File(filePath);  

myDelFile.delete();  

}  

catch  (Exception  e)  

{  

System.out.println("删除文件操作出错");  

 

}  

}  

public  void  delFolder(String  folderPath)  {  //删除文件夹

try  

{  

delAllFile(folderPath);  //删除完里面所有内容  

String  filePath  =  folderPath;  

filePath  =  filePath.toString();  

java.io.File  myFilePath  =  new  java.io.File(filePath);  

myFilePath.delete();  //删除空文件夹  

}  

catch  (Exception  e)  {  

System.out.println("删除文件夹操作出错");  

//e.printStackTrace();  

}  

}  

public  void  delAllFile(String  path)  {  //删除文件夹里面的所有文件  

File  file  =  new  File(path);  

if  (!file.exists())  {  

return;  

}  

if  (!file.isDirectory())  {  

return;  

}  

String[]  tempList  =  file.list();  

File  temp  =  null;  

for  (int  i  =  0;  i  <  tempList.length;  i++)  {  

if  (path.endsWith(File.separator))  {  

temp  =  new  File(path  +  tempList[i]);  

}  

else  

{  

temp  =  new  File(path  +  File.separator  +  tempList[i]);  

}  

if  (temp.isFile())  {  

temp.delete();  

}  

if  (temp.isDirectory())  {  

delAllFile(path+"/"+  tempList[i]);//先删除文件夹里面的文件  

delFolder(path+"/"+  tempList[i]);//再删除空文件夹  

}  

}  

}  

 

public void copyfile(String source,String dest)//文件复制方法

{

try{

File in=new File(source);

File out=new File(dest);

FileInputStream inFile=new FileInputStream(in);

FileOutputStream outFile=new FileOutputStream(out);

byte[] buffere=new byte[1024];

int i=0;

while((i=inFile.read(buffere))!=-1)

{    

outFile.write(buffere,0,i);

}

inFile.close();

outFile.close();

}

catch(Exception e)

{

e.printStackTrace();

}

}

public void copyDict(String source,String dest)

{

 String source1;String dest1;

 File[] file=(new File(source).listFiles());

 for(int i=0;i

 

 

 

 

 

 

 

 

 

 

 

 


你可能感兴趣的:(java仿文件资源管理器)