在 C# 中创建 Java 集成开发环境 (IDE)






4.95/5 (8投票s)
在本文中,
引言
我在 Visual Studio 中创建了名为 Silver-J 的项目,并使用了 ICSharpCode.TextEditor.dll 作为文本编辑器。您可以根据需要使用任何其他文本编辑器。本文档将重点介绍如何创建项目文件、读取项目文件以及启动用于编译 Java 源文件的进程。我已在同一项目中定义了所有函数,而没有创建其他库(dll)。其中可能包含一些额外、不必要、占用内存的代码。
要理解此源代码,请阅读 在 C# 中创建高级记事本 文章。
您可以使用以下文章来创建或自定义您的 IDE。
我使用 C# 编程语言创建了这个 IDE,但也可以使用 Java 来创建 IDE。使用 Java 的好处是可以访问其所有功能,它还支持许多语法高亮库。C# 和 Java 在语法上是相同的。
以下文章可能有助于您了解如何在 Java 中创建标签式记事本编辑器:在 Java 中创建高级标签式记事本。
要求
- Visual Studio 2013 Professional
- .NET Framework 4.5
- ICSharpCode.TextEditor.dll 库
- 我在此项目中使用此库是因为它是免费的,但您可以使用任何其他库进行语法高亮,我也使用了一些此库的功能。
您可以从以下网站下载它
https://nuget.net.cn/packages/ICSharpCode.TextEditor/
要使用此库,请参阅以下文章
- 我在此项目中使用此库是因为它是免费的,但您可以使用任何其他库进行语法高亮,我也使用了一些此库的功能。
文件
对于此应用程序,我们需要许多文件来存储数据。
以下文件存储在应用程序位置的 files 文件夹中。
- appletcode.slvjappletfile
- config.slvjfile
- defaultprojloc.slvjfile
- files.slvjfile
- jkeywords.slvjfile
- jpackages.slvjfile
- mainhtmlsource.slvjmainhtmlfile
- themesfile.slvjthemefile
- <project_name>.slvjproj
下载源代码。
- appletcode.slvjappletfile:此文件包含带有
<applet></applet>
标签的 HTML 源代码。 - config.slvjfile:此文件包含有关我们应用程序所有信息的数据,例如 JDK 路径和浏览器路径。是否显示 ToolStrip、StatusStrip 或 SplitContainer 的值。例如
<?xml version="1.0" encoding="utf-8"?> <!-- Silver-J Free light weight IDE for Java Copyright(c) 2016. All rights reserved --> <SilverJConfiguration> <!--JDK Path--> <JDKPath>C:\Program Files\Java\jdk1.8.0_25\bin</JDKPath> <!-- web browser --> <WebBrowser>C:\Program Files (x86)\Google\Chrome\Application\chrome.exe</WebBrowser> <!--text editor font & font size--> <Font>Microsoft YaHei UI</Font> <FontSize>10</FontSize> <!--views--> <!--Appearance--> <Appearance>Default</Appearance> <!--text editor views--> <ShowLineNumbers>true</ShowLineNumbers> <ShowLineHighlighter>true</ShowLineHighlighter> <ShowInvalidLines>false</ShowInvalidLines> <ShowEndOfLineMarker>false</ShowEndOfLineMarker> <ShowVisibleSpaces>false</ShowVisibleSpaces> <BracesMatching>true</BracesMatching> <AutoCompleteBraces>true</AutoCompleteBraces> <!--split containers--> <SplitContainer1>1132</SplitContainer1> <SplitContainer2>559</SplitContainer2> <SplitContainer3>280</SplitContainer3> <SplitContainer4>315</SplitContainer4> <!--tabs,documents etc views--> <TabsAlignment>Top</TabsAlignment> <ShowStatusStrip>true</ShowStatusStrip> <ShowToolStrip>true</ShowToolStrip> <ShowProjectExplorer>true</ShowProjectExplorer> <ShowClassesView>true</ShowClassesView> <ShowMethodsView>true</ShowMethodsView> <ShowErrorList>true</ShowErrorList> <ShowErrorDialog>false</ShowErrorDialog> <ShowStartPageOnStartUp>true</ShowStartPageOnStartUp> <!--Auto Compile Java--> <AutoCompileJava>false</AutoCompileJava> <!--Auto Completion Mode--> <AutoCompletion>true</AutoCompletion> </SilverJConfiguration>
- defaultprojloc.slvjfile:此文件包含当前创建或打开的项目名称、项目文件夹路径、项目文件夹文件(.slvjproj)和项目类型。
<?xml version="1.0" encoding="utf-8"?> <SilverJ> <DefaultProjectLocation>C:\My Java Projects</DefaultProjectLocation> <CurrentProjectName>LookAndFeelDemo</CurrentProjectName> <CurrentProjectFileName>C:\My Java Projects\LookAndFeelDemo\LookAndFeelDemo.slvjproj</CurrentProjectFileName> <CurrentProjectType>ApplicationType</CurrentProjectType> </SilverJ>
- files.slvjfile:此文件包含从打开的项目文件名中的
<VisualFile></VisualFile>
标签读取的文件名。 - jkeywords.slvjfile:此文件包含用于代码补全的 Java 关键字(请参阅 MyTabPage.cs 文件)
- jpackages.slvjfile:此文件包含用于在 Edit->Insert->Packages 选项中插入的 Java 包
- mainhtmlsource.slvjmainhtmlfile:当添加或创建 New->HTML 文件时,包含 HTML 源代码。
- themesfile.slvjthemefile:此文件包含使用 Java 主题创建 Java 类时的 Java 代码。
- <project_name>.slvjproj:此文件存储在用户的项目文件夹中。此文件包含 ProjectName、ProjectLocationFolder、ProjectType、MainClassFile、JavaClassFile、VisualFile、OtherFile。例如 LookAndFeelDemo.slvjproj
<?xml version="1.0" encoding="utf-8"?> <SilverJProject> <!--Silver-J (1.0) Java Application Project--> <ProjectName>LookAndFeelDemo</ProjectName> <ProjectLocationFolder>C:\My Java Projects\LookAndFeelDemo</ProjectLocationFolder> <ProjectLocationFile>C:\My Java Projects\LookAndFeelDemo\LookAndFeelDemo.slvjproj</ProjectLocationFile> <ProjectType>ApplicationType</ProjectType> <MainClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\LookAndFeelDemo.java</MainClassFile> <JavaClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\JavaBlueTheme.java</JavaClassFile> <JavaClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\JavaGreenTheme.java</JavaClassFile> <JavaClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\JavaRedTheme.java</JavaClassFile> <JavaClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\LookAndFeelDemo.java</JavaClassFile> <JavaClassFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\TestFrame.java</JavaClassFile> <VisualFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\LookAndFeelDemo.java</VisualFile> <VisualFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\JavaGreenTheme.java</VisualFile> <VisualFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\JavaRedTheme.java</VisualFile> <VisualFile>C:\My Java Projects\LookAndFeelDemo\srcclasses\TestFrame.java</VisualFile> </SilverJProject>
VisualFile 是 JavaClassFile,仅用于在项目打开时将其显示在选项卡中或不显示。
Using the Code
创建 Java 项目
向项目中添加新的 Windows Form。此处我使用了 **New_JavaApplicationProject_Form**(New_JavaApplicationProject_Form.cs 文件)并使用 **Project Name 文本框**、**Project Location 文本框**、带 **Browse** 的 **Create Java Class 复选框**、**Finish** 和 **Cancel** 按钮进行设计。
在此文件 New_JavaApplicationProject_Form.cs 中,我们将只读取文件 \\files\\defaultprojloc.slvjfile。
我们还将从上述表单获取项目名称、项目位置等输入。
我使用了以下变量来存储它,
String projloc = ProjectLocationTextBox.Text;
String projfolder = projectfolderlabel.Text;
String projectname = ProjectNameTextBox.Text;
String projectfile;
现在我们需要在读取的项目位置文件夹(projfolder)中创建一个与项目名称相同的文件夹(目录)。一旦创建了目录,我们将在其中创建名为 classes、src、srcclasses 的目录。
项目目录创建完成后,我们需要创建一个文件扩展名为 .slvjproj 的项目文件(文件名与创建的项目名称相同)。在该文件中,我们将以 XML 格式保存我们的项目数据,如上面“文件”部分所定义。
以下是执行操作的函数。
public void CreateJavaProject()
{
String projloc = ProjectLocationTextBox.Text;
String projfolder = projectfolderlabel.Text;
String projectname = ProjectNameTextBox.Text;
String projectfile;
if (projloc != "" && projectname != "")
{
projectfile = projectname + ".slvjproj";
if (checkBox1.Checked == false)
{
if (Directory.Exists(projloc + "\\" + projfolder))
{
MessageBox.Show("Entered project name folder is already exists in current location","Error............");
}
else
{
//create project directory & project file
Directory.CreateDirectory(projloc + "\\" + projfolder);
//create classes directory
Directory.CreateDirectory(projloc + "\\" + projfolder + "\\classes");
//creating & writing slvjproj file
using (XmlWriter xmlwriter = XmlWriter.Create(projloc + "\\" + projfolder + "\\" + projectfile))
{
xmlwriter.WriteStartDocument();
xmlwriter.WriteStartElement("SilverJProject");
xmlwriter.WriteString("\n");
xmlwriter.WriteComment("Silver-J (1.0) Java Application Project");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectName", projectname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFolder", projloc + "\\" + projfolder);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFile", projloc + "\\" + projfolder + "\\" + projectfile);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectType", "ApplicationType");
xmlwriter.WriteEndElement();
xmlwriter.WriteEndDocument();
xmlwriter.Close();
}
String defaultprojfilepath = Application.StartupPath + "\\files\\defaultprojloc.slvjfile";
projectfilename = projloc + "\\" + projfolder + "\\" + projectfile;
XmlDocument doc = new XmlDocument();
doc.Load(defaultprojfilepath);
doc.SelectSingleNode("SilverJ/DefaultProjectLocation").InnerText = ProjectLocationTextBox.Text;
doc.SelectSingleNode("SilverJ/CurrentProjectName").InnerText = ProjectNameTextBox.Text;
doc.SelectSingleNode("SilverJ/CurrentProjectFileName").InnerText = projectfilename;
doc.SelectSingleNode("SilverJ/CurrentProjectType").InnerText = "ApplicationType";
doc.Save(defaultprojfilepath);
a = 1;
this.Close();
isfinished = true;
}
}
else if (checkBox1.Checked == true)
{
if (JavaClassTextBox.Text != "")
{
String classname = JavaClassTextBox.Text;
if (classname.Contains(".java"))
{
}
else
{
classname = classname + ".java";
}
String javafilename = classname;
if (Directory.Exists(projloc + "\\" + projfolder))
{
MessageBox.Show("Entered project name folder is already exists in current location", "Error............");
}
else
{
//create project directory & project file
Directory.CreateDirectory(projloc + "\\" + projfolder);
//create srcclasses directory
Directory.CreateDirectory(projloc + "\\" + projfolder + "\\srcclasses");
//create classes directory
Directory.CreateDirectory(projloc + "\\" + projfolder + "\\classes");
String fname = projloc + "\\" + projfolder + "\\srcclasses\\" + javafilename;
createdfilename = fname;
String filename = fname.Substring(fname.LastIndexOf("\\") + 1);
//creating & writing slvjproj file
using (XmlWriter xmlwriter = XmlWriter.Create(projloc + "\\" + projfolder + "\\" + projectfile))
{
xmlwriter.WriteStartDocument();
xmlwriter.WriteStartElement("SilverJProject");
xmlwriter.WriteString("\n");
xmlwriter.WriteComment("Silver-J (1.0) Java Application Project");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectName", projectname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFolder", projloc + "\\" + projfolder);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFile", projloc + "\\" + projfolder + "\\" + projectfile);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectType", "ApplicationType");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("MainClassFile", fname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("JavaClassFile", fname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("VisualFile", fname);
xmlwriter.WriteEndElement();
xmlwriter.WriteEndDocument();
xmlwriter.Close();
}
isSaved = true;
String defaultprojfilepath = Application.StartupPath + "\\files\\defaultprojloc.slvjfile";
projectfilename = projloc + "\\" + projfolder + "\\" + projectfile;
XmlDocument doc = new XmlDocument();
doc.Load(defaultprojfilepath);
doc.SelectSingleNode("SilverJ/DefaultProjectLocation").InnerText = ProjectLocationTextBox.Text;
doc.SelectSingleNode("SilverJ/CurrentProjectName").InnerText = ProjectNameTextBox.Text;
doc.SelectSingleNode("SilverJ/CurrentProjectFileName").InnerText = projectfilename;
doc.SelectSingleNode("SilverJ/CurrentProjectType").InnerText = "ApplicationType";
doc.Save(defaultprojfilepath);
a = 2;
this.Close();
isfinished = true;
}
}
}
}
}
首先检查项目位置和项目名称是否不是空字符串。然后检查 **Create Java Class** 复选框是否被选中。如果未选中,则仅在没有 .java 源文件的情况下创建项目。
首先创建我们的 Java 项目文件(projectfile = projectname + ".slvjproj"
;)。然后我们创建该文件并开始使用 XmlWriter
类写入该文件。
我们将写入 Project Name、Project Location Folder、Project type 标签及其读取的值。完成后,我们需要更改文件 defaultprojloc.slvjfile 的内容
在此文件中,我们将保存当前创建/打开的项目名称、位置文件夹、项目位置文件、项目类型。
如果 **Create Java Class** 复选框被选中,我们将执行上述所有操作,只是将以下标签和信息添加到其中,其中 fname
是输入的 Java 类文件名
xmlwriter.WriteElementString("MainClassFile", fname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("JavaClassFile", fname);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("VisualFile", fname);
我正在跟踪已创建的项目,这意味着如果项目在未创建 Java 类的情况下创建(即“Create Java Class”复选框未选中),则 CheckProjectType()
函数返回 1,否则返回 2(变量 a 用于此)。这用于在 MainForm.cs 文件中创建文件、向 tabcontrol 添加标签、将 projectname 和 filename 添加到 treeview 等。
假设您已经设计了您的主 IDE。
现在是 File->New->New Java Application Project 的点击事件
首先显示新的 Java 应用程序对话框。
下载源代码。
ReadCurrentProjectFileName()
函数通过读取文件 \files\defaultprojloc.slvjfile 并读取 CurrentProjectFileName 标签来返回项目文件名字符串。
如果 CheckProjectType()
为 2,我们将创建一个文件,通过读取当前项目的 JavaClassFile
标签文本,向 tabcontrol 添加具有文本编辑器控件的选项卡,更改 MainForm 的文本,将 projectname 和文件名添加到 ProjectExplorerTreeView,然后我们将保存该文件。
private void File_New_JavaApplicationProjectMenuItem_Click(object sender, EventArgs e)
{
New_JavaApplicationProject_Form njap = new New_JavaApplicationProject_Form(this, ProjectExplorerTreeView, myTabControl);
njap.ShowDialog();
String projectname = "";
String javaclassfilename = "";
//create project with class
if (njap.CheckProjectType() == 2)
{
if (ReadCurrentProjectFileName() != "" && File.Exists(ReadCurrentProjectFileName()))
{
//first reading project name & java class file when project type = 2
String projectfilename = ReadCurrentProjectFileName();
if (File.Exists(projectfilename))
{
using (XmlReader xmlreader = XmlReader.Create(projectfilename))
{
while (xmlreader.Read())
{
if (xmlreader.IsStartElement())
{
switch (xmlreader.Name.ToString())
{
case "ProjectName": projectname = xmlreader.ReadString();
break;
case "JavaClassFile": javaclassfilename = xmlreader.ReadString();
break;
}
}
}
}
if (projectfilename != "" && javaclassfilename != "" && njap.getCreatedFileName() != "")
{
//adding nodes to tree view
//changing main form name to project name
//adding file name to filenametoolstriplabel
ProjectExplorerTreeView.Nodes.Clear();
myTabControl.TabPages.Clear();
String prjname = projectfilename.Substring(projectfilename.LastIndexOf("\\") + 1);
prjname = prjname.Remove(prjname.Length - 9);
this.Text = "Silver-J - [ " + prjname + " ]";
String jclassfilename = javaclassfilename.Substring(javaclassfilename.LastIndexOf("\\") + 1);
String jclassnamewithoutjava = jclassfilename.Remove(jclassfilename.Length - 5);
MyTabPage mytabpage = new MyTabPage(this);
mytabpage.Text = jclassfilename;
mytabpage.textEditor.Text = "/*******************************\n "+prjname+" \n*********************************/"
+ "\npublic class " + jclassnamewithoutjava + " {" + "\n " + "\n}";
mytabpage.textEditor.ContextMenuStrip = textEditorContextMenuStrip;
myTabControl.TabPages.Add(mytabpage);
myTabControl.SelectedTab = mytabpage;
TreeNode projecttreenode = new TreeNode();
projecttreenode.Text = prjname;
projecttreenode.ImageIndex = 6;
projecttreenode.SelectedImageIndex = 6;
ProjectExplorerTreeView.Nodes.Add(projecttreenode);
ProjectExplorerTreeView.SelectedNode = projecttreenode;
TreeNode trnode = ProjectExplorerTreeView.Nodes[0];
TreeNode jclassnode = new TreeNode();
jclassnode.Text = jclassfilename;
jclassnode.ImageIndex = 2;
jclassnode.SelectedImageIndex = 2;
trnode.Nodes.Add(jclassnode);
ProjectExplorerTreeView.ExpandAll();
if (njap.getCreatedFileName() != "")
{
try
{
StreamWriter strw = new StreamWriter(njap.getCreatedFileName());
strw.Write(mytabpage.textEditor.Text);
strw.Close();
strw.Dispose();
}
catch
{ }
}
}
}
}
}
//create project without class
else if (njap.CheckProjectType() == 1)
{
if (ReadCurrentProjectFileName() != "" && File.Exists(ReadCurrentProjectFileName()))
{
String projectfilename2 = ReadCurrentProjectFileName();
if (File.Exists(projectfilename2))
{
using (XmlReader xmlreader = XmlReader.Create(projectfilename2))
{
while (xmlreader.Read())
{
if (xmlreader.IsStartElement())
{
switch (xmlreader.Name.ToString())
{
case "ProjectName": projectname = xmlreader.ReadString();
break;
}
}
}
}
if (projectfilename2 != "")
{
ProjectExplorerTreeView.Nodes.Clear();
myTabControl.TabPages.Clear();
String prjname = projectfilename2.Substring(projectfilename2.LastIndexOf("\\") + 1);
prjname = prjname.Remove(prjname.Length - 9);
this.Text = "Silver-J - [ " + prjname + " ]";
TreeNode projecttreenode = new TreeNode();
projecttreenode.Text = prjname;
projecttreenode.ImageIndex = 6;
projecttreenode.SelectedImageIndex = 6;
ProjectExplorerTreeView.Nodes.Add(projecttreenode);
ProjectExplorerTreeView.SelectedNode = projecttreenode;
}
}
}
}
if (njap.IsFinished() == true)
{
FilenameToolStripLabel.Text = "Silver-J";
AddFilesToProjectExplorerTreeView();
WriteCurrentFileNames();
CopyAllSourceFilesToSRCFolder();
UpdateWindowsList_WindowMenu();
SetVisibilityOfToolStripButtons();
myTabControl_SelectedIndexChanged(sender, e);
}
}
如果 njap.isFinished()==true
,它将调用所有需要更改或修改 IDE 的函数,例如将文件添加到 project explorer tree view,设置 toolstrip 按钮的可见性,将 FilenameToolStripLabel 的文本更改为当前打开的文件名。
WriteCurrentFileNames()
此函数从当前打开的项目文件名读取所有文件,并将这些文件名写入 \files\files.slvjfile 以便保存。CopyAllSourceFilesToSRCFolder()
此函数将所有文件从 srcclasses 复制到 src 文件夹,但不包括 .class 文件。UpdateWindowsList_WindowMenu()
此函数检查 tabcontrol 中的选项卡,并将这些选项卡的文本添加到 Window 菜单,通过创建新的菜单项来选择每个选项卡。
我们在这里做的是,
在 New_JavaApplicationProject_Form.cs 文件中,我们创建项目文件(<project_name>.slvjproj),将项目数据写入此文件,创建目录(在其中创建 Project 名称的目录,classes,src、srcclasses 目录)。
在 MainForm.cs 文件中,我们读取创建的项目文件(<project_name>.slvjproj),向 tabcontrol 添加具有创建文件名文本的选项卡,创建该文件并将其内容写入文件,同时还将内容添加到 ProjectExplorerTreeview。其中选项卡是 **MyTabPage**,它将添加到 tabcontrol。(请参阅 MyTabPage.cs)
有关添加选项卡的更多信息,请参阅以下文章:在 C# 中创建高级记事本
创建新的 Java Applet 项目的操作相同,只是多创建一个文件,即 index.html 文件。
新建 Java 类
现在我们需要一个类表单来创建 Java 类。要创建类,必须在 IDE 中创建或打开 Java 项目。以下是用于创建或向应用程序中当前打开的项目添加 Java 类的表单。
在 New_Class_Form.cs 文件中,我们读取类名,还读取修饰符、超类等。一旦点击 Finish 按钮,选项卡就会被添加到 tabcontrol 中,其名称与类名相同,只需在末尾添加 .java,并返回此文件名及其完整路径(getCreatedFileName()
函数)。
在 MainForm.cs 文件中,在 File_New_ClassMenuItem_Click()
事件中,我们将获取此文件名(getCreatedFileName()
),从 New_Class_Form.cs 文件添加到 tabcontrol 的文本编辑器中读取内容,创建该文件并使用 StreamWriter 类将这些内容写入文件。
最后,添加 <JavaClassFile>
和 <VisualFile>
标签,文本为创建的文件名。还添加 <MainClassFile>
标签,当我们要编译文件时,此标签的文本会被读取。
下载源代码以查看 IDE 的完整代码。
以下是选择 File->New->Class 选项时的代码
private void File_New_ClassMenuItem_Click(object sender, EventArgs e)
{
MyTabPage tb = new MyTabPage(this);
New_Class_Form ncf = new New_Class_Form(tb, myTabControl);
ncf.ShowDialog();
String filename = ncf.getCreatedFileName();
int sel = myTabControl.SelectedIndex;
if (sel != -1)
{
var mytexteditor = myTabControl.TabPages[sel].Controls[0];
mytexteditor.ContextMenuStrip = textEditorContextMenuStrip;
if (filename != "")
{
//check file name is already exists
//if not then create that file
if (File.Exists(filename))
{
MessageBox.Show("The file name you entered is already exists in the folder or already added to your project", "Error......");
}
else
{
try
{
StreamWriter strw = new StreamWriter(File.Create(filename));
strw.Write(mytexteditor.Text);
strw.Close();
strw.Dispose();
}
catch
{ }
//adding entry to current opened project file
//JavaClassFile & VisualFile
if (ReadCurrentProjectFileName() != "")
{
String projectfilename = ReadCurrentProjectFileName();
XmlDocument xmldoc = new XmlDocument();
xmldoc.Load(projectfilename);
XmlNode node = xmldoc.CreateNode(XmlNodeType.Element, "JavaClassFile", null);
node.InnerText = filename;
xmldoc.DocumentElement.AppendChild(node);
xmldoc.Save(projectfilename);
XmlDocument xmldoc2 = new XmlDocument();
xmldoc2.Load(projectfilename);
XmlNode node2 = xmldoc2.CreateNode(XmlNodeType.Element, "VisualFile", null);
node2.InnerText = filename;
xmldoc2.DocumentElement.AppendChild(node2);
xmldoc2.Save(projectfilename);
}
}
}
}
if (ncf.IsFinished() == true)
{
AddFilesToProjectExplorerTreeView();
WriteCurrentFileNames();
CopyAllSourceFilesToSRCFolder();
UpdateWindowsList_WindowMenu();
myTabControl_SelectedIndexChanged(sender, e);
//check srcclasses directory exists or not
if (Directory.Exists(getCurrentProjectLocationFolder() + "\\srcclasses"))
{
String mainclassfile = "";
using (XmlReader reader = XmlReader.Create(ReadCurrentProjectFileName()))
{
while (reader.Read())
{
if (reader.IsStartElement())
{
switch (reader.Name.ToString())
{
case "MainClassFile":
mainclassfile = reader.ReadString();
break;
}
}
}
}
if (mainclassfile == "")
{
if (ReadCurrentProjectFileName() != "")
{
String projectfilename = ReadCurrentProjectFileName();
XmlDocument xmldoc = new XmlDocument();
xmldoc.Load(projectfilename);
XmlNode node = xmldoc.CreateNode(XmlNodeType.Element, "MainClassFile", null);
node.InnerText = filename;
xmldoc.DocumentElement.AppendChild(node);
xmldoc.Save(projectfilename);
}
}
}
}
}
新建包 - 在这里我们将在项目文件夹中创建文件夹。当输入 aaa.bbb.ccc 包名时,我们将用 \ 替换 .(aaa\bbb\ccc),并在当前打开的项目位置文件夹中创建这些目录,还将在 aaa\bbb\ccc 文件夹中创建 Java 类。
对于其他选项,例如,
File->New->Interface, File->New->Enums
File->New->HTML File, File->New->CSS File
File->New->Text File, File->New->JavaScript File
File->New->SQL File, File->New->XML File
File->New->New File
代码与创建新的 Java 类相同,只是创建带有自己扩展名的文件。
代码与创建新的 Java 类相同,只是创建带有自己扩展名的文件。
打开项目:(File->Open Project)这不过是读取 OpenFileDialog 中的文件(.slvjproj),从中读取内容,并执行关于它的操作,例如将应用程序窗体文本添加到项目名称文本,通过获取标签中的文件将选项卡添加到 tabcontrol
<JavaClassFile>,<HTMLFile> 等。项目打开后,将 Project Type、ProjectName、Project Location Folder 添加到 \files\defaultprojloc.slvjfile。
打开文件:(File->Open Files)这与上面的(打开项目)相同,只是为了读取文件,将它们的名字添加到 ProjectExplorerTreeView,在选项卡中打开这些文件,并将所有文件名及其完整路径添加到 \files\files.slvjfile。
保存:(File->Save)为了保存已打开的选项卡文件,我使用 FilenameToolStripLabel 在选项卡上显示/存储当前打开的文件名的完整路径。
我正在检查 FilenameToolStripLabel 是否包含 ‘\’。如果包含,则从当前选定的选项卡读取文本编辑器内容,并将其写入 FilenameToolStripLabel.Text 中的文件,或者您可以在这里读取 files\files.slvjfile,其中包含当前打开的所有项目文件及其完整路径。
全部保存 :(File->Save All)为此,我正在读取文件 \files\files.slvjfile,将每个选项卡与从 files.slvjfile 读取的每个文件名进行比较,如果匹配,则将该选项卡设置为选中状态,通过读取当前设置的选项卡文本编辑器和文件名来保存该文件。
加载示例项目
正如每个 IDE 都提供了一些示例项目一样,这里我们将提供以下示例项目。
首先设计您的示例项目表单,用于选择要创建的项目类型。
创建示例项目只不过是创建一个项目文件(.slvjproj)、项目目录、在其中创建子目录(src、classes、srcclasses)、在这些目录中创建项目文件(.java),将此创建的项目信息添加到 \files\defaultprojloc.slvjfile,然后调用 OpenProject
函数并传入创建的项目文件名。
这些项目文件位于 Samples 文件夹中。
首先,我们定义变量来存储需要从 Samples 文件夹读取的文件。
这里我定义了 notepad_files
(notepad 源文件)、notepad_2
(我们想要在/作为项目创建的源文件名)
String[] notepad_files = {
Application.StartupPath+"\\Samples\\Notepad\\Notepad.slvjfile"
};
String[] notepad_2 ={
"Notepad.java"
};
String defaultprojfilepath = Application.StartupPath + "\\files\\defaultprojloc.slvjfile";
public String ProjectLocaionFoder()
{
String projectfolder = "";
using (XmlReader reader = XmlReader.Create(defaultprojfilepath))
{
while (reader.Read())
{
if (reader.IsStartElement())
{
switch (reader.Name.ToString())
{
case "DefaultProjectLocation":
projectfolder = reader.ReadString();
break;
}
}
}
}
return projectfolder;
}
String selected_item = listBox1.SelectedItem.ToString();
String projectfolder = ProjectLocaionFoder();
listBox1
是添加到表单的控件(见上图)。selected_item
包含选定的示例项目名称,projectfolder
包含用户的项目文件夹。
if (selected_item == "Notepad")
{
project_name = "Notepad";
String directory = projectfolder + "\\Notepad";
String projectfile = "Notepad.slvjproj";
if (Directory.Exists(directory))
{
MessageBox.Show("The selected project is already exists in current location", "Error............");
}
else
{
Directory.CreateDirectory(directory);
if (Directory.Exists(directory))
{
project_folder = directory;
project_file = directory + "\\" + projectfile;
}
if (File.Exists(notepad_files[0]))
{
String filename = notepad_files[0];
String fname = filename.Substring(filename.LastIndexOf("\\") + 1);
fname = fname.Remove(fname.Length - 9);
fname = fname + ".java";
if (Directory.Exists(directory))
{
String src = directory + "\\src";
String srcclasses = directory + "\\srcclasses";
String classes = directory + "\\classes";
Directory.CreateDirectory(src);
Directory.CreateDirectory(srcclasses);
Directory.CreateDirectory(classes);
String content = "";
content = File.ReadAllText(notepad_files[0]);
if (Directory.Exists(srcclasses))
{
StreamWriter strw = new StreamWriter(File.Create(srcclasses + "\\" + fname));
strw.Write(content);
strw.Close();
strw.Dispose();
}
//creating & writing slvjproj file
using (XmlWriter xmlwriter = XmlWriter.Create(directory + "\\" + projectfile))
{
xmlwriter.WriteStartDocument();
xmlwriter.WriteStartElement("SilverJProject");
xmlwriter.WriteString("\n");
xmlwriter.WriteComment("Silver-J (1.0) Java Application Project");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectName", "Notepad");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFolder", directory);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectLocationFile", directory + "\\" + projectfile);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("ProjectType", "ApplicationType");
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("MainClassFile", directory + "\\srcclasses" + "\\" + notepad_2[0]);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("JavaClassFile", directory + "\\srcclasses" + "\\" + notepad_2[0]);
xmlwriter.WriteString("\n");
xmlwriter.WriteElementString("VisualFile", directory + "\\srcclasses" + "\\" + notepad_2[0]);
xmlwriter.WriteEndElement();
xmlwriter.WriteEndDocument();
xmlwriter.Close();
}
}
}
is_project_created = true;
}
}
这里我们执行的操作与创建具有“Create Java Class”复选框已选中的新 Java 应用程序项目相同。
编译与运行
使用 IDE 进行编译意味着通过进程运行命令。但在这里,我们编译 Java 源文件不需要显示任何窗口,我们只需要编译的输出,例如错误和警告。创建进程很简单。我们需要一个布尔值来表示编译进程是否已启动。
假设您正在使用 cmd 编译 Java 程序,我们在这里做的是同样的事情。
例如:cd C:\MyJava\Hello
javac.exe HelloWorld.java
下载源代码。
请参阅以下代码
其中 EXE 是应用程序 javac.exe,带有完整路径
WorkingDirectory 是我们的源文件目录(srcclasses)(上面 e.g. C:\MyJava\Hello)
FileName 是我们的主要 Java 源文件,我们想要编译它(HelloWorld.java)
我们只需要一个 Java 源文件来编译,您可以提供更多文件。
主源文件在项目文件(.slvjproj)中以 <MainClassFile>
标签的形式保存。此文件可以通过转到 Run->Main Class 进行更改。
public bool Compile(String EXE, String WorkingDirectory, String FileName)
{
bool processStarted = false;
if (File.Exists(EXE))
{
process.StartInfo.FileName = EXE;
process.StartInfo.Arguments = FileName;
process.StartInfo.WorkingDirectory = WorkingDirectory;
process.StartInfo.CreateNoWindow = true;
process.StartInfo.ErrorDialog = false;
process.StartInfo.UseShellExecute = false;
process.StartInfo.RedirectStandardOutput = true;
process.StartInfo.RedirectStandardError = true;
processStarted = process.Start();
}
else
{
MessageBox.Show("Unable to compile java file. Check your Java Path settings: Current Java Path : ");
}
return processStarted;
}
public void CompileJava(String file, String jdkpath)
{
String mystr = file;
if (mystr.Contains(".java"))
{
mystr = mystr.Remove(mystr.Length - 5);
}
if (this.Compile(jdkpath + "\\javac.exe", Path.GetDirectoryName(file), Path.GetFileName(file)))
{
ErrorReader = process.StandardError;
string response = ErrorReader.ReadToEnd();
if (response != "")
{
ErrorTextBox.Text = response;
if (showErrorDialog == true)
{
MessageBox.Show("" + response, "Errors");
}
}
else if (response == "")
{
ErrorTextBox.Text = "Program Compiled Successfully.................!";
}
else if (response.Contains("uses or overrides a deprecated API."))
{
ErrorTextBox.Text = "Program Compiled Successfully.................!";
}
else
{
ErrorTextBox.Text = "Program Compiled Successfully.................!";
}
}
else if (File.Exists("" + mystr + ".class"))
{
ErrorTextBox.Text = "Program Compiled Successfully.................!";
}
//set caret position to error line number
if(myTabControl.TabCount>0)
{
if(myTabControl.SelectedTab.Text.Contains(".java"))
{
String compilejavafilename = myTabControl.SelectedTab.Text;
if (ErrorTextBox.Text.Contains(compilejavafilename))
{
int select_index = myTabControl.SelectedIndex;
var texteditor = (TextEditorControl)myTabControl.TabPages[select_index].Controls[0];
RichTextBox rtb = new RichTextBox();
rtb.Text = texteditor.Text;
for(int i=0;i<rtb.Lines.Length;i++)
{
if(ErrorTextBox.Lines[0].Contains(i.ToString()))
{
texteditor.ActiveTextAreaControl.TextArea.Caret.Line = i-1;
}
}
}
}
}
}
showErrorDialog
用于控制在点击 compile 菜单项后是否显示对话框。如果找到错误,则显示它,并将光标定位到错误行号。
您知道如何在 cmd 上运行 Java 程序。
首先编译 Java 源文件,它将在转到位置文件夹后创建一个 .class 文件。然后使用 java.exe 命令运行该类文件。
例如:cd C:\MyJava\Hello
java.exe HelloWorld.class
我使用 java.exe 文件的完整路径(jdk_path\bin\java.exe)作为字符串,而不是仅使用 java.exe。
String projectlocationfolder = getCurrentProjectLocationFolder();
if (Directory.Exists(projectlocationfolder + "\\srcclasses"))
{
if (filename.Contains(".java"))
{
String ffname = filename.Remove(filename.Length - 5);
ffname = ffname + ".class";
if (File.Exists(ffname))
{
ProcessStartInfo ProcessInfo;
//Process process;
String javapath = "\"" + jdkpath + "\\java.exe" + "\"";
String getfilename = filename.Substring(filename.LastIndexOf("\\") + 1);
String fname = "";
if (getfilename.Contains(".java"))
{
fname = getfilename.Remove(getfilename.Length - 5);
}
ProcessInfo = new ProcessStartInfo("cmd.exe", "/K" + " cd/ && cd " + workingDirectory + " && " + javapath + " " + fname);
ProcessInfo.CreateNoWindow = true;
ProcessInfo.UseShellExecute = true;
Process.Start(ProcessInfo);
}
}
}
ProcessInfo = new ProcessStartInfo("cmd.exe", "/K" + " cd/ && cd " + workingDirectory + " && " + javapath + " " + fname);
这行代码运行程序。首先,它使用命令 cd/ 启动 cmd.exe。
然后使用 cd 进入项目目录(workingDirectory(srcclasses))。
然后调用 java.exe 文件名完整路径,后跟 .class 文件名。
对于 **Run with Parameter** 选项,操作相同,只是在 fname 后面添加这些参数。
对于 **Run Applet** 选项,操作相同,只是使用 appletviewer.exe 和 HTML 源文件。
构建可执行 Jar 包
要创建可执行 jar 文件,我们需要一个清单文件(manifest.mf)。该文件包含以下内容。
Manifest-Version: 1.0
Ant-Version: Apache Ant 1.9.4
Created-By: 1.8.0_25-b18 (Oracle Corporation)
Class-Path:
X-COMMENT: Main-Class will be added automatically by build
Main-Class:
Main-Class:
其中 Main-Class:应包含主类文件名(仅文件名,不带任何文件扩展名)。
Created-By:是 JDK 版本。
使用 cmd 创建 jar 文件,
首先转到工作目录。
jar.exe cmf <manifest_file> <outputfile> <class_files>
例如
jar.exe cmf manifest.mf Hello.jar HelloWorld.class
在 Run_BuildMenuItem_Click()
中,我使用了一个文本框来粘贴所有 .class 文件,并将 textbox.Text 作为类文件。它不会添加 .java 源文件。
它还通过将目录名添加到文本框来将目录添加到 jar 文件。
该过程与运行 Java 程序相同,只是在命令、输入和参数方面有所不同。
jar 文件创建完成后,我们将在项目位置文件夹中创建一个 build 文件夹,并将创建的 jar 文件复制到其中。
private void Run_BuildMenuItem_Click(object sender, EventArgs e)
{
String projectfolderpath = getCurrentProjectLocationFolder();
if (projectfolderpath != "")
{
if (Directory.Exists(projectfolderpath + "\\srcclasses"))
{
String mainclass = getMainClassFileName();
String mnclass = mainclass.Substring(mainclass.LastIndexOf("\\") + 1);
mnclass = mnclass.Remove(mnclass.Length - 5);
//create mainclass manifest file
String maintexttomanifest = "Manifest-Version: 1.0"
+ "\nAnt-Version: Apache Ant 1.9.4"
+ "\nCreated-By: 1.8.0_25-b18 (Oracle Corporation)"
+ "\nClass-Path: "
+ "\nX-COMMENT: Main-Class will be added automatically by build"
+ "\nMain-Class: " + mnclass
+ "\nMain-Class: " + mnclass;
String manifestfile = projectfolderpath + "\\srcclasses\\mainclass.mf";
StreamWriter strw = new StreamWriter(manifestfile);
strw.Write(maintexttomanifest);
strw.Close();
strw.Dispose();
if (File.Exists(manifestfile))
{
String srcclassesfolderpath = projectfolderpath + "\\srcclasses";
List<string> packagenameslist = getPackageNamesList();
TextBox textbox = new TextBox();
string[] files = Directory.GetFiles(srcclassesfolderpath);
foreach (string filePath in files)
{
if (Path.GetExtension(filePath) != ".java" && Path.GetExtension(filePath) != ".mf")
{
textbox.Paste(" " + Path.GetFileName(filePath));
}
}
//check package folder exists or not
RichTextBox rtb = new RichTextBox();
String[] dirs = Directory.GetDirectories(srcclassesfolderpath);
foreach (String packagefolder in packagenameslist)
{
rtb.Text = rtb.Text.Insert(rtb.SelectionStart, "" + packagefolder + " ");
}
//get folder by leaving package folders
foreach (String dirsname in dirs)
{
String dirs2 = dirsname.Substring(dirsname.LastIndexOf("\\") + 1);
if (rtb.Text.Contains(dirs2)) { }
else
{
textbox.Paste(" " + dirs2 + "* ");
}
}
//create jar file
if (File.Exists(manifestfile))
{
String jarfilepath = "\"" + getJDKPath() + "\\jar.exe" + "\"";
String prjfolder = getCurrentProjectLocationFolder() + "\\srcclasses";
String manifestfilename = manifestfile.Substring(manifestfile.LastIndexOf("\\") + 1);
String classes = textbox.Text;
String mainclassfile = mainclass.Substring(mainclass.LastIndexOf("\\") + 1);
mainclassfile = mainclassfile.Remove(mainclassfile.Length - 5);
String jarfilename = mainclassfile + ".jar";
ProcessStartInfo ProcessInfo;
Process Process;
ProcessInfo = new ProcessStartInfo("cmd.exe", "/K " + "cd/ && cd " + prjfolder + " && " + jarfilepath + " cmf " + manifestfilename + " " + jarfilename + " " + classes);
ProcessInfo.CreateNoWindow = true;
ProcessInfo.UseShellExecute = true;
ProcessInfo.WindowStyle = ProcessWindowStyle.Hidden;
Process = Process.Start(ProcessInfo);
}
//create build folder and moved created jar file to build folder
String createdjarfile = mainclass.Remove(mainclass.Length - 5) + ".jar";
if (File.Exists(createdjarfile))
{
String buildfolder = getCurrentProjectLocationFolder() + "\\build";
if (Directory.Exists(buildfolder))
{
String createdjarfile2 = createdjarfile.Replace("srcclasses", "build");
File.Delete(createdjarfile2);
File.Copy(createdjarfile, createdjarfile2);
try
{
File.Delete(createdjarfile);
}
catch { }
ShowAboutToolStripLabel.Text = "Build Completed";
Run_BuildMenuItem_Click(sender, e);
}
else
{
Directory.CreateDirectory(buildfolder);
String createdjarfile2 = createdjarfile.Replace("srcclasses", "build");
File.Copy(createdjarfile, createdjarfile2);
ShowAboutToolStripLabel.Text = "Build Completed";
Run_BuildMenuItem_Click(sender, e);
}
}
}
}
}
}
</string>
外观
IDE 还有不同的主题。这里我提供默认、系统、浅色、深色和夜间外观。
外观只是改变组件的颜色。
对于 MenuStrip 和 ToolStrip,我们需要编写代码来呈现其外观,通过绘制。这些渲染器类定义在 MyRenderer.cs 文件中。
我创建了 MyMenuStripZ
、MyToolStripZ
类,它们继承自 MenuStrip 和 ToolStrip,并将渲染器从 MyRenderer.cs 文件添加到其中。
以下是将夜间主题设置为 IDE 的代码
if(type=="Night")
{
MyMenuStripZ.Renderer = new NightMenuRenderer();
textEditorContextMenuStrip.Renderer = new NightMenuRenderer();
ProjectExplorerTreeViewContextMenuStrip.Renderer = new NightMenuRenderer();
myTabControlContextMenuStrip.Renderer = new NightMenuRenderer();
ErrorsListContextMenuStrip.Renderer = new NightMenuRenderer();
MyToolStripZ.Renderer = new NightToolStripRenderer();
myTabControl.DrawMode = TabDrawMode.OwnerDrawFixed;
myTabControl.Transparent1 = 255;
myTabControl.Transparent2 = 255;
toolstrippanel.Transparent1 = 255;
toolstrippanel.Transparent2 = 255;
projectexplorerpanel.Transparent1 = 255;
projectexplorerpanel.Transparent2 = 255;
classespanel.Transparent1 = 255;
classespanel.Transparent2 = 255;
methodspanel.Transparent1 = 255;
methodspanel.Transparent2 = 255;
errorslistpanel.Transparent1 = 255;
errorslistpanel.Transparent2 = 255;
MyMenuStripZ.BackColor = Color.FromArgb(255, 30, 30, 30);
toolstrippanel.StartColor = Color.FromArgb(30, 30, 30);
toolstrippanel.EndColor = Color.FromArgb(30, 30, 30);
MyToolStripZ.BackColor = Color.FromArgb(250, 30, 30, 30);
projectexplorerpanel.StartColor = Color.FromArgb(15, 15, 15);
projectexplorerpanel.EndColor = Color.FromArgb(15, 15, 15);
classespanel.StartColor = Color.FromArgb(15, 15, 15);
classespanel.EndColor = Color.FromArgb(15, 15, 15);
methodspanel.StartColor = Color.FromArgb(15, 15, 15);
methodspanel.EndColor = Color.FromArgb(15, 15, 15);
errorslistpanel.StartColor = Color.FromArgb(15, 15, 15);
errorslistpanel.EndColor = Color.FromArgb(15, 15, 15);
projectexplorerlabel.ForeColor = Color.White;
classeslabel.ForeColor = Color.White;
methodslabel.ForeColor = Color.White;
errorslabel.ForeColor = Color.White;
myTabControl.ActiveTabStartColor = Color.FromArgb(10, 10, 30);
myTabControl.ActiveTabEndColor = Color.FromArgb(10, 10, 30);
myTabControl.NonActiveTabStartColor = Color.FromArgb(60, 60, 60);
myTabControl.NonActiveTabEndColor = Color.FromArgb(60, 60, 60);
myTabControl.TextColor = Color.White;
splitContainer1.BackColor = Color.FromArgb(255,10, 10, 10);
ProjectExplorerTreeView.BackColor = Color.FromArgb(255, 25, 25, 25);
ClassesTreeView.BackColor = Color.FromArgb(255, 25, 25, 25);
MethodsTreeView.BackColor = Color.FromArgb(255, 25, 25, 25);
ErrorTextBox.BackColor = Color.FromArgb(255, 25, 25, 25);
ProjectExplorerTreeView.ForeColor = Color.White;
ClassesTreeView.ForeColor = Color.White;
MethodsTreeView.ForeColor = Color.White;
ErrorTextBox.ForeColor = Color.FromArgb(255, 255, 220, 220);
}