file:commonsjava
1 package org.crazyit.editor.commons; 2 3 import org.crazyit.editor.EditorFrame; 4 import org.crazyit.editor.handler.add.AddHandler; 5 6 /** 7 * 添加的信息對象 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public class AddInfo { 16 17 //字符串, 在新增界面的text前顯示, 例如: 文件名稱 18 private String info; 19 20 //受新增操做影響的主frame 21 private EditorFrame editorFrame; 22 23 //新增完後的處理類 24 private AddHandler handler; 25 26 public AddInfo(String info, EditorFrame editorFrame, AddHandler handler) { 27 this.info = info; 28 this.editorFrame = editorFrame; 29 this.handler = handler; 30 } 31 32 public AddHandler getHandler() { 33 return handler; 34 } 35 36 public void setHandler(AddHandler handler) { 37 this.handler = handler; 38 } 39 40 public String getInfo() { 41 return info; 42 } 43 44 public void setInfo(String info) { 45 this.info = info; 46 } 47 48 public EditorFrame getEditorFrame() { 49 return editorFrame; 50 } 51 52 public void setEditorFrame(EditorFrame editorFrame) { 53 this.editorFrame = editorFrame; 54 } 55 56 }
1 package org.crazyit.editor.commons; 2 3 import java.io.File; 4 5 import javax.swing.JInternalFrame; 6 7 import org.crazyit.editor.EditPane; 8 9 /** 10 * 編輯的文件對象 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class EditFile { 19 20 //當前編輯的文件 21 private File file; 22 23 //該文件是否已經被保存 24 private boolean saved; 25 26 //該文件對應的窗口 27 private JInternalFrame iframe; 28 29 //該文件所對應的編輯器 30 private EditPane editPane; 31 32 public EditFile(File file, boolean saved, JInternalFrame iframe, 33 EditPane editPane) { 34 this.file = file; 35 this.saved = saved; 36 this.iframe = iframe; 37 this.editPane = editPane; 38 } 39 40 public EditPane getEditPane() { 41 return editPane; 42 } 43 44 public void setEditPane(EditPane editPane) { 45 this.editPane = editPane; 46 } 47 48 public JInternalFrame getIframe() { 49 return iframe; 50 } 51 52 53 public void setIframe(JInternalFrame iframe) { 54 this.iframe = iframe; 55 } 56 57 58 public boolean isSaved() { 59 return saved; 60 } 61 62 public void setSaved(boolean saved) { 63 this.saved = saved; 64 } 65 66 public File getFile() { 67 return file; 68 } 69 70 public void setFile(File file) { 71 this.file = file; 72 } 73 74 75 76 }
1 package org.crazyit.editor.commons; 2 3 import java.io.File; 4 5 import javax.swing.JInternalFrame; 6 7 import org.crazyit.editor.EditPane; 8 9 /** 10 * 編輯的文件對象 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class EditFile { 19 20 //當前編輯的文件 21 private File file; 22 23 //該文件是否已經被保存 24 private boolean saved; 25 26 //該文件對應的窗口 27 private JInternalFrame iframe; 28 29 //該文件所對應的編輯器 30 private EditPane editPane; 31 32 public EditFile(File file, boolean saved, JInternalFrame iframe, 33 EditPane editPane) { 34 this.file = file; 35 this.saved = saved; 36 this.iframe = iframe; 37 this.editPane = editPane; 38 } 39 40 public EditPane getEditPane() { 41 return editPane; 42 } 43 44 public void setEditPane(EditPane editPane) { 45 this.editPane = editPane; 46 } 47 48 public JInternalFrame getIframe() { 49 return iframe; 50 } 51 52 53 public void setIframe(JInternalFrame iframe) { 54 this.iframe = iframe; 55 } 56 57 58 public boolean isSaved() { 59 return saved; 60 } 61 62 public void setSaved(boolean saved) { 63 this.saved = saved; 64 } 65 66 public File getFile() { 67 return file; 68 } 69 70 public void setFile(File file) { 71 this.file = file; 72 } 73 74 75 76 }
file:confignode
1 package org.crazyit.editor.config; 2 3 /** 4 * 編譯配置對象 5 * 6 * @author yangenxiong yangenxiong2009@gmail.com 7 * @version 1.0 8 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 9 * <br>Copyright (C), 2009-2010, yangenxiong 10 * <br>This program is protected by copyright laws. 11 */ 12 public class CompileConfig { 13 14 //記錄源文件的目錄 15 public final static String SRC_DIR = "src"; 16 17 //記錄項目編譯目錄 18 public final static String OUTPUT_DIR = "classes"; 19 }
file:expectionwindows
1 package org.crazyit.editor.exception; 2 3 /** 4 * 文件異常類 5 * 6 * @author yangenxiong yangenxiong2009@gmail.com 7 * @version 1.0 8 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 9 * <br>Copyright (C), 2009-2010, yangenxiong 10 * <br>This program is protected by copyright laws. 11 */ 12 public class FileException extends RuntimeException { 13 14 public FileException(String message) { 15 super(message); 16 } 17 }
file:handler數組
1 package org.crazyit.editor.handler.add; 2 3 import java.io.File; 4 5 import javax.swing.JOptionPane; 6 7 import org.crazyit.editor.AddFrame; 8 import org.crazyit.editor.EditorFrame; 9 import org.crazyit.editor.exception.FileException; 10 import org.crazyit.editor.tree.ProjectTreeModel; 11 import org.crazyit.editor.tree.ProjectTreeNode; 12 13 /** 14 * 添加文件處理類 15 * 16 * @author yangenxiong yangenxiong2009@gmail.com 17 * @version 1.0 18 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 19 * <br>Copyright (C), 2009-2010, yangenxiong 20 * <br>This program is protected by copyright laws. 21 */ 22 public class AddFileHandler implements AddHandler { 23 24 public void afterAdd(EditorFrame editorFrame, AddFrame addFrame, Object data) { 25 try { 26 //得到當前所選擇的樹節點 27 ProjectTreeNode selectNode = editorFrame.getSelectNode(); 28 //獲取當前選擇節點所對應的文件 29 File folder = selectNode.getFile(); 30 //若是folder不是一個目錄,則用selectNode的父節點(是一個目錄)做爲新文件的存放目錄 31 if (!folder.isDirectory()) { 32 ProjectTreeNode parent = (ProjectTreeNode)selectNode.getParent(); 33 selectNode = parent; 34 folder = parent.getFile(); 35 } 36 //建立文件,放到folder下 37 File newFile = new File(folder.getAbsoluteFile() + File.separator + data); 38 //若是文件已經存在,就彈出提示並返回 39 if (newFile.exists()) { 40 JOptionPane.showMessageDialog(addFrame, "文件已經存在"); 41 return; 42 } 43 newFile.createNewFile(); 44 editorFrame.reloadNode(selectNode); 45 //使主編輯frame可用 46 editorFrame.setEnabled(true); 47 ///讓添加的frame不可見 48 addFrame.setVisible(false); 49 } catch (Exception e) { 50 throw new FileException("create file error: " + e.getMessage()); 51 } 52 } 53 54 }
1 package org.crazyit.editor.handler.add; 2 3 import java.io.File; 4 5 import javax.swing.JOptionPane; 6 7 import org.crazyit.editor.AddFrame; 8 import org.crazyit.editor.EditorFrame; 9 import org.crazyit.editor.exception.FileException; 10 import org.crazyit.editor.tree.ProjectTreeNode; 11 12 /** 13 * 添加目錄處理類 14 * 15 * @author yangenxiong yangenxiong2009@gmail.com 16 * @version 1.0 17 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 18 * <br>Copyright (C), 2009-2010, yangenxiong 19 * <br>This program is protected by copyright laws. 20 */ 21 public class AddFolderHandler implements AddHandler { 22 23 public void afterAdd(EditorFrame editorFrame, AddFrame addFrame, Object data) { 24 try { 25 //得到樹中所選取的節點 26 ProjectTreeNode selectNode = editorFrame.getSelectNode(); 27 //獲取該節點所對應的文件對象 28 File folder = selectNode.getFile(); 29 //若是folder不是一個目錄,則用selectNode的父節點(是一個目錄)做爲新目錄的父目錄 30 if (!folder.isDirectory()) { 31 ProjectTreeNode parent = (ProjectTreeNode)selectNode.getParent(); 32 //讓當前所選擇的文件的父目錄做爲當前選擇的目錄 33 selectNode = parent; 34 folder = parent.getFile(); 35 } 36 //建立一個文件目錄對象 37 File newFolder = new File(folder.getAbsoluteFile() + File.separator + data); 38 //若是該目錄已經存在,彈出提示並返回 39 if (newFolder.exists()) { 40 JOptionPane.showMessageDialog(addFrame, "目錄已經存在"); 41 return; 42 } 43 //建立新的目錄 44 newFolder.mkdir(); 45 //刷新樹的節點 46 editorFrame.reloadNode(selectNode); 47 //讓EditorFrame可用 48 editorFrame.setEnabled(true); 49 //讓添加的frame不可見 50 addFrame.setVisible(false); 51 } catch (Exception e) { 52 throw new FileException("create folder error: " + e.getMessage()); 53 } 54 } 55 56 }
1 package org.crazyit.editor.handler.add; 2 3 import org.crazyit.editor.AddFrame; 4 import org.crazyit.editor.EditorFrame; 5 6 /** 7 * 添加事件的接口 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public interface AddHandler { 16 17 //新增完後須要作的事情,須要作的事情由實現類去實現 18 //參數爲EditorFrame,AddFrame,輸入的信息data 19 void afterAdd(EditorFrame editorFrame, AddFrame addFrame, Object data); 20 }
1 package org.crazyit.editor.handler.add; 2 3 import java.io.File; 4 5 import javax.swing.JOptionPane; 6 import javax.swing.JTree; 7 8 import org.crazyit.editor.AddFrame; 9 import org.crazyit.editor.EditorFrame; 10 import org.crazyit.editor.commons.WorkSpace; 11 import org.crazyit.editor.config.CompileConfig; 12 import org.crazyit.editor.exception.FileException; 13 14 /** 15 * 添加項目處理類 16 * 17 * @author yangenxiong yangenxiong2009@gmail.com 18 * @version 1.0 19 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 20 * <br>Copyright (C), 2009-2010, yangenxiong 21 * <br>This program is protected by copyright laws. 22 */ 23 public class AddProjectHandler implements AddHandler { 24 25 public void afterAdd(EditorFrame editorFrame, AddFrame addFrame, Object data) { 26 try { 27 //獲取工做空間所在的目錄 28 File spaceFolder = editorFrame.getWorkSpace().getFolder(); 29 //建立.project文件 30 File projectFile = new File(spaceFolder.getAbsoluteFile() + 31 File.separator + data + ".project"); 32 //建立項目目錄 33 File projectFolder = new File(spaceFolder.getAbsoluteFile() + File.separator + data); 34 //項目已經存在,彈出警告並返回 35 if (projectFile.exists() && projectFolder.exists()) { 36 JOptionPane.showMessageDialog(addFrame, "項目已經存在"); 37 return; 38 } 39 //項目文件不存在, 建立項目文件 40 if (!projectFile.exists()) projectFile.createNewFile(); 41 //項目目錄不存在, 建立項目文件目錄 42 if (!projectFolder.exists()) projectFolder.mkdir(); 43 //建立項目的src目錄和編譯目錄 44 File src = new File(projectFolder.getAbsoluteFile() + 45 File.separator + CompileConfig.SRC_DIR); 46 //Java文件編譯的輸入目錄 47 File output = new File(projectFolder.getAbsoluteFile() + 48 File.separator + CompileConfig.OUTPUT_DIR); 49 //建立src和output兩個目錄 50 src.mkdir(); 51 output.mkdir(); 52 //刷新整棵樹 53 JTree newTree = editorFrame.getTreeCreator().createTree(editorFrame); 54 editorFrame.refreshTree(newTree); 55 //讓EditorFrame變得可用 56 editorFrame.setEnabled(true); 57 //讓添加的frame不可見 58 addFrame.setVisible(false); 59 } catch (Exception e) { 60 throw new FileException("create project error: " + e.getMessage()); 61 } 62 } 63 64 }
file:runapp
1 package org.crazyit.editor.handler.run; 2 3 import java.io.File; 4 5 import org.crazyit.editor.EditorFrame; 6 import org.crazyit.editor.config.CompileConfig; 7 import org.crazyit.editor.util.CommandUtil; 8 9 /** 10 * 運行Java文件處理類 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class JavaRunHandler { 19 20 public String run(EditorFrame editorFrame) { 21 try { 22 //得到項目目錄的路徑 23 String projectPath = editorFrame.getCurrentProject().getAbsolutePath(); 24 //得到源文件的全路徑 25 String sourcePath = editorFrame.getCurrentFile().getFile().getAbsolutePath(); 26 //得到項目的編譯路徑,項目目錄加CompileConfig中配置的輸出目錄 27 String classPath = editorFrame.getCurrentProject().getAbsolutePath() 28 + File.separator + CompileConfig.OUTPUT_DIR; 29 //獲取類名 30 String className = getClassName(projectPath, sourcePath); 31 //拼裝命令 32 String command = "java -cp \"" + classPath + "\" " + className; 33 Process p = CommandUtil.executeCommand(command); 34 return CommandUtil.getRunString(p); 35 } catch (Exception e) { 36 return e.getMessage(); 37 } 38 } 39 40 //根據項目目錄的路徑和Java源文件的路徑獲取一個類的全限定類名 41 private String getClassName(String projectPath, String sourcePath) { 42 String temp = projectPath + File.separator + CompileConfig.SRC_DIR + 43 File.separator; 44 String result = sourcePath.replace(temp, ""); 45 result = result.replace(".java", ""); 46 result = result.replace(String.valueOf(File.separatorChar), "."); 47 return result; 48 } 49 50 51 }
file:save編輯器
1 package org.crazyit.editor.handler.save; 2 3 import org.crazyit.editor.EditorFrame; 4 import org.crazyit.editor.commons.EditFile; 5 import org.crazyit.editor.util.FileUtil; 6 7 /** 8 * 執行普通保存的處理類 9 * 10 * @author yangenxiong yangenxiong2009@gmail.com 11 * @version 1.0 12 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 13 * <br>Copyright (C), 2009-2010, yangenxiong 14 * <br>This program is protected by copyright laws. 15 */ 16 public class CommonSaveHandler implements SaveHandler { 17 18 //提供一個保存方法,做爲普通的保存 19 public String save(EditorFrame editorFrame) { 20 EditFile editFile = editorFrame.getCurrentFile(); 21 FileUtil.writeFile(editFile.getFile(), editFile.getEditPane().getText()); 22 return null; 23 } 24 25 }
1 package org.crazyit.editor.handler.save; 2 3 import java.io.File; 4 import java.io.FileWriter; 5 import java.io.InputStream; 6 7 import org.crazyit.editor.EditorFrame; 8 import org.crazyit.editor.config.CompileConfig; 9 import org.crazyit.editor.util.CommandUtil; 10 11 /** 12 * 保存Java文件的處理類 13 * 14 * @author yangenxiong yangenxiong2009@gmail.com 15 * @version 1.0 16 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 17 * <br>Copyright (C), 2009-2010, yangenxiong 18 * <br>This program is protected by copyright laws. 19 */ 20 public class JavaSaveHandler extends CommonSaveHandler { 21 22 23 24 public String save(EditorFrame editorFrame) { 25 //調用父類的保存方法 26 super.save(editorFrame); 27 return javac(editorFrame); 28 } 29 30 //執行javac命令 31 private String javac(EditorFrame editorFrame) { 32 try { 33 //得到項目的編譯路徑,項目目錄加CompileConfig中配置的輸出目錄 34 String classPath = editorFrame.getCurrentProject().getAbsolutePath() 35 + File.separator + CompileConfig.OUTPUT_DIR; 36 //得到源文件的文件路徑 37 String filePath = editorFrame.getCurrentFile().getFile().getAbsolutePath(); 38 //拼裝字符串命令,該命令只可在windows下運行 39 String command = "javac -d \"" + classPath + "\" \"" + filePath + "\""; 40 Process p = CommandUtil.executeCommand(command); 41 return CommandUtil.getProcessString(p); 42 } catch (Exception e) { 43 return e.getMessage(); 44 } 45 } 46 47 48 }
1 package org.crazyit.editor.handler.save; 2 3 import org.crazyit.editor.EditorFrame; 4 5 /** 6 * 保存處理接口 7 * 8 * @author yangenxiong yangenxiong2009@gmail.com 9 * @version 1.0 10 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 11 * <br>Copyright (C), 2009-2010, yangenxiong 12 * <br>This program is protected by copyright laws. 13 */ 14 public interface SaveHandler { 15 16 //執行保存的接口方法 17 String save(EditorFrame editorFrame); 18 }
1 package org.crazyit.editor.handler.save; 2 3 import org.crazyit.editor.EditorFrame; 4 5 /** 6 * 保存的中介者 7 * 8 * @author yangenxiong yangenxiong2009@gmail.com 9 * @version 1.0 10 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 11 * <br>Copyright (C), 2009-2010, yangenxiong 12 * <br>This program is protected by copyright laws. 13 */ 14 public abstract class SaveMediator { 15 16 //須要子類去實現的保存方法 17 public abstract String doSave(EditorFrame editorFramet); 18 }
1 package org.crazyit.editor.handler.save; 2 3 import org.crazyit.editor.EditorFrame; 4 import org.crazyit.editor.commons.EditFile; 5 6 /** 7 * 保存動做的中介者實現 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public class SaveMediatorConcrete extends SaveMediator { 16 17 private SaveHandler commonHandler; 18 19 private SaveHandler javaHandler; 20 21 //構造兩個處理保存的對象 22 public SaveMediatorConcrete() { 23 this.commonHandler = new CommonSaveHandler(); 24 this.javaHandler = new JavaSaveHandler(); 25 } 26 27 public String doSave(EditorFrame editorFrame) { 28 //得到當前編輯的文件名 29 String fileName = editorFrame.getCurrentFile().getFile().getName(); 30 String result = null; 31 //判斷文件是否爲Java文件, 再決定處理類 32 if (fileName.endsWith(".java")) {//保存java文件 33 result = javaHandler.save(editorFrame); 34 } else {//執行普通的保存 35 result = commonHandler.save(editorFrame); 36 } 37 return result; 38 } 39 40 }
file:treeide
1 package org.crazyit.editor.tree; 2 3 import javax.swing.tree.DefaultTreeModel; 4 import javax.swing.tree.TreeNode; 5 6 /** 7 * 項目樹的Model對象 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public class ProjectTreeModel extends DefaultTreeModel { 16 17 public ProjectTreeModel(ProjectTreeNode arg0) { 18 super(arg0); 19 } 20 21 public void reload(ProjectTreeNode node, TreeCreator creator) { 22 //獲取node節點的父節點 23 ProjectTreeNode parent = (ProjectTreeNode)node.getParent(); 24 //父節點爲null,返回,不須要reload 25 if (parent == null) return; 26 //獲取node節點在父節點的索引 27 int index = parent.getIndex(node); 28 //先裝node節點從parent中刪除 29 parent.remove(index); 30 //再經過TreeCreator獲取新的節點 31 node = creator.createNode(node.getFile()); 32 //添加到父節點中 33 parent.insert(node, index); 34 //調用DefaultTreeModel的reload方法 35 super.reload(node); 36 } 37 38 39 40 41 42 }
1 package org.crazyit.editor.tree; 2 3 import java.io.File; 4 import java.util.ArrayList; 5 import java.util.List; 6 7 import javax.swing.tree.DefaultMutableTreeNode; 8 9 /** 10 * 項目樹的節點對象 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class ProjectTreeNode extends DefaultMutableTreeNode { 19 20 //該節點對應的文件 21 private File file; 22 23 //該節點下的子節點 24 private List<ProjectTreeNode> children; 25 26 //ProjectTreeNode的構造器,參數分別時該節點對應的文件,是否容許有子節點 27 public ProjectTreeNode(File file, boolean allowsChildren) { 28 super(file.getName(), allowsChildren); 29 this.file = file; 30 //初始化該節點下的子節點集合 31 children = new ArrayList<ProjectTreeNode>(); 32 } 33 34 public File getFile() { 35 return file; 36 } 37 38 public void setFile(File file) { 39 this.file = file; 40 } 41 42 public List<ProjectTreeNode> getChildren() { 43 //清空children, 再從新獲取一次 44 children.removeAll(children); 45 for (int i = 0; i < getChildCount(); i++) { 46 children.add((ProjectTreeNode)getChildAt(i)); 47 } 48 return this.children; 49 } 50 51 52 53 54 55 }
1 package org.crazyit.editor.tree; 2 3 import java.awt.event.MouseAdapter; 4 import java.awt.event.MouseEvent; 5 6 import javax.swing.event.TreeSelectionEvent; 7 8 import org.crazyit.editor.EditorFrame; 9 10 /** 11 * 項目樹選擇監聽器 12 * 13 * @author yangenxiong yangenxiong2009@gmail.com 14 * @version 1.0 15 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 16 * <br>Copyright (C), 2009-2010, yangenxiong 17 * <br>This program is protected by copyright laws. 18 */ 19 public class ProjectTreeSelectionListener extends MouseAdapter { 20 21 //主界面的frame 22 private EditorFrame editorFrame; 23 24 //將主界面的frame(EditorFrame)做爲構造參數傳入監聽器 25 public ProjectTreeSelectionListener(EditorFrame editorFrame) { 26 this.editorFrame = editorFrame; 27 } 28 29 public void mousePressed(MouseEvent e) { 30 //獲得當前所選擇的節點 31 ProjectTreeNode selectNode = this.editorFrame.getSelectNode(); 32 //若是沒有選擇節點,就返回 33 if (selectNode == null) return; 34 //若是選擇的是一個目錄,返回 35 if (selectNode.getFile().isDirectory()) return; 36 //使用EditorFrame的方法來打開文件 37 this.editorFrame.openFile(selectNode.getFile()); 38 } 39 40 }
1 package org.crazyit.editor.tree; 2 3 import java.io.File; 4 5 import javax.swing.JTree; 6 7 import org.crazyit.editor.EditorFrame; 8 9 /** 10 * 樹建立接口 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public interface TreeCreator { 19 20 /** 21 * 根據編輯的EditorFrame對象建立項目樹 22 * @param editorFrame 23 * @return 24 */ 25 JTree createTree(EditorFrame editorFrame); 26 27 /** 28 * 根據一個目錄建立它的節點 29 * @param folder 30 * @return 31 */ 32 ProjectTreeNode createNode(File folder); 33 }
1 package org.crazyit.editor.tree; 2 3 import java.io.File; 4 import java.util.ArrayList; 5 import java.util.List; 6 7 import javax.swing.JTree; 8 import javax.swing.tree.DefaultTreeCellRenderer; 9 import javax.swing.tree.TreePath; 10 11 import org.crazyit.editor.EditorFrame; 12 import org.crazyit.editor.util.ImageUtil; 13 14 /** 15 * 樹建立實現類 16 * 17 * @author yangenxiong yangenxiong2009@gmail.com 18 * @version 1.0 19 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 20 * <br>Copyright (C), 2009-2010, yangenxiong 21 * <br>This program is protected by copyright laws. 22 */ 23 public class TreeCreatorImpl implements TreeCreator { 24 25 26 @Override 27 public JTree createTree(EditorFrame editorFrame) { 28 File spaceFolder = editorFrame.getWorkSpace().getFolder(); 29 ProjectTreeNode root = new ProjectTreeNode(spaceFolder, true); 30 ProjectTreeModel treeModel = new ProjectTreeModel(root); 31 JTree tree = new JTree(treeModel); 32 //獲取工做空間下面全部的目錄(即與有projectName.project相對應的目錄),也就是項目目錄 33 List<File> projectFolders = getProjectFolders(spaceFolder); 34 //遍歷項目目錄集合,併爲其建立子節點 35 for (int i = 0; i < projectFolders.size(); i++) { 36 //獲取循環中的目錄 37 File projectFolder = projectFolders.get(i); 38 //調用createNode建立它全部的子節點 39 ProjectTreeNode node = createNode(projectFolder); 40 //向根節點添加子節點(項目目錄) 41 root.add(node); 42 } 43 44 //定製節點圖片 45 DefaultTreeCellRenderer renderer = new DefaultTreeCellRenderer(); 46 //目錄打開時的圖片 47 renderer.setOpenIcon(ImageUtil.getImageIcon(ImageUtil.FOLDER_OPEN)); 48 //節點沒有子節點的圖片 49 renderer.setLeafIcon(ImageUtil.getImageIcon(ImageUtil.FILE)); 50 //目錄關閉時的圖片 51 renderer.setClosedIcon(ImageUtil.getImageIcon(ImageUtil.FOLDER_CLOSE)); 52 //設置樹的部件處理類爲上面的renderer 53 tree.setCellRenderer(renderer); 54 //爲項目樹添加一個樹選擇監聽器 55 tree.addMouseListener(new ProjectTreeSelectionListener(editorFrame)); 56 //建立根在項目樹中的路徑 57 TreePath path = new TreePath(root); 58 //讓樹默認展開根節點 59 tree.expandPath(path); 60 //設置樹的根節點不可見 61 tree.setRootVisible(false); 62 return tree; 63 } 64 65 /* 66 * 根據一個目錄建立它的全部直接節點 67 */ 68 private List<ProjectTreeNode> createNodes(File folder) { 69 //獲取該目錄下的全部文件 70 File[] files = folder.listFiles(); 71 List<ProjectTreeNode> result = new ArrayList<ProjectTreeNode>(); 72 //對該目錄下的全部文件的數組進行兩次遍歷 73 for (File file : files) { 74 //第一次遍歷,若是是目錄的話,就加入到結果集合中 75 if (file.isDirectory()) { 76 result.add(new ProjectTreeNode(file, true)); 77 } 78 } 79 for (File file : files) { 80 //第二次遍歷,若是非目錄的話,就加入到結果集合中 81 if (!file.isDirectory()) {//再加普通文件 82 result.add(new ProjectTreeNode(file, false)); 83 } 84 } 85 return result; 86 } 87 88 //根據一個目錄去建立該目錄所對應的節點對象,該對象的全部的子節點都已經建立 89 public ProjectTreeNode createNode(File folder) { 90 //建立一個父節點,即本方法即將返回的節點對象 91 ProjectTreeNode parent = null; 92 //若是參數foler不是一個目錄的話,建立一個ProjectTreeNode對象並返回,代表它不容許擁有子節點 93 if (!folder.isDirectory()) { 94 return new ProjectTreeNode(folder, false); 95 } else { 96 //若是是一個目錄的話,則建立上面的parent,代表它是一個目錄,能夠擁有子節點 97 parent = new ProjectTreeNode(folder, true); 98 } 99 //利用上面的parent節點去查找它下面全部的直接節點 100 List<ProjectTreeNode> nodes = createNodes(parent.getFile()); 101 //獲取到parent下面的全部直接子節點後,再去循環遞歸調用本方法 102 for (ProjectTreeNode node : nodes) { 103 //遞歸建立子節點,並將返回的節點添加到parent中 104 parent.add(createNode(node.getFile())); 105 } 106 return parent; 107 } 108 109 110 /** 111 * 獲取工做空間目錄下全部的項目名稱 112 * @return 113 */ 114 private List<String> getProjectNames(File spaceFolder) { 115 List<String> result = new ArrayList<String>(); 116 for (File file : spaceFolder.listFiles()) { 117 if (file.getName().endsWith(".project")) {//取以.project結尾的文件 118 result.add(file.getName().substring(0, file.getName().indexOf(".project"))); 119 } 120 } 121 return result; 122 } 123 124 /* 125 * 獲取工做空間目錄下全部的項目目錄 126 */ 127 private List<File> getProjectFolders(File spaceFolder) { 128 List<String> projectNames = getProjectNames(spaceFolder); 129 List<File> result = new ArrayList<File>(); 130 //獲取工做空間下面全部的文件 131 File[] files = spaceFolder.listFiles(); 132 for (String projectName : projectNames) { 133 for (File file : files) { 134 if (file.isDirectory()) {//若是工做空間下面的文件是目錄,再去判斷是不是項目目錄 135 if (projectName.equals(file.getName())) { 136 result.add(file); 137 } 138 } 139 } 140 } 141 return result; 142 } 143 }
file: util工具
1 package org.crazyit.editor.util; 2 3 import java.io.File; 4 import java.io.FileWriter; 5 import java.io.IOException; 6 import java.io.InputStream; 7 8 /** 9 * 命令工具類 10 * 11 * @author yangenxiong yangenxiong2009@gmail.com 12 * @version 1.0 13 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 14 * <br>Copyright (C), 2009-2010, yangenxiong 15 * <br>This program is protected by copyright laws. 16 */ 17 public class CommandUtil { 18 19 public final static String WINDOWS_COMMAND = "cmd /c "; 20 21 //返回進程process的錯誤信息 22 public static String getErrorMessage(Process process) { 23 return getProcessString(process.getErrorStream()); 24 } 25 26 private static String getProcessString(InputStream is) { 27 try { 28 StringBuffer buffer = new StringBuffer(); 29 byte[] b = new byte[4096]; 30 for (int n; (n = is.read(b)) != -1;) 31 buffer.append(new String(b, 0, n)); 32 is.close(); 33 return buffer.toString(); 34 } catch (Exception e) { 35 return e.getMessage(); 36 } 37 } 38 39 //獲取一個進程的錯誤信息 40 public static String getProcessString(Process process) { 41 StringBuffer result = new StringBuffer(); 42 //調用CommandUtil的方法 43 String errorString = getErrorMessage(process); 44 if (errorString.length() != 0) result.append("錯誤: " + errorString); 45 else result.append("執行完成"); 46 return result.toString(); 47 } 48 49 //返回一個進程的信息 50 public static String getRunString(Process process) { 51 String error = getErrorMessage(process); 52 String message = getProcessString(process.getInputStream()); 53 return error + message; 54 } 55 56 //執行一個命令並返回相應的信息 57 public static Process executeCommand(String command) { 58 try { 59 //在windows下將命令生成一份bat文件, 再執行該bat文件 60 File batFile = new File("dump.bat"); 61 if (!batFile.exists()) batFile.createNewFile(); 62 //將命令寫入文件中 63 FileWriter writer = new FileWriter(batFile); 64 writer.write(command); 65 writer.close(); 66 //執行該bat文件 67 Process process =Runtime.getRuntime().exec(WINDOWS_COMMAND + batFile.getAbsolutePath()); 68 process.waitFor(); 69 //將bat文件刪除 70 batFile.delete(); 71 return process; 72 } catch (Exception e) { 73 return null; 74 } 75 } 76 }
1 package org.crazyit.editor.util; 2 3 import java.io.File; 4 import java.io.FileInputStream; 5 import java.io.FileOutputStream; 6 import java.io.IOException; 7 import java.io.PrintStream; 8 9 import javax.swing.JTextArea; 10 11 import org.crazyit.editor.exception.FileException; 12 13 /** 14 * 文件處理工具類 15 * 16 * @author yangenxiong yangenxiong2009@gmail.com 17 * @version 1.0 18 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 19 * <br>Copyright (C), 2009-2010, yangenxiong 20 * <br>This program is protected by copyright laws. 21 */ 22 public class FileUtil { 23 24 //讀取一個文件的內容 25 public static String readFile(File file) { 26 StringBuffer result = new StringBuffer(); 27 try { 28 //使用IO流讀取文件 29 FileInputStream fis= new FileInputStream(file); 30 String content = null; 31 byte[] arr = new byte[1024]; 32 int readLength ; 33 while ((readLength = fis.read(arr)) > 0) { 34 content = new String(arr, 0, readLength); 35 result.append(content); 36 } 37 fis.close(); 38 } 39 catch(IOException e) { 40 throw new FileException("read '" + file.getAbsolutePath() + "' file error"); 41 } 42 return result.toString(); 43 } 44 45 //使用IO流將參數content寫入到參數file中 46 public static void writeFile(File file, String content) { 47 try { 48 FileOutputStream fos = new FileOutputStream(file); 49 PrintStream ps = new PrintStream(fos); 50 ps.print(content); 51 ps.close(); 52 fos.close(); 53 } catch (IOException e) { 54 throw new FileException("write file error"); 55 } 56 } 57 }
1 package org.crazyit.editor.util; 2 3 import java.awt.Image; 4 import java.io.File; 5 6 import javax.imageio.ImageIO; 7 import javax.swing.ImageIcon; 8 9 /** 10 * 圖片工具類 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class ImageUtil { 19 20 //目錄關閉圖片 21 public static String FOLDER_CLOSE = "images/folder-close.gif"; 22 //目錄打開圖片 23 public static String FOLDER_OPEN = "images/folder-open.gif"; 24 //無子節點的文件圖片 25 public static String FILE = "images/file.gif"; 26 //使用ImageIO流讀取圖片 27 public static Image getImage(String path) { 28 try { 29 return ImageIO.read(new File(path)); 30 } catch (Exception e) { 31 e.printStackTrace(); 32 return null; 33 } 34 } 35 36 public static ImageIcon getImageIcon(String path) { 37 return new ImageIcon(getImage(path)); 38 } 39 }
file:src佈局
1 package org.crazyit.editor; 2 3 import java.awt.event.ActionEvent; 4 import java.awt.event.ActionListener; 5 import java.awt.event.KeyAdapter; 6 import java.awt.event.KeyEvent; 7 import java.awt.event.WindowAdapter; 8 9 import javax.swing.BoxLayout; 10 import javax.swing.JButton; 11 import javax.swing.JFrame; 12 import javax.swing.JLabel; 13 import javax.swing.JPanel; 14 import javax.swing.JTextField; 15 16 import org.crazyit.editor.commons.AddInfo; 17 18 /** 19 * 添加界面 20 * 21 * @author yangenxiong yangenxiong2009@gmail.com 22 * @version 1.0 23 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 24 * <br>Copyright (C), 2009-2010, yangenxiong 25 * <br>This program is protected by copyright laws. 26 */ 27 public class AddFrame extends JFrame { 28 29 //該Frame的JPanel 30 private JPanel mainPanel; 31 32 //項目名稱 33 private JPanel namePanel; 34 35 //顯示文件的JLabel 36 private JLabel nameLabel; 37 38 //輸入名稱的JTextField 39 private JTextField nameText; 40 41 //放按鈕的Panel 42 private JPanel buttonPanel; 43 44 //肯定按鈕 45 private JButton confirmButton; 46 47 //取消按鈕 48 private JButton cancelButton; 49 50 51 public AddFrame(final AddInfo info) { 52 mainPanel = new JPanel(); 53 namePanel = new JPanel(); 54 //設置nameLabel的文字 55 nameLabel = new JLabel(info.getInfo()); 56 nameText = new JTextField("", 20); 57 buttonPanel = new JPanel(); 58 confirmButton = new JButton("肯定"); 59 cancelButton = new JButton("取消"); 60 61 mainPanel.setLayout(new BoxLayout(mainPanel, BoxLayout.Y_AXIS)); 62 addWindowListener(new WindowAdapter() { 63 public void windowClosing(java.awt.event.WindowEvent e) { 64 cancel(info); 65 } 66 }); 67 setLocation(200, 200); 68 setResizable(false); 69 //文本框前面的字 70 namePanel.setLayout(new BoxLayout(namePanel, BoxLayout.X_AXIS)); 71 namePanel.add(nameLabel); 72 namePanel.add(nameText); 73 nameText.addKeyListener(new KeyAdapter() { 74 public void keyReleased(KeyEvent e) { 75 //判斷項目路徑與名稱是否有值, 若是兩個text field都有值, 則肯定按鈕可用 76 if (nameText.getText().equals("")) { 77 confirmButton.setEnabled(false); 78 } else { 79 confirmButton.setEnabled(true); 80 } 81 } 82 }); 83 84 //肯定和取消的按鈕 85 buttonPanel.setLayout(new BoxLayout(buttonPanel, BoxLayout.X_AXIS)); 86 confirmButton.setEnabled(false); 87 buttonPanel.add(confirmButton); 88 buttonPanel.add(new JLabel(" ")); 89 buttonPanel.add(cancelButton); 90 91 //爲取消按鈕添加監聽器 92 cancelButton.addActionListener(new ActionListener(){ 93 public void actionPerformed(ActionEvent e) { 94 cancel(info); 95 } 96 }); 97 //爲肯定按鈕添加監聽器 98 confirmButton.addActionListener(new ActionListener() { 99 public void actionPerformed(ActionEvent e) { 100 //若是輸入框沒有值,返回 101 if (nameText.getText() == "") return; 102 handerConfirm(info); 103 } 104 }); 105 mainPanel.add(namePanel); 106 mainPanel.add(buttonPanel); 107 add(mainPanel); 108 pack(); 109 } 110 111 //處理肯定按鈕的點擊 112 private void handerConfirm(AddInfo info) { 113 //獲取得用戶輸入 114 String data = nameText.getText(); 115 //新增後會涉及的一些與業務相關的操做留給Handler類處理 116 info.getHandler().afterAdd(info.getEditorFrame(), this, data); 117 } 118 119 private void cancel(AddInfo info) { 120 //設置EditorFrame可用 121 info.getEditorFrame().setEnabled(true); 122 //讓本窗口不可見 123 setVisible(false); 124 } 125 126 127 128 }
1 package org.crazyit.editor; 2 3 import javax.swing.event.DocumentEvent; 4 import javax.swing.event.DocumentListener; 5 6 /** 7 * 文檔監聽器 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public class EditDocumentListener implements DocumentListener { 16 //主界面對象 17 private EditorFrame editorFrame; 18 public EditDocumentListener(EditorFrame editorFrame) { 19 this.editorFrame = editorFrame; 20 } 21 public void changedUpdate(DocumentEvent e) { 22 } 23 public void insertUpdate(DocumentEvent e) { 24 //設置當前編輯的文件的saved屬性爲false 25 this.editorFrame.getCurrentFile().setSaved(false); 26 } 27 public void removeUpdate(DocumentEvent e) { 28 } 29 }
1 package org.crazyit.editor; 2 3 import java.awt.BorderLayout; 4 import java.awt.Color; 5 import java.awt.Insets; 6 import java.awt.event.ActionEvent; 7 import java.awt.event.InputEvent; 8 import java.io.File; 9 import java.util.ArrayList; 10 import java.util.List; 11 12 import javax.swing.AbstractAction; 13 import javax.swing.Action; 14 import javax.swing.Box; 15 import javax.swing.BoxLayout; 16 import javax.swing.ImageIcon; 17 import javax.swing.JDesktopPane; 18 import javax.swing.JFileChooser; 19 import javax.swing.JFrame; 20 import javax.swing.JInternalFrame; 21 import javax.swing.JMenu; 22 import javax.swing.JMenuBar; 23 import javax.swing.JOptionPane; 24 import javax.swing.JScrollPane; 25 import javax.swing.JSplitPane; 26 import javax.swing.JTabbedPane; 27 import javax.swing.JTextArea; 28 import javax.swing.JToolBar; 29 import javax.swing.JTree; 30 import javax.swing.KeyStroke; 31 import javax.swing.tree.TreePath; 32 33 import org.crazyit.editor.commons.AddInfo; 34 import org.crazyit.editor.commons.EditFile; 35 import org.crazyit.editor.commons.WorkSpace; 36 import org.crazyit.editor.handler.add.AddFileHandler; 37 import org.crazyit.editor.handler.add.AddFolderHandler; 38 import org.crazyit.editor.handler.add.AddProjectHandler; 39 import org.crazyit.editor.handler.run.JavaRunHandler; 40 import org.crazyit.editor.handler.save.SaveMediator; 41 import org.crazyit.editor.handler.save.SaveMediatorConcrete; 42 import org.crazyit.editor.tree.ProjectTreeModel; 43 import org.crazyit.editor.tree.ProjectTreeNode; 44 import org.crazyit.editor.tree.TreeCreator; 45 46 /** 47 * 編輯界面 48 * 49 * @author yangenxiong yangenxiong2009@gmail.com 50 * @version 1.0 51 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 52 * <br>Copyright (C), 2009-2010, yangenxiong 53 * <br>This program is protected by copyright laws. 54 */ 55 public class EditorFrame extends JFrame { 56 57 //多文件的tab標題 58 private JTabbedPane tabPane; 59 60 //存放tabPane與desk 61 private Box box; 62 63 //建立一個多文檔的桌面容器 64 private JDesktopPane desk; 65 66 //用於分隔主編輯區和信息顯示區的容器 67 private JSplitPane editorSplitPane; 68 69 //能夠滾動的JScrollPane對象,用於放infoArea 70 private JScrollPane infoPane; 71 72 //用於顯示信息的文本域 73 private JTextArea infoArea; 74 75 //存放樹的可滾動容器 76 private JScrollPane treePane; 77 78 //整個界面的分隔組件的容器 79 private JSplitPane mainSplitPane; 80 81 //項目樹對象 82 private JTree tree; 83 84 //菜單欄對象 85 private JMenuBar menuBar; 86 87 //編輯菜單對象 88 private JMenu editMenu; 89 90 //文件菜單 91 private JMenu fileMenu; 92 93 //工具條 94 private JToolBar toolBar; 95 96 private WorkSpace workSpace; 97 98 private TreeCreator treeCreator; 99 100 //添加的界面 101 private AddFrame addFrame; 102 103 //文件選擇器 104 private FileChooser fileChooser; 105 106 //當前正在編輯的文件對象 107 private EditFile currentFile; 108 109 //窗口監聽器 110 private IFrameListener iframeListener; 111 112 //打開文件的集合 113 private List<EditFile> openFiles = new ArrayList<EditFile>(); 114 115 //中介者對象 116 private SaveMediator saveMediator; 117 118 //運行class文件的處理類 119 private JavaRunHandler runHandler; 120 121 //新建文件的Action對象 122 private Action fileNew = new AbstractAction("新建文件", new ImageIcon("images/newFile.gif")) { 123 public void actionPerformed(ActionEvent e) { 124 newFile(); 125 } 126 }; 127 //新建目錄的Action對象 128 private Action folerNew = new AbstractAction("新建目錄", new ImageIcon("images/newFile.gif")) { 129 public void actionPerformed(ActionEvent e) { 130 newFolder(); 131 } 132 }; 133 //新建項目的Action對象 134 private Action projectNew = new AbstractAction("新建項目", new ImageIcon("images/newFile.gif")) { 135 public void actionPerformed(ActionEvent e) { 136 newProject(); 137 } 138 }; 139 //打開文件的Action對象 140 private Action open = new AbstractAction("打 開", new ImageIcon("images/open.gif")) { 141 public void actionPerformed(ActionEvent e) { 142 selectFile(); 143 } 144 }; 145 //保存文件的Action對象 146 private Action save = new AbstractAction("保 存", new ImageIcon("images/save.gif")) { 147 public void actionPerformed(ActionEvent e) { 148 saveFile(getCurrentFile()); 149 } 150 }; 151 //刷新樹的Action對象 152 private Action refresh = new AbstractAction("刷 新", new ImageIcon("images/refresh.gif")) { 153 public void actionPerformed(ActionEvent e) { 154 reloadNode(getSelectNode()); 155 } 156 }; 157 //運行文件的Action對象 158 private Action run = new AbstractAction("運 行", new ImageIcon("images/run.gif")) { 159 public void actionPerformed(ActionEvent e) { 160 run(); 161 } 162 }; 163 //退出的Action對象 164 private Action exit = new AbstractAction("退 出") { 165 public void actionPerformed(ActionEvent e) { 166 System.exit(0);//直接退出 167 } 168 }; 169 //複製文本的Action對象 170 private Action copy = new AbstractAction("復 制", new ImageIcon("images/copy.gif")) { 171 public void actionPerformed(ActionEvent e) { 172 if (getCurrentFile() != null) { 173 getCurrentFile().getEditPane().copy(); 174 } 175 } 176 }; 177 //剪切文本的Action對象 178 private Action cut = new AbstractAction("剪 切", new ImageIcon("images/cut.gif")) { 179 public void actionPerformed(ActionEvent e) { 180 if (getCurrentFile() != null) { 181 getCurrentFile().getEditPane().cut(); 182 } 183 } 184 }; 185 //粘貼文本的Action對象 186 private Action paste = new AbstractAction("粘 貼", new ImageIcon("images/paste.gif")) { 187 public void actionPerformed(ActionEvent e) { 188 if (getCurrentFile() != null) { 189 getCurrentFile().getEditPane().paste(); 190 } 191 } 192 }; 193 194 public EditorFrame(String title, TreeCreator treeCreator) { 195 super(title); //設置標題 196 this.treeCreator = treeCreator; 197 this.iframeListener = new IFrameListener(this); 198 this.saveMediator = new SaveMediatorConcrete(); 199 this.runHandler = new JavaRunHandler(); 200 } 201 202 public void initFrame(WorkSpace space) { 203 this.workSpace = space; 204 //設置窗口關閉,退出程序 205 setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 206 //建立主編輯區的tabPane 207 tabPane = new JTabbedPane(JTabbedPane.TOP, JTabbedPane.SCROLL_TAB_LAYOUT ); 208 desk = new JDesktopPane();//建立JDesktopPane對象 209 desk.setBackground(Color.GRAY);//設置desk的背景顏色爲灰色 210 box = new Box(BoxLayout.Y_AXIS);//設置box的佈局 211 box.add(tabPane); 212 box.add(desk); 213 //建立信息顯示區的文本域 214 infoArea = new JTextArea("", 5, 50); 215 //將infoArea文本域做爲組件放到infoPane中 216 infoPane = new JScrollPane(infoArea); 217 //設置信息區不可編輯 218 infoArea.setEditable(false); 219 //建立這個分隔組件的容器,並將box對象和infoPane放置其中 220 editorSplitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT, box, infoPane); 221 editorSplitPane.setDividerSize(3); 222 editorSplitPane.setDividerLocation(500); 223 //建立樹 224 tree = treeCreator.createTree(this); 225 //建立可滾動的容器對象 226 treePane = new JScrollPane(tree); 227 //建立主界面的JSplitPane,橫向,左邊爲treePane,右邊爲editorSplitPane 228 mainSplitPane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT, treePane, 229 editorSplitPane); 230 //設置分隔條的位置 231 mainSplitPane.setDividerLocation(200); 232 //設置分隔條的粗細 233 mainSplitPane.setDividerSize(3); 234 add(mainSplitPane); 235 236 //建立菜單欄對象 237 menuBar = new JMenuBar(); 238 //建立編輯菜單對象 239 editMenu = new JMenu("編輯"); 240 //建立文件菜單 241 fileMenu = new JMenu("文件"); 242 //將文件菜單添加到菜單欄中 243 menuBar.add(fileMenu); 244 //將編輯菜單添加到菜單欄中 245 menuBar.add(editMenu); 246 //設置JFrame的菜單欄 247 setJMenuBar(menuBar); 248 249 toolBar = new JToolBar(); 250 toolBar.setFloatable(false);//設置工具欄不可移動 251 toolBar.setMargin(new Insets(0, 10, 5, 5));//設置工具欄的邊距 252 add(toolBar, BorderLayout.NORTH);//將工具欄添加到EditorFrame中 253 254 pack();//使JFrame調整最佳大小 255 addListeners(); 256 } 257 258 public TreeCreator getTreeCreator() { 259 return treeCreator; 260 } 261 262 //爲EditorFrame中的組件添加監聽器 263 public void addListeners() { 264 //新建文件的監聽器 265 fileMenu.add(fileNew).setAccelerator(KeyStroke.getKeyStroke('N', InputEvent.CTRL_MASK)); 266 //新建目錄的監聽器 267 fileMenu.add(folerNew).setAccelerator(KeyStroke.getKeyStroke('F', InputEvent.CTRL_MASK)); 268 //新建項目的監聽器 269 fileMenu.add(projectNew).setAccelerator(KeyStroke.getKeyStroke('P', InputEvent.CTRL_MASK)); 270 //打開菜單添加監聽器 271 fileMenu.add(open).setAccelerator(KeyStroke.getKeyStroke('O', InputEvent.CTRL_MASK)); 272 //爲保存菜單添加監聽器 273 fileMenu.add(save).setAccelerator(KeyStroke.getKeyStroke('S', InputEvent.CTRL_MASK)); 274 //爲刷新菜單添加監聽器 275 fileMenu.add(refresh).setAccelerator(KeyStroke.getKeyStroke("F5")); 276 //爲運行菜單添加監聽器 277 fileMenu.add(run).setAccelerator(KeyStroke.getKeyStroke('R', InputEvent.CTRL_MASK)); 278 fileMenu.add(exit); 279 //添加複製監聽器 280 editMenu.add(copy).setAccelerator(KeyStroke.getKeyStroke('C', InputEvent.CTRL_MASK)); 281 //添加剪切監聽器 282 editMenu.add(cut).setAccelerator(KeyStroke.getKeyStroke('X', InputEvent.CTRL_MASK)); 283 //添加粘貼監聽器 284 editMenu.add(paste).setAccelerator(KeyStroke.getKeyStroke('V', InputEvent.CTRL_MASK)); 285 286 //爲工具條添加各個操做 287 toolBar.add(fileNew).setToolTipText("新建文件"); 288 toolBar.add(open).setToolTipText("打開"); 289 toolBar.add(save).setToolTipText("保存"); 290 toolBar.add(refresh).setToolTipText("刷新"); 291 toolBar.add(run).setToolTipText("運行"); 292 toolBar.add(copy).setToolTipText("複製"); 293 toolBar.add(cut).setToolTipText("剪切"); 294 toolBar.add(paste).setToolTipText("粘貼"); 295 296 //爲tabPane添加監聽器 297 tabPane.addChangeListener(new TabListener(this)); 298 } 299 300 //獲取編輯器主界面項目樹中所選中的節點 301 public ProjectTreeNode getSelectNode() { 302 //得到當前樹選擇的節點在樹中的路徑 303 TreePath path = tree.getSelectionPath(); 304 //若是當前選擇了節點 305 if (path != null) { 306 //建立一個ProjectTreeNode對象並用於返回 307 ProjectTreeNode selectNode = (ProjectTreeNode)path.getLastPathComponent(); 308 return selectNode; 309 } 310 //當前沒有選擇節就返回null 311 return null; 312 } 313 314 //顯示iframe對象 315 public void showIFrame(JInternalFrame iframe) { 316 try { 317 iframe.setSelected(true); 318 iframe.toFront(); 319 } catch (Exception ex) { 320 } 321 } 322 323 //打開文件的方法 324 public void openFile(File file) { 325 if (currentFile != null) { 326 //若是參數file是當前正在編輯的文件 327 if (file.equals(currentFile.getFile())) return; 328 } 329 //在打開文件的集合中查找該文件, 再判斷該文件是否已經打開 330 EditFile openedFile = getOpenFile(file); 331 //若是文件已經打開了,調用打開方法(打開已經在編輯tab頁面中顯示的文件) 332 if (openedFile != null) { 333 openExistFile(openedFile, file); 334 return; 335 } 336 //打開新的文件 337 openNewFile(file); 338 } 339 340 //從本類中記錄已經打開的文件集合中獲得與參數file同樣的EditFile對象 341 private EditFile getOpenFile(File file) { 342 for (EditFile openFile : openFiles) { 343 if (openFile.getFile().equals(file)) return openFile; 344 } 345 return null; 346 } 347 348 //根據參數file獲取該file對應的tab頁中的索引 349 private int getFileIndex(File file) { 350 //若是從打開文件的集合中找不到與參數file對應的EditFile對象,返回-1 351 EditFile openFile = getEditFile(file); 352 if (openFile == null) return -1; 353 return getTabIndex(openFile.getIframe().getToolTipText()); 354 } 355 356 //在打開的文件中得到文件是file的EditFile對象 357 private EditFile getEditFile(File file) { 358 for (EditFile openFile : openFiles) { 359 if (openFile.getFile().equals(file)) return openFile; 360 } 361 return null; 362 } 363 364 //根據tab頁中的tips找到所對應的在tabPane的索引 365 public int getTabIndex(String tips) { 366 for (int i = 0; i < this.tabPane.getTabCount(); i++) { 367 if (this.tabPane.getToolTipTextAt(i).equals(tips)) return i; 368 } 369 return -1; 370 } 371 372 //打開已經存在的文件(已經在編輯文件集合中的文件),openFiles集合中的文件 373 public void openExistFile(EditFile openedFile, File willOpenFile) { 374 //將tab頁變成當前所選擇文件的索引 375 tabPane.setSelectedIndex(getFileIndex(willOpenFile)); 376 //顯示iframe 377 showIFrame(openedFile.getIframe()); 378 //設置當前打開文件 379 this.currentFile = openedFile; 380 //添加到當前打開的文件集合中 381 this.openFiles.add(openedFile); 382 } 383 384 //打開一個不在編輯集合中的文件 385 public void openNewFile(File file) { 386 //設置EditorFrame的標題爲該文件的全路徑 387 setTitle(file.getAbsolutePath()); 388 //建立一個JInternalFrame對象,title爲文件的絕對路徑 389 JInternalFrame iframe = new JInternalFrame(file.getAbsolutePath(), true, true, true, true); 390 391 //新建一個EditPane對象 392 EditPane editPane = new EditPane(file); 393 394 //爲EditPane添加鍵盤監聽器 395 editPane.getDocument().addDocumentListener(new EditDocumentListener(this)); 396 iframe.add(new JScrollPane(editPane)); 397 //爲JInternalFrame添加窗口監聽器 398 iframe.addInternalFrameListener(this.iframeListener); 399 desk.add(iframe); 400 iframe.show(); 401 iframe.reshape(0, 0, 400, 300); 402 tabPane.addTab(file.getName(), null, null, file.getAbsolutePath()); 403 tabPane.setSelectedIndex(tabPane.getTabCount() - 1); 404 //設置當前的文件對象 405 this.currentFile = new EditFile(file, true, iframe, editPane); 406 //將當前的文件加到打開的文件集合中 407 this.openFiles.add(this.currentFile); 408 } 409 410 public void selectFile() { 411 fileChooser = new FileChooser(this); 412 } 413 414 //新建文件的方法 415 public void newFile() { 416 //當沒有選擇一個節點而新建目錄的時候,須要提醒 417 if (getSelectNode() == null) { 418 JOptionPane.showMessageDialog(this, "請選擇目錄"); 419 return; 420 } 421 AddInfo info = new AddInfo("文件名稱:", this, new AddFileHandler()); 422 showAddFrame(info); 423 } 424 //顯示新增的界面 425 private void showAddFrame(AddInfo info) { 426 //使EditorFrame變爲不可用 427 setEnabled(false); 428 addFrame = new AddFrame(info); 429 addFrame.pack(); 430 addFrame.setVisible(true); 431 } 432 433 //刷新樹節點 434 public void reloadNode(ProjectTreeNode selectNode) { 435 if (selectNode == null) return; 436 //刷新樹的節點 437 ProjectTreeModel model = (ProjectTreeModel)getTree().getModel(); 438 //從新加載所選擇的節點 439 model.reload(selectNode, treeCreator); 440 } 441 442 public WorkSpace getWorkSpace() { 443 return workSpace; 444 } 445 446 public JTree getTree() { 447 return this.tree; 448 } 449 450 //新建目錄的方法 451 public void newFolder() { 452 //當沒有選擇一個節點而新建目錄的時候,須要提醒 453 if (getSelectNode() == null) { 454 JOptionPane.showMessageDialog(this, "請選擇目錄"); 455 return; 456 } 457 AddInfo info = new AddInfo("目錄名稱:", this, new AddFolderHandler()); 458 showAddFrame(info); 459 } 460 461 //新建項目的方法 462 public void newProject() { 463 AddInfo info = new AddInfo("項目名稱:", this, new AddProjectHandler()); 464 showAddFrame(info); 465 } 466 467 //從新在treePane中構造一次樹 468 public void refreshTree(JTree newTree) { 469 //將tree對象變爲參數中的newTree 470 this.tree = newTree; 471 //讓treePane(放樹的容器)設置newTree爲新的視圖 472 treePane.setViewportView(newTree); 473 //更新界面 474 treePane.updateUI(); 475 } 476 477 public EditFile getCurrentFile() { 478 return currentFile; 479 } 480 481 public void setCurrentFile(EditFile currentFile) { 482 this.currentFile = currentFile; 483 } 484 485 public List<EditFile> getOpenFiles() { 486 return openFiles; 487 } 488 489 public JDesktopPane getDesk() { 490 return desk; 491 } 492 493 public JTabbedPane getTabPane() { 494 return tabPane; 495 } 496 497 //根據JInternalFrame標題找到JInternalFrame對象 498 public JInternalFrame getIFrame(String title) { 499 JInternalFrame[] iframes = desk.getAllFrames(); 500 for (JInternalFrame iframe : iframes) { 501 if (iframe.getTitle().equals(title)) return iframe; 502 } 503 return null; 504 } 505 506 //根據JInternalFrame在打開的文件集合中獲取相應的文件對象 507 public EditFile getEditFile(JInternalFrame iframe) { 508 for (EditFile openFile : openFiles) { 509 if (openFile.getIframe().equals(iframe)) return openFile; 510 } 511 return null; 512 } 513 514 //詢問是否要保存, 參數爲將被打開的文件 515 public void askSave(EditFile file) { 516 //該份文件修改過沒有保存 517 if (!file.isSaved()) { 518 //彈出詢問 519 int val = JOptionPane.showConfirmDialog(this, "是否要保存?", "詢問", 520 JOptionPane.YES_NO_OPTION); 521 //點擊了須要保存 522 if (JOptionPane.YES_OPTION == val) { 523 //調用EditorFrame的保存方法對文件進行保存 524 saveFile(file); 525 } 526 } 527 } 528 529 //用於保存當前所打開的文件 530 public void saveFile(EditFile file) { 531 if (file == null) return; 532 //調用中介者對象的方法去保存文件 533 String result = saveMediator.doSave(this); 534 //將結果放到信息顯示區的文本域中 535 infoArea.setText(result); 536 //寫完文件後,設置當前文件的保存狀態爲true,表示已經保存 537 file.setSaved(true); 538 } 539 540 //關閉一個窗口 541 public void closeIFrame(JInternalFrame iframe) { 542 //得到當前的文件,即要關閉的文件對象 543 EditFile closeFile = getEditFile(iframe); 544 //設置本類中的currentFile屬性 545 afterClose(closeFile); 546 //得到該iframe在tab頁中對應的索引 547 int index = getTabIndex(iframe.getTitle()); 548 //從tab頁中刪除 549 getTabPane().remove(index); 550 //從打開的文件集合中刪除這個關閉的文件 551 openFiles.remove(closeFile); 552 } 553 554 //當關閉一份文件後,設置本對象的currentFile屬性 555 private void afterClose(EditFile closeFile) { 556 //獲取關閉文件在打開文件集合中的索引 557 int openFilesIndex = getEditFileIndex(closeFile); 558 //若是該文件已是全部打開的文件的最後一份 559 if (this.openFiles.size() == 1) { 560 this.currentFile = null; 561 } else {//若是還有其餘文件,判斷關閉的文件位置 562 if (openFilesIndex == 0) { 563 //若是關閉的文件是第一份,拿集合中的第二份 564 this.currentFile = openFiles.get(openFilesIndex + 1); 565 } else if (openFilesIndex == (openFiles.size() - 1)) { 566 //若是關閉的是最後一份,取倒數第二份 567 this.currentFile = openFiles.get(openFiles.size() - 2); 568 } else { 569 //不是第一份,也不是最後一份 570 this.currentFile = openFiles.get(openFilesIndex - 1); 571 } 572 } 573 } 574 575 //獲取editFile在打開的文件集合中的索引 576 private int getEditFileIndex(EditFile editFile) { 577 for (int i = 0; i < this.openFiles.size(); i++) { 578 if (openFiles.get(i).equals(editFile)) return i; 579 } 580 return -1; 581 } 582 583 //返回項目樹當前所選中的節點所屬的項目節點對應的目錄 584 public File getCurrentProject() { 585 //獲取根節點(工做空間) 586 ProjectTreeNode root = (ProjectTreeNode)getSelectNode().getRoot(); 587 //獲取根節點下的全部子節點(即項目節點集合) 588 List<ProjectTreeNode> projects = root.getChildren(); 589 ProjectTreeNode selectNode = getSelectNode(); 590 if (selectNode != null) { 591 for (ProjectTreeNode project : projects) { 592 //當前先中節點是該project下的子節點 593 if (selectNode.isNodeAncestor(project)) { 594 return project.getFile(); 595 } 596 } 597 } 598 return null; 599 } 600 601 //運行文件的方法 602 public void run() { 603 //運行前先保存 604 saveFile(getCurrentFile()); 605 //將結果顯示 606 String result = runHandler.run(this); 607 infoArea.setText(result); 608 } 609 610 } 611 class FileChooser extends JFileChooser { 612 613 private EditorFrame editorFrame; 614 615 616 public FileChooser(EditorFrame editorFrame){ 617 //調用父類的構造器 618 //利用editorFrame的工做空間做爲文件選擇器打開時的默認目錄 619 super(editorFrame.getWorkSpace().getFolder()); 620 this.editorFrame = editorFrame; 621 showOpenDialog(editorFrame); 622 } 623 624 public void approveSelection() { 625 File file = getSelectedFile(); 626 //設置樹當前選擇的節點爲null, 即樹沒有被選中 627 this.editorFrame.getTree().setSelectionPath(null); 628 this.editorFrame.openFile(file); 629 super.approveSelection(); 630 } 631 }
1 package org.crazyit.editor; 2 3 import java.awt.Color; 4 import java.awt.Graphics; 5 import java.awt.Insets; 6 import java.awt.event.KeyAdapter; 7 import java.awt.event.KeyEvent; 8 import java.io.File; 9 import java.io.FileNotFoundException; 10 import java.util.ArrayList; 11 import java.util.HashMap; 12 import java.util.Map; 13 import java.util.Scanner; 14 15 import javax.swing.JTextPane; 16 import javax.swing.text.Element; 17 import javax.swing.text.SimpleAttributeSet; 18 import javax.swing.text.StyleConstants; 19 import javax.swing.text.StyledDocument; 20 21 import org.crazyit.editor.util.FileUtil; 22 23 /** 24 * 編輯界面 25 * 26 * @author yangenxiong yangenxiong2009@gmail.com 27 * @version 1.0 28 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 29 * <br>Copyright (C), 2009-2010, yangenxiong 30 * <br>This program is protected by copyright laws. 31 */ 32 public class EditPane extends JTextPane { 33 34 //樣式文檔對象 35 protected StyledDocument doc; 36 //構造一個文本格式器 37 protected SyntaxFormatter formatter = new SyntaxFormatter("java.stx"); 38 private SimpleAttributeSet quotAttr = new SimpleAttributeSet(); 39 //保存文檔改變的開始位置 40 private int docChangeStart = 0; 41 //保存文檔改變的長度 42 private int docChangeLength = 0; 43 //定義文檔中行數文本的外觀屬性 44 private SimpleAttributeSet lineAttr = new SimpleAttributeSet(); 45 46 public EditPane(File file) { 47 this.setText(FileUtil.readFile(file)); 48 this.doc = getStyledDocument(); 49 //設置該文檔的頁邊距 50 this.setMargin(new Insets(3, 40, 0, 0)); 51 syntaxParse(); 52 //添加按鍵監聽器,當按鍵鬆開時進行語法分析 53 this.addKeyListener(new KeyAdapter() { 54 public void keyReleased(KeyEvent ke) 55 { 56 syntaxParse(); 57 } 58 }); 59 } 60 // 61 // //重寫父類方法,使JTextPane不會自動換行 62 // public boolean getScrollableTracksViewportWidth() { 63 // return (getSize().width < getParent().getSize().width - 100); 64 // } 65 // 66 // //重寫父類方法,使JTextPane不會自動換行 67 // public void setSize(Dimension d) { 68 // if (d.width < getParent().getSize().width) { 69 // d.width = getParent().getSize().width; 70 // } 71 // d.width += 100; 72 // super.setSize(d); 73 // } 74 75 public void syntaxParse() { 76 try { 77 //獲取文檔的根元素,即文檔內的所有內容 78 Element root = doc.getDefaultRootElement(); 79 //獲取文檔中光標插入符的位置 80 int cursorPos = this.getCaretPosition(); 81 int line = root.getElementIndex(cursorPos); 82 //獲取光標所在位置的行 83 Element para = root.getElement(line); 84 //定義光標所在行的行頭在文檔中位置 85 int start = para.getStartOffset(); 86 //若是文檔修改位置比當前行還前 87 if (start > docChangeStart) { 88 start = docChangeStart; 89 } 90 //定義被修改部分的長度 91 int length = para.getEndOffset() - start; 92 if (length < docChangeLength) { 93 length = docChangeLength + 1; 94 } 95 //取出全部被修改的字符串 96 String s = doc.getText(start, length); 97 //以空格、點號等做爲分隔符 98 String[] tokens = s.split("\\s+|\\.|\\(|\\)|\\{|\\}|\\[|\\]"); 99 //定義當前分析單詞的在s字符串中的開始位置 100 int curStart = 0; 101 boolean isQuot = false; 102 for (String token : tokens) { 103 //找出當前分析單詞在s字符串的中位置 104 int tokenPos = s.indexOf(token , curStart); 105 if (isQuot && (token.endsWith("\"") || token.endsWith("\'"))) { 106 doc.setCharacterAttributes(start + tokenPos, token.length(), quotAttr, false); 107 isQuot = false; 108 } 109 else if (isQuot && !(token.endsWith("\"") || token.endsWith("\'"))) { 110 doc.setCharacterAttributes(start + tokenPos, token.length(), quotAttr, false); 111 } 112 else if ((token.startsWith("\"") || token.startsWith("\'")) 113 && (token.endsWith("\"") || token.endsWith("\'"))) { 114 doc.setCharacterAttributes(start + tokenPos, token.length(), quotAttr, false); 115 } 116 else if ((token.startsWith("\"") || token.startsWith("\'")) 117 && !(token.endsWith("\"") || token.endsWith("\'"))) { 118 doc.setCharacterAttributes(start + tokenPos, token.length(), quotAttr, false); 119 isQuot = true; 120 } 121 else { 122 //使用格式器對當前單詞設置顏色 123 formatter.setHighLight(doc , token , start + tokenPos, token.length()); 124 } 125 //開始分析下一個單詞 126 curStart = tokenPos + token.length(); 127 } 128 } 129 catch (Exception ex) { 130 ex.printStackTrace(); 131 } 132 } 133 //重畫該組件,設置行號 134 public void paint(Graphics g){ 135 super.paint(g); 136 Element root = doc.getDefaultRootElement(); 137 //得到行號 138 int line = root.getElementIndex(doc.getLength()); 139 //設置顏色 140 g.setColor(new Color(230, 230, 230)); 141 //繪製行數矩形框 142 g.fillRect(0, 0, this.getMargin().left - 10, getSize().height); 143 //設置行號的顏色 144 g.setColor(new Color(40, 40, 40)); 145 //每行繪製一個行號 146 for (int count = 0, j = 1; count <= line; count++, j++) { 147 g.drawString(String.valueOf(j), 3, 148 (int)((count + 1) * 1.5020 * StyleConstants.getFontSize(lineAttr))); 149 } 150 } 151 } 152 class SyntaxFormatter { 153 //以一個Map保存關鍵字和顏色的對應關係 154 private Map<SimpleAttributeSet , ArrayList> attMap 155 = new HashMap<SimpleAttributeSet , ArrayList>(); 156 //定義文檔的正常文本的外觀屬性 157 SimpleAttributeSet normalAttr = new SimpleAttributeSet(); 158 public SyntaxFormatter(String syntaxFile) { 159 //設置正常文本的顏色、大小 160 StyleConstants.setForeground(normalAttr, Color.BLACK); 161 //StyleConstants.setFontSize(normalAttr, 14); 162 //建立一個Scanner對象,負責根據語法文件加載顏色信息 163 Scanner scaner = null; 164 try { 165 scaner = new Scanner(new File(syntaxFile)); 166 } 167 catch (FileNotFoundException e) { 168 throw new RuntimeException("丟失語法文件:" + e.getMessage()); 169 } 170 int color = -1; 171 ArrayList<String> keywords = new ArrayList<String>(); 172 //不斷讀取語法文件的內容行 173 while(scaner.hasNextLine()) { 174 String line = scaner.nextLine(); 175 //若是當前行以#開頭 176 if (line.startsWith("#")) { 177 if (keywords.size() > 0 && color > -1) { 178 //取出當前行的顏色值,並封裝成SimpleAttributeSet對象 179 SimpleAttributeSet att = new SimpleAttributeSet(); 180 StyleConstants.setForeground(att, new Color(color)); 181 //StyleConstants.setFontSize(att, 14); 182 //將當前顏色和關鍵字List對應起來 183 attMap.put(att , keywords); 184 } 185 //從新建立新的關鍵字List,爲下一個語法格式準備 186 keywords = new ArrayList<String>(); 187 color = Integer.parseInt(line.substring(1) , 16); 188 } else { 189 //對於普通行,每行內容添加到關鍵字List裏 190 if (line.trim().length() > 0) { 191 keywords.add(line.trim()); 192 } 193 } 194 } 195 //把最後的關鍵字和顏色對應起來 196 if (keywords.size() > 0 && color > -1) { 197 SimpleAttributeSet att = new SimpleAttributeSet(); 198 StyleConstants.setForeground(att, new Color(color)); 199 attMap.put(att , keywords); 200 } 201 } 202 //返回該格式器里正常文本的外觀屬性 203 public SimpleAttributeSet getNormalAttributeSet() { 204 return normalAttr; 205 } 206 //設置語法高亮 207 public void setHighLight(StyledDocument doc , String token , 208 int start , int length) { 209 //保存須要對當前單詞對應的外觀屬性 210 SimpleAttributeSet currentAttributeSet = null; 211 outer : 212 for (SimpleAttributeSet att : attMap.keySet()) 213 { 214 //取出當前顏色對應的全部關鍵字 215 ArrayList keywords = attMap.get(att); 216 //遍歷全部關鍵字 217 for (Object keyword : keywords) 218 { 219 //若是該關鍵字與當前單詞相同 220 if (keyword.toString().equals(token)) 221 { 222 //跳出循環,並設置當前單詞對應的外觀屬性 223 currentAttributeSet = att; 224 break outer; 225 } 226 } 227 } 228 //若是當前單詞對應的外觀屬性不爲空 229 if (currentAttributeSet != null){ 230 //設置當前單詞的顏色 231 doc.setCharacterAttributes(start, length, currentAttributeSet, false); 232 } else {//不然使用普通外觀來設置該單詞 233 doc.setCharacterAttributes(start, length, normalAttr, false); 234 } 235 } 236 }
1 package org.crazyit.editor; 2 3 import javax.swing.JInternalFrame; 4 import javax.swing.event.InternalFrameAdapter; 5 import javax.swing.event.InternalFrameEvent; 6 7 import org.crazyit.editor.commons.EditFile; 8 9 /** 10 * 窗口監聽器 11 * 12 * @author yangenxiong yangenxiong2009@gmail.com 13 * @version 1.0 14 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 15 * <br>Copyright (C), 2009-2010, yangenxiong 16 * <br>This program is protected by copyright laws. 17 */ 18 public class IFrameListener extends InternalFrameAdapter { 19 20 private EditorFrame editorFrame; 21 22 public IFrameListener(EditorFrame editorFrame) { 23 this.editorFrame = editorFrame; 24 } 25 26 public void internalFrameActivated(InternalFrameEvent e) { 27 JInternalFrame iframe = editorFrame.getDesk().getSelectedFrame(); 28 int tapIndex = editorFrame.getTabIndex(iframe.getTitle()); 29 editorFrame.getTabPane().setSelectedIndex(tapIndex); 30 } 31 32 public void internalFrameClosing(InternalFrameEvent e) { 33 //獲取當前關閉操做所對應的JInternalFrame 34 JInternalFrame iframe = (JInternalFrame)e.getSource(); 35 //獲取當前操做的文件 36 EditFile editFile = editorFrame.getCurrentFile(); 37 //詢問是否要保存 38 editorFrame.askSave(editFile); 39 //關閉當前的iframe 40 editorFrame.closeIFrame(iframe); 41 } 42 }
1 package org.crazyit.editor; 2 3 import java.awt.Label; 4 import java.awt.event.ActionEvent; 5 import java.awt.event.ActionListener; 6 import java.io.File; 7 8 import javax.swing.BoxLayout; 9 import javax.swing.JButton; 10 import javax.swing.JFileChooser; 11 import javax.swing.JFrame; 12 import javax.swing.JLabel; 13 import javax.swing.JPanel; 14 import javax.swing.JTextField; 15 16 import org.crazyit.editor.commons.WorkSpace; 17 18 /** 19 * 工做空間界面 20 * 21 * @author yangenxiong yangenxiong2009@gmail.com 22 * @version 1.0 23 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 24 * <br>Copyright (C), 2009-2010, yangenxiong 25 * <br>This program is protected by copyright laws. 26 */ 27 public class SpaceFrame extends JFrame { 28 29 private JPanel mainPanel; 30 31 private JLabel infoLabel; 32 33 private JPanel chosePanel; 34 35 private JLabel workTextLabel; 36 37 //工做空間中顯示用戶選擇文件目錄的JTextField 38 private JTextField pathText; 39 40 private JButton choseButton; 41 42 43 private JPanel buttonPanel; 44 45 //工做空間中的肯定按鈕 46 private JButton confirmButton; 47 48 private JButton cancelButton; 49 50 private SpaceChooser chooser; 51 52 //用戶選擇的文件目錄對象 53 private File folder; 54 55 public SpaceFrame(EditorFrame editorFrame) { 56 mainPanel = new JPanel(); 57 infoLabel = new JLabel("請選擇工做空間"); 58 chosePanel = new JPanel(); 59 workTextLabel = new JLabel("工做空間: "); 60 pathText = new JTextField("", 40); 61 choseButton = new JButton("選擇"); 62 buttonPanel = new JPanel(); 63 confirmButton = new JButton("肯定"); 64 cancelButton = new JButton("取消"); 65 chooser = new SpaceChooser(this); 66 67 //設置主Panel的佈局 68 mainPanel.setLayout(new BoxLayout(mainPanel, BoxLayout.Y_AXIS)); 69 mainPanel.add(infoLabel); 70 //設置選擇區的佈局 71 chosePanel.setLayout(new BoxLayout(chosePanel, BoxLayout.X_AXIS)); 72 choseButton.addActionListener(new ChoseButtonListener(chooser)); 73 pathText.setEditable(false); 74 chosePanel.add(workTextLabel); 75 chosePanel.add(pathText); 76 chosePanel.add(choseButton); 77 mainPanel.add(chosePanel); 78 79 confirmButton.setEnabled(false); 80 //爲肯定按鈕添加肯定的事件, 即建立一個WorkSpace對象 81 confirmButton.addActionListener(new ConfirmButtonListener(this, editorFrame)); 82 buttonPanel.add(confirmButton); 83 buttonPanel.add(new Label(" ")); 84 buttonPanel.add(cancelButton); 85 //爲取消按鈕添加退出事件 86 cancelButton.addActionListener(new ActionListener() { 87 public void actionPerformed(ActionEvent arg0) { 88 System.exit(0); 89 } 90 }); 91 mainPanel.add(buttonPanel); 92 add(mainPanel); 93 pack(); 94 setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 95 setLocation(300, 200); 96 setResizable(false); 97 } 98 99 public File getFolder() { 100 return folder; 101 } 102 103 public void setFolder(File folder) { 104 this.folder = folder; 105 } 106 107 public JTextField getPathText() { 108 return pathText; 109 } 110 111 public JButton getConfirmButton() { 112 return confirmButton; 113 } 114 } 115 116 /** 117 * 肯定按鈕的監聽器 118 * @author hp 119 * 120 */ 121 class ConfirmButtonListener implements ActionListener { 122 123 private SpaceFrame spaceFrame; 124 125 private EditorFrame editorFrame; 126 127 public ConfirmButtonListener(SpaceFrame spaceFrame, EditorFrame editorFrame) { 128 this.spaceFrame = spaceFrame; 129 this.editorFrame = editorFrame; 130 } 131 132 public void actionPerformed(ActionEvent arg0) { 133 //調EditorFrame的initFrame方法初始化界面 134 editorFrame.initFrame(new WorkSpace(spaceFrame.getFolder(), editorFrame)); 135 //將EditorFrame設爲可見 136 editorFrame.setVisible(true); 137 editorFrame.setSize(900, 600); 138 //讓工做選擇空間界面不可見 139 spaceFrame.setVisible(false); 140 } 141 } 142 143 /** 144 * 選擇按鈕的監聽器 145 * @author hp 146 * 147 */ 148 class ChoseButtonListener implements ActionListener { 149 150 private JFileChooser chooser; 151 152 public ChoseButtonListener(JFileChooser chooser) { 153 this.chooser = chooser; 154 } 155 156 @Override 157 public void actionPerformed(ActionEvent arg0) { 158 chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY); 159 chooser.showOpenDialog(null); 160 } 161 162 } 163 164 /** 165 * 文件選擇器 166 * @author hp 167 * 168 */ 169 class SpaceChooser extends JFileChooser { 170 171 private SpaceFrame spaceFrame; 172 173 //須要將SpaceFrame做爲構造參數 174 public SpaceChooser(SpaceFrame spaceFrame) { 175 //設置選擇器打開時的目錄 176 super("/"); 177 this.spaceFrame = spaceFrame; 178 } 179 180 //重寫父類的選擇文件方法 181 public void approveSelection() { 182 //獲取用戶選擇的文件 183 File folder = getSelectedFile(); 184 //設置SpaceFrame的屬性folder的值 185 spaceFrame.setFolder(folder); 186 //設置SpaceFrame文本框 187 spaceFrame.getPathText().setText(folder.getAbsolutePath()); 188 //設置肯定按鈕可用 189 spaceFrame.getConfirmButton().setEnabled(true); 190 //調用父類的選擇文件方法 191 super.approveSelection(); 192 } 193 }
1 package org.crazyit.editor; 2 3 import javax.swing.JInternalFrame; 4 import javax.swing.JTabbedPane; 5 import javax.swing.event.ChangeEvent; 6 import javax.swing.event.ChangeListener; 7 8 import org.crazyit.editor.commons.EditFile; 9 10 /** 11 * tab頁轉換監聽器 12 * 13 * @author yangenxiong yangenxiong2009@gmail.com 14 * @version 1.0 15 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 16 * <br>Copyright (C), 2009-2010, yangenxiong 17 * <br>This program is protected by copyright laws. 18 */ 19 public class TabListener implements ChangeListener { 20 21 private EditorFrame editorFrame; 22 23 public TabListener(EditorFrame editorFrame) { 24 this.editorFrame = editorFrame; 25 } 26 27 public void stateChanged(ChangeEvent e) { 28 //得到當前點擊tab頁對象 29 JTabbedPane tab = (JTabbedPane)e.getSource(); 30 //得到tab頁的索引 31 int index = tab.getSelectedIndex(); 32 if (index == -1) return; 33 //根據tab頁的tips(文件的絕對路徑)得到當前的JInternalFrame對象 34 JInternalFrame currentFrame = editorFrame.getIFrame(tab.getToolTipTextAt(index)); 35 //讓當前點擊的JInternalFrame對象可見 36 editorFrame.showIFrame(currentFrame); 37 //根據當前的JInternalFrame對象得到對應的文件 38 EditFile currentFile = editorFrame.getEditFile(currentFrame); 39 //設置EditorFrame當前編輯的文件爲tab對應的文件 40 editorFrame.setCurrentFile(currentFile); 41 } 42 43 }
1 package org.crazyit.editor; 2 3 import org.crazyit.editor.tree.TreeCreator; 4 import org.crazyit.editor.tree.TreeCreatorImpl; 5 6 /** 7 * 程序入口類 8 * 9 * @author yangenxiong yangenxiong2009@gmail.com 10 * @version 1.0 11 * <br/>網站: <a href="http://www.crazyit.org">瘋狂Java聯盟</a> 12 * <br>Copyright (C), 2009-2010, yangenxiong 13 * <br>This program is protected by copyright laws. 14 */ 15 public class Main { 16 17 public static void main(String[] args) { 18 TreeCreator treeCreator = new TreeCreatorImpl(); 19 //建立EditorFrame,暫時不用設置可見 20 EditorFrame editorFrame = new EditorFrame("ide", treeCreator); 21 //將editorFrame對象做爲SpaceFrame的構造參數 22 SpaceFrame spaceFrame = new SpaceFrame(editorFrame); 23 //讓SpaceFrame可見 24 spaceFrame.setVisible(true); 25 } 26 }