From cfacbc1f9799773833156719b30a5a2d2845fd30 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Tue, 1 May 2018 19:26:04 +0200 Subject: [PATCH] version 1.2018.4 --- pom.xml | 3 +- .../sourceforge/plantuml/AnnotatedWorker.java | 50 +++--- src/net/sourceforge/plantuml/CornerParam.java | 2 +- .../sourceforge/plantuml/GeneratedImage.java | 2 + .../plantuml/GeneratedImageImpl.java | 8 +- .../plantuml/ISourceFileReader.java | 5 +- src/net/sourceforge/plantuml/LineParam.java | 4 +- src/net/sourceforge/plantuml/Option.java | 9 +- src/net/sourceforge/plantuml/OptionPrint.java | 1 + .../sourceforge/plantuml/PSystemError.java | 5 +- .../sourceforge/plantuml/PSystemUtils.java | 25 ++- src/net/sourceforge/plantuml/Run.java | 1 + src/net/sourceforge/plantuml/SkinParam.java | 9 + .../plantuml/SourceFileReader.java | 148 +++------------- .../plantuml/SourceFileReader2.java | 74 +------- ...act.java => SourceFileReaderAbstract.java} | 15 +- src/net/sourceforge/plantuml/UmlDiagram.java | 2 +- .../plantuml/ZSourceFileReader.java | 162 ------------------ .../plantuml/ZSourceFileReader2.java | 66 ------- .../command/CommandPartition3.java | 20 ++- .../ftile/vcompact/FtileRepeat.java | 2 +- .../ImageDataAbstract.java} | 47 +++-- .../plantuml/api/ImageDataComplex.java | 21 +-- .../plantuml/api/ImageDataSimple.java | 32 ++-- .../plantuml/code/AsciiEncoderBase64.java | 147 ++++++++++++++++ .../plantuml/code/CompressionZlib.java | 3 + .../plantuml/code/TranscoderImpl.java | 4 +- .../plantuml/code/TranscoderSmart.java | 8 +- .../plantuml/command/CommandScale.java | 9 +- .../sourceforge/plantuml/core/ImageData.java | 2 + .../plantuml/cucadiagram/CucaDiagram.java | 13 +- .../plantuml/cucadiagram/Link.java | 40 +++-- .../cucadiagram/dot/GraphvizVersion.java | 6 +- .../dot/GraphvizVersionFinder.java | 15 +- .../command/CommandCreateElementFull.java | 4 +- .../command/CommandPackageWithUSymbol.java | 4 +- .../plantuml/directdot/PSystemDot.java | 21 +-- .../plantuml/ditaa/PSystemDitaa.java | 6 +- .../plantuml/donors/PSystemDonors.java | 3 +- .../plantuml/flowdiagram/FlowDiagram.java | 8 +- .../plantuml/graphic/SkinParameter.java | 5 +- .../jdot/CucaDiagramFileMakerJDot.java | 2 +- .../plantuml/postit/PostItDiagram.java | 2 +- .../plantuml/project/PSystemProject.java | 7 +- .../plantuml/project2/PSystemProject2.java | 7 +- .../plantuml/project3/Solver3.java | 8 +- .../plantuml/salt/PSystemSalt.java | 2 +- .../graphic/ArrowAndParticipant.java | 4 +- .../sourceforge/plantuml/skin/rose/Rose.java | 40 ++--- .../sourceforge/plantuml/svek/Cluster.java | 3 +- .../svek/CucaDiagramFileMakerSvek.java | 9 +- .../plantuml/svek/DecorateEntityImage.java | 15 +- src/net/sourceforge/plantuml/svek/Line.java | 8 +- .../svek/extremity/ExtremityCircle.java | 21 ++- .../extremity/ExtremityFactoryCircle.java | 9 +- .../svek/image/EntityImageDescription.java | 29 +++- .../plantuml/swing/MainWindow2.java | 2 +- .../sourceforge/plantuml/version/Version.java | 4 +- .../plantuml/vizjs/GraphvizJs.java | 6 +- 59 files changed, 555 insertions(+), 634 deletions(-) rename src/net/sourceforge/plantuml/{ZSourceFileReaderAbstract.java => SourceFileReaderAbstract.java} (91%) delete mode 100644 src/net/sourceforge/plantuml/ZSourceFileReader.java delete mode 100644 src/net/sourceforge/plantuml/ZSourceFileReader2.java rename src/net/sourceforge/plantuml/{project3/Solver2.java => api/ImageDataAbstract.java} (64%) create mode 100644 src/net/sourceforge/plantuml/code/AsciiEncoderBase64.java diff --git a/pom.xml b/pom.xml index a6e030141..7bad54d02 100644 --- a/pom.xml +++ b/pom.xml @@ -30,7 +30,8 @@ Script Author: Julien Eluard --> - + 4.0.0 net.sourceforge.plantuml diff --git a/src/net/sourceforge/plantuml/AnnotatedWorker.java b/src/net/sourceforge/plantuml/AnnotatedWorker.java index 2fa421a81..9714539cf 100644 --- a/src/net/sourceforge/plantuml/AnnotatedWorker.java +++ b/src/net/sourceforge/plantuml/AnnotatedWorker.java @@ -64,13 +64,13 @@ public class AnnotatedWorker { } private TextBlock addLegend(TextBlock original) { - if (DisplayPositionned.isNull(annotated.getLegend())) { + final DisplayPositionned legend = annotated.getLegend(); + if (DisplayPositionned.isNull(legend)) { return original; } - final TextBlock text = EntityImageLegend.create(annotated.getLegend().getDisplay(), getSkinParam()); + final TextBlock text = EntityImageLegend.create(legend.getDisplay(), getSkinParam()); - return DecorateEntityImage.add(original, text, annotated.getLegend().getHorizontalAlignment(), annotated - .getLegend().getVerticalAlignment()); + return DecorateEntityImage.add(original, text, legend.getHorizontalAlignment(), legend.getVerticalAlignment()); } private ISkinParam getSkinParam() { @@ -78,7 +78,8 @@ public class AnnotatedWorker { } private TextBlock addCaption(TextBlock original) { - if (DisplayPositionned.isNull(annotated.getCaption())) { + final DisplayPositionned caption = annotated.getCaption(); + if (DisplayPositionned.isNull(caption)) { return original; } final TextBlock text = getCaption(); @@ -87,14 +88,12 @@ public class AnnotatedWorker { } public TextBlock getCaption() { - if (DisplayPositionned.isNull(annotated.getCaption())) { + final DisplayPositionned caption = annotated.getCaption(); + if (DisplayPositionned.isNull(caption)) { return TextBlockUtils.empty(0, 0); } - return annotated - .getCaption() - .getDisplay() - .create(new FontConfiguration(getSkinParam(), FontParam.CAPTION, null), HorizontalAlignment.CENTER, - getSkinParam()); + return caption.getDisplay().create(new FontConfiguration(getSkinParam(), FontParam.CAPTION, null), + HorizontalAlignment.CENTER, getSkinParam()); } private TextBlock addTitle(TextBlock original) { @@ -110,22 +109,23 @@ public class AnnotatedWorker { } private TextBlock addHeaderAndFooter(TextBlock original) { - if (DisplayPositionned.isNull(annotated.getFooter()) && DisplayPositionned.isNull(annotated.getHeader())) { + final DisplayPositionned footer = annotated.getFooter(); + final DisplayPositionned header = annotated.getHeader(); + if (DisplayPositionned.isNull(footer) && DisplayPositionned.isNull(header)) { return original; } - final TextBlock textFooter = DisplayPositionned.isNull(annotated.getFooter()) ? null : annotated - .getFooter() - .getDisplay() - .create(new FontConfiguration(getSkinParam(), FontParam.FOOTER, null), - annotated.getFooter().getHorizontalAlignment(), getSkinParam()); - final TextBlock textHeader = DisplayPositionned.isNull(annotated.getHeader()) ? null : annotated - .getHeader() - .getDisplay() - .create(new FontConfiguration(getSkinParam(), FontParam.HEADER, null), - annotated.getHeader().getHorizontalAlignment(), getSkinParam()); + TextBlock textFooter = null; + if (DisplayPositionned.isNull(footer) == false) { + textFooter = footer.getDisplay().create(new FontConfiguration(getSkinParam(), FontParam.FOOTER, null), + footer.getHorizontalAlignment(), getSkinParam()); + } + TextBlock textHeader = null; + if (DisplayPositionned.isNull(header) == false) { + textHeader = header.getDisplay().create(new FontConfiguration(getSkinParam(), FontParam.HEADER, null), + header.getHorizontalAlignment(), getSkinParam()); + } - return new DecorateEntityImage(original, textHeader, annotated.getHeader().getHorizontalAlignment(), - textFooter, annotated.getFooter().getHorizontalAlignment()); + return DecorateEntityImage.addTopAndBottom(original, textHeader, header.getHorizontalAlignment(), textFooter, + footer.getHorizontalAlignment()); } - } diff --git a/src/net/sourceforge/plantuml/CornerParam.java b/src/net/sourceforge/plantuml/CornerParam.java index 453acff19..eb2271d98 100644 --- a/src/net/sourceforge/plantuml/CornerParam.java +++ b/src/net/sourceforge/plantuml/CornerParam.java @@ -36,7 +36,7 @@ package net.sourceforge.plantuml; public enum CornerParam { - DEFAULT, diagramBorder, titleBorder, rectangle, component; + DEFAULT, diagramBorder, titleBorder, rectangle, component, card, agent; public String getRoundKey() { if (this == DEFAULT) { diff --git a/src/net/sourceforge/plantuml/GeneratedImage.java b/src/net/sourceforge/plantuml/GeneratedImage.java index 1354014e5..ddf7cce78 100644 --- a/src/net/sourceforge/plantuml/GeneratedImage.java +++ b/src/net/sourceforge/plantuml/GeneratedImage.java @@ -45,4 +45,6 @@ public interface GeneratedImage extends Comparable { public int lineErrorRaw(); + public int getStatus(); + } diff --git a/src/net/sourceforge/plantuml/GeneratedImageImpl.java b/src/net/sourceforge/plantuml/GeneratedImageImpl.java index 6a3d3cd7c..0d92a7299 100644 --- a/src/net/sourceforge/plantuml/GeneratedImageImpl.java +++ b/src/net/sourceforge/plantuml/GeneratedImageImpl.java @@ -44,11 +44,17 @@ public class GeneratedImageImpl implements GeneratedImage { private final File pngFile; private final String description; private final BlockUml blockUml; + private final int status; - public GeneratedImageImpl(File pngFile, String description, BlockUml blockUml) { + public final int getStatus() { + return status; + } + + public GeneratedImageImpl(File pngFile, String description, BlockUml blockUml, int status) { this.blockUml = blockUml; this.pngFile = pngFile; this.description = description; + this.status = status; } public File getPngFile() { diff --git a/src/net/sourceforge/plantuml/ISourceFileReader.java b/src/net/sourceforge/plantuml/ISourceFileReader.java index 8de17e392..3be74d025 100644 --- a/src/net/sourceforge/plantuml/ISourceFileReader.java +++ b/src/net/sourceforge/plantuml/ISourceFileReader.java @@ -41,12 +41,13 @@ import java.util.List; public interface ISourceFileReader { public List getGeneratedImages() throws IOException; - + public List getBlocks(); public boolean hasError(); - + public void setFileFormatOption(FileFormatOption fileFormatOption); + public void setCheckMetadata(boolean checkMetadata); } diff --git a/src/net/sourceforge/plantuml/LineParam.java b/src/net/sourceforge/plantuml/LineParam.java index e16358aaa..9737d3780 100644 --- a/src/net/sourceforge/plantuml/LineParam.java +++ b/src/net/sourceforge/plantuml/LineParam.java @@ -55,7 +55,9 @@ public enum LineParam { titleBorder, diagramBorder, rectangleBorder, - componentBorder; + componentBorder, + cardBorder, + agentBorder; // sequenceBoxBorder(0.1); } diff --git a/src/net/sourceforge/plantuml/Option.java b/src/net/sourceforge/plantuml/Option.java index 47ab6fc77..adf127da2 100644 --- a/src/net/sourceforge/plantuml/Option.java +++ b/src/net/sourceforge/plantuml/Option.java @@ -78,6 +78,7 @@ public class Option { private int nbThreads = 0; private int ftpPort = -1; private boolean hideMetadata = false; + private boolean checkMetadata = false; private int imageIndex = 0; private File outputDir = null; @@ -319,6 +320,8 @@ public class Option { textProgressBar = true; } else if (s.equalsIgnoreCase("-nometadata")) { hideMetadata = true; + } else if (s.equalsIgnoreCase("-checkmetadata")) { + checkMetadata = true; } else if (s.equalsIgnoreCase("-pipeimageindex")) { i++; if (i == arg.length) { @@ -406,7 +409,7 @@ public class Option { } public final static String getPattern() { - return "(?i)^.*\\.(txt|tex|java|htm|html|c|h|cpp|apt|pu)$"; + return "(?i)^.*\\.(txt|tex|java|htm|html|c|h|cpp|apt|pu|pump|hpp|hh)$"; } public void setOutputDir(File f) { @@ -569,4 +572,8 @@ public class Option { this.filename = filename; } + public final boolean isCheckMetadata() { + return checkMetadata; + } + } diff --git a/src/net/sourceforge/plantuml/OptionPrint.java b/src/net/sourceforge/plantuml/OptionPrint.java index 8b7d5b6ea..5c0f3da7c 100644 --- a/src/net/sourceforge/plantuml/OptionPrint.java +++ b/src/net/sourceforge/plantuml/OptionPrint.java @@ -104,6 +104,7 @@ public class OptionPrint { System.out.println(" -e[x]clude pattern\tTo exclude files that match the provided pattern"); System.out.println(" -metadata\t\tTo retrieve PlantUML sources from PNG images"); System.out.println(" -nometadata\t\tTo NOT export metadata in PNG/SVG generated files"); + System.out.println(" -checkmetadata\t\tSkip PNG files that don't need to be regenerated"); System.out.println(" -version\t\tTo display information about PlantUML and Java versions"); System.out.println(" -checkversion\tTo check if a newer version is available for download"); System.out.println(" -v[erbose]\t\tTo have log information"); diff --git a/src/net/sourceforge/plantuml/PSystemError.java b/src/net/sourceforge/plantuml/PSystemError.java index 5c889ae4b..d87bc5d33 100644 --- a/src/net/sourceforge/plantuml/PSystemError.java +++ b/src/net/sourceforge/plantuml/PSystemError.java @@ -47,6 +47,7 @@ import java.util.Iterator; import java.util.LinkedHashSet; import java.util.List; +import net.sourceforge.plantuml.api.ImageDataAbstract; import net.sourceforge.plantuml.api.ImageDataSimple; import net.sourceforge.plantuml.asciiart.UmlCharArea; import net.sourceforge.plantuml.core.DiagramDescription; @@ -148,7 +149,9 @@ public class PSystemError extends AbstractPSystem { udrawable = addMessage(udrawable); } imageBuilder.setUDrawable(udrawable); - return imageBuilder.writeImageTOBEMOVED(fileFormat, seed(), os); + final ImageData imageData = imageBuilder.writeImageTOBEMOVED(fileFormat, seed(), os); + ((ImageDataAbstract) imageData).setStatus(400); + return imageData; } private TextBlockBackcolored getWelcome() throws IOException { diff --git a/src/net/sourceforge/plantuml/PSystemUtils.java b/src/net/sourceforge/plantuml/PSystemUtils.java index fbcf029d4..534ebe61e 100644 --- a/src/net/sourceforge/plantuml/PSystemUtils.java +++ b/src/net/sourceforge/plantuml/PSystemUtils.java @@ -51,14 +51,37 @@ import net.sourceforge.plantuml.core.ImageData; import net.sourceforge.plantuml.cucadiagram.CucaDiagram; import net.sourceforge.plantuml.graphic.HtmlColorUtils; import net.sourceforge.plantuml.html.CucaDiagramHtmlMaker; +import net.sourceforge.plantuml.png.MetadataTag; import net.sourceforge.plantuml.png.PngSplitter; import net.sourceforge.plantuml.project3.GanttDiagram; import net.sourceforge.plantuml.sequencediagram.SequenceDiagram; public class PSystemUtils { - public static List exportDiagrams(Diagram system, SuggestedFile suggestedFile, + public static List exportDiagrams(Diagram system, SuggestedFile suggested, FileFormatOption fileFormatOption) throws IOException { + return exportDiagrams(system, suggested, fileFormatOption, false); + } + + public static List exportDiagrams(Diagram system, SuggestedFile suggestedFile, + FileFormatOption fileFormatOption, boolean checkMetadata) throws IOException { + + final File existing = suggestedFile.getFile(0); + if (checkMetadata && existing.exists() && system.getNbImages() == 1) { + final MetadataTag tag = new MetadataTag(existing, "plantuml"); + final String previousMetadata = tag.getData(); + // final String version = Version.versionString(); + // System.out.println(system.getMetadata()); + // System.out.println(data); + // System.out.println(version); + // System.out.println(data.contains(version)); + final boolean sameMetadata = system.getMetadata().equals(previousMetadata); + if (sameMetadata) { + Log.info("Skipping " + existing.getAbsolutePath() + " because metadata has not changed."); + return Arrays.asList(new FileImageData(existing, null)); + } + } + if (system instanceof NewpagedDiagram) { return exportDiagramsNewpaged((NewpagedDiagram) system, suggestedFile, fileFormatOption); } diff --git a/src/net/sourceforge/plantuml/Run.java b/src/net/sourceforge/plantuml/Run.java index 1115036a6..a3dd9576d 100644 --- a/src/net/sourceforge/plantuml/Run.java +++ b/src/net/sourceforge/plantuml/Run.java @@ -406,6 +406,7 @@ public class Run { sourceFileReader = new SourceFileReader2(option.getDefaultDefines(f), f, option.getOutputFile(), option.getConfig(), option.getCharset(), option.getFileFormatOption()); } + sourceFileReader.setCheckMetadata(option.isCheckMetadata()); if (option.isComputeurl()) { for (BlockUml s : sourceFileReader.getBlocks()) { System.out.println(s.getEncodedUrl()); diff --git a/src/net/sourceforge/plantuml/SkinParam.java b/src/net/sourceforge/plantuml/SkinParam.java index c9df5ab12..b24ca1344 100644 --- a/src/net/sourceforge/plantuml/SkinParam.java +++ b/src/net/sourceforge/plantuml/SkinParam.java @@ -420,6 +420,15 @@ public class SkinParam implements ISkinParam { result.add("TabSize"); result.add("MaxAsciiMessageLength"); result.add("ColorArrowSeparationSpace"); + result.add("ResponseMessageBelowArrow"); + result.add("GenericDisplay"); + result.add("PathHoverColor"); + result.add("SwimlaneWidth"); + result.add("PageBorderColor"); + result.add("PageExternalColor"); + result.add("PageMargin"); + + for (FontParam p : EnumSet.allOf(FontParam.class)) { final String h = humanName(p.name()); result.add(h + "FontStyle"); diff --git a/src/net/sourceforge/plantuml/SourceFileReader.java b/src/net/sourceforge/plantuml/SourceFileReader.java index 434ca2ea7..de35dddd5 100644 --- a/src/net/sourceforge/plantuml/SourceFileReader.java +++ b/src/net/sourceforge/plantuml/SourceFileReader.java @@ -35,33 +35,14 @@ */ package net.sourceforge.plantuml; -import java.io.BufferedOutputStream; import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStream; -import java.io.PrintStream; -import java.io.Reader; -import java.io.UnsupportedEncodingException; -import java.util.ArrayList; import java.util.Collections; import java.util.List; -import java.util.Set; -import net.sourceforge.plantuml.core.Diagram; import net.sourceforge.plantuml.preproc.Defines; -import net.sourceforge.plantuml.preproc.FileWithSuffix; -public class SourceFileReader implements ISourceFileReader { - - private final File file; - private final File outputDirectory; - - private final BlockUmlBuilder builder; - private FileFormatOption fileFormatOption; +public class SourceFileReader extends SourceFileReaderAbstract implements ISourceFileReader { public SourceFileReader(File file) throws IOException { this(file, file.getAbsoluteFile().getParentFile()); @@ -105,15 +86,6 @@ public class SourceFileReader implements ISourceFileReader { .getParentFile(), file.getAbsolutePath()); } - public boolean hasError() { - for (final BlockUml b : builder.getBlockUmls()) { - if (b.getDiagram() instanceof PSystemError) { - return true; - } - } - return false; - } - private File getDirIfDirectory(String newName) { Log.info("Checking=" + newName); if (endsWithSlashOrAntislash(newName)) { @@ -161,107 +133,31 @@ public class SourceFileReader implements ISourceFileReader { } - public List getGeneratedImages() throws IOException { - Log.info("Reading file: " + file); - - int cpt = 0; - final List result = new ArrayList(); - - for (BlockUml blockUml : builder.getBlockUmls()) { - final String newName = blockUml.getFileOrDirname(); - SuggestedFile suggested = null; - if (newName != null) { - Log.info("name from block=" + newName); - final File dir = getDirIfDirectory(newName); - if (dir == null) { - Log.info(newName + " is not taken as a directory"); - suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, newName), - fileFormatOption.getFileFormat(), 0); - } else { - Log.info("We are going to create files in directory " + dir); - suggested = SuggestedFile.fromOutputFile(new File(dir, file.getName()), - fileFormatOption.getFileFormat(), 0); - } - Log.info("We are going to put data in " + suggested); + @Override + protected SuggestedFile getSuggestedFile(BlockUml blockUml) { + final String newName = blockUml.getFileOrDirname(); + SuggestedFile suggested = null; + if (newName != null) { + Log.info("name from block=" + newName); + final File dir = getDirIfDirectory(newName); + if (dir == null) { + Log.info(newName + " is not taken as a directory"); + suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, newName), + fileFormatOption.getFileFormat(), 0); + } else { + Log.info("We are going to create files in directory " + dir); + suggested = SuggestedFile.fromOutputFile(new File(dir, file.getName()), + fileFormatOption.getFileFormat(), 0); } - if (suggested == null) { - suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, file.getName()), - fileFormatOption.getFileFormat(), cpt++); - } - suggested.getParentFile().mkdirs(); - - final Diagram system; - try { - system = blockUml.getDiagram(); - } catch (Throwable t) { - final GeneratedImage image = new GeneratedImageImpl(suggested.getFile(0), "Crash Error", blockUml); - OutputStream os = null; - try { - os = new BufferedOutputStream(new FileOutputStream(suggested.getFile(0))); - UmlDiagram.exportDiagramError(os, t, fileFormatOption, 42, null, blockUml.getFlashData(), - UmlDiagram.getFailureText2(t, blockUml.getFlashData())); - } finally { - if (os != null) { - os.close(); - } - } - - return Collections.singletonList(image); - } - - final List exportDiagrams = PSystemUtils.exportDiagrams(system, suggested, fileFormatOption); - if (exportDiagrams.size() > 1) { - cpt += exportDiagrams.size() - 1; - } - OptionFlags.getInstance().logData(file, system); - - for (FileImageData fdata : exportDiagrams) { - final String desc = "[" + file.getName() + "] " + system.getDescription(); - final File f = fdata.getFile(); - if (OptionFlags.getInstance().isWord()) { - final String warnOrError = system.getWarningOrError(); - if (warnOrError != null) { - final String name = f.getName().substring(0, f.getName().length() - 4) + ".err"; - final File errorFile = new File(f.getParentFile(), name); - final PrintStream ps = new PrintStream(new FileOutputStream(errorFile)); - ps.print(warnOrError); - ps.close(); - } - } - final GeneratedImage generatedImage = new GeneratedImageImpl(f, desc, blockUml); - result.add(generatedImage); - } - + Log.info("We are going to put data in " + suggested); } - - Log.info("Number of image(s): " + result.size()); - - return Collections.unmodifiableList(result); - } - - private boolean endsWithSlashOrAntislash(String newName) { - return newName.endsWith("/") || newName.endsWith("\\"); - } - - public List getBlocks() { - return builder.getBlockUmls(); - } - - private Reader getReader(String charset) throws FileNotFoundException, UnsupportedEncodingException { - if (charset == null) { - Log.info("Using default charset"); - return new InputStreamReader(new FileInputStream(file)); + if (suggested == null) { + suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, file.getName()), + fileFormatOption.getFileFormat(), cpt++); } - Log.info("Using charset " + charset); - return new InputStreamReader(new FileInputStream(file), charset); + suggested.getParentFile().mkdirs(); + return suggested; } - public final void setFileFormatOption(FileFormatOption fileFormatOption) { - this.fileFormatOption = fileFormatOption; - } - - public final Set getIncludedFiles() { - return builder.getIncludedFiles(); - } } diff --git a/src/net/sourceforge/plantuml/SourceFileReader2.java b/src/net/sourceforge/plantuml/SourceFileReader2.java index aa7862333..1821a2ef0 100644 --- a/src/net/sourceforge/plantuml/SourceFileReader2.java +++ b/src/net/sourceforge/plantuml/SourceFileReader2.java @@ -36,28 +36,12 @@ package net.sourceforge.plantuml; import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.Reader; -import java.io.UnsupportedEncodingException; -import java.util.ArrayList; -import java.util.Collections; import java.util.List; -import java.util.Set; -import net.sourceforge.plantuml.core.Diagram; import net.sourceforge.plantuml.preproc.Defines; -import net.sourceforge.plantuml.preproc.FileWithSuffix; -public class SourceFileReader2 implements ISourceFileReader { - - private final File file; - private final File outputFile; - - private final BlockUmlBuilder builder; - private FileFormatOption fileFormatOption; +public class SourceFileReader2 extends SourceFileReaderAbstract implements ISourceFileReader { public SourceFileReader2(Defines defines, final File file, File outputFile, List config, String charset, FileFormatOption fileFormatOption) throws IOException { @@ -73,58 +57,10 @@ public class SourceFileReader2 implements ISourceFileReader { .getParentFile(), file.getAbsolutePath()); } - public boolean hasError() { - for (final BlockUml b : builder.getBlockUmls()) { - if (b.getDiagram() instanceof PSystemError) { - return true; - } - } - return false; - } - - public List getGeneratedImages() throws IOException { - Log.info("Reading file: " + file); - - final List result = new ArrayList(); - - for (BlockUml blockUml : builder.getBlockUmls()) { - final SuggestedFile suggested = SuggestedFile.fromOutputFile(outputFile, fileFormatOption.getFileFormat()); - - final Diagram system = blockUml.getDiagram(); - OptionFlags.getInstance().logData(file, system); - - for (FileImageData fdata : PSystemUtils.exportDiagrams(system, suggested, fileFormatOption)) { - final String desc = "[" + file.getName() + "] " + system.getDescription(); - final GeneratedImage generatedImage = new GeneratedImageImpl(fdata.getFile(), desc, blockUml); - result.add(generatedImage); - } - - } - - Log.info("Number of image(s): " + result.size()); - - return Collections.unmodifiableList(result); - } - - private Reader getReader(String charset) throws FileNotFoundException, UnsupportedEncodingException { - if (charset == null) { - Log.info("Using default charset"); - return new InputStreamReader(new FileInputStream(file)); - } - Log.info("Using charset " + charset); - return new InputStreamReader(new FileInputStream(file), charset); - } - - public final void setFileFormatOption(FileFormatOption fileFormatOption) { - this.fileFormatOption = fileFormatOption; - } - - public final Set getIncludedFiles2() { - return builder.getIncludedFiles(); - } - - public List getBlocks() { - return builder.getBlockUmls(); + @Override + protected SuggestedFile getSuggestedFile(BlockUml blockUml) { + final SuggestedFile suggested = SuggestedFile.fromOutputFile(outputFile, fileFormatOption.getFileFormat()); + return suggested; } } diff --git a/src/net/sourceforge/plantuml/ZSourceFileReaderAbstract.java b/src/net/sourceforge/plantuml/SourceFileReaderAbstract.java similarity index 91% rename from src/net/sourceforge/plantuml/ZSourceFileReaderAbstract.java rename to src/net/sourceforge/plantuml/SourceFileReaderAbstract.java index 52eec6965..24dc698d5 100644 --- a/src/net/sourceforge/plantuml/ZSourceFileReaderAbstract.java +++ b/src/net/sourceforge/plantuml/SourceFileReaderAbstract.java @@ -54,7 +54,7 @@ import java.util.Set; import net.sourceforge.plantuml.core.Diagram; import net.sourceforge.plantuml.preproc.FileWithSuffix; -public abstract class ZSourceFileReaderAbstract { +public abstract class SourceFileReaderAbstract { protected File file; protected File outputDirectory; @@ -62,6 +62,11 @@ public abstract class ZSourceFileReaderAbstract { protected BlockUmlBuilder builder; protected FileFormatOption fileFormatOption; + private boolean checkMetadata; + + public void setCheckMetadata(boolean checkMetadata) { + this.checkMetadata = checkMetadata; + } public boolean hasError() { for (final BlockUml b : builder.getBlockUmls()) { @@ -97,8 +102,8 @@ public abstract class ZSourceFileReaderAbstract { return newName.endsWith("/") || newName.endsWith("\\"); } - protected List getCrashedImage(BlockUml blockUml, Throwable t, File outputFile) throws IOException { - final GeneratedImage image = new GeneratedImageImpl(outputFile, "Crash Error", blockUml); + private List getCrashedImage(BlockUml blockUml, Throwable t, File outputFile) throws IOException { + final GeneratedImage image = new GeneratedImageImpl(outputFile, "Crash Error", blockUml, 503); OutputStream os = null; try { os = new BufferedOutputStream(new FileOutputStream(outputFile)); @@ -145,7 +150,7 @@ public abstract class ZSourceFileReaderAbstract { } OptionFlags.getInstance().logData(file, system); - final List exportDiagrams = PSystemUtils.exportDiagrams(system, suggested, fileFormatOption); + final List exportDiagrams = PSystemUtils.exportDiagrams(system, suggested, fileFormatOption, checkMetadata); if (exportDiagrams.size() > 1) { cpt += exportDiagrams.size() - 1; } @@ -154,7 +159,7 @@ public abstract class ZSourceFileReaderAbstract { final String desc = "[" + file.getName() + "] " + system.getDescription(); final File f = fdata.getFile(); exportWarnOrErrIfWord(f, system); - final GeneratedImage generatedImage = new GeneratedImageImpl(f, desc, blockUml); + final GeneratedImage generatedImage = new GeneratedImageImpl(f, desc, blockUml, fdata.getImageData().getStatus()); result.add(generatedImage); } diff --git a/src/net/sourceforge/plantuml/UmlDiagram.java b/src/net/sourceforge/plantuml/UmlDiagram.java index fd1a6f776..4c1b1504f 100644 --- a/src/net/sourceforge/plantuml/UmlDiagram.java +++ b/src/net/sourceforge/plantuml/UmlDiagram.java @@ -238,7 +238,7 @@ public abstract class UmlDiagram extends AbstractPSystem implements Diagram, Ann e.printStackTrace(); exportDiagramError(os, e, fileFormatOption, seed, null); } - return new ImageDataSimple(); + return ImageDataSimple.error(); } private void exportDiagramError(OutputStream os, Throwable exception, FileFormatOption fileFormat, long seed, diff --git a/src/net/sourceforge/plantuml/ZSourceFileReader.java b/src/net/sourceforge/plantuml/ZSourceFileReader.java deleted file mode 100644 index b10e088bf..000000000 --- a/src/net/sourceforge/plantuml/ZSourceFileReader.java +++ /dev/null @@ -1,162 +0,0 @@ -/* ======================================================================== - * PlantUML : a free UML diagram generator - * ======================================================================== - * - * (C) Copyright 2009-2017, Arnaud Roques - * - * Project Info: http://plantuml.com - * - * If you like this project or if you find it useful, you can support us at: - * - * http://plantuml.com/patreon (only 1$ per month!) - * http://plantuml.com/paypal - * - * This file is part of PlantUML. - * - * PlantUML is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * PlantUML distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public - * License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, - * USA. - * - * - * Original Author: Arnaud Roques - * - * - */ -package net.sourceforge.plantuml; - -import java.io.File; -import java.io.IOException; -import java.util.Collections; -import java.util.List; - -import net.sourceforge.plantuml.preproc.Defines; - -public class ZSourceFileReader extends ZSourceFileReaderAbstract implements ISourceFileReader { - - public ZSourceFileReader(File file) throws IOException { - this(file, file.getAbsoluteFile().getParentFile()); - } - - public ZSourceFileReader(File file, File outputDirectory, String charset) throws IOException { - this(Defines.createWithFileName(file), file, outputDirectory, Collections. emptyList(), charset, - new FileFormatOption(FileFormat.PNG)); - } - - public ZSourceFileReader(final File file, File outputDirectory) throws IOException { - this(Defines.createWithFileName(file), file, outputDirectory, Collections. emptyList(), null, - new FileFormatOption(FileFormat.PNG)); - } - - public ZSourceFileReader(final File file, File outputDirectory, FileFormatOption fileFormatOption) - throws IOException { - this(Defines.createWithFileName(file), file, outputDirectory, Collections. emptyList(), null, - fileFormatOption); - } - - public ZSourceFileReader(Defines defines, final File file, File outputDirectory, List config, - String charset, FileFormatOption fileFormatOption) throws IOException { - this.file = file; - this.fileFormatOption = fileFormatOption; - if (file.exists() == false) { - throw new IllegalArgumentException(); - } - FileSystem.getInstance().setCurrentDir(file.getAbsoluteFile().getParentFile()); - if (outputDirectory == null) { - outputDirectory = file.getAbsoluteFile().getParentFile(); - } else if (outputDirectory.isAbsolute() == false) { - outputDirectory = FileSystem.getInstance().getFile(outputDirectory.getPath()); - } - if (outputDirectory.exists() == false) { - outputDirectory.mkdirs(); - } - this.outputDirectory = outputDirectory; - - builder = new BlockUmlBuilder(config, charset, defines, getReader(charset), file.getAbsoluteFile() - .getParentFile(), file.getAbsolutePath()); - } - - private File getDirIfDirectory(String newName) { - Log.info("Checking=" + newName); - if (endsWithSlashOrAntislash(newName)) { - Log.info("It ends with / so it looks like a directory"); - newName = newName.substring(0, newName.length() - 1); - File f = new File(newName); - Log.info("f=" + f); - if (f.isAbsolute() == false) { - Log.info("It's relative, so let's change it"); - f = new File(outputDirectory, newName); - Log.info("f=" + f); - } - if (f.exists() == false) { - Log.info("It does not exist: let's create it"); - try { - f.mkdirs(); - } catch (Exception e) { - Log.info("Error " + e); - } - if (f.exists() && f.isDirectory()) { - Log.info("Creation ok"); - return f; - } - Log.info("We cannot create it"); - } else if (f.isDirectory() == false) { - Log.info("It exists, but is not a directory: we ignore it"); - return null; - } - return f; - - } - File f = new File(newName); - Log.info("f=" + f); - if (f.isAbsolute() == false) { - Log.info("Relative, so let's change it"); - f = new File(outputDirectory, newName); - Log.info("f=" + f); - } - if (f.exists() && f.isDirectory()) { - Log.info("It's an existing directory"); - return f; - } - Log.info("It's not a directory"); - return null; - - } - - @Override - protected SuggestedFile getSuggestedFile(BlockUml blockUml) { - final String newName = blockUml.getFileOrDirname(); - SuggestedFile suggested = null; - if (newName != null) { - Log.info("name from block=" + newName); - final File dir = getDirIfDirectory(newName); - if (dir == null) { - Log.info(newName + " is not taken as a directory"); - suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, newName), - fileFormatOption.getFileFormat(), 0); - } else { - Log.info("We are going to create files in directory " + dir); - suggested = SuggestedFile.fromOutputFile(new File(dir, file.getName()), - fileFormatOption.getFileFormat(), 0); - } - Log.info("We are going to put data in " + suggested); - } - if (suggested == null) { - suggested = SuggestedFile.fromOutputFile(new File(outputDirectory, file.getName()), - fileFormatOption.getFileFormat(), cpt++); - } - suggested.getParentFile().mkdirs(); - return suggested; - } - -} diff --git a/src/net/sourceforge/plantuml/ZSourceFileReader2.java b/src/net/sourceforge/plantuml/ZSourceFileReader2.java deleted file mode 100644 index e70780fff..000000000 --- a/src/net/sourceforge/plantuml/ZSourceFileReader2.java +++ /dev/null @@ -1,66 +0,0 @@ -/* ======================================================================== - * PlantUML : a free UML diagram generator - * ======================================================================== - * - * (C) Copyright 2009-2017, Arnaud Roques - * - * Project Info: http://plantuml.com - * - * If you like this project or if you find it useful, you can support us at: - * - * http://plantuml.com/patreon (only 1$ per month!) - * http://plantuml.com/paypal - * - * This file is part of PlantUML. - * - * PlantUML is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * PlantUML distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public - * License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, - * USA. - * - * - * Original Author: Arnaud Roques - * - * - */ -package net.sourceforge.plantuml; - -import java.io.File; -import java.io.IOException; -import java.util.List; - -import net.sourceforge.plantuml.preproc.Defines; - -public class ZSourceFileReader2 extends ZSourceFileReaderAbstract implements ISourceFileReader { - - public ZSourceFileReader2(Defines defines, final File file, File outputFile, List config, String charset, - FileFormatOption fileFormatOption) throws IOException { - this.file = file; - this.fileFormatOption = fileFormatOption; - this.outputFile = outputFile; - if (file.exists() == false) { - throw new IllegalArgumentException(); - } - FileSystem.getInstance().setCurrentDir(file.getAbsoluteFile().getParentFile()); - - builder = new BlockUmlBuilder(config, charset, defines, getReader(charset), file.getAbsoluteFile() - .getParentFile(), file.getAbsolutePath()); - } - - @Override - protected SuggestedFile getSuggestedFile(BlockUml blockUml) { - final SuggestedFile suggested = SuggestedFile.fromOutputFile(outputFile, fileFormatOption.getFileFormat()); - return suggested; - } - -} diff --git a/src/net/sourceforge/plantuml/activitydiagram3/command/CommandPartition3.java b/src/net/sourceforge/plantuml/activitydiagram3/command/CommandPartition3.java index 82c3d2575..336a85674 100644 --- a/src/net/sourceforge/plantuml/activitydiagram3/command/CommandPartition3.java +++ b/src/net/sourceforge/plantuml/activitydiagram3/command/CommandPartition3.java @@ -63,24 +63,27 @@ public class CommandPartition3 extends SingleLineCommand2 { new RegexLeaf("[%s]+"), // new RegexOptional(// new RegexConcat( // - color().getRegex(),// + color("BACK1").getRegex(),// new RegexLeaf("[%s]+"))), // - new RegexLeaf("TITLECOLOR", "(?:(#\\w+)[%s]+)?"), // new RegexLeaf("NAME", "([%g][^%g]+[%g]|\\S+)"), // + new RegexOptional(// + new RegexConcat( // + new RegexLeaf("[%s]+"), // + color("BACK2").getRegex())), // new RegexLeaf("[%s]*\\{?$")); } - private static ColorParser color() { - return ColorParser.simpleColor(ColorType.BACK); + private static ColorParser color(String id) { + return ColorParser.simpleColor(ColorType.BACK, id); } @Override protected CommandExecutionResult executeArg(ActivityDiagram3 diagram, RegexResult arg) { final String partitionTitle = StringUtils.eventuallyRemoveStartingAndEndingDoubleQuote(arg.get("NAME", 0)); - final HtmlColor titleColor = diagram.getSkinParam().getIHtmlColorSet() - .getColorIfValid(arg.get("TITLECOLOR", 0)); - final Colors colors = color().getColor(arg, diagram.getSkinParam().getIHtmlColorSet()); + final String b1 = arg.get("BACK1", 0); + final Colors colors = color(b1 == null ? "BACK2" : "BACK1").getColor(arg, + diagram.getSkinParam().getIHtmlColorSet()); final HtmlColor backColorInSkinparam = diagram.getSkinParam().getHtmlColor(ColorParam.partitionBackground, null, false); @@ -89,9 +92,10 @@ public class CommandPartition3 extends SingleLineCommand2 { backColor = colors.getColor(ColorType.BACK); } else { backColor = backColorInSkinparam; - } + final HtmlColor titleColor = colors.getColor(ColorType.HEADER); + // Warning : titleColor unused in FTileGroupW HtmlColor borderColor = diagram.getSkinParam().getHtmlColor(ColorParam.partitionBorder, null, false); if (borderColor == null) { borderColor = HtmlColorUtils.BLACK; diff --git a/src/net/sourceforge/plantuml/activitydiagram3/ftile/vcompact/FtileRepeat.java b/src/net/sourceforge/plantuml/activitydiagram3/ftile/vcompact/FtileRepeat.java index b6216db84..743699d81 100644 --- a/src/net/sourceforge/plantuml/activitydiagram3/ftile/vcompact/FtileRepeat.java +++ b/src/net/sourceforge/plantuml/activitydiagram3/ftile/vcompact/FtileRepeat.java @@ -125,7 +125,7 @@ class FtileRepeat extends AbstractFtile { final Ftile diamond1; if (backStart == null) { - diamond1 = new FtileDiamond(repeat.skinParam(), backColor, borderColor, swimlane); + diamond1 = new FtileDiamond(repeat.skinParam(), backColor, borderColor, repeat.getSwimlaneIn()); } else { diamond1 = backStart; } diff --git a/src/net/sourceforge/plantuml/project3/Solver2.java b/src/net/sourceforge/plantuml/api/ImageDataAbstract.java similarity index 64% rename from src/net/sourceforge/plantuml/project3/Solver2.java rename to src/net/sourceforge/plantuml/api/ImageDataAbstract.java index ff6de6bc7..ebc07bc43 100644 --- a/src/net/sourceforge/plantuml/project3/Solver2.java +++ b/src/net/sourceforge/plantuml/api/ImageDataAbstract.java @@ -30,27 +30,44 @@ * * * Original Author: Arnaud Roques - * + * * */ -package net.sourceforge.plantuml.project3; +package net.sourceforge.plantuml.api; -public class Solver2 { +import java.awt.geom.Dimension2D; - public Instant solveEnd(Instant start, int fullLoad, LoadPlanable plan) { - while (fullLoad > 0) { - fullLoad -= plan.getLoadAt(start); - start = start.increment(); - } - return start; +import net.sourceforge.plantuml.core.ImageData; + +public abstract class ImageDataAbstract implements ImageData { + + private final int width; + private final int height; + private int status; + + public ImageDataAbstract(int width, int height) { + this.width = width; + this.height = height; } - public Instant solveStart(Instant end, int fullLoad, LoadPlanable plan) { - while (fullLoad > 0) { - fullLoad -= plan.getLoadAt(end); - end = end.decrement(); - } - return end; + public ImageDataAbstract(Dimension2D dim) { + this((int) dim.getWidth(), (int) dim.getHeight()); + } + + public final int getWidth() { + return width; + } + + public final int getHeight() { + return height; + } + + public final int getStatus() { + return status; + } + + public final void setStatus(int status) { + this.status = status; } } diff --git a/src/net/sourceforge/plantuml/api/ImageDataComplex.java b/src/net/sourceforge/plantuml/api/ImageDataComplex.java index 621407f30..218f15a32 100644 --- a/src/net/sourceforge/plantuml/api/ImageDataComplex.java +++ b/src/net/sourceforge/plantuml/api/ImageDataComplex.java @@ -38,35 +38,18 @@ package net.sourceforge.plantuml.api; import java.awt.geom.Dimension2D; import net.sourceforge.plantuml.CMapData; -import net.sourceforge.plantuml.core.ImageData; -public class ImageDataComplex implements ImageData { +public class ImageDataComplex extends ImageDataAbstract { - private final Dimension2D info; private final CMapData cmap; private final String warningOrError; -// public ImageDataComplex(Dimension2D info, CMapData cmap) { -// this(info, cmap, null); -// } - public ImageDataComplex(Dimension2D info, CMapData cmap, String warningOrError) { - if (info==null) { - throw new IllegalArgumentException(); - } - this.info = info; + super(info); this.cmap = cmap; this.warningOrError = warningOrError; } - public int getWidth() { - return (int) info.getWidth(); - } - - public int getHeight() { - return (int) info.getHeight(); - } - public boolean containsCMapData() { return cmap != null && cmap.containsData(); } diff --git a/src/net/sourceforge/plantuml/api/ImageDataSimple.java b/src/net/sourceforge/plantuml/api/ImageDataSimple.java index f50316afb..d58b950b8 100644 --- a/src/net/sourceforge/plantuml/api/ImageDataSimple.java +++ b/src/net/sourceforge/plantuml/api/ImageDataSimple.java @@ -39,30 +39,18 @@ import java.awt.geom.Dimension2D; import net.sourceforge.plantuml.core.ImageData; -public class ImageDataSimple implements ImageData { - - private final int width; - private final int height; +public class ImageDataSimple extends ImageDataAbstract { public ImageDataSimple(int width, int height) { - this.width = width; - this.height = height; - } - - public ImageDataSimple() { - this(0, 0); + super(width, height); } public ImageDataSimple(Dimension2D dim) { - this((int) dim.getWidth(), (int) dim.getHeight()); + super(dim); } - public int getWidth() { - return width; - } - - public int getHeight() { - return height; + private ImageDataSimple() { + this(0, 0); } public boolean containsCMapData() { @@ -77,4 +65,14 @@ public class ImageDataSimple implements ImageData { return null; } + public static ImageData error() { + final ImageDataSimple result = new ImageDataSimple(); + result.setStatus(503); + return result; + } + + public static ImageData ok() { + return new ImageDataSimple(); + } + } diff --git a/src/net/sourceforge/plantuml/code/AsciiEncoderBase64.java b/src/net/sourceforge/plantuml/code/AsciiEncoderBase64.java new file mode 100644 index 000000000..d8974066b --- /dev/null +++ b/src/net/sourceforge/plantuml/code/AsciiEncoderBase64.java @@ -0,0 +1,147 @@ +/* ======================================================================== + * PlantUML : a free UML diagram generator + * ======================================================================== + * + * (C) Copyright 2009-2017, Arnaud Roques + * + * Project Info: http://plantuml.com + * + * If you like this project or if you find it useful, you can support us at: + * + * http://plantuml.com/patreon (only 1$ per month!) + * http://plantuml.com/paypal + * + * This file is part of PlantUML. + * + * PlantUML is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * PlantUML distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public + * License for more details. + * + * You should have received a copy of the GNU General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, + * USA. + * + * + * Original Author: Arnaud Roques + * + * + */ +package net.sourceforge.plantuml.code; + +public class AsciiEncoderBase64 implements URLEncoder { + + final static private char encode6bit[] = new char[64]; + final static private byte decode6bit[] = new byte[128]; + + static { + for (byte b = 0; b < 64; b++) { + encode6bit[b] = encode6bit(b); + decode6bit[encode6bit[b]] = b; + } + } + + public String encode(byte data[]) { + if (data == null) { + return ""; + } + final StringBuilder result = new StringBuilder((data.length * 4 + 2) / 3); + for (int i = 0; i < data.length; i += 3) { + append3bytes(result, data[i] & 0xFF, i + 1 < data.length ? data[i + 1] & 0xFF : 0, + i + 2 < data.length ? data[i + 2] & 0xFF : 0); + } + return result.toString(); + } + + public byte[] decode(String s) { + // if (s.length() % 4 != 0) { + // throw new IllegalArgumentException("Cannot decode " + s); + // } + final byte data[] = new byte[computeSize(s.length())]; + int pos = 0; + for (int i = 0; i < s.length(); i += 4) { + decode3bytes(data, pos, scharAt(s, i), scharAt(s, i + 1), scharAt(s, i + 2), scharAt(s, i + 3)); + pos += 3; + } + return data; + } + + private int computeSize(int length) { + // while (length % 4 != 0) { + // length++; + // } + final int r = length % 4; + if (r != 0) { + length += 4 - r; + } + // System.err.println("length=" + length); + // System.err.println("length1=" + (length % 4)); + // length += length % 4; + // System.err.println("length2=" + length); + assert length % 4 == 0 : "length=" + length; + return (length * 3 + 3) / 4; + } + + private char scharAt(String s, int i) { + if (i >= s.length()) { + return 'A'; + } + return s.charAt(i); + } + + public static int decode6bit(char c) { + return decode6bit[c]; + } + + public static char encode6bit(byte b) { + assert b >= 0 && b < 64; + if (b < 26) { + return (char) ('A' + b); + } + b -= 26; + if (b < 26) { + return (char) ('a' + b); + } + b -= 26; + if (b < 10) { + return (char) ('0' + b); + } + b -= 10; + if (b == 0) { + return '-'; + } + if (b == 1) { + return '_'; + } + assert false; + return '?'; + } + + private void append3bytes(StringBuilder sb, int b1, int b2, int b3) { + final int c1 = b1 >> 2; + final int c2 = ((b1 & 0x3) << 4) | (b2 >> 4); + final int c3 = ((b2 & 0xF) << 2) | (b3 >> 6); + final int c4 = b3 & 0x3F; + sb.append(encode6bit[c1 & 0x3F]); + sb.append(encode6bit[c2 & 0x3F]); + sb.append(encode6bit[c3 & 0x3F]); + sb.append(encode6bit[c4 & 0x3F]); + } + + private void decode3bytes(byte r[], int pos, char cc1, char cc2, char cc3, char cc4) { + final int c1 = decode6bit[cc1]; + final int c2 = decode6bit[cc2]; + final int c3 = decode6bit[cc3]; + final int c4 = decode6bit[cc4]; + r[pos] = (byte) ((c1 << 2) | (c2 >> 4)); + r[pos + 1] = (byte) (((c2 & 0x0F) << 4) | (c3 >> 2)); + r[pos + 2] = (byte) (((c3 & 0x3) << 6) | c4); + } + +} diff --git a/src/net/sourceforge/plantuml/code/CompressionZlib.java b/src/net/sourceforge/plantuml/code/CompressionZlib.java index 1c57f4176..cb1fc0b15 100644 --- a/src/net/sourceforge/plantuml/code/CompressionZlib.java +++ b/src/net/sourceforge/plantuml/code/CompressionZlib.java @@ -96,6 +96,9 @@ public class CompressionZlib implements Compression { } private byte[] tryDecompress(byte[] in, final int len) throws IOException { + if (len > 200000) { + throw new IOException("OutOfMemory"); + } // Decompress the bytes final byte[] tmp = new byte[len]; final Inflater decompresser = new Inflater(true); diff --git a/src/net/sourceforge/plantuml/code/TranscoderImpl.java b/src/net/sourceforge/plantuml/code/TranscoderImpl.java index 46c853d2d..308fa8726 100644 --- a/src/net/sourceforge/plantuml/code/TranscoderImpl.java +++ b/src/net/sourceforge/plantuml/code/TranscoderImpl.java @@ -43,11 +43,11 @@ public class TranscoderImpl implements Transcoder { private final URLEncoder urlEncoder; private final StringCompressor stringCompressor; - public TranscoderImpl() { + private TranscoderImpl() { this(new AsciiEncoder(), new StringCompressorNone(), new CompressionHuffman()); } - public TranscoderImpl(Compression compression) { + private TranscoderImpl(Compression compression) { this(new AsciiEncoder(), new StringCompressorNone(), compression); } diff --git a/src/net/sourceforge/plantuml/code/TranscoderSmart.java b/src/net/sourceforge/plantuml/code/TranscoderSmart.java index 6f2fa37cf..fa6c1bc8d 100644 --- a/src/net/sourceforge/plantuml/code/TranscoderSmart.java +++ b/src/net/sourceforge/plantuml/code/TranscoderSmart.java @@ -40,12 +40,16 @@ import java.io.IOException; public class TranscoderSmart implements Transcoder { private final Transcoder oldOne = new TranscoderImpl(new AsciiEncoder(), new CompressionHuffman()); + private final Transcoder zlibBase64 = new TranscoderImpl(new AsciiEncoderBase64(), new CompressionZlib()); private final Transcoder zlib = new TranscoderImpl(new AsciiEncoder(), new CompressionZlib()); - private final Transcoder brotli = new TranscoderImpl(new AsciiEncoder(), new CompressionBrotli()); + private final Transcoder brotliBase64 = new TranscoderImpl(new AsciiEncoderBase64(), new CompressionBrotli()); public String decode(String code) throws IOException { if (code.startsWith("0")) { - return brotli.decode(code.substring(1)); + return zlibBase64.decode(code.substring(1)); + } + if (code.startsWith("1")) { + return brotliBase64.decode(code.substring(1)); } try { return zlib.decode(code); diff --git a/src/net/sourceforge/plantuml/command/CommandScale.java b/src/net/sourceforge/plantuml/command/CommandScale.java index 85429d0d8..dc630acfa 100644 --- a/src/net/sourceforge/plantuml/command/CommandScale.java +++ b/src/net/sourceforge/plantuml/command/CommandScale.java @@ -49,8 +49,15 @@ public class CommandScale extends SingleLineCommand { @Override protected CommandExecutionResult executeArg(AbstractPSystem diagram, List arg) { double scale = Double.parseDouble(arg.get(0)); + if (scale == 0) { + return CommandExecutionResult.error("Scale cannot be zero"); + } if (arg.get(1) != null) { - scale /= Double.parseDouble(arg.get(1)); + final double div = Double.parseDouble(arg.get(1)); + if (div == 0) { + return CommandExecutionResult.error("Scale cannot be zero"); + } + scale /= div; } diagram.setScale(new ScaleSimple(scale)); return CommandExecutionResult.ok(); diff --git a/src/net/sourceforge/plantuml/core/ImageData.java b/src/net/sourceforge/plantuml/core/ImageData.java index d83f84522..22fbe4dc1 100644 --- a/src/net/sourceforge/plantuml/core/ImageData.java +++ b/src/net/sourceforge/plantuml/core/ImageData.java @@ -84,6 +84,8 @@ public interface ImageData { public String getCMapData(String nameId); public String getWarningOrError(); + + public int getStatus(); } diff --git a/src/net/sourceforge/plantuml/cucadiagram/CucaDiagram.java b/src/net/sourceforge/plantuml/cucadiagram/CucaDiagram.java index 6a6ce3cdb..3a861aeee 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/CucaDiagram.java +++ b/src/net/sourceforge/plantuml/cucadiagram/CucaDiagram.java @@ -289,7 +289,6 @@ public abstract class CucaDiagram extends UmlDiagram implements GroupHierarchy, this.horizontalPages = horizontalPages; } - final public int getVerticalPages() { return verticalPages; } @@ -297,14 +296,12 @@ public abstract class CucaDiagram extends UmlDiagram implements GroupHierarchy, final public void setVerticalPages(int verticalPages) { this.verticalPages = verticalPages; } - + @Override public int getNbImages() { return this.horizontalPages * this.verticalPages; } - - // final public List createPng2(File pngFile) throws IOException, // InterruptedException { // final CucaDiagramPngMaker3 maker = new CucaDiagramPngMaker3(this); @@ -357,17 +354,17 @@ public abstract class CucaDiagram extends UmlDiagram implements GroupHierarchy, } catch (Throwable t) { t.printStackTrace(new PrintStream(os)); } - return new ImageDataSimple(); + return ImageDataSimple.ok(); } if (fileFormat.name().startsWith("XMI")) { createFilesXmi(os, fileFormat); - return new ImageDataSimple(); + return ImageDataSimple.ok(); } if (fileFormat == FileFormat.SCXML) { createFilesScxml(os); - return new ImageDataSimple(); + return ImageDataSimple.ok(); } if (getUmlDiagramType() == UmlDiagramType.COMPOSITE) { @@ -382,7 +379,7 @@ public abstract class CucaDiagram extends UmlDiagram implements GroupHierarchy, final ImageData result = maker.createFile(os, getDotStrings(), fileFormatOption); if (result == null) { - return new ImageDataSimple(); + return ImageDataSimple.error(); } this.warningOrError = result.getWarningOrError(); return result; diff --git a/src/net/sourceforge/plantuml/cucadiagram/Link.java b/src/net/sourceforge/plantuml/cucadiagram/Link.java index a4d92f67d..f7e76abf8 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/Link.java +++ b/src/net/sourceforge/plantuml/cucadiagram/Link.java @@ -119,9 +119,9 @@ public class Link implements Hideable, Removeable { this.type = type; if (Display.isNull(label)) { this.label = Display.NULL; -// } else if (doWeHaveToRemoveUrlAtStart(label)) { -// this.url = label.initUrl(); -// this.label = label.removeHeadingUrl(url).manageGuillemet(); + // } else if (doWeHaveToRemoveUrlAtStart(label)) { + // this.url = label.initUrl(); + // this.label = label.removeHeadingUrl(url).manageGuillemet(); } else { this.label = label.manageGuillemet(); } @@ -142,16 +142,16 @@ public class Link implements Hideable, Removeable { // } } -// private static boolean doWeHaveToRemoveUrlAtStart(Display label) { -// if (label.size() == 0) { -// return false; -// } -// final String s = label.get(0).toString(); -// if (s.matches("^\\[\\[\\S+\\]\\].+$")) { -// return true; -// } -// return false; -// } + // private static boolean doWeHaveToRemoveUrlAtStart(Display label) { + // if (label.size() == 0) { + // return false; + // } + // final String s = label.get(0).toString(); + // if (s.matches("^\\[\\[\\S+\\]\\].+$")) { + // return true; + // } + // return false; + // } public Link getInv() { // if (getLength() == 1) { @@ -392,6 +392,20 @@ public class Link implements Hideable, Removeable { return false; } +// public boolean containsWithDecors(ILeaf leaf) { +// LinkType linkType = this.getType(); +// if (isInverted()) { +// linkType = linkType.getInversed(); +// } +// if (getEntity2() == leaf && linkType.getDecor1() != LinkDecor.NONE) { +// return true; +// } +// if (getEntity1() == leaf && linkType.getDecor2() != LinkDecor.NONE) { +// return true; +// } +// return false; +// } + public IEntity getOther(IEntity entity) { if (getEntity1() == entity) { return getEntity2(); diff --git a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersion.java b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersion.java index 4b9f04905..6f0b5497f 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersion.java +++ b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersion.java @@ -40,10 +40,10 @@ public interface GraphvizVersion { public boolean useProtectionWhenThereALinkFromOrToGroup(); - public boolean modeSafe(); + public boolean useXLabelInsteadOfLabel(); public boolean isVizjs(); - - // COMMON, V2_34_0 + + public boolean ignoreHorizontalLinks(); } diff --git a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java index b8df542c2..968134e00 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java +++ b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java @@ -53,13 +53,17 @@ public class GraphvizVersionFinder { return true; } - public boolean modeSafe() { + public boolean useXLabelInsteadOfLabel() { return false; } public boolean isVizjs() { return false; } + + public boolean ignoreHorizontalLinks() { + return false; + } }; public GraphvizVersionFinder(File dotExe) { @@ -89,7 +93,7 @@ public class GraphvizVersionFinder { return true; } - public boolean modeSafe() { + public boolean useXLabelInsteadOfLabel() { return false; } @@ -97,6 +101,13 @@ public class GraphvizVersionFinder { return false; } + public boolean ignoreHorizontalLinks() { + if (v == 230) { + return true; + } + return false; + } + }; } diff --git a/src/net/sourceforge/plantuml/descdiagram/command/CommandCreateElementFull.java b/src/net/sourceforge/plantuml/descdiagram/command/CommandCreateElementFull.java index cc6dee34e..467b3e9bb 100644 --- a/src/net/sourceforge/plantuml/descdiagram/command/CommandCreateElementFull.java +++ b/src/net/sourceforge/plantuml/descdiagram/command/CommandCreateElementFull.java @@ -109,9 +109,9 @@ public class CommandCreateElementFull extends SingleLineCommand2\\>))?"), // new RegexLeaf("[%s]*as[%s]+"), // new RegexLeaf("CODE1", "([^#%s{}]+)") // @@ -81,7 +81,7 @@ public class CommandPackageWithUSymbol extends SingleLineCommand2\\>))?"), // new RegexLeaf("[%s]*as[%s]+"), // - new RegexLeaf("DISPLAY2", "([%g][^%g]+[%g])") // + new RegexLeaf("DISPLAY2", "([%g].+?[%g])") // ), // new RegexConcat( // new RegexLeaf("DISPLAY3", "([^#%s{}%g]+)"), // diff --git a/src/net/sourceforge/plantuml/directdot/PSystemDot.java b/src/net/sourceforge/plantuml/directdot/PSystemDot.java index 5c778404b..ae0971a02 100644 --- a/src/net/sourceforge/plantuml/directdot/PSystemDot.java +++ b/src/net/sourceforge/plantuml/directdot/PSystemDot.java @@ -75,21 +75,22 @@ public class PSystemDot extends AbstractPSystem { if (graphviz.getExeState() != ExeState.OK) { final TextBlock result = GraphicStrings.createForError( Arrays.asList("There is an issue with your Dot/Graphviz installation"), false); - UGraphicUtils.writeImage(os, null, fileFormat, seed(), new ColorMapperIdentity(), - HtmlColorUtils.WHITE, result); - return new ImageDataSimple(); + UGraphicUtils.writeImage(os, null, fileFormat, seed(), new ColorMapperIdentity(), HtmlColorUtils.WHITE, + result); + return ImageDataSimple.error(); } final CounterOutputStream counter = new CounterOutputStream(os); final ProcessState state = graphviz.createFile3(counter); - if (state.differs(ProcessState.TERMINATED_OK())) { - throw new IllegalStateException("Timeout1 " + state); - } - if (counter.getLength() == 0) { + // if (state.differs(ProcessState.TERMINATED_OK())) { + // throw new IllegalStateException("Timeout1 " + state); + // } + if (counter.getLength() == 0 || state.differs(ProcessState.TERMINATED_OK())) { final TextBlock result = GraphicStrings.createForError(Arrays.asList("Graphivz has crashed"), false); - UGraphicUtils.writeImage(os, null, fileFormat, seed(), new ColorMapperIdentity(), - HtmlColorUtils.WHITE, result); + UGraphicUtils.writeImage(os, null, fileFormat, seed(), new ColorMapperIdentity(), HtmlColorUtils.WHITE, + result); + return ImageDataSimple.error(); } - return new ImageDataSimple(); + return ImageDataSimple.ok(); } } diff --git a/src/net/sourceforge/plantuml/ditaa/PSystemDitaa.java b/src/net/sourceforge/plantuml/ditaa/PSystemDitaa.java index 3a4caa854..6c1644542 100644 --- a/src/net/sourceforge/plantuml/ditaa/PSystemDitaa.java +++ b/src/net/sourceforge/plantuml/ditaa/PSystemDitaa.java @@ -69,8 +69,8 @@ public class PSystemDitaa extends AbstractPSystem { } PSystemDitaa add(String line) { - return new PSystemDitaa(data + line + BackSlash.NEWLINE, processingOptions.performSeparationOfCommonEdges(), dropShadows, - scale); + return new PSystemDitaa(data + line + BackSlash.NEWLINE, processingOptions.performSeparationOfCommonEdges(), + dropShadows, scale); } public DiagramDescription getDescription() { @@ -82,7 +82,7 @@ public class PSystemDitaa extends AbstractPSystem { throws IOException { if (fileFormat.getFileFormat() == FileFormat.ATXT) { os.write(getSource().getPlainString().getBytes()); - return new ImageDataSimple(); + return ImageDataSimple.ok(); } // ditaa can only export png so file format is mostly ignored final ConversionOptions options = new ConversionOptions(); diff --git a/src/net/sourceforge/plantuml/donors/PSystemDonors.java b/src/net/sourceforge/plantuml/donors/PSystemDonors.java index 830e25cf4..51f3cb1d3 100644 --- a/src/net/sourceforge/plantuml/donors/PSystemDonors.java +++ b/src/net/sourceforge/plantuml/donors/PSystemDonors.java @@ -46,6 +46,7 @@ import java.util.StringTokenizer; import net.sourceforge.plantuml.AbstractPSystem; import net.sourceforge.plantuml.BackSlash; import net.sourceforge.plantuml.FileFormatOption; +import net.sourceforge.plantuml.code.AsciiEncoder; import net.sourceforge.plantuml.code.CompressionBrotli; import net.sourceforge.plantuml.code.Transcoder; import net.sourceforge.plantuml.code.TranscoderImpl; @@ -126,7 +127,7 @@ public class PSystemDonors extends AbstractPSystem { private List getDonors() throws IOException { final List lines = new ArrayList(); - final Transcoder t = new TranscoderImpl(new CompressionBrotli()); + final Transcoder t = new TranscoderImpl(new AsciiEncoder(), new CompressionBrotli()); final String s = t.decode(DONORS).replace('*', '.'); final StringTokenizer st = new StringTokenizer(s, BackSlash.NEWLINE); while (st.hasMoreTokens()) { diff --git a/src/net/sourceforge/plantuml/flowdiagram/FlowDiagram.java b/src/net/sourceforge/plantuml/flowdiagram/FlowDiagram.java index 8965621df..4b857a7b7 100644 --- a/src/net/sourceforge/plantuml/flowdiagram/FlowDiagram.java +++ b/src/net/sourceforge/plantuml/flowdiagram/FlowDiagram.java @@ -126,9 +126,9 @@ public class FlowDiagram extends UmlDiagram implements TextBlock { @Override protected ImageData exportDiagramInternal(OutputStream os, int index, FileFormatOption fileFormatOption) throws IOException { - UGraphicUtils.writeImage(os, null, fileFormatOption, seed(), new ColorMapperIdentity(), - HtmlColorUtils.WHITE, this); - return new ImageDataSimple(); + UGraphicUtils.writeImage(os, null, fileFormatOption, seed(), new ColorMapperIdentity(), HtmlColorUtils.WHITE, + this); + return ImageDataSimple.ok(); } public void drawU(UGraphic ug) { @@ -210,7 +210,7 @@ public class FlowDiagram extends UmlDiagram implements TextBlock { final MinMaxGolem minMax = getMinMax(); return new Dimension2DDouble(minMax.getWidth() * SINGLE_SIZE_X, minMax.getHeight() * SINGLE_SIZE_Y); } - + public MinMax getMinMax(StringBounder stringBounder) { throw new UnsupportedOperationException(); } diff --git a/src/net/sourceforge/plantuml/graphic/SkinParameter.java b/src/net/sourceforge/plantuml/graphic/SkinParameter.java index 421f799ad..029f6d799 100644 --- a/src/net/sourceforge/plantuml/graphic/SkinParameter.java +++ b/src/net/sourceforge/plantuml/graphic/SkinParameter.java @@ -79,7 +79,7 @@ public class SkinParameter { CornerParam.component); public static final SkinParameter AGENT = new SkinParameter("AGENT", ColorParam.agentBackground, - ColorParam.agentBorder, FontParam.AGENT, FontParam.AGENT_STEREOTYPE); + ColorParam.agentBorder, FontParam.AGENT, FontParam.AGENT_STEREOTYPE, LineParam.agentBorder, CornerParam.agent); public static final SkinParameter FOLDER = new SkinParameter("FOLDER", ColorParam.folderBackground, ColorParam.folderBorder, FontParam.FOLDER, FontParam.FOLDER_STEREOTYPE); @@ -91,7 +91,8 @@ public class SkinParameter { ColorParam.packageBorder, FontParam.FOLDER, FontParam.FOLDER_STEREOTYPE); public static final SkinParameter CARD = new SkinParameter("CARD", ColorParam.cardBackground, - ColorParam.cardBorder, FontParam.CARD, FontParam.CARD_STEREOTYPE); + ColorParam.cardBorder, FontParam.CARD, FontParam.CARD_STEREOTYPE, LineParam.cardBorder, + CornerParam.card); public static final SkinParameter RECTANGLE = new SkinParameter("RECTANGLE", ColorParam.rectangleBackground, ColorParam.rectangleBorder, FontParam.RECTANGLE, FontParam.RECTANGLE_STEREOTYPE, LineParam.rectangleBorder, diff --git a/src/net/sourceforge/plantuml/jdot/CucaDiagramFileMakerJDot.java b/src/net/sourceforge/plantuml/jdot/CucaDiagramFileMakerJDot.java index 2649655e7..7e2dbc547 100644 --- a/src/net/sourceforge/plantuml/jdot/CucaDiagramFileMakerJDot.java +++ b/src/net/sourceforge/plantuml/jdot/CucaDiagramFileMakerJDot.java @@ -449,7 +449,7 @@ public class CucaDiagramFileMakerJDot implements CucaDiagramFileMaker { } catch (Throwable e) { UmlDiagram.exportDiagramError(os, e, fileFormatOption, diagram.seed(), diagram.getMetadata(), diagram.getFlashData(), getFailureText3(e)); - return new ImageDataSimple(); + return ImageDataSimple.error(); } finally { Z.close(); } diff --git a/src/net/sourceforge/plantuml/postit/PostItDiagram.java b/src/net/sourceforge/plantuml/postit/PostItDiagram.java index 77fac5bc4..9e8ef9b43 100644 --- a/src/net/sourceforge/plantuml/postit/PostItDiagram.java +++ b/src/net/sourceforge/plantuml/postit/PostItDiagram.java @@ -85,7 +85,7 @@ public class PostItDiagram extends UmlDiagram { final UGraphicEps eps = (UGraphicEps) ug; os.write(eps.getEPSCode().getBytes()); } - return new ImageDataSimple(); + return ImageDataSimple.ok(); } public DiagramDescription getDescription() { diff --git a/src/net/sourceforge/plantuml/project/PSystemProject.java b/src/net/sourceforge/plantuml/project/PSystemProject.java index a0f26fc08..bb20a6c4e 100644 --- a/src/net/sourceforge/plantuml/project/PSystemProject.java +++ b/src/net/sourceforge/plantuml/project/PSystemProject.java @@ -82,8 +82,9 @@ public class PSystemProject extends AbstractPSystem { final BufferedImage im = createImage(diagram); PngIO.write(im, os, fileFormatOption.isWithMetadata() ? getMetadata() : null, 96); } else if (fileFormat == FileFormat.SVG) { - final UGraphicSvg svg = new UGraphicSvg(true, new Dimension2DDouble(0, 0), colorMapper, StringUtils.getAsHtml(background), false, 1.0, - fileFormatOption.getSvgLinkTarget(), fileFormatOption.getHoverColor(), seed()); + final UGraphicSvg svg = new UGraphicSvg(true, new Dimension2DDouble(0, 0), colorMapper, + StringUtils.getAsHtml(background), false, 1.0, fileFormatOption.getSvgLinkTarget(), + fileFormatOption.getHoverColor(), seed()); diagram.draw(svg, 0, 0); svg.createXml(os, fileFormatOption.isWithMetadata() ? getMetadata() : null); } else if (fileFormat == FileFormat.EPS) { @@ -97,7 +98,7 @@ public class PSystemProject extends AbstractPSystem { } else { throw new UnsupportedOperationException(); } - return new ImageDataSimple(); + return ImageDataSimple.ok(); } private BufferedImage createImage(GanttDiagramUnused diagram) { diff --git a/src/net/sourceforge/plantuml/project2/PSystemProject2.java b/src/net/sourceforge/plantuml/project2/PSystemProject2.java index b5b53ccc4..926e1d1f0 100644 --- a/src/net/sourceforge/plantuml/project2/PSystemProject2.java +++ b/src/net/sourceforge/plantuml/project2/PSystemProject2.java @@ -81,8 +81,9 @@ public class PSystemProject2 extends AbstractPSystem { final BufferedImage im = createImage(diagram); PngIO.write(im, os, fileFormatOption.isWithMetadata() ? getMetadata() : null, 96); } else if (fileFormat == FileFormat.SVG) { - final UGraphicSvg svg = new UGraphicSvg(true, new Dimension2DDouble(0, 0),colorMapper, StringUtils.getAsHtml(background), false, 1.0, - fileFormatOption.getSvgLinkTarget(), fileFormatOption.getHoverColor(), seed()); + final UGraphicSvg svg = new UGraphicSvg(true, new Dimension2DDouble(0, 0), colorMapper, + StringUtils.getAsHtml(background), false, 1.0, fileFormatOption.getSvgLinkTarget(), + fileFormatOption.getHoverColor(), seed()); diagram.draw(svg, 0, 0); svg.createXml(os, fileFormatOption.isWithMetadata() ? getMetadata() : null); } else if (fileFormat == FileFormat.EPS) { @@ -96,7 +97,7 @@ public class PSystemProject2 extends AbstractPSystem { } else { throw new UnsupportedOperationException(); } - return new ImageDataSimple(); + return ImageDataSimple.ok(); } private BufferedImage createImage(GanttDiagram2 diagram) { diff --git a/src/net/sourceforge/plantuml/project3/Solver3.java b/src/net/sourceforge/plantuml/project3/Solver3.java index fc438ee7d..70da38035 100644 --- a/src/net/sourceforge/plantuml/project3/Solver3.java +++ b/src/net/sourceforge/plantuml/project3/Solver3.java @@ -51,7 +51,13 @@ public class Solver3 { } public void setData(TaskAttribute attribute, Value value) { - values.remove(attribute); + final Value previous = values.remove(attribute); + if (previous != null && attribute == TaskAttribute.START) { + final Instant previousInstant = (Instant) previous; + if (previousInstant.compareTo((Instant) value) > 0) { + value = previous; + } + } values.put(attribute, value); if (values.size() > 2) { removeFirstElement(); diff --git a/src/net/sourceforge/plantuml/salt/PSystemSalt.java b/src/net/sourceforge/plantuml/salt/PSystemSalt.java index 78476dac7..a9071d8bf 100644 --- a/src/net/sourceforge/plantuml/salt/PSystemSalt.java +++ b/src/net/sourceforge/plantuml/salt/PSystemSalt.java @@ -94,7 +94,7 @@ public class PSystemSalt extends AbstractPSystem { } catch (Exception e) { e.printStackTrace(); UmlDiagram.exportDiagramError(os, e, fileFormat, seed, getMetadata(), "none", new ArrayList()); - return new ImageDataSimple(); + return ImageDataSimple.error(); } } diff --git a/src/net/sourceforge/plantuml/sequencediagram/graphic/ArrowAndParticipant.java b/src/net/sourceforge/plantuml/sequencediagram/graphic/ArrowAndParticipant.java index 3a1253ca2..99a9a9984 100644 --- a/src/net/sourceforge/plantuml/sequencediagram/graphic/ArrowAndParticipant.java +++ b/src/net/sourceforge/plantuml/sequencediagram/graphic/ArrowAndParticipant.java @@ -46,12 +46,14 @@ class ArrowAndParticipant extends Arrow implements InGroupable { private final Arrow arrow; private final ParticipantBox participantBox; + private final double paddingParticipant; public ArrowAndParticipant(StringBounder stringBounder, Arrow arrow, ParticipantBox participantBox, double paddingParticipant) { super(arrow.getStartingY(), arrow.getSkin(), arrow.getArrowComponent(), arrow.getUrl()); this.arrow = arrow; this.participantBox = participantBox; + this.paddingParticipant = paddingParticipant; arrow.setPaddingArrowHead(participantBox.getPreferredWidth(stringBounder) / 2 - paddingParticipant); } @@ -95,7 +97,7 @@ class ArrowAndParticipant extends Arrow implements InGroupable { arrow.drawInternalU(ug, maxX, context); } else { final double boxWidth = participantBox.getPreferredWidth(ug.getStringBounder()); - arrow.drawInternalU(ug.apply(new UTranslate(boxWidth / 2, 0)), maxX, context); + arrow.drawInternalU(ug.apply(new UTranslate(boxWidth / 2 - paddingParticipant, 0)), maxX, context); } final double arrowHeight = arrow.getPreferredHeight(ug.getStringBounder()); diff --git a/src/net/sourceforge/plantuml/skin/rose/Rose.java b/src/net/sourceforge/plantuml/skin/rose/Rose.java index 4f77cdd7b..dcdcc680a 100644 --- a/src/net/sourceforge/plantuml/skin/rose/Rose.java +++ b/src/net/sourceforge/plantuml/skin/rose/Rose.java @@ -149,53 +149,53 @@ public class Rose implements Skin { } if (type == ComponentType.BOUNDARY_HEAD) { return new ComponentRoseBoundary(getSymbolContext(param, ColorParam.boundaryBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.BOUNDARY), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, + FontParam.BOUNDARY_STEREOTYPE)); } if (type == ComponentType.BOUNDARY_TAIL) { return new ComponentRoseBoundary(getSymbolContext(param, ColorParam.boundaryBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.BOUNDARY), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, + FontParam.BOUNDARY_STEREOTYPE)); } if (type == ComponentType.CONTROL_HEAD) { return new ComponentRoseControl(getSymbolContext(param, ColorParam.controlBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.CONTROL), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, + FontParam.CONTROL_STEREOTYPE)); } if (type == ComponentType.CONTROL_TAIL) { return new ComponentRoseControl(getSymbolContext(param, ColorParam.controlBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.CONTROL), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, + FontParam.CONTROL_STEREOTYPE)); } if (type == ComponentType.ENTITY_HEAD) { return new ComponentRoseEntity(getSymbolContext(param, ColorParam.entityBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.ENTITY), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, + FontParam.ENTITY_STEREOTYPE)); } if (type == ComponentType.ENTITY_TAIL) { return new ComponentRoseEntity(getSymbolContext(param, ColorParam.entityBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.ENTITY), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, + FontParam.ENTITY_STEREOTYPE)); } if (type == ComponentType.QUEUE_HEAD) { return new ComponentRoseQueue(getSymbolContext(param, ColorParam.entityBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.QUEUE), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, + FontParam.QUEUE_STEREOTYPE)); } if (type == ComponentType.QUEUE_TAIL) { return new ComponentRoseQueue(getSymbolContext(param, ColorParam.entityBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.QUEUE), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, + FontParam.QUEUE_STEREOTYPE)); } if (type == ComponentType.DATABASE_HEAD) { return new ComponentRoseDatabase(getSymbolContext(param, ColorParam.databaseBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.DATABASE), stringsToDisplay, true, param, newFontForStereotype, getFontColor(param, + FontParam.DATABASE_STEREOTYPE)); } if (type == ComponentType.DATABASE_TAIL) { return new ComponentRoseDatabase(getSymbolContext(param, ColorParam.databaseBorder), getUFont2(param, - FontParam.ACTOR), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, - FontParam.SEQUENCE_STEREOTYPE)); + FontParam.DATABASE), stringsToDisplay, false, param, newFontForStereotype, getFontColor(param, + FontParam.DATABASE_STEREOTYPE)); } if (type == ComponentType.NOTE) { return new ComponentRoseNote(getSymbolContext(param, ColorParam.noteBorder), getUFont2(param, diff --git a/src/net/sourceforge/plantuml/svek/Cluster.java b/src/net/sourceforge/plantuml/svek/Cluster.java index 4842df73c..9e85611b3 100644 --- a/src/net/sourceforge/plantuml/svek/Cluster.java +++ b/src/net/sourceforge/plantuml/svek/Cluster.java @@ -582,7 +582,8 @@ public class Cluster implements Moveable { added = true; } - if (skinParam.useRankSame() && dotMode != DotMode.NO_LEFT_RIGHT_AND_XLABEL) { + if (skinParam.useRankSame() && dotMode != DotMode.NO_LEFT_RIGHT_AND_XLABEL + && graphvizVersion.ignoreHorizontalLinks() == false) { appendRankSame(sb, lines); } diff --git a/src/net/sourceforge/plantuml/svek/CucaDiagramFileMakerSvek.java b/src/net/sourceforge/plantuml/svek/CucaDiagramFileMakerSvek.java index eb8a6e516..5c25be471 100644 --- a/src/net/sourceforge/plantuml/svek/CucaDiagramFileMakerSvek.java +++ b/src/net/sourceforge/plantuml/svek/CucaDiagramFileMakerSvek.java @@ -47,6 +47,7 @@ import net.sourceforge.plantuml.FileFormatOption; import net.sourceforge.plantuml.NamedOutputStream; import net.sourceforge.plantuml.Scale; import net.sourceforge.plantuml.UmlDiagramType; +import net.sourceforge.plantuml.api.ImageDataAbstract; import net.sourceforge.plantuml.core.ImageData; import net.sourceforge.plantuml.cucadiagram.CucaDiagram; import net.sourceforge.plantuml.cucadiagram.Link; @@ -107,6 +108,7 @@ public final class CucaDiagramFileMakerSvek implements CucaDiagramFileMaker { fileFormatOption.getDefaultStringBounder()); result = svek2.buildImage(basefile, diagram.getDotStringSkek()); } + final boolean isGraphvizCrash = result instanceof GraphvizCrash; result = new AnnotatedWorker(diagram, diagram.getSkinParam()).addAdd(result); final String widthwarning = diagram.getSkinParam().getValue("widthwarning"); @@ -121,8 +123,11 @@ public final class CucaDiagramFileMakerSvek implements CucaDiagramFileMaker { fileFormatOption.isWithMetadata() ? diagram.getMetadata() : null, warningOrError, 0, 10, diagram.getAnimation(), result.getBackcolor()); imageBuilder.setUDrawable(result); - return imageBuilder.writeImageTOBEMOVED(fileFormatOption, diagram.seed(), os); - + final ImageData imageData = imageBuilder.writeImageTOBEMOVED(fileFormatOption, diagram.seed(), os); + if (isGraphvizCrash) { + ((ImageDataAbstract) imageData).setStatus(503); + } + return imageData; } private List getOrderedLinks() { diff --git a/src/net/sourceforge/plantuml/svek/DecorateEntityImage.java b/src/net/sourceforge/plantuml/svek/DecorateEntityImage.java index e718952d2..dfbebc508 100644 --- a/src/net/sourceforge/plantuml/svek/DecorateEntityImage.java +++ b/src/net/sourceforge/plantuml/svek/DecorateEntityImage.java @@ -59,15 +59,15 @@ public class DecorateEntityImage extends AbstractTextBlock implements TextBlockB private double deltaX; private double deltaY; - public static DecorateEntityImage addTop(TextBlock original, TextBlock text, HorizontalAlignment horizontal) { + public static TextBlock addTop(TextBlock original, TextBlock text, HorizontalAlignment horizontal) { return new DecorateEntityImage(original, text, horizontal, null, null); } - public static DecorateEntityImage addBottom(TextBlock original, TextBlock text, HorizontalAlignment horizontal) { + public static TextBlock addBottom(TextBlock original, TextBlock text, HorizontalAlignment horizontal) { return new DecorateEntityImage(original, null, null, text, horizontal); } - public static DecorateEntityImage add(TextBlock original, TextBlock text, HorizontalAlignment horizontal, + public static TextBlock add(TextBlock original, TextBlock text, HorizontalAlignment horizontal, VerticalAlignment verticalAlignment) { if (verticalAlignment == VerticalAlignment.TOP) { return addTop(original, text, horizontal); @@ -75,7 +75,12 @@ public class DecorateEntityImage extends AbstractTextBlock implements TextBlockB return addBottom(original, text, horizontal); } - public DecorateEntityImage(TextBlock original, TextBlock text1, HorizontalAlignment horizontal1, TextBlock text2, + public static TextBlock addTopAndBottom(TextBlock original, TextBlock text1, HorizontalAlignment horizontal1, + TextBlock text2, HorizontalAlignment horizontal2) { + return new DecorateEntityImage(original, text1, horizontal1, text2, horizontal2); + } + + private DecorateEntityImage(TextBlock original, TextBlock text1, HorizontalAlignment horizontal1, TextBlock text2, HorizontalAlignment horizontal2) { this.original = original; this.horizontal1 = horizontal1; @@ -141,7 +146,7 @@ public class DecorateEntityImage extends AbstractTextBlock implements TextBlockB getTextDim(text2, stringBounder)); return Dimension2DDouble.mergeTB(dimOriginal, dimText); } - + @Override public MinMax getMinMax(StringBounder stringBounder) { return MinMax.fromDim(calculateDimension(stringBounder)); diff --git a/src/net/sourceforge/plantuml/svek/Line.java b/src/net/sourceforge/plantuml/svek/Line.java index e993b0c75..5b3103228 100644 --- a/src/net/sourceforge/plantuml/svek/Line.java +++ b/src/net/sourceforge/plantuml/svek/Line.java @@ -356,9 +356,9 @@ public class Line implements Moveable, Hideable { sb.append(decoration); int length = link.getLength(); - // if (graphvizVersion == GraphvizVersion.V2_34_0 && length == 1) { - // length = 2; - // } + if (graphvizVersion.ignoreHorizontalLinks() && length == 1) { + length = 2; + } if (useRankSame) { if (pragma.horizontalLineBetweenDifferentPackageAllowed() || link.isInvis() || length != 1) { // if (graphvizVersion.isJs() == false) { @@ -373,7 +373,7 @@ public class Line implements Moveable, Hideable { sb.append("color=\"" + StringUtils.getAsHtml(lineColor) + "\""); if (labelText != null) { sb.append(","); - if (graphvizVersion.modeSafe() || dotMode == DotMode.NO_LEFT_RIGHT_AND_XLABEL) { + if (graphvizVersion.useXLabelInsteadOfLabel() || dotMode == DotMode.NO_LEFT_RIGHT_AND_XLABEL) { sb.append("xlabel=<"); } else { sb.append("label=<"); diff --git a/src/net/sourceforge/plantuml/svek/extremity/ExtremityCircle.java b/src/net/sourceforge/plantuml/svek/extremity/ExtremityCircle.java index d47373901..c3aabf818 100644 --- a/src/net/sourceforge/plantuml/svek/extremity/ExtremityCircle.java +++ b/src/net/sourceforge/plantuml/svek/extremity/ExtremityCircle.java @@ -38,6 +38,7 @@ package net.sourceforge.plantuml.svek.extremity; import java.awt.geom.Point2D; import net.sourceforge.plantuml.graphic.HtmlColorUtils; +import net.sourceforge.plantuml.graphic.UDrawable; import net.sourceforge.plantuml.ugraphic.UChangeBackColor; import net.sourceforge.plantuml.ugraphic.UEllipse; import net.sourceforge.plantuml.ugraphic.UGraphic; @@ -47,19 +48,31 @@ import net.sourceforge.plantuml.ugraphic.UTranslate; class ExtremityCircle extends Extremity { private final Point2D dest; - private final double radius = 6; + private static final double radius = 6; @Override public Point2D somePoint() { return dest; } - public ExtremityCircle(Point2D p1) { - this.dest = new Point2D.Double(p1.getX(), p1.getY()); + // public static UDrawable createContact(Point2D p1, double angle) { + // final double x = p1.getX() - radius + radius * Math.sin(angle); + // final double y = p1.getY() - radius - radius * Math.cos(angle); + // return new ExtremityCircle(x, y); + // } + + public static UDrawable create(Point2D center) { + return new ExtremityCircle(center.getX(), center.getY()); + } + + private ExtremityCircle(double x, double y) { + this.dest = new Point2D.Double(x, y); } public void drawU(UGraphic ug) { - ug.apply(new UStroke(1.5)).apply(new UChangeBackColor(HtmlColorUtils.WHITE)).apply(new UTranslate(dest.getX() - radius, dest.getY() - radius)).draw(new UEllipse(radius * 2, radius * 2)); + ug.apply(new UStroke(1.5)).apply(new UChangeBackColor(HtmlColorUtils.WHITE)) + .apply(new UTranslate(dest.getX() - radius, dest.getY() - radius)) + .draw(new UEllipse(radius * 2, radius * 2)); } } diff --git a/src/net/sourceforge/plantuml/svek/extremity/ExtremityFactoryCircle.java b/src/net/sourceforge/plantuml/svek/extremity/ExtremityFactoryCircle.java index 5bea50ed0..686a8d945 100644 --- a/src/net/sourceforge/plantuml/svek/extremity/ExtremityFactoryCircle.java +++ b/src/net/sourceforge/plantuml/svek/extremity/ExtremityFactoryCircle.java @@ -43,9 +43,14 @@ import net.sourceforge.plantuml.svek.Side; public class ExtremityFactoryCircle extends AbstractExtremityFactory implements ExtremityFactory { + @Override + public UDrawable createUDrawable(Point2D center, double angle, Side side) { + // return ExtremityCircle.createContact(center, angle); + return ExtremityCircle.create(center); + } + public UDrawable createUDrawable(Point2D p0, Point2D p1, Point2D p2, Side side) { - // final double ortho = atan2(p0, p2); - return new ExtremityCircle(p1); + return ExtremityCircle.create(p1); } } diff --git a/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java b/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java index 51bd9a361..781d22f48 100644 --- a/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java +++ b/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java @@ -38,6 +38,8 @@ package net.sourceforge.plantuml.svek.image; import java.awt.geom.Dimension2D; import java.util.Collection; +import java.util.HashSet; +import java.util.Set; import net.sourceforge.plantuml.Dimension2DDouble; import net.sourceforge.plantuml.ISkinParam; @@ -46,6 +48,7 @@ import net.sourceforge.plantuml.Url; import net.sourceforge.plantuml.cucadiagram.BodyEnhanced; import net.sourceforge.plantuml.cucadiagram.Display; import net.sourceforge.plantuml.cucadiagram.EntityPortion; +import net.sourceforge.plantuml.cucadiagram.IEntity; import net.sourceforge.plantuml.cucadiagram.ILeaf; import net.sourceforge.plantuml.cucadiagram.Link; import net.sourceforge.plantuml.cucadiagram.PortionShower; @@ -171,7 +174,13 @@ public class EntityImageDescription extends AbstractEntityImage { if (hideText == false) { return Margins.NONE; } - if (useRankSame && hasSomeHorizontalLink((ILeaf) getEntity(), links)) { + // if (useRankSame && hasSomeHorizontalLink((ILeaf) getEntity(), links)) { + // return Margins.NONE; + // } + if (isThereADoubleLink((ILeaf) getEntity(), links)) { + return Margins.NONE; + } + if (hasSomeHorizontalLinkVisible((ILeaf) getEntity(), links)) { return Margins.NONE; } if (hasSomeHorizontalLinkDoubleDecorated((ILeaf) getEntity(), links)) { @@ -189,15 +198,29 @@ public class EntityImageDescription extends AbstractEntityImage { return new Margins(suppX / 2, suppX / 2, y, y); } - private boolean hasSomeHorizontalLink(ILeaf leaf, Collection links) { + private boolean hasSomeHorizontalLinkVisible(ILeaf leaf, Collection links) { for (Link link : links) { - if (link.getLength() == 1 && link.contains(leaf)) { + if (link.getLength() == 1 && link.contains(leaf) && link.isInvis() == false) { return true; } } return false; } + private boolean isThereADoubleLink(ILeaf leaf, Collection links) { + final Set others = new HashSet(); + for (Link link : links) { + if (link.contains(leaf)) { + final IEntity other = link.getOther(leaf); + final boolean changed = others.add(other); + if (changed == false) { + return true; + } + } + } + return false; + } + private boolean hasSomeHorizontalLinkDoubleDecorated(ILeaf leaf, Collection links) { for (Link link : links) { if (link.getLength() == 1 && link.contains(leaf) && link.getType().isDoubleDecorated()) { diff --git a/src/net/sourceforge/plantuml/swing/MainWindow2.java b/src/net/sourceforge/plantuml/swing/MainWindow2.java index ba0da1a1e..bb611c0a0 100644 --- a/src/net/sourceforge/plantuml/swing/MainWindow2.java +++ b/src/net/sourceforge/plantuml/swing/MainWindow2.java @@ -108,7 +108,7 @@ public class MainWindow2 extends JFrame { } private String getDefaultFileExtensions() { - return "txt, tex, java, htm, html, c, h, cpp, apt, pu, puml"; + return "txt, tex, java, htm, html, c, h, cpp, apt, pu, puml, hpp, hh"; } private void changeExtensions(String ext) { diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index d186ba5be..cdf8664e5 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -43,7 +43,7 @@ public class Version { private static final int MAJOR_SEPARATOR = 1000000; public static int version() { - return 1201803; + return 1201804; } public static int versionPatched() { @@ -88,7 +88,7 @@ public class Version { } public static long compileTime() { - return 1522947555139L; + return 1525191499228L; } public static String compileTimeString() { diff --git a/src/net/sourceforge/plantuml/vizjs/GraphvizJs.java b/src/net/sourceforge/plantuml/vizjs/GraphvizJs.java index fdde31728..3035b6f33 100644 --- a/src/net/sourceforge/plantuml/vizjs/GraphvizJs.java +++ b/src/net/sourceforge/plantuml/vizjs/GraphvizJs.java @@ -129,13 +129,17 @@ public class GraphvizJs implements Graphviz { return true; } - public boolean modeSafe() { + public boolean useXLabelInsteadOfLabel() { return modeSafe; } public boolean isVizjs() { return true; } + + public boolean ignoreHorizontalLinks() { + return false; + } }; }