mirror of
https://github.com/Noratrieb/UMLetClassParser.git
synced 2026-01-15 00:55:04 +01:00
maven and abstract class
This commit is contained in:
parent
b90e34f501
commit
b2ef2883c5
17 changed files with 116 additions and 8 deletions
3
src/main/java/META-INF/MANIFEST.MF
Normal file
3
src/main/java/META-INF/MANIFEST.MF
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
Manifest-Version: 1.0
|
||||
Main-Class: UMLConverterMain
|
||||
|
||||
123
src/main/java/Regex.java
Normal file
123
src/main/java/Regex.java
Normal file
|
|
@ -0,0 +1,123 @@
|
|||
import java.util.regex.Pattern;
|
||||
|
||||
/**
|
||||
* Contains all Regex
|
||||
*/
|
||||
public abstract class Regex {
|
||||
|
||||
/**
|
||||
* Matches any method in the UML format, including a constructor, encapsulation optional
|
||||
*
|
||||
* <p>Examples:</p>
|
||||
* <ul>
|
||||
* <li>+ doStuff(foo: int, foo: int): int</li>
|
||||
* <li>+ getFoo(): int</li>
|
||||
* <li>work()</li>
|
||||
* </ul>
|
||||
*
|
||||
* <p> Groups:
|
||||
* <ul>
|
||||
* <li>1 The encapsulate modifier (+-~#)</li>
|
||||
* <li>2 The name</li>
|
||||
* <li>3 All Arguments</li>
|
||||
* <li>4 The return type, "" if no return type is specified (void)</li>
|
||||
* </ul>
|
||||
*
|
||||
*/
|
||||
public static final Pattern METHOD_FIND_REGEX = Pattern.compile(" *(?<capsule>[+\\-~#])? *(?<name>\\w+) *\\( *(?<args>(?: *\\w+ *: *[\\w<>]+ *,? *)*) *\\) *(?:: *(?<return>[\\w<>]+))?");
|
||||
|
||||
|
||||
/**
|
||||
* Matches any method in the UML format, including a constructor, forces the encapsulation modifier
|
||||
*
|
||||
* <p>Examples:</p>
|
||||
* <ul>
|
||||
* <li>+ doStuff(foo: int, foo: int): int</li>
|
||||
* <li>+ getFoo(): int</li>
|
||||
* <li>- work()</li>
|
||||
* </ul>
|
||||
*
|
||||
* <p> Groups:
|
||||
* <ul>
|
||||
* <li>1 The encapsulate modifier (+-~#)</li>
|
||||
* <li>2 The name</li>
|
||||
* <li>3 All Arguments</li>
|
||||
* <li>4 The return type, "" if no return type is specified (void)</li>
|
||||
* </ul>
|
||||
*
|
||||
*/
|
||||
public static final Pattern METHOD_FIND_REGEX_FORCE_ENCAPSULATION = Pattern.compile(" *(?<capsule>[+\\-~#]) *(?<name>\\w+) *\\( *(?<args>(?: *\\w+ *: *[\\w<>]+ *,? *)*) *\\) *(?:: *(?<return>[\\w<>]+))?");
|
||||
|
||||
|
||||
/**
|
||||
* Matches any Field in the UML format, including a constructor, encapsulation optional
|
||||
*y
|
||||
* <p>Examples:</p>
|
||||
* <ul>
|
||||
* <li>- age: int</li>
|
||||
* <li>- name: String</li>
|
||||
* <li>age: int</li>
|
||||
* </ul>
|
||||
*
|
||||
* <p> Groups:
|
||||
* <ul>
|
||||
* <li>1 The encapsulate modifier (+-~#)</li>
|
||||
* <li>2 The name</li>
|
||||
* <li>3 The datatype</li>
|
||||
* </ul>
|
||||
*
|
||||
*/
|
||||
public static final Pattern FIELD_FIND_REGEX = Pattern.compile(" *(?<capsule>[+\\-~#])? *(?<name>\\w+) *: *(?<type>[\\w<>]+)");
|
||||
|
||||
|
||||
/**
|
||||
* Matches any Field in the UML format, including a constructor, forces the encapsulation modifier
|
||||
*y
|
||||
* <p>Examples:</p>
|
||||
* <ul>
|
||||
* <li>- age: int</li>
|
||||
* <li>- name: String</li>
|
||||
* <li># date: LocalDate</li>
|
||||
* </ul>
|
||||
*
|
||||
* <p> Groups:
|
||||
* <ul>
|
||||
* <li>1 The encapsulate modifier (+-~#)</li>
|
||||
* <li>2 The name</li>
|
||||
* <li>3 The datatype</li>
|
||||
* </ul>
|
||||
*
|
||||
*/
|
||||
public static final Pattern FIELD_FIND_REGEX_FORCE_ENCAPSULATION = Pattern.compile(" *(?<capsule>[+\\-~#]) *(?<name>\\w+) *: *(?<type>[\\w<>]+)");
|
||||
|
||||
|
||||
/**
|
||||
* Matches a single arg in a method
|
||||
*
|
||||
* <p> Groups:
|
||||
* <ul>
|
||||
* <li>1 The name</li>
|
||||
* <li>2 The datatype</li>
|
||||
* </ul>
|
||||
*/
|
||||
public static final Pattern ARG_SPLIT_REGEX = Pattern.compile(" *(\\w+) *: *([\\w<>]+)");
|
||||
|
||||
/**
|
||||
* Get a method pattern
|
||||
* @param encapsulationOptional True: Do not force encapsulation, False: Force encapsulation
|
||||
* @return The pattern as a String
|
||||
*/
|
||||
public static String getMethodPattern(boolean encapsulationOptional){
|
||||
return encapsulationOptional ? METHOD_FIND_REGEX.pattern() : METHOD_FIND_REGEX_FORCE_ENCAPSULATION.pattern();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a field pattern
|
||||
* @param encapsulationOptional True: Do not force encapsulation, False: Force encapsulation
|
||||
* @return The pattern as a String
|
||||
*/
|
||||
public static String getFieldPattern(boolean encapsulationOptional){
|
||||
return encapsulationOptional ? FIELD_FIND_REGEX.pattern() : FIELD_FIND_REGEX_FORCE_ENCAPSULATION.pattern();
|
||||
}
|
||||
|
||||
}
|
||||
100
src/main/java/UMLClass.java
Normal file
100
src/main/java/UMLClass.java
Normal file
|
|
@ -0,0 +1,100 @@
|
|||
import java.util.ArrayList;
|
||||
|
||||
public class UMLClass {
|
||||
|
||||
private final String name;
|
||||
private final String fullName;
|
||||
private final String packageString;
|
||||
|
||||
private final boolean isAbstract;
|
||||
|
||||
private final ArrayList<UMLField> fields = new ArrayList<>();
|
||||
private final ArrayList<UMLMethod> methods = new ArrayList<>();
|
||||
|
||||
private UMLManager manager;
|
||||
|
||||
/**
|
||||
* Contains all information about a Java class loaded from a UMLet XML file
|
||||
* Use the {@link #toString()} method to get the class as compilable, valid Java Code
|
||||
* @param classDiagram
|
||||
* @param packageString
|
||||
* @param manager
|
||||
*/
|
||||
public UMLClass(String classDiagram, String packageString, UMLManager manager) {
|
||||
|
||||
this.manager = manager;
|
||||
this.packageString = packageString;
|
||||
|
||||
String[] lines = classDiagram.split("\n");
|
||||
|
||||
String[] linesBeheaded = new String[lines.length - 1];
|
||||
|
||||
String name = lines[0];
|
||||
if(name.matches("/.+/")){
|
||||
isAbstract = true;
|
||||
this.fullName = name.replaceAll("/(.+)/", "$1");
|
||||
} else {
|
||||
isAbstract = false;
|
||||
this.fullName = name;
|
||||
}
|
||||
|
||||
this.name = lines[0].split(" ")[0];
|
||||
|
||||
System.arraycopy(lines, 1, linesBeheaded, 0, linesBeheaded.length);
|
||||
|
||||
for (String line : linesBeheaded) {
|
||||
if (line != null) {
|
||||
if (line.matches(Regex.getMethodPattern(manager.isIgnoreEcapsulation()))) { //MATCHES METHOD
|
||||
methods.add(new UMLMethod(line, name, manager));
|
||||
} else if (line.matches(Regex.getFieldPattern(manager.isIgnoreEcapsulation()))) { //MATCHES FIELD
|
||||
fields.add(new UMLField(line, manager));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the class as compilable Java code
|
||||
* @return The class as compilable Java code
|
||||
*/
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder s = new StringBuilder();
|
||||
|
||||
if(manager.isShowWatermark()) {
|
||||
s.append("//TODO AUTO-GENERATED METHODS\n\n");
|
||||
}
|
||||
|
||||
if (!packageString.equals("")) {
|
||||
s.append("package ").append(packageString).append(";\n\n");
|
||||
}
|
||||
s.append("public ").append(isAbstract ? "abstract " : "").append("class ").append(fullName).append(" {\n\n");
|
||||
|
||||
if (fields.size() > 0) {
|
||||
for (UMLField field : fields) {
|
||||
s.append(field.toString());
|
||||
}
|
||||
}
|
||||
|
||||
if (methods.size() > 0) {
|
||||
for (UMLMethod method : methods) {
|
||||
s.append(method.toString());
|
||||
}
|
||||
}
|
||||
|
||||
if(manager.isGetSetAuto()){
|
||||
for(UMLField field : fields){
|
||||
s.append(field.getter());
|
||||
s.append(field.setter());
|
||||
}
|
||||
}
|
||||
|
||||
s.append("}");
|
||||
|
||||
return s.toString();
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
}
|
||||
165
src/main/java/UMLClassView.form
Normal file
165
src/main/java/UMLClassView.form
Normal file
|
|
@ -0,0 +1,165 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<form xmlns="http://www.intellij.com/uidesigner/form/" version="1" bind-to-class="UMLClassView">
|
||||
<grid id="27dc6" binding="panel1" default-binding="true" layout-manager="GridLayoutManager" row-count="7" column-count="3" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="3" left="3" bottom="3" right="3"/>
|
||||
<constraints>
|
||||
<xy x="20" y="20" width="500" height="400"/>
|
||||
</constraints>
|
||||
<properties/>
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<tabbedpane id="97eb">
|
||||
<constraints>
|
||||
<grid row="0" column="0" row-span="1" col-span="3" vsize-policy="3" hsize-policy="3" anchor="0" fill="3" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="200" height="200"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties/>
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<grid id="fc27a" layout-manager="GridLayoutManager" row-count="4" column-count="2" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<constraints>
|
||||
<tabbedpane title="File Mode"/>
|
||||
</constraints>
|
||||
<properties/>
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<component id="71a25" class="javax.swing.JLabel">
|
||||
<constraints>
|
||||
<grid row="0" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="0" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value=" .uxf File Path:"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="a9bfd" class="javax.swing.JTextField" binding="pathField">
|
||||
<constraints>
|
||||
<grid row="0" column="1" row-span="1" col-span="1" vsize-policy="0" hsize-policy="6" anchor="8" fill="1" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="150" height="-1"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties/>
|
||||
</component>
|
||||
<component id="fa74" class="javax.swing.JButton" binding="convertFileButton">
|
||||
<constraints>
|
||||
<grid row="2" column="0" row-span="1" col-span="2" vsize-policy="0" hsize-policy="3" anchor="0" fill="1" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value="convert"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="17a65" class="javax.swing.JLabel">
|
||||
<constraints>
|
||||
<grid row="1" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="0" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<labelFor value="96709"/>
|
||||
<text value="Package Destination Path"/>
|
||||
</properties>
|
||||
</component>
|
||||
<vspacer id="1a17d">
|
||||
<constraints>
|
||||
<grid row="3" column="0" row-span="1" col-span="2" vsize-policy="6" hsize-policy="1" anchor="0" fill="2" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
</vspacer>
|
||||
<component id="96709" class="javax.swing.JTextField" binding="packagePathField">
|
||||
<constraints>
|
||||
<grid row="1" column="1" row-span="1" col-span="1" vsize-policy="0" hsize-policy="6" anchor="8" fill="1" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="150" height="-1"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties/>
|
||||
</component>
|
||||
</children>
|
||||
</grid>
|
||||
<grid id="425fa" layout-manager="GridLayoutManager" row-count="2" column-count="1" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<constraints>
|
||||
<tabbedpane title="Text Mode"/>
|
||||
</constraints>
|
||||
<properties/>
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<component id="aeb5e" class="javax.swing.JTextArea" binding="inputArea">
|
||||
<constraints>
|
||||
<grid row="0" column="0" row-span="1" col-span="1" vsize-policy="6" hsize-policy="6" anchor="0" fill="3" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="150" height="50"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties/>
|
||||
</component>
|
||||
<component id="54ac1" class="javax.swing.JTextArea" binding="outputArea">
|
||||
<constraints>
|
||||
<grid row="1" column="0" row-span="1" col-span="1" vsize-policy="6" hsize-policy="6" anchor="0" fill="3" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="150" height="50"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties>
|
||||
<editable value="false"/>
|
||||
</properties>
|
||||
</component>
|
||||
</children>
|
||||
</grid>
|
||||
</children>
|
||||
</tabbedpane>
|
||||
<component id="fa538" class="javax.swing.JLabel">
|
||||
<constraints>
|
||||
<grid row="1" column="0" row-span="1" col-span="3" vsize-policy="0" hsize-policy="0" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value="Settings:"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="8f883" class="javax.swing.JCheckBox" binding="watermarkBox">
|
||||
<constraints>
|
||||
<grid row="2" column="0" row-span="1" col-span="3" vsize-policy="0" hsize-policy="3" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<selected value="false"/>
|
||||
<text value="Add Watermark"/>
|
||||
<toolTipText value="Add a TODO watermark to all auto-generated classes"/>
|
||||
</properties>
|
||||
</component>
|
||||
<vspacer id="5f3c8">
|
||||
<constraints>
|
||||
<grid row="6" column="2" row-span="1" col-span="1" vsize-policy="6" hsize-policy="1" anchor="0" fill="2" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
</vspacer>
|
||||
<component id="fe6ca" class="javax.swing.JCheckBox" binding="generateGetSetBox">
|
||||
<constraints>
|
||||
<grid row="3" column="0" row-span="1" col-span="3" vsize-policy="0" hsize-policy="3" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value="Generate Getter/Setter"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="9da58" class="javax.swing.JCheckBox" binding="autoFillConstructorBox">
|
||||
<constraints>
|
||||
<grid row="4" column="0" row-span="1" col-span="3" vsize-policy="0" hsize-policy="3" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value="Auto-Fill Contructor"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="af39e" class="javax.swing.JCheckBox" binding="ignoreEncapsulationBox">
|
||||
<constraints>
|
||||
<grid row="5" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="3" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text value="Ignore Encapsulation"/>
|
||||
</properties>
|
||||
</component>
|
||||
<component id="9a1ec" class="javax.swing.JTextField" binding="defaultEncapsulationField">
|
||||
<constraints>
|
||||
<grid row="5" column="1" row-span="1" col-span="1" vsize-policy="0" hsize-policy="6" anchor="8" fill="1" indent="0" use-parent-layout="false">
|
||||
<preferred-size width="150" height="-1"/>
|
||||
</grid>
|
||||
</constraints>
|
||||
<properties>
|
||||
<enabled value="false"/>
|
||||
</properties>
|
||||
</component>
|
||||
</children>
|
||||
</grid>
|
||||
</form>
|
||||
135
src/main/java/UMLClassView.java
Normal file
135
src/main/java/UMLClassView.java
Normal file
|
|
@ -0,0 +1,135 @@
|
|||
import javax.swing.*;
|
||||
import java.awt.datatransfer.DataFlavor;
|
||||
import java.awt.dnd.DnDConstants;
|
||||
import java.awt.dnd.DropTarget;
|
||||
import java.awt.dnd.DropTargetDropEvent;
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.awt.event.KeyAdapter;
|
||||
import java.awt.event.KeyEvent;
|
||||
import java.io.File;
|
||||
import java.util.List;
|
||||
|
||||
public class UMLClassView {
|
||||
private JTextArea inputArea;
|
||||
private JPanel panel1;
|
||||
private JTextArea outputArea;
|
||||
private JTextField pathField;
|
||||
private JButton convertFileButton;
|
||||
private JTextField packagePathField;
|
||||
private JCheckBox watermarkBox;
|
||||
private JCheckBox generateGetSetBox;
|
||||
private JCheckBox autoFillConstructorBox;
|
||||
private JCheckBox ignoreEncapsulationBox;
|
||||
private JTextField defaultEncapsulationField;
|
||||
|
||||
private UMLManager manager;
|
||||
|
||||
/**
|
||||
* Creates the GUI for the application
|
||||
*/
|
||||
public UMLClassView() {
|
||||
|
||||
inputArea.addKeyListener(new KeyAdapter() {
|
||||
@Override
|
||||
public void keyPressed(KeyEvent e) {
|
||||
refreshTextArea();
|
||||
}
|
||||
@Override
|
||||
public void keyReleased(KeyEvent e) {
|
||||
refreshTextArea();
|
||||
}
|
||||
});
|
||||
|
||||
convertFileButton.addActionListener(e -> {
|
||||
String path = pathField.getText();
|
||||
String packagePath = packagePathField.getText();
|
||||
XMLParser parser = new XMLParser(path);
|
||||
manager.parseClasses(parser.getClassesText(), packagePath);
|
||||
});
|
||||
|
||||
pathField.setDropTarget(new DropTarget() {
|
||||
@Override
|
||||
public synchronized void drop(DropTargetDropEvent dtde) {
|
||||
try {
|
||||
dtde.acceptDrop(DnDConstants.ACTION_COPY);
|
||||
List<File> droppedFiles = (List<File>)
|
||||
dtde.getTransferable().getTransferData(DataFlavor.javaFileListFlavor);
|
||||
for (File file : droppedFiles) {
|
||||
String path = file.getAbsolutePath();
|
||||
pathField.setText(path);
|
||||
String packagePath = packagePathField.getText();
|
||||
XMLParser parser = new XMLParser(path);
|
||||
manager.parseClasses(parser.getClassesText(), packagePath);
|
||||
}
|
||||
} catch (Exception ex) {
|
||||
ex.printStackTrace();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
watermarkBox.addActionListener(e -> {
|
||||
manager.setShowWatermark(watermarkBox.isSelected());
|
||||
refreshTextArea();
|
||||
});
|
||||
|
||||
generateGetSetBox.addActionListener(new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
manager.setGetSetAuto(generateGetSetBox.isSelected());
|
||||
refreshTextArea();
|
||||
}
|
||||
});
|
||||
autoFillConstructorBox.addActionListener(new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
manager.setAutoGenerateConstructor(autoFillConstructorBox.isSelected());
|
||||
refreshTextArea();
|
||||
}
|
||||
});
|
||||
ignoreEncapsulationBox.addActionListener(new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
manager.setIgnoreEcapsulation(ignoreEncapsulationBox.isSelected());
|
||||
defaultEncapsulationField.setEnabled(ignoreEncapsulationBox.isSelected());
|
||||
refreshTextArea();
|
||||
}
|
||||
});
|
||||
|
||||
defaultEncapsulationField.addKeyListener(new KeyAdapter() {
|
||||
|
||||
@Override
|
||||
public void keyReleased(KeyEvent e) {
|
||||
manager.setDefaultEncapsulation(defaultEncapsulationField.getText() + " ");
|
||||
refreshTextArea();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void refreshTextArea(){
|
||||
String text = inputArea.getText();
|
||||
UMLClass umlClass = new UMLClass(text, "", manager);
|
||||
outputArea.setText(umlClass.toString());
|
||||
}
|
||||
|
||||
public JPanel getPanel1() {
|
||||
return panel1;
|
||||
}
|
||||
|
||||
public void setManager(UMLManager manager) {
|
||||
this.manager = manager;
|
||||
}
|
||||
|
||||
public boolean isWatermarkSelected(){
|
||||
return watermarkBox.isSelected();
|
||||
}
|
||||
|
||||
public boolean isGetSetAutoSelected() {
|
||||
return generateGetSetBox.isSelected();
|
||||
}
|
||||
|
||||
public boolean isAutoConstructorSelected() {
|
||||
return autoFillConstructorBox.isSelected();
|
||||
}
|
||||
}
|
||||
21
src/main/java/UMLConverterMain.java
Normal file
21
src/main/java/UMLConverterMain.java
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
import javax.swing.*;
|
||||
|
||||
/**
|
||||
* Starts the UMLetClassParser
|
||||
*/
|
||||
public class UMLConverterMain {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
JFrame frame = new JFrame();
|
||||
UMLClassView view = new UMLClassView();
|
||||
new UMLManager(view);
|
||||
frame.setContentPane(view.getPanel1());
|
||||
frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
|
||||
frame.setSize(700, 500);
|
||||
frame.setVisible(true);
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
78
src/main/java/UMLField.java
Normal file
78
src/main/java/UMLField.java
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
/**
|
||||
* Stores all information about a field in a class and converts it into Java code using the {@link #toString()} method
|
||||
*/
|
||||
public class UMLField {
|
||||
|
||||
private final String dataType;
|
||||
private final String name;
|
||||
private final String encapsulation;
|
||||
|
||||
private UMLManager manager;
|
||||
|
||||
private boolean valid;
|
||||
|
||||
/**
|
||||
* New Field from UML line
|
||||
*
|
||||
* @param line Format: "- name: String"
|
||||
*/
|
||||
public UMLField(String line, UMLManager manager) {
|
||||
this.manager = manager;
|
||||
|
||||
String formatted = line.replaceAll(Regex.getFieldPattern(manager.isIgnoreEcapsulation()), "$1;$3;$2");
|
||||
String[] formattedSplit = formatted.split(";");
|
||||
|
||||
if(!manager.isIgnoreEcapsulation()) {
|
||||
System.out.println("not ignore");
|
||||
this.encapsulation = switch (formattedSplit[0]) {
|
||||
case "+" -> "public ";
|
||||
case "-" -> "private ";
|
||||
case "#" -> "protected ";
|
||||
case "~" -> "";
|
||||
default -> "[undefined] ";
|
||||
};
|
||||
} else {
|
||||
this.encapsulation = manager.getDefaultEncapsulation();
|
||||
}
|
||||
|
||||
this.name = formattedSplit[2];
|
||||
this.dataType = formattedSplit[1];
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the field as the Java code representation
|
||||
* @return The field as the Java code representation
|
||||
*/
|
||||
@Override
|
||||
public String toString() {
|
||||
return " " + encapsulation + dataType + " " + name + ";\n";
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate a Setter Method for this field
|
||||
*
|
||||
* @return The Setter Method as a String
|
||||
*/
|
||||
public String setter() {
|
||||
String nameCC = "set" + name.toUpperCase().charAt(0) + name.substring(1);
|
||||
UMLMethod setter = new UMLMethod("void ", nameCC, "public ");
|
||||
setter.addArg(name, dataType);
|
||||
setter.addBodyLine("this." + name + " = " + name + ";");
|
||||
|
||||
return setter.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate a Getter Method for this field
|
||||
*
|
||||
* @return The Getter Method as a String
|
||||
*/
|
||||
public String getter() {
|
||||
String nameCC = "get" + name.toUpperCase().charAt(0) + name.substring(1);
|
||||
UMLMethod setter = new UMLMethod(dataType + " ", nameCC, "public ");
|
||||
setter.addBodyLine("return " + name + ";");
|
||||
|
||||
return setter.toString();
|
||||
}
|
||||
}
|
||||
99
src/main/java/UMLManager.java
Normal file
99
src/main/java/UMLManager.java
Normal file
|
|
@ -0,0 +1,99 @@
|
|||
import java.io.BufferedWriter;
|
||||
import java.io.FileWriter;
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
|
||||
/**
|
||||
* Manages everything about the parsing
|
||||
*/
|
||||
public class UMLManager {
|
||||
|
||||
private String defaultEncapsulation = "";
|
||||
private UMLClassView view;
|
||||
private boolean showWatermark;
|
||||
private boolean getSetAuto;
|
||||
private boolean autoFillConstructor;
|
||||
private boolean ignoreEcapsulation;
|
||||
|
||||
public UMLManager(UMLClassView view) {
|
||||
this.view = view;
|
||||
this.showWatermark = view.isWatermarkSelected();
|
||||
this.getSetAuto = view.isGetSetAutoSelected();
|
||||
this.autoFillConstructor = view.isAutoConstructorSelected();
|
||||
view.setManager(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts the class text into compilable Java files at the package destination containing the code
|
||||
* @param classesText An ArrayList of Type String containing all classes in UML text represantation
|
||||
* @param packagePath The path to the package where the classes should be stored to
|
||||
*/
|
||||
public void parseClasses(ArrayList<String> classesText, String packagePath) {
|
||||
|
||||
String packageString = packagePath.replaceAll(".*src\\\\(.*)", "$1");
|
||||
packageString = packageString.replaceAll("\\\\", ".");
|
||||
|
||||
ArrayList<UMLClass> classes = new ArrayList<>();
|
||||
|
||||
for (String text : classesText) {
|
||||
classes.add(new UMLClass(text, packageString, this));
|
||||
}
|
||||
|
||||
classes.forEach(e -> System.out.println(e.toString()));
|
||||
|
||||
for (UMLClass c : classes) {
|
||||
try {
|
||||
String path = packagePath + "/" + c.getName() + ".java";
|
||||
FileWriter fw = new FileWriter(path);
|
||||
BufferedWriter bw = new BufferedWriter(fw);
|
||||
bw.write(c.toString());
|
||||
bw.close();
|
||||
fw.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isShowWatermark() {
|
||||
return showWatermark;
|
||||
}
|
||||
|
||||
public void setShowWatermark(boolean showWatermark) {
|
||||
this.showWatermark = showWatermark;
|
||||
}
|
||||
|
||||
public void setGetSetAuto(boolean getSetAuto) {
|
||||
this.getSetAuto = getSetAuto;
|
||||
}
|
||||
|
||||
public boolean isGetSetAuto() {
|
||||
return getSetAuto;
|
||||
}
|
||||
|
||||
public boolean isAutoFillConstructor(){
|
||||
return autoFillConstructor;
|
||||
}
|
||||
|
||||
public void setAutoGenerateConstructor(boolean selected) {
|
||||
autoFillConstructor = selected;
|
||||
}
|
||||
|
||||
public boolean isIgnoreEcapsulation() {
|
||||
return ignoreEcapsulation;
|
||||
}
|
||||
|
||||
public void setIgnoreEcapsulation(boolean ignoreEcapsulation) {
|
||||
this.ignoreEcapsulation = ignoreEcapsulation;
|
||||
}
|
||||
|
||||
public void setDefaultEncapsulation(String defaultEncapsulation) {
|
||||
this.defaultEncapsulation = defaultEncapsulation;
|
||||
}
|
||||
|
||||
public String getDefaultEncapsulation() {
|
||||
return defaultEncapsulation;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
134
src/main/java/UMLMethod.java
Normal file
134
src/main/java/UMLMethod.java
Normal file
|
|
@ -0,0 +1,134 @@
|
|||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
* Stores all information about a method in a class and converts it into Java code using the {@link #toString()} method
|
||||
*/
|
||||
public class UMLMethod {
|
||||
|
||||
private final String returnType;
|
||||
private final String name;
|
||||
private final String encapsulation;
|
||||
|
||||
private final ArrayList<String> argsNames = new ArrayList<>();
|
||||
private final ArrayList<String> argsTypes = new ArrayList<>();
|
||||
|
||||
private boolean isConstructor;
|
||||
|
||||
private UMLManager manager;
|
||||
|
||||
private String methodBody = "";
|
||||
|
||||
/**
|
||||
* Create a new method/constructor from the UML representation of that method
|
||||
*
|
||||
* @param line The line in the UML diagram
|
||||
* @param className The name of the class
|
||||
*/
|
||||
public UMLMethod(String line, String className, UMLManager manager) {
|
||||
|
||||
this.manager = manager;
|
||||
|
||||
//First, format it nicely
|
||||
|
||||
String formatted = line.replaceAll(Regex.METHOD_FIND_REGEX.pattern(), "$1;$4;$2;$3");
|
||||
String[] parts = formatted.split(";");
|
||||
if(!manager.isIgnoreEcapsulation()) {
|
||||
this.encapsulation = switch (parts[0]) {
|
||||
case "+" -> "public ";
|
||||
case "-" -> "private ";
|
||||
case "#" -> "protected ";
|
||||
case "~" -> "";
|
||||
default -> "[undefined] ";
|
||||
};
|
||||
} else {
|
||||
this.encapsulation = manager.getDefaultEncapsulation();
|
||||
}
|
||||
|
||||
this.name = parts[2];
|
||||
|
||||
if(className.equals(name)){
|
||||
isConstructor = true;
|
||||
}
|
||||
|
||||
if (parts[1].equals("") && !isConstructor) {
|
||||
this.returnType = "void ";
|
||||
} else {
|
||||
this.returnType = parts[1] + " ";
|
||||
}
|
||||
|
||||
if (parts.length == 4) {
|
||||
String args = parts[3];
|
||||
String[] argsSplit = args.split(",");
|
||||
|
||||
for (String s : argsSplit) {
|
||||
if (s.matches(Regex.ARG_SPLIT_REGEX.pattern())) {
|
||||
String argFormatted = s.replaceAll(Regex.ARG_SPLIT_REGEX.pattern(), "$1;$2");
|
||||
String[] formattedSplit = argFormatted.split(";");
|
||||
argsNames.add(formattedSplit[0]);
|
||||
argsTypes.add(formattedSplit[1]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public UMLMethod(String returnType, String name, String encapsulation) {
|
||||
this.returnType = returnType;
|
||||
this.name = name;
|
||||
this.encapsulation = encapsulation;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the method as the Java code representation
|
||||
*
|
||||
* @return The method as the Java code representation
|
||||
*/
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder returnString = new StringBuilder();
|
||||
returnString.append("\n ").append(encapsulation).append(returnType).append(name).append(" (");
|
||||
|
||||
for (int i = 0; i < argsNames.size(); i++) {
|
||||
returnString.append(argsTypes.get(i)).append(" ").append(argsNames.get(i));
|
||||
if (i != argsNames.size() - 1) {
|
||||
returnString.append(", ");
|
||||
}
|
||||
}
|
||||
|
||||
returnString.append(") {\n");
|
||||
|
||||
if(isConstructor && manager.isAutoFillConstructor()){
|
||||
for (String argsName : argsNames) {
|
||||
addBodyLine("this." + argsName + " = " + argsName + ";");
|
||||
}
|
||||
}
|
||||
|
||||
returnString.append(methodBody);
|
||||
returnString.append("\n }\n");
|
||||
|
||||
return returnString.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Add an argument to the method
|
||||
*
|
||||
* @param name The name of the variable
|
||||
* @param dataType The type
|
||||
*/
|
||||
public void addArg(String name, String dataType) {
|
||||
argsNames.add(name);
|
||||
argsTypes.add(dataType);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a line to the method body
|
||||
* @param line The line (not containing any linebreaks)
|
||||
*/
|
||||
public void addBodyLine(String line) {
|
||||
if (methodBody.equals("")) {
|
||||
methodBody += " " + line;
|
||||
} else {
|
||||
methodBody += "\n " + line;
|
||||
}
|
||||
}
|
||||
}
|
||||
59
src/main/java/XMLParser.java
Normal file
59
src/main/java/XMLParser.java
Normal file
|
|
@ -0,0 +1,59 @@
|
|||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Element;
|
||||
import org.w3c.dom.Node;
|
||||
import org.w3c.dom.NodeList;
|
||||
import org.xml.sax.SAXException;
|
||||
|
||||
import javax.xml.parsers.DocumentBuilder;
|
||||
import javax.xml.parsers.DocumentBuilderFactory;
|
||||
import javax.xml.parsers.ParserConfigurationException;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
|
||||
/**
|
||||
* Opens a UMLet XML file and parses its content to an ArrayList of Type String containing all UML class texts
|
||||
*/
|
||||
public class XMLParser {
|
||||
|
||||
private Document doc;
|
||||
private boolean valid;
|
||||
|
||||
public XMLParser(String path) {
|
||||
try {
|
||||
File inputFile = new File(path);
|
||||
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||
doc = builder.parse(inputFile);
|
||||
valid = true;
|
||||
} catch (ParserConfigurationException | SAXException | IOException ignored){
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all classes from a UMLet XML file
|
||||
* @return an ArrayList of Type String containing all UML classes in their text form
|
||||
*/
|
||||
public ArrayList<String> getClassesText(){
|
||||
|
||||
ArrayList<String> classes = new ArrayList<>();
|
||||
if(valid) {
|
||||
NodeList nList = doc.getDocumentElement().getElementsByTagName("element");
|
||||
|
||||
for (int i = 0; i < nList.getLength(); i++) { Node node = nList.item(i);
|
||||
|
||||
if (node.getNodeType() == Node.ELEMENT_NODE) {
|
||||
|
||||
Element element = (Element) node;
|
||||
|
||||
if (element.getElementsByTagName("id").item(0).getTextContent().equals("UMLClass")) {
|
||||
String classBody = element.getElementsByTagName("panel_attributes").item(0).getTextContent();
|
||||
classes.add(classBody);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return classes;
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue