From dbe4feae250552d9ce73fd0f34e5559c549ab475 Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Sat, 4 Jun 2022 16:37:33 +0200 Subject: [PATCH 01/14] upd: more generic version Change version to: `M.YYYY.m-SNAPSHOT` --- gradle.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gradle.properties b/gradle.properties index 92dd41656..7ca89723a 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1 +1 @@ -version = 1.2022.1-SNAPSHOT +version = M.YYYY.m-SNAPSHOT From 26f5b7f1fd5be26389b80b92de70b9f63659476d Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Mon, 6 Jun 2022 12:35:27 +0200 Subject: [PATCH 02/14] Add support for GraphViz 4 --- src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizUtils.java | 2 +- .../plantuml/cucadiagram/dot/GraphvizVersionFinder.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizUtils.java b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizUtils.java index d5bc7d0e1..c320205fa 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizUtils.java +++ b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizUtils.java @@ -195,7 +195,7 @@ public class GraphvizUtils { if (s == null) return -1; - final Pattern p = Pattern.compile("\\s([23])\\.(\\d\\d?)\\D"); + final Pattern p = Pattern.compile("\\s([23456])\\.(\\d\\d?)\\D"); final Matcher m = p.matcher(s); if (m.find() == false) return -1; diff --git a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java index d7884ce8a..2fb92e2bb 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java +++ b/src/net/sourceforge/plantuml/cucadiagram/dot/GraphvizVersionFinder.java @@ -72,7 +72,7 @@ public class GraphvizVersionFinder { public GraphvizVersion getVersion() { final String dotVersion = dotVersion(); - final Pattern p = Pattern.compile("([23])\\.(\\d\\d?)"); + final Pattern p = Pattern.compile("([23456])\\.(\\d\\d?)"); final Matcher m = p.matcher(dotVersion); final boolean find = m.find(); if (find == false) { From 5e06dae80953aabbf34e73935f5b1f748027e7db Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Mon, 6 Jun 2022 14:07:52 +0200 Subject: [PATCH 03/14] upd: add a pseudo version of snapshot Add a pseudo version of snapshot taken from Version.java --- .github/workflows/ci.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 7f3665009..8c0671b96 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -59,6 +59,8 @@ jobs: elif [[ "${GITHUB_EVENT_NAME}" =~ push|workflow_dispatch && "${REF}" == "refs/heads/master" ]]; then echo "::notice title=::This run will release a snapshot" echo "::set-output name=do_snapshot_release::true" + v=$(perl -ne 'if (/return (\d{6,7});/) {$v=$1} if (/final int beta = (\d+);/) {$b=$1} END{print(substr($v, 0, 1),".", substr($v, 1, 4),"."); if ($b) {print(int(substr($v+1, 5)), "beta", $b);} else {print(int(substr($v, 5)))}}' src/net/sourceforge/plantuml/version/Version.java) + echo "::set-output name=pom_version::$v-SNAPSHOT" # pom_version is taken from Version.java else echo "This run will NOT make a release" From a9e9ca81e0ba1682d1db809d9751daa096c852e5 Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Mon, 6 Jun 2022 14:26:57 +0200 Subject: [PATCH 04/14] upd: add a pseudo version of snapshot Add a pseudo version of snapshot: `snapshot (~vM.YYYY.mmbetaBB [YYYY-MM-DD at hh:mm:ss (UTC)])` --- .github/scripts/release-snapshot.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/scripts/release-snapshot.sh b/.github/scripts/release-snapshot.sh index aef91a4a7..cd91fb0b5 100755 --- a/.github/scripts/release-snapshot.sh +++ b/.github/scripts/release-snapshot.sh @@ -42,8 +42,8 @@ EOF gh release create \ --prerelease \ --target "${GITHUB_SHA}" \ - --title "${TAG}" \ + --title "${TAG} (~v${POM_VERSION%-SNAPSHOT} [${DATE_TIME_UTC}])" \ --notes-file notes.txt \ "${TAG}" ${RELEASE_DIR}/* -echo "::notice title=release snapshot::Snapshot released at ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/releases/tag/${TAG} and taken the ${DATE_TIME_UTC}" +echo "::notice title=release snapshot::Snapshot (~v${POM_VERSION%-SNAPSHOT}) released at ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/releases/tag/${TAG} and taken the ${DATE_TIME_UTC}" From 6e3ba0e4dad1a84db6ccac7289bf0ac71732ee89 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Mon, 6 Jun 2022 14:36:58 +0200 Subject: [PATCH 05/14] wip --- .../plantuml/command/CommandMultilines.java | 6 +- .../plantuml/command/CommandMultilines2.java | 6 +- .../plantuml/command/CommandMultilines3.java | 6 +- .../command/CommandMultilinesBracket.java | 6 +- .../plantuml/command/SingleLineCommand2.java | 7 +- .../plantuml/creole/atom/AtomImg.java | 6 +- .../plantuml/creole/legacy/CreoleParser.java | 5 +- .../plantuml/cucadiagram/Display.java | 80 ++++++++++--------- src/net/sourceforge/plantuml/graphic/Img.java | 26 +++--- .../plantuml/graphic/TileImageSvg.java | 6 +- .../command/CommandCreateJson.java | 41 ++++++++-- .../skin/AbstractTextualComponent.java | 12 +-- .../plantuml/style/FromSkinparamToStyle.java | 11 ++- .../plantuml/ugraphic/UImageSvg.java | 8 +- .../plantuml/ugraphic/UPolygon.java | 2 +- 15 files changed, 135 insertions(+), 93 deletions(-) diff --git a/src/net/sourceforge/plantuml/command/CommandMultilines.java b/src/net/sourceforge/plantuml/command/CommandMultilines.java index 79007fa72..d511c305b 100644 --- a/src/net/sourceforge/plantuml/command/CommandMultilines.java +++ b/src/net/sourceforge/plantuml/command/CommandMultilines.java @@ -72,15 +72,15 @@ public abstract class CommandMultilines implements Command if (m1.matches() == false) return CommandControl.OK_PARTIAL; - actionIfCommandValid(); - return CommandControl.OK; + return finalVerification(); } protected boolean isCommandForbidden() { return false; } - protected void actionIfCommandValid() { + protected CommandControl finalVerification() { + return CommandControl.OK; } protected final Pattern2 getStartingPattern() { diff --git a/src/net/sourceforge/plantuml/command/CommandMultilines2.java b/src/net/sourceforge/plantuml/command/CommandMultilines2.java index 7bc1dc30f..0e56f5bb4 100644 --- a/src/net/sourceforge/plantuml/command/CommandMultilines2.java +++ b/src/net/sourceforge/plantuml/command/CommandMultilines2.java @@ -96,8 +96,7 @@ public abstract class CommandMultilines2 implements Command implements Command implements Command implements Command implements Com return new String[] { "BRACKET: " + starting.pattern() }; } - protected void actionIfCommandValid() { + protected CommandControl finalVerification() { + return CommandControl.OK; } protected final Pattern2 getStartingPattern() { @@ -98,8 +99,7 @@ public abstract class CommandMultilinesBracket implements Com if (level != 0) return CommandControl.OK_PARTIAL; - actionIfCommandValid(); - return CommandControl.OK; + return finalVerification(); } protected abstract boolean isLineConsistent(String line, int level); diff --git a/src/net/sourceforge/plantuml/command/SingleLineCommand2.java b/src/net/sourceforge/plantuml/command/SingleLineCommand2.java index 95723c695..6d9cd4ffc 100644 --- a/src/net/sourceforge/plantuml/command/SingleLineCommand2.java +++ b/src/net/sourceforge/plantuml/command/SingleLineCommand2.java @@ -104,9 +104,9 @@ public abstract class SingleLineCommand2 implements Command implements Command { private final HorizontalAlignment naturalHorizontalAlignment; private final boolean isNull; private final CreoleMode defaultCreoleMode; + private final boolean showStereotype; - public final static Display NULL = new Display(null, null, true, CreoleMode.FULL); + public final static Display NULL = new Display(true, null, null, true, CreoleMode.FULL); + + public boolean showStereotype() { + return showStereotype; + } public Display withoutStereotypeIfNeeded(Style usedStyle) { if (this == NULL) return NULL; - final boolean showStereotype = usedStyle.value(PName.ShowStereotype).asBoolean(); - if (showStereotype) + final Value showStereotype = usedStyle.value(PName.ShowStereotype); + if (showStereotype instanceof ValueNull || showStereotype.asBoolean()) return this; - final List copy = new ArrayList<>(displayData); - final Display result = new Display(naturalHorizontalAlignment, isNull, defaultCreoleMode); - for (Iterator it = copy.iterator(); it.hasNext();) { - final CharSequence cs = it.next(); - if (cs instanceof Stereotype && usedStyle.getSignature().match(((Stereotype) cs))) - it.remove(); + return new Display(false, this, this.defaultCreoleMode); - } - result.displayData.addAll(copy); - return result; } public Stereotype getStereotypeIfAny() { @@ -121,7 +120,7 @@ public class Display implements Iterable { } public Display replaceBackslashT() { - final Display result = new Display(this, defaultCreoleMode); + final Display result = new Display(this.showStereotype, this, defaultCreoleMode); for (int i = 0; i < result.displayData.size(); i++) { final CharSequence s = displayData.get(i); if (s.toString().contains("\\t")) @@ -138,7 +137,7 @@ public class Display implements Iterable { newDisplay.add(cs); } - return new Display(newDisplay, naturalHorizontalAlignment, isNull, defaultCreoleMode); + return new Display(showStereotype, newDisplay, naturalHorizontalAlignment, isNull, defaultCreoleMode); } public boolean isWhite() { @@ -147,7 +146,7 @@ public class Display implements Iterable { } public static Display empty() { - return new Display((HorizontalAlignment) null, false, CreoleMode.FULL); + return new Display(true, (HorizontalAlignment) null, false, CreoleMode.FULL); } public static Display create(CharSequence... s) { @@ -165,7 +164,7 @@ public class Display implements Iterable { } public static Display create(Collection other) { - return new Display(other, null, false, CreoleMode.FULL); + return new Display(true, other, null, false, CreoleMode.FULL); } public static Display getWithNewlines(Code s) { @@ -221,24 +220,26 @@ public class Display implements Iterable { } } result.add(current.toString()); - return new Display(result, naturalHorizontalAlignment, false, CreoleMode.FULL); + return new Display(true, result, naturalHorizontalAlignment, false, CreoleMode.FULL); } - private Display(Display other, CreoleMode mode) { - this(other.naturalHorizontalAlignment, other.isNull, mode); + private Display(boolean showStereotype, Display other, CreoleMode mode) { + this(showStereotype, other.naturalHorizontalAlignment, other.isNull, mode); this.displayData.addAll(other.displayData); } - private Display(HorizontalAlignment naturalHorizontalAlignment, boolean isNull, CreoleMode defaultCreoleMode) { + private Display(boolean showStereotype, HorizontalAlignment naturalHorizontalAlignment, boolean isNull, + CreoleMode defaultCreoleMode) { + this.showStereotype = showStereotype; this.defaultCreoleMode = defaultCreoleMode; this.isNull = isNull; this.displayData = isNull ? null : new ArrayList(); this.naturalHorizontalAlignment = isNull ? null : naturalHorizontalAlignment; } - private Display(Collection other, HorizontalAlignment naturalHorizontalAlignment, - boolean isNull, CreoleMode defaultCreoleMode) { - this(naturalHorizontalAlignment, isNull, defaultCreoleMode); + private Display(boolean showStereotype, Collection other, + HorizontalAlignment naturalHorizontalAlignment, boolean isNull, CreoleMode defaultCreoleMode) { + this(showStereotype, naturalHorizontalAlignment, isNull, defaultCreoleMode); if (isNull == false) this.displayData.addAll(manageEmbeddedDiagrams(other)); @@ -284,7 +285,8 @@ public class Display implements Iterable { } first = false; } - return new Display(result, this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + return new Display(showStereotype, result, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); } public Display withPage(int page, int lastpage) { @@ -297,7 +299,8 @@ public class Display implements Iterable { line = line.toString().replace("%lastpage%", "" + lastpage); result.add(line); } - return new Display(result, this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + return new Display(showStereotype, result, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); } public Display removeEndingStereotype() { @@ -305,7 +308,8 @@ public class Display implements Iterable { if (m.matches()) { final List result = new ArrayList<>(this.displayData); result.set(result.size() - 1, m.group(1)); - return new Display(result, this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + return new Display(showStereotype, result, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); } return this; } @@ -325,7 +329,8 @@ public class Display implements Iterable { for (CharSequence line : displayData) result.add("" + line); - return new Display(result, this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + return new Display(showStereotype, result, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); } public Display underlinedName() { @@ -342,14 +347,15 @@ public class Display implements Iterable { result.add("" + line); } } - return new Display(result, this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + return new Display(showStereotype, result, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); } public Display withCreoleMode(CreoleMode mode) { if (isNull) throw new IllegalArgumentException(); - return new Display(this, mode); + return new Display(this.showStereotype, this, mode); } @Override @@ -371,25 +377,25 @@ public class Display implements Iterable { } public Display addAll(Display other) { - final Display result = new Display(this, this.defaultCreoleMode); + final Display result = new Display(this.showStereotype, this, this.defaultCreoleMode); result.displayData.addAll(other.displayData); return result; } public Display addFirst(CharSequence s) { - final Display result = new Display(this, this.defaultCreoleMode); + final Display result = new Display(this.showStereotype, this, this.defaultCreoleMode); result.displayData.add(0, s); return result; } public Display add(CharSequence s) { - final Display result = new Display(this, this.defaultCreoleMode); + final Display result = new Display(this.showStereotype, this, this.defaultCreoleMode); result.displayData.add(s); return result; } public Display addGeneric(CharSequence s) { - final Display result = new Display(this, this.defaultCreoleMode); + final Display result = new Display(this.showStereotype, this, this.defaultCreoleMode); final int size = displayData.size(); if (size == 0) result.displayData.add("<" + s + ">"); @@ -415,7 +421,7 @@ public class Display implements Iterable { } public Display subList(int i, int size) { - return new Display(displayData.subList(i, size), this.naturalHorizontalAlignment, this.isNull, + return new Display(showStereotype, displayData.subList(i, size), this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); } @@ -448,7 +454,8 @@ public class Display implements Iterable { public List splitMultiline(Pattern2 separator) { final List result = new ArrayList<>(); - Display pending = new Display(this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + Display pending = new Display(showStereotype, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); result.add(pending); for (CharSequence line : displayData) { final Matcher2 m = separator.matcher(line); @@ -456,7 +463,8 @@ public class Display implements Iterable { final CharSequence s1 = line.subSequence(0, m.start()); pending.displayData.add(s1); final CharSequence s2 = line.subSequence(m.end(), line.length()); - pending = new Display(this.naturalHorizontalAlignment, this.isNull, this.defaultCreoleMode); + pending = new Display(showStereotype, this.naturalHorizontalAlignment, this.isNull, + this.defaultCreoleMode); result.add(pending); pending.displayData.add(s2); } else { diff --git a/src/net/sourceforge/plantuml/graphic/Img.java b/src/net/sourceforge/plantuml/graphic/Img.java index ceda56359..840a19d2d 100644 --- a/src/net/sourceforge/plantuml/graphic/Img.java +++ b/src/net/sourceforge/plantuml/graphic/Img.java @@ -63,17 +63,17 @@ public class Img implements HtmlCommand { static int getVspace(String html) { final Matcher2 m = vspacePattern.matcher(html); - if (m.find() == false) { + if (m.find() == false) return 0; - } + return Integer.parseInt(m.group(1)); } static ImgValign getValign(String html) { final Matcher2 m = valignPattern.matcher(html); - if (m.find() == false) { + if (m.find() == false) return ImgValign.TOP; - } + return ImgValign.valueOf(StringUtils.goUpperCase(m.group(1))); } @@ -99,28 +99,28 @@ public class Img implements HtmlCommand { // Check if valid URL if (src.startsWith("http:") || src.startsWith("https:")) { final SURL tmp = SURL.create(src); - if (tmp == null) { + if (tmp == null) return new Text("(Cannot decode: " + src + ")"); - } + final BufferedImage read = tmp.readRasterImageFromURL(); - if (read == null) { + if (read == null) return new Text("(Cannot decode: " + src + ")"); - } + return new Img(new TileImage(read, valign, vspace)); } return new Text("(Cannot decode: " + f + ")"); } if (f.getName().endsWith(".svg")) { final String tmp = FileUtils.readSvg(f); - if (tmp == null) { + if (tmp == null) return new Text("(Cannot decode: " + f + ")"); - } - return new Img(new TileImageSvg(tmp)); + + return new Img(new TileImageSvg(tmp, 1)); } final BufferedImage read = f.readRasterImageFromFile(); - if (read == null) { + if (read == null) return new Text("(Cannot decode: " + f + ")"); - } + return new Img(new TileImage(f.readRasterImageFromFile(), valign, vspace)); } catch (IOException e) { e.printStackTrace(); diff --git a/src/net/sourceforge/plantuml/graphic/TileImageSvg.java b/src/net/sourceforge/plantuml/graphic/TileImageSvg.java index 82911a800..06be3a753 100644 --- a/src/net/sourceforge/plantuml/graphic/TileImageSvg.java +++ b/src/net/sourceforge/plantuml/graphic/TileImageSvg.java @@ -43,9 +43,11 @@ import net.sourceforge.plantuml.ugraphic.UImageSvg; public class TileImageSvg extends AbstractTextBlock implements TextBlock { private final UImageSvg svg; + private final double scale; - public TileImageSvg(String svg) { - this.svg = new UImageSvg(svg, 1); + public TileImageSvg(String svg, double scale) { + this.svg = new UImageSvg(svg, scale); + this.scale = scale; } public Dimension2D calculateDimension(StringBounder stringBounder) { diff --git a/src/net/sourceforge/plantuml/objectdiagram/command/CommandCreateJson.java b/src/net/sourceforge/plantuml/objectdiagram/command/CommandCreateJson.java index 39d5f4ea0..b3c816297 100644 --- a/src/net/sourceforge/plantuml/objectdiagram/command/CommandCreateJson.java +++ b/src/net/sourceforge/plantuml/objectdiagram/command/CommandCreateJson.java @@ -39,6 +39,7 @@ import net.sourceforge.plantuml.FontParam; import net.sourceforge.plantuml.StringLocated; import net.sourceforge.plantuml.UrlBuilder; import net.sourceforge.plantuml.command.BlocLines; +import net.sourceforge.plantuml.command.CommandControl; import net.sourceforge.plantuml.command.CommandExecutionResult; import net.sourceforge.plantuml.command.CommandMultilines2; import net.sourceforge.plantuml.command.MultilinesStrategy; @@ -97,22 +98,46 @@ public class CommandCreateJson extends CommandMultilines2 0; - System.err.println("l=" + line); sb.append(line); } sb.append("}"); - - final DefaultHandler handler = new DefaultHandler(); - new JsonParser(handler).parse(sb.toString()); - final JsonValue json = handler.getValue(); - ((BodierJSon) entity1.getBodier()).setJson(json); - - return CommandExecutionResult.ok(); + return sb.toString(); } private IEntity executeArg0(AbstractClassOrObjectDiagram diagram, RegexResult line0) throws NoSuchColorException { diff --git a/src/net/sourceforge/plantuml/skin/AbstractTextualComponent.java b/src/net/sourceforge/plantuml/skin/AbstractTextualComponent.java index 8a4effb9d..d4ec560d8 100644 --- a/src/net/sourceforge/plantuml/skin/AbstractTextualComponent.java +++ b/src/net/sourceforge/plantuml/skin/AbstractTextualComponent.java @@ -55,8 +55,6 @@ import net.sourceforge.plantuml.ugraphic.color.HColorSet; public abstract class AbstractTextualComponent extends AbstractComponent { - private final Display display; - private final int marginX1; private final int marginX2; private final int marginY; @@ -91,20 +89,18 @@ public abstract class AbstractTextualComponent extends AbstractComponent { final UFont fontForStereotype = stereo.getUFont(); final HColor htmlColorForStereotype = stereo.value(PName.FontColor).asColor(spriteContainer.getThemeStyle(), getIHtmlColorSet()); - this.display = display.withoutStereotypeIfNeeded(style); + display = display.withoutStereotypeIfNeeded(style); this.marginX1 = marginX1; this.marginX2 = marginX2; this.marginY = marginY; - // this.display = keepStereotype ? display : display.withoutStereotype(); - if (this.display.size() == 1 && this.display.get(0).length() == 0) + if (display.size() == 1 && display.get(0).length() == 0) textBlock = new TextBlockEmpty(); else if (enhanced) - textBlock = BodyFactory.create3(this.display, spriteContainer, horizontalAlignment, fc, maxMessageSize, - style); + textBlock = BodyFactory.create3(display, spriteContainer, horizontalAlignment, fc, maxMessageSize, style); else - textBlock = this.display.create0(fc, horizontalAlignment, spriteContainer, maxMessageSize, CreoleMode.FULL, + textBlock = display.create0(fc, horizontalAlignment, spriteContainer, maxMessageSize, CreoleMode.FULL, fontForStereotype, htmlColorForStereotype, marginX1, marginX2); this.alignment = horizontalAlignment; diff --git a/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java b/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java index 7d9a33c6c..fb956333f 100644 --- a/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java +++ b/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java @@ -210,7 +210,16 @@ public class FromSkinparamToStyle { addMagic(SName.usecase); addMagic(SName.map); addMagic(SName.archimate); - + + addConvert("IconPrivateColor", PName.LineColor, SName.visibilityIcon, SName.private_); + addConvert("IconPrivateBackgroundColor", PName.BackGroundColor, SName.visibilityIcon, SName.private_); + addConvert("IconPackageColor", PName.LineColor, SName.visibilityIcon, SName.package_); + addConvert("IconPackageBackgroundColor", PName.BackGroundColor, SName.visibilityIcon, SName.package_); + addConvert("IconProtectedColor", PName.LineColor, SName.visibilityIcon, SName.protected_); + addConvert("IconProtectedBackgroundColor", PName.BackGroundColor, SName.visibilityIcon, SName.protected_); + addConvert("IconPublicColor", PName.LineColor, SName.visibilityIcon, SName.public_); + addConvert("IconPublicBackgroundColor", PName.BackGroundColor, SName.visibilityIcon, SName.public_); + // addConvert("nodeStereotypeFontSize", PName.FontSize, SName.node, SName.stereotype); // addConvert("sequenceStereotypeFontSize", PName.FontSize, SName.stereotype); diff --git a/src/net/sourceforge/plantuml/ugraphic/UImageSvg.java b/src/net/sourceforge/plantuml/ugraphic/UImageSvg.java index 6152a05ff..cc4b988c4 100644 --- a/src/net/sourceforge/plantuml/ugraphic/UImageSvg.java +++ b/src/net/sourceforge/plantuml/ugraphic/UImageSvg.java @@ -128,12 +128,12 @@ public class UImageSvg implements UShape { throw new IllegalStateException("Cannot find " + name); } - public int getHeight() { - return this.getData("height"); + public double getHeight() { + return this.getData("height") * scale; } - public int getWidth() { - return this.getData("width"); + public double getWidth() { + return this.getData("width") * scale; } public double getScale() { diff --git a/src/net/sourceforge/plantuml/ugraphic/UPolygon.java b/src/net/sourceforge/plantuml/ugraphic/UPolygon.java index 23bb3f404..13ad6fa58 100644 --- a/src/net/sourceforge/plantuml/ugraphic/UPolygon.java +++ b/src/net/sourceforge/plantuml/ugraphic/UPolygon.java @@ -73,7 +73,7 @@ public class UPolygon extends AbstractShadowable { (pt1.getY() + pt2.getY()) / 2); final double delta = middle.distance(center); if (delta < 1) - return all.get((i - 1) % all.size()); + return all.get((i + all.size() - 1) % all.size()); } return null; From 24c18715aec5d487a9704ee466f7a96cdae1d5c1 Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Mon, 6 Jun 2022 19:46:45 +0200 Subject: [PATCH 06/14] upd: improve pseudo version of snapshot - Suppress date-time on release title - Add subtitle: `Version ~v${POM_VERSION%-SNAPSHOT} of the ${DATE_TIME_UTC}` --- .github/scripts/release-snapshot.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/scripts/release-snapshot.sh b/.github/scripts/release-snapshot.sh index cd91fb0b5..c850400bf 100755 --- a/.github/scripts/release-snapshot.sh +++ b/.github/scripts/release-snapshot.sh @@ -34,6 +34,7 @@ fi echo -n "${DATE_TIME_UTC}" > "${RELEASE_DIR}/plantuml-SNAPSHOT.timestamp" cat <<-EOF >notes.txt + ## Version ~v${POM_VERSION%-SNAPSHOT} of the ${DATE_TIME_UTC} This is a pre-release of [the latest development work](https://github.com/plantuml/plantuml/commits/). ⚠️ **It is not ready for general use** ⚠️ ⏱ _Snapshot taken the ${DATE_TIME_UTC}_ @@ -42,7 +43,7 @@ EOF gh release create \ --prerelease \ --target "${GITHUB_SHA}" \ - --title "${TAG} (~v${POM_VERSION%-SNAPSHOT} [${DATE_TIME_UTC}])" \ + --title "${TAG} (~v${POM_VERSION%-SNAPSHOT})" \ --notes-file notes.txt \ "${TAG}" ${RELEASE_DIR}/* From 3dd8b13f6c17592cdb8bee70d9823189b19d925f Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Mon, 6 Jun 2022 20:00:16 +0200 Subject: [PATCH 07/14] upd: add `Checkout` before `Configure workflow` - Adding `Checkout the repository` _(I don't know if it optimized or not...)_ before the `Configure workflow` - Fix variable in Uppercase --- .github/workflows/ci.yml | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 8c0671b96..c973cb87d 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -27,6 +27,9 @@ jobs: do_snapshot_release: ${{ steps.config.outputs.do_snapshot_release }} pom_version: ${{ steps.config.outputs.pom_version }} steps: + - name: Checkout the repository + uses: actions/checkout@v3 + - name: Configure workflow id: config env: @@ -59,8 +62,8 @@ jobs: elif [[ "${GITHUB_EVENT_NAME}" =~ push|workflow_dispatch && "${REF}" == "refs/heads/master" ]]; then echo "::notice title=::This run will release a snapshot" echo "::set-output name=do_snapshot_release::true" - v=$(perl -ne 'if (/return (\d{6,7});/) {$v=$1} if (/final int beta = (\d+);/) {$b=$1} END{print(substr($v, 0, 1),".", substr($v, 1, 4),"."); if ($b) {print(int(substr($v+1, 5)), "beta", $b);} else {print(int(substr($v, 5)))}}' src/net/sourceforge/plantuml/version/Version.java) - echo "::set-output name=pom_version::$v-SNAPSHOT" # pom_version is taken from Version.java + V=$(perl -ne 'if (/return (\d{6,7});/) {$v=$1} if (/final int beta = (\d+);/) {$b=$1} END{print(substr($v, 0, 1),".", substr($v, 1, 4),"."); if ($b) {print(int(substr($v+1, 5)), "beta", $b);} else {print(int(substr($v, 5)))}}' src/net/sourceforge/plantuml/version/Version.java) + echo "::set-output name=pom_version::$V-SNAPSHOT" # pom_version is taken from Version.java else echo "This run will NOT make a release" From 285c21492fe7611ab9d902361c7819f4f25d72e4 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Wed, 22 Jun 2022 09:30:15 +0200 Subject: [PATCH 08/14] Import version 1.2022.6 --- .../plantuml/activitydiagram3/ftile/Snake.java | 4 ++-- .../sourceforge/plantuml/graphic/Rainbow.java | 17 +++++++++++++---- .../plantuml/style/FromSkinparamToStyle.java | 5 ++--- src/net/sourceforge/plantuml/style/PName.java | 1 + .../sourceforge/plantuml/version/Version.java | 6 +++--- 5 files changed, 21 insertions(+), 12 deletions(-) diff --git a/src/net/sourceforge/plantuml/activitydiagram3/ftile/Snake.java b/src/net/sourceforge/plantuml/activitydiagram3/ftile/Snake.java index 08767b436..054243b4b 100644 --- a/src/net/sourceforge/plantuml/activitydiagram3/ftile/Snake.java +++ b/src/net/sourceforge/plantuml/activitydiagram3/ftile/Snake.java @@ -321,9 +321,9 @@ public class Snake implements UShape { if (same(this.getLast(), other.getFirst())) { final UPolygon oneOf = other.endDecoration == null ? endDecoration : other.endDecoration; - if (this.startDecoration != null || other.startDecoration != null) { + if (this.startDecoration != null || other.startDecoration != null) throw new UnsupportedOperationException("Not yet coded: to be done"); - } + final ArrayList mergeTexts = new ArrayList(this.texts); mergeTexts.addAll(other.texts); final Snake result = new Snake(skinParam, null, color, oneOf, this.worm.merge(other.worm, strategy), diff --git a/src/net/sourceforge/plantuml/graphic/Rainbow.java b/src/net/sourceforge/plantuml/graphic/Rainbow.java index 76aabc9fe..5e2cfba83 100644 --- a/src/net/sourceforge/plantuml/graphic/Rainbow.java +++ b/src/net/sourceforge/plantuml/graphic/Rainbow.java @@ -42,17 +42,18 @@ import java.util.Objects; import net.sourceforge.plantuml.ISkinParam; import net.sourceforge.plantuml.api.ThemeStyle; -import net.sourceforge.plantuml.skin.rose.Rose; import net.sourceforge.plantuml.style.PName; import net.sourceforge.plantuml.style.Style; +import net.sourceforge.plantuml.style.Value; +import net.sourceforge.plantuml.style.ValueNull; +import net.sourceforge.plantuml.ugraphic.color.ColorUtils; import net.sourceforge.plantuml.ugraphic.color.HColor; import net.sourceforge.plantuml.ugraphic.color.HColorSet; +import net.sourceforge.plantuml.ugraphic.color.HColorUtils; import net.sourceforge.plantuml.ugraphic.color.NoSuchColorException; public class Rainbow { - private final static Rose rose = new Rose(); - private final List colors = new ArrayList<>(); private final int colorArrowSeparationSpace; @@ -83,7 +84,15 @@ public class Rainbow { public static Rainbow build(Style style, HColorSet set, ThemeStyle themeStyle) { final HColor color = style.value(PName.LineColor).asColor(themeStyle, set); - return fromColor(color, null); + final Value head = style.value(PName.HeadColor); + HColor colorHead; + if (head instanceof ValueNull) + colorHead = color; + else + colorHead = head.asColor(themeStyle, set); + if (colorHead == null) + colorHead = HColorUtils.transparent(); + return fromColor(color, colorHead); } public Rainbow withDefault(Rainbow defaultColor) { diff --git a/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java b/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java index fb956333f..fc1a28449 100644 --- a/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java +++ b/src/net/sourceforge/plantuml/style/FromSkinparamToStyle.java @@ -144,6 +144,7 @@ public class FromSkinparamToStyle { addConvert("arrowThickness", PName.LineThickness, SName.arrow); addConvert("arrowColor", PName.LineColor, SName.arrow); addConvert("arrowStyle", PName.LineStyle, SName.arrow); + addConvert("arrowHeadColor", PName.HeadColor, SName.arrow); addConvert("defaulttextalignment", PName.HorizontalAlignment, SName.root); addConvert("defaultFontName", PName.FontName, SName.root); @@ -220,14 +221,12 @@ public class FromSkinparamToStyle { addConvert("IconPublicColor", PName.LineColor, SName.visibilityIcon, SName.public_); addConvert("IconPublicBackgroundColor", PName.BackGroundColor, SName.visibilityIcon, SName.public_); - // addConvert("nodeStereotypeFontSize", PName.FontSize, SName.node, SName.stereotype); // addConvert("sequenceStereotypeFontSize", PName.FontSize, SName.stereotype); // addConvert("sequenceStereotypeFontStyle", PName.FontStyle, SName.stereotype); // addConvert("sequenceStereotypeFontColor", PName.FontColor, SName.stereotype); // addConvert("sequenceStereotypeFontName", PName.FontName, SName.stereotype); - } private static void addMagic(SName sname) { @@ -240,7 +239,7 @@ public class FromSkinparamToStyle { addConvert(cleanName + "BorderStyle", PName.LineStyle, sname); addConFont(cleanName, sname); addConvert(cleanName + "Shadowing", PName.Shadowing, sname); - + addConvert(cleanName + "StereotypeFontSize", PName.FontSize, SName.stereotype, sname); addConvert(cleanName + "StereotypeFontStyle", PName.FontStyle, SName.stereotype, sname); addConvert(cleanName + "StereotypeFontColor", PName.FontColor, SName.stereotype, sname); diff --git a/src/net/sourceforge/plantuml/style/PName.java b/src/net/sourceforge/plantuml/style/PName.java index 5f6fb524c..04b918e1f 100644 --- a/src/net/sourceforge/plantuml/style/PName.java +++ b/src/net/sourceforge/plantuml/style/PName.java @@ -46,6 +46,7 @@ public enum PName { LineThickness, // DiagonalCorner, // HyperLinkColor, // + HeadColor, // LineColor, // LineStyle, // Padding, // diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index 8adf14f32..729f441ea 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -44,7 +44,7 @@ public class Version { private static final int MAJOR_SEPARATOR = 1000000; public static int version() { - return 1202205; + return 1202206; } public static int versionPatched() { @@ -80,7 +80,7 @@ public class Version { } public static int beta() { - final int beta = 5; + final int beta = 0; return beta; } @@ -93,7 +93,7 @@ public class Version { } public static long compileTime() { - return 1651316152000L; + return 1655832889469L; } public static String compileTimeString() { From e801884415e0887782489934a2f8e12bf970a795 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Mon, 27 Jun 2022 18:33:45 +0200 Subject: [PATCH 09/14] wip --- .../sourceforge/plantuml/AnnotatedWorker.java | 5 +- .../ftile/EntityImageLegend.java | 2 +- .../ftile/vertical/FtileBoxOld.java | 21 +- .../command/CommandCreateClassMultilines.java | 82 +++---- .../plantuml/command/regex/MyPattern.java | 2 +- .../plantuml/cucadiagram/DisplaySection.java | 2 +- .../cucadiagram/entity/EntityImpl.java | 215 ++++++++---------- .../plantuml/elk/CucaDiagramFileMakerElk.java | 11 +- src/net/sourceforge/plantuml/elk/ElkPath.java | 21 +- .../plantuml/graphic/TextBlockBordered.java | 52 ++--- .../plantuml/graphic/TextBlockUtils.java | 20 +- .../command/CommandCreateMap.java | 29 ++- .../sourceforge/plantuml/png/PngTitler.java | 2 +- .../plantuml/preproc/ReadLineReader.java | 12 +- .../sourceforge/plantuml/security/SURL.java | 2 +- .../SequenceDiagramFileMakerPuma2.java | 4 +- .../teoz/SequenceDiagramFileMakerTeoz.java | 2 +- .../skin/rose/ComponentRoseArrow.java | 17 +- src/net/sourceforge/plantuml/style/Style.java | 8 +- .../plantuml/svek/ClusterDecoration.java | 4 +- .../plantuml/svek/image/EntityImageClass.java | 8 +- .../plantuml/svek/image/EntityImageMap.java | 13 +- .../plantuml/svek/image/Footprint.java | 8 + .../sourceforge/plantuml/tim/EaterTheme.java | 7 +- .../timingdiagram/graphic/Ribbon.java | 3 +- .../sourceforge/plantuml/ugraphic/ULine.java | 9 + .../sourceforge/plantuml/version/Version.java | 2 +- .../sourceforge/plantuml/yaml/YamlLines.java | 21 +- 28 files changed, 287 insertions(+), 297 deletions(-) diff --git a/src/net/sourceforge/plantuml/AnnotatedWorker.java b/src/net/sourceforge/plantuml/AnnotatedWorker.java index 080fbbfc4..4cac307da 100644 --- a/src/net/sourceforge/plantuml/AnnotatedWorker.java +++ b/src/net/sourceforge/plantuml/AnnotatedWorker.java @@ -179,7 +179,8 @@ public class AnnotatedWorker { final Style style = StyleSignatureBasic.of(SName.root, SName.document, SName.caption) .getMergedStyle(skinParam.getCurrentStyleBuilder()); - return style.createTextBlockBordered(caption.getDisplay(), skinParam.getIHtmlColorSet(), skinParam); + return style.createTextBlockBordered(caption.getDisplay(), skinParam.getIHtmlColorSet(), skinParam, + Style.ID_CAPTION); } @@ -191,7 +192,7 @@ public class AnnotatedWorker { final Style style = StyleSignatureBasic.of(SName.root, SName.document, SName.title) .getMergedStyle(skinParam.getCurrentStyleBuilder()); final TextBlock block = style.createTextBlockBordered(title.getDisplay(), skinParam.getIHtmlColorSet(), - skinParam); + skinParam, Style.ID_TITLE); return DecorateEntityImage.addTop(original, block, HorizontalAlignment.CENTER); } diff --git a/src/net/sourceforge/plantuml/activitydiagram3/ftile/EntityImageLegend.java b/src/net/sourceforge/plantuml/activitydiagram3/ftile/EntityImageLegend.java index d64176e79..e84c09991 100644 --- a/src/net/sourceforge/plantuml/activitydiagram3/ftile/EntityImageLegend.java +++ b/src/net/sourceforge/plantuml/activitydiagram3/ftile/EntityImageLegend.java @@ -49,7 +49,7 @@ public class EntityImageLegend { final Style style = StyleSignatureBasic .of(SName.root, SName.root, SName.document, skinParam.getUmlDiagramType().getStyleName(), SName.legend) .getMergedStyle(skinParam.getCurrentStyleBuilder()); - return style.createTextBlockBordered(note, skinParam.getIHtmlColorSet(), skinParam); + return style.createTextBlockBordered(note, skinParam.getIHtmlColorSet(), skinParam, Style.ID_LEGEND); } } diff --git a/src/net/sourceforge/plantuml/activitydiagram3/ftile/vertical/FtileBoxOld.java b/src/net/sourceforge/plantuml/activitydiagram3/ftile/vertical/FtileBoxOld.java index d0501f0db..ff82a7c2f 100644 --- a/src/net/sourceforge/plantuml/activitydiagram3/ftile/vertical/FtileBoxOld.java +++ b/src/net/sourceforge/plantuml/activitydiagram3/ftile/vertical/FtileBoxOld.java @@ -57,7 +57,6 @@ import net.sourceforge.plantuml.creole.SheetBlock1; import net.sourceforge.plantuml.creole.SheetBlock2; import net.sourceforge.plantuml.creole.Stencil; import net.sourceforge.plantuml.cucadiagram.Display; -import net.sourceforge.plantuml.cucadiagram.Stereotype; import net.sourceforge.plantuml.graphic.FontConfiguration; import net.sourceforge.plantuml.graphic.HorizontalAlignment; import net.sourceforge.plantuml.graphic.Rainbow; @@ -135,23 +134,6 @@ public class FtileBoxOld extends AbstractFtile { } - public static FtileBoxOld create(ISkinParam skinParam, Display label, Swimlane swimlane, BoxStyle boxStyle, - Stereotype stereotype) { - final Style style = getDefaultStyleDefinitionActivity().withTOBECHANGED(stereotype) - .getMergedStyle(skinParam.getCurrentStyleBuilder()); - final Style styleArrow = getDefaultStyleDefinitionArrow().getMergedStyle(skinParam.getCurrentStyleBuilder()); - - return new FtileBoxOld(skinParam, label, swimlane, boxStyle, style, styleArrow); - } - - public static TextBlock createWbs(StyleBuilder styleBuilder, ISkinParam skinParam, Display label, - StyleSignatureBasic styleDefinition) { - final Style style = styleDefinition.getMergedStyle(styleBuilder); - final Style styleArrow = style; - - return new FtileBoxOld(skinParam, label, null, BoxStyle.PLAIN, style, styleArrow); - } - public static TextBlock createWbs(Style style, ISkinParam skinParam, Display label) { final Style styleArrow = style; return new FtileBoxOld(skinParam, label, null, BoxStyle.PLAIN, style, styleArrow); @@ -232,8 +214,7 @@ public class FtileBoxOld extends AbstractFtile { tb.drawU(ug.apply(new UTranslate(dimTotal.getWidth() - tbWidth(stringBounder) - padding.getRight(), padding.getBottom()))); else if (horizontalAlignment == HorizontalAlignment.CENTER) - tb.drawU(ug.apply(new UTranslate(padding.getRight() + (dimTotal.getWidth() - tbWidth(stringBounder)) / 2, - padding.getBottom()))); + tb.drawU(ug.apply(new UTranslate((dimTotal.getWidth() - tbWidth(stringBounder)) / 2, padding.getBottom()))); } diff --git a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java index f011d49d7..1274ab806 100644 --- a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java +++ b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java @@ -92,7 +92,8 @@ public class CommandCreateClassMultilines extends CommandMultilines2 1) { entity.setCodeLine(lines.getAt(0).getLocation()); lines = lines.subExtract(1, 1); @@ -165,9 +166,9 @@ public class CommandCreateClassMultilines extends CommandMultilines2 0 && VisibilityModifier.isVisibilityCharacter(s.getString())) { + if (s.getString().length() > 0 && VisibilityModifier.isVisibilityCharacter(s.getString())) diagram.setVisibilityModifierPresent(true); - } + entity.getBodier().addFieldOrMethod(s.getString()); } // if (url != null) { @@ -183,9 +184,9 @@ public class CommandCreateClassMultilines extends CommandMultilines2 LIMIT) { // Log.debug("Line truncated from " + s.length() + " to " + LIMIT); // s = s.substring(0, LIMIT); // } - if (s.startsWith("\uFEFF")) { + if (s.startsWith("\uFEFF")) s = s.substring(1); - } + s = s.replace('\u2013', '-'); // s = BackSlash.convertHiddenNewLine(s); // s = s.replace('\u00A0', ' '); diff --git a/src/net/sourceforge/plantuml/security/SURL.java b/src/net/sourceforge/plantuml/security/SURL.java index fb9a48777..c8533b84d 100644 --- a/src/net/sourceforge/plantuml/security/SURL.java +++ b/src/net/sourceforge/plantuml/security/SURL.java @@ -244,7 +244,7 @@ public class SURL { } private boolean forbiddenURL(String full) { - if (full.matches("^https?://[.0-9]+/.*")) + if (full.matches("^https?://[-#.0-9:\\[\\]+]+/.*")) return true; if (full.matches("^https?://[^.]+/.*")) return true; diff --git a/src/net/sourceforge/plantuml/sequencediagram/graphic/SequenceDiagramFileMakerPuma2.java b/src/net/sourceforge/plantuml/sequencediagram/graphic/SequenceDiagramFileMakerPuma2.java index 4068599af..a70690ce6 100644 --- a/src/net/sourceforge/plantuml/sequencediagram/graphic/SequenceDiagramFileMakerPuma2.java +++ b/src/net/sourceforge/plantuml/sequencediagram/graphic/SequenceDiagramFileMakerPuma2.java @@ -149,7 +149,7 @@ public class SequenceDiagramFileMakerPuma2 implements FileMaker { final Style style = StyleSignatureBasic.of(SName.root, SName.document, SName.title) .getMergedStyle(diagram.getSkinParam().getCurrentStyleBuilder()); compTitle = style.createTextBlockBordered(page.getTitle(), diagram.getSkinParam().getIHtmlColorSet(), - diagram.getSkinParam()); + diagram.getSkinParam(), Style.ID_TITLE); final Dimension2D dimTitle = compTitle.calculateDimension(stringBounder); area.setTitleArea(dimTitle.getWidth(), dimTitle.getHeight()); } @@ -163,7 +163,7 @@ public class SequenceDiagramFileMakerPuma2 implements FileMaker { final Style style = StyleSignatureBasic.of(SName.root, SName.document, SName.legend) .getMergedStyle(diagram.getSkinParam().getCurrentStyleBuilder()); legendBlock = style.createTextBlockBordered(diagram.getLegend().getDisplay(), - diagram.getSkinParam().getIHtmlColorSet(), diagram.getSkinParam()); + diagram.getSkinParam().getIHtmlColorSet(), diagram.getSkinParam(), Style.ID_LEGEND); } final Dimension2D dimLegend = legendBlock.calculateDimension(stringBounder); area.setLegend(dimLegend, isLegendTop(), diagram.getLegend().getHorizontalAlignment()); diff --git a/src/net/sourceforge/plantuml/sequencediagram/teoz/SequenceDiagramFileMakerTeoz.java b/src/net/sourceforge/plantuml/sequencediagram/teoz/SequenceDiagramFileMakerTeoz.java index d78dbe13f..18f84328c 100644 --- a/src/net/sourceforge/plantuml/sequencediagram/teoz/SequenceDiagramFileMakerTeoz.java +++ b/src/net/sourceforge/plantuml/sequencediagram/teoz/SequenceDiagramFileMakerTeoz.java @@ -209,7 +209,7 @@ public class SequenceDiagramFileMakerTeoz implements FileMaker { final Style style = StyleSignatureBasic.of(SName.root, SName.document, SName.title) .getMergedStyle(diagram.getSkinParam().getCurrentStyleBuilder()); final TextBlock compTitle = style.createTextBlockBordered(diagram.getTitle().getDisplay(), - diagram.getSkinParam().getIHtmlColorSet(), diagram.getSkinParam()); + diagram.getSkinParam().getIHtmlColorSet(), diagram.getSkinParam(), Style.ID_TITLE); return compTitle; } diff --git a/src/net/sourceforge/plantuml/skin/rose/ComponentRoseArrow.java b/src/net/sourceforge/plantuml/skin/rose/ComponentRoseArrow.java index 58dc71596..eec849af2 100644 --- a/src/net/sourceforge/plantuml/skin/rose/ComponentRoseArrow.java +++ b/src/net/sourceforge/plantuml/skin/rose/ComponentRoseArrow.java @@ -150,11 +150,10 @@ public class ComponentRoseArrow extends AbstractComponentRoseArrow { if (inclination1 == 0 && inclination2 == 0) getArrowConfiguration().applyStroke(ug).apply(new UTranslate(start, posArrow)).draw(new ULine(len, 0)); - else if (inclination1 != 0) { + else if (inclination1 != 0) drawLine(getArrowConfiguration().applyStroke(ug), start + len, posArrow, 0, posArrow + inclination1); - } else if (inclination2 != 0) { + else if (inclination2 != 0) drawLine(getArrowConfiguration().applyStroke(ug), start, posArrow, pos2, posArrow + inclination2); - } final ArrowDirection direction2 = getDirection2(); final double textPos; @@ -203,10 +202,12 @@ public class ComponentRoseArrow extends AbstractComponentRoseArrow { if (dressing.getHead() == ArrowHead.ASYNC) { if (dressing.getPart() != ArrowPart.BOTTOM_PART) - getArrowConfiguration().applyThicknessOnly(ug).draw(new ULine(getArrowDeltaX(), -getArrowDeltaY())); + getArrowConfiguration().applyThicknessOnly(ug).draw( + new ULine(getArrowDeltaX(), -getArrowDeltaY()).rotate(Math.atan2(-inclination1, lenFull))); if (dressing.getPart() != ArrowPart.TOP_PART) - getArrowConfiguration().applyThicknessOnly(ug).draw(new ULine(getArrowDeltaX(), getArrowDeltaY())); + getArrowConfiguration().applyThicknessOnly(ug) + .draw(new ULine(getArrowDeltaX(), getArrowDeltaY()).rotate(Math.atan2(-inclination1, lenFull))); } else if (dressing.getHead() == ArrowHead.CROSSX) { ug = ug.apply(new UStroke(2)); @@ -237,10 +238,12 @@ public class ComponentRoseArrow extends AbstractComponentRoseArrow { if (dressing.getHead() == ArrowHead.ASYNC) { if (dressing.getPart() != ArrowPart.BOTTOM_PART) - getArrowConfiguration().applyThicknessOnly(ug).draw(new ULine(-getArrowDeltaX(), -getArrowDeltaY())); + getArrowConfiguration().applyThicknessOnly(ug).draw( + new ULine(-getArrowDeltaX(), -getArrowDeltaY()).rotate(Math.atan2(inclination2, lenFull))); if (dressing.getPart() != ArrowPart.TOP_PART) - getArrowConfiguration().applyThicknessOnly(ug).draw(new ULine(-getArrowDeltaX(), getArrowDeltaY())); + getArrowConfiguration().applyThicknessOnly(ug) + .draw(new ULine(-getArrowDeltaX(), getArrowDeltaY()).rotate(Math.atan2(inclination2, lenFull))); } else if (dressing.getHead() == ArrowHead.CROSSX) { ug = ug.apply(new UStroke(2)); diff --git a/src/net/sourceforge/plantuml/style/Style.java b/src/net/sourceforge/plantuml/style/Style.java index c6badc0b3..9fc2b5763 100644 --- a/src/net/sourceforge/plantuml/style/Style.java +++ b/src/net/sourceforge/plantuml/style/Style.java @@ -269,8 +269,12 @@ public class Style { final FontConfiguration fc = getFontConfiguration(spriteContainer.getThemeStyle(), set); return display.create(fc, alignment, spriteContainer); } + + public static final String ID_TITLE = "_title"; + public static final String ID_CAPTION = "_caption"; + public static final String ID_LEGEND = "_legend"; - public TextBlock createTextBlockBordered(Display note, HColorSet set, ISkinSimple spriteContainer) { + public TextBlock createTextBlockBordered(Display note, HColorSet set, ISkinSimple spriteContainer, String id) { final HorizontalAlignment alignment = this.getHorizontalAlignment(); final TextBlock textBlock = this.createTextBlockInternal(note, set, spriteContainer, alignment); @@ -281,7 +285,7 @@ public class Style { final ClockwiseTopRightBottomLeft margin = this.getMargin(); final ClockwiseTopRightBottomLeft padding = this.getPadding(); final TextBlock result = TextBlockUtils.bordered(textBlock, stroke, lineColor, backgroundColor, cornersize, - padding); + padding, id); return TextBlockUtils.withMargin(result, margin); } diff --git a/src/net/sourceforge/plantuml/svek/ClusterDecoration.java b/src/net/sourceforge/plantuml/svek/ClusterDecoration.java index 4fce7f333..ba421b441 100644 --- a/src/net/sourceforge/plantuml/svek/ClusterDecoration.java +++ b/src/net/sourceforge/plantuml/svek/ClusterDecoration.java @@ -70,9 +70,9 @@ public class ClusterDecoration { } private static USymbol guess(USymbol symbol, PackageStyle style) { - if (symbol != null) { + if (symbol != null) return symbol; - } + return style.toUSymbol(); } diff --git a/src/net/sourceforge/plantuml/svek/image/EntityImageClass.java b/src/net/sourceforge/plantuml/svek/image/EntityImageClass.java index 1659a933c..5faae7513 100644 --- a/src/net/sourceforge/plantuml/svek/image/EntityImageClass.java +++ b/src/net/sourceforge/plantuml/svek/image/EntityImageClass.java @@ -169,14 +169,14 @@ public class EntityImageClass extends AbstractEntityImage implements Stencil, Wi double shadow = 0; - HColor classBorder = lineConfig.getColors().getColor(ColorType.LINE); + HColor borderColor = lineConfig.getColors().getColor(ColorType.LINE); HColor headerBackcolor = getEntity().getColors().getColor(ColorType.HEADER); HColor backcolor = getEntity().getColors().getColor(ColorType.BACK); shadow = getStyle().value(PName.Shadowing).asDouble(); - if (classBorder == null) - classBorder = getStyle().value(PName.LineColor).asColor(getSkinParam().getThemeStyle(), + if (borderColor == null) + borderColor = getStyle().value(PName.LineColor).asColor(getSkinParam().getThemeStyle(), getSkinParam().getIHtmlColorSet()); if (headerBackcolor == null) @@ -189,7 +189,7 @@ public class EntityImageClass extends AbstractEntityImage implements Stencil, Wi rect.setDeltaShadow(shadow); - ug = ug.apply(classBorder); + ug = ug.apply(borderColor); ug = ug.apply(backcolor.bg()); final UStroke stroke = getStyle().getStroke(lineConfig.getColors()); diff --git a/src/net/sourceforge/plantuml/svek/image/EntityImageMap.java b/src/net/sourceforge/plantuml/svek/image/EntityImageMap.java index af27409c3..05391cfcd 100644 --- a/src/net/sourceforge/plantuml/svek/image/EntityImageMap.java +++ b/src/net/sourceforge/plantuml/svek/image/EntityImageMap.java @@ -156,13 +156,16 @@ public class EntityImageMap extends AbstractEntityImage implements Stencil, With final double heightTotal = dimTotal.getHeight(); final Shadowable rect = new URectangle(widthTotal, heightTotal).rounded(roundCorner); + HColor borderColor = lineConfig.getColors().getColor(ColorType.LINE); HColor backcolor = getEntity().getColors().getColor(ColorType.BACK); HColor headerBackcolor = getEntity().getColors().getColor(ColorType.HEADER); final Style style = getStyle(); - final HColor borderColor = style.value(PName.LineColor).asColor(getSkinParam().getThemeStyle(), - getSkinParam().getIHtmlColorSet()); - + + if (borderColor == null) + borderColor = getStyle().value(PName.LineColor).asColor(getSkinParam().getThemeStyle(), + getSkinParam().getIHtmlColorSet()); + if (headerBackcolor == null) headerBackcolor = backcolor == null ? getStyleHeader().value(PName.BackGroundColor) .asColor(getSkinParam().getThemeStyle(), getSkinParam().getIHtmlColorSet()) : backcolor; @@ -170,7 +173,7 @@ public class EntityImageMap extends AbstractEntityImage implements Stencil, With if (backcolor == null) backcolor = style.value(PName.BackGroundColor).asColor(getSkinParam().getThemeStyle(), getSkinParam().getIHtmlColorSet()); - + rect.setDeltaShadow(style.value(PName.Shadowing).asDouble()); final UStroke stroke = style.getStroke(); @@ -184,7 +187,7 @@ public class EntityImageMap extends AbstractEntityImage implements Stencil, With typeIDent.put(UGroupType.ID, "elem_" + getEntity().getCode()); ug.startGroup(typeIDent); ug.apply(stroke).draw(rect); - + if (roundCorner == 0 && headerBackcolor != null && backcolor.equals(headerBackcolor) == false) { final Shadowable rect2 = new URectangle(widthTotal, dimTitle.getHeight()); final UGraphic ugHeader = ug.apply(headerBackcolor.bg()); diff --git a/src/net/sourceforge/plantuml/svek/image/Footprint.java b/src/net/sourceforge/plantuml/svek/image/Footprint.java index 0e8b2afa4..bb99e9ed9 100644 --- a/src/net/sourceforge/plantuml/svek/image/Footprint.java +++ b/src/net/sourceforge/plantuml/svek/image/Footprint.java @@ -46,6 +46,7 @@ import net.sourceforge.plantuml.graphic.StringBounder; import net.sourceforge.plantuml.graphic.UDrawable; import net.sourceforge.plantuml.ugraphic.UBackground; import net.sourceforge.plantuml.ugraphic.UChange; +import net.sourceforge.plantuml.ugraphic.UEllipse; import net.sourceforge.plantuml.ugraphic.UEmpty; import net.sourceforge.plantuml.ugraphic.UGraphic; import net.sourceforge.plantuml.ugraphic.UGraphicNo; @@ -111,6 +112,8 @@ public class Footprint { drawPath(x, y, (UPath) shape); } else if (shape instanceof URectangle) { drawRectangle(x, y, (URectangle) shape); + } else if (shape instanceof UEllipse) { + drawEllipse(x, y, (UEllipse) shape); } else if (shape instanceof UEmpty) { drawEmpty(x, y, (UEmpty) shape); } else { @@ -153,6 +156,11 @@ public class Footprint { addPoint(x + rect.getWidth(), y + rect.getHeight()); } + private void drawEllipse(double x, double y, UEllipse rect) { + addPoint(x, y); + addPoint(x + rect.getWidth(), y + rect.getHeight()); + } + private void drawEmpty(double x, double y, UEmpty rect) { addPoint(x, y); addPoint(x + rect.getWidth(), y + rect.getHeight()); diff --git a/src/net/sourceforge/plantuml/tim/EaterTheme.java b/src/net/sourceforge/plantuml/tim/EaterTheme.java index d78b1fe63..782a93ce6 100644 --- a/src/net/sourceforge/plantuml/tim/EaterTheme.java +++ b/src/net/sourceforge/plantuml/tim/EaterTheme.java @@ -38,6 +38,7 @@ import static java.nio.charset.StandardCharsets.UTF_8; import java.io.BufferedReader; import java.io.IOException; +import java.io.Reader; import java.io.UnsupportedEncodingException; import net.sourceforge.plantuml.AFile; @@ -114,7 +115,11 @@ public class EaterTheme extends Eater { try { final FileWithSuffix file = context.getFileWithSuffix(from, realName); - return ReadLineReader.create(file.getReader(UTF_8), "theme " + realName); + final Reader tmp = file.getReader(UTF_8); + if (tmp == null) + throw EaterException.located("No such theme " + realName); + + return ReadLineReader.create(tmp, "theme " + realName); } catch (IOException e) { e.printStackTrace(); throw EaterException.located("Cannot load " + realName); diff --git a/src/net/sourceforge/plantuml/timingdiagram/graphic/Ribbon.java b/src/net/sourceforge/plantuml/timingdiagram/graphic/Ribbon.java index 57265ff66..adbec2af6 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/graphic/Ribbon.java +++ b/src/net/sourceforge/plantuml/timingdiagram/graphic/Ribbon.java @@ -151,7 +151,8 @@ public class Ribbon implements PDrawing { private void drawNotes(UGraphic ug, final Position position) { for (TimingNote note : notes) if (note.getPosition() == position) { - final double x = ruler.getPosInPixel(note.getWhen()); + final TimeTick when = note.getWhen(); + final double x = when == null ? 0 : ruler.getPosInPixel(when); note.drawU(ug.apply(UTranslate.dx(x))); } } diff --git a/src/net/sourceforge/plantuml/ugraphic/ULine.java b/src/net/sourceforge/plantuml/ugraphic/ULine.java index cb5c5be3e..2f6fbed49 100644 --- a/src/net/sourceforge/plantuml/ugraphic/ULine.java +++ b/src/net/sourceforge/plantuml/ugraphic/ULine.java @@ -35,6 +35,7 @@ */ package net.sourceforge.plantuml.ugraphic; +import java.awt.geom.AffineTransform; import java.awt.geom.Point2D; public class ULine extends AbstractShadowable implements UShapeSized { @@ -51,6 +52,14 @@ public class ULine extends AbstractShadowable implements UShapeSized { this.dy = dy; } + public ULine rotate(double theta) { + if (theta == 0) + return this; + final AffineTransform rot = AffineTransform.getRotateInstance(theta); + final Point2D result = rot.transform(new Point2D.Double(dx, dy), null); + return new ULine(result.getX(), result.getY()); + } + public static ULine hline(double dx) { return new ULine(dx, 0); } diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index 729f441ea..0c650fa8d 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -80,7 +80,7 @@ public class Version { } public static int beta() { - final int beta = 0; + final int beta = 1; return beta; } diff --git a/src/net/sourceforge/plantuml/yaml/YamlLines.java b/src/net/sourceforge/plantuml/yaml/YamlLines.java index 7fdf08ad0..5ea9b1afe 100644 --- a/src/net/sourceforge/plantuml/yaml/YamlLines.java +++ b/src/net/sourceforge/plantuml/yaml/YamlLines.java @@ -44,15 +44,15 @@ import java.util.regex.Pattern; public class YamlLines implements Iterable { - public static final String KEY = "([^:\\s]+)"; + public static final String KEY = "([^:]+)"; private List lines = new ArrayList<>(); public YamlLines(List rawLines) { for (String s : rawLines) { - if (s.startsWith("#")) { + if (s.startsWith("#")) continue; - } + s = removeDiese(s); if (s.trim().length() == 0) continue; @@ -79,9 +79,9 @@ public class YamlLines implements Iterable { private String removeDiese(String s) { final int idx = s.indexOf(" #"); - if (idx == -1) { + if (idx == -1) return s; - } + return s.substring(0, idx); } @@ -104,9 +104,9 @@ public class YamlLines implements Iterable { } private void removeFirstCols(int startingEmptyCols) { - if (startingEmptyCols == 0) { + if (startingEmptyCols == 0) return; - } + for (ListIterator it = lines.listIterator(); it.hasNext();) { final String s = it.next().substring(startingEmptyCols); it.set(s); @@ -117,9 +117,8 @@ public class YamlLines implements Iterable { int result = Integer.MAX_VALUE; for (String s : lines) { result = Math.min(result, startingSpaces(s)); - if (result == 0) { + if (result == 0) return 0; - } } return result; } @@ -127,9 +126,9 @@ public class YamlLines implements Iterable { private static int startingSpaces(String s) { final Pattern p1 = Pattern.compile("^(\\s*).*"); final Matcher m1 = p1.matcher(s); - if (m1.matches()) { + if (m1.matches()) return m1.group(1).length(); - } + return 0; } From 649a13e04b725b2455770e0c6f3b824a33e72db7 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Mon, 27 Jun 2022 18:34:58 +0200 Subject: [PATCH 10/14] Workaround for issue https://github.com/plantuml/plantuml/issues/1036 --- .../ascii2image/graphics/CompositeDiagramShape.java | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/org/stathissideris/ascii2image/graphics/CompositeDiagramShape.java b/src/org/stathissideris/ascii2image/graphics/CompositeDiagramShape.java index 108f01e4a..1d7ab045e 100644 --- a/src/org/stathissideris/ascii2image/graphics/CompositeDiagramShape.java +++ b/src/org/stathissideris/ascii2image/graphics/CompositeDiagramShape.java @@ -122,7 +122,12 @@ public class CompositeDiagramShape extends DiagramComponent { if(workGrid.cellContainsDashedLineChar(previousCell)) shape.setStrokeDashed(true); boolean finished = false; + int nb = 0; while(!finished) { + // https://github.com/plantuml/plantuml/issues/1036 + nb++; + if (nb > 1000) + return result; visitedCells.add(cell); if(workGrid.isPointCell(cell)) { if(DEBUG) System.out.println("point at "+cell+" (call from line: "+DebugUtils.getLineNumber()+")"); From ac9d76cda6b2d7c7faa48ee011da070de868f3dc Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Wed, 29 Jun 2022 18:45:19 +0200 Subject: [PATCH 11/14] wip --- .../plantuml/cucadiagram/Elected.java | 5 ++ .../plantuml/cucadiagram/EntityPort.java | 8 +-- .../cucadiagram/MethodsOrFieldsArea.java | 39 ++++++++---- src/net/sourceforge/plantuml/style/SName.java | 1 + .../plantuml/timingdiagram/PlayerAnalog.java | 59 +++++++++++++------ .../plantuml/timingdiagram/PlayerBinary.java | 1 + .../plantuml/timingdiagram/PlayerClock.java | 1 + .../plantuml/timingdiagram/TimingDiagram.java | 4 +- .../timingdiagram/command/CommandAnalog.java | 18 +++++- .../sourceforge/plantuml/version/Version.java | 2 +- 10 files changed, 101 insertions(+), 37 deletions(-) diff --git a/src/net/sourceforge/plantuml/cucadiagram/Elected.java b/src/net/sourceforge/plantuml/cucadiagram/Elected.java index 0a99093eb..f1b445159 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/Elected.java +++ b/src/net/sourceforge/plantuml/cucadiagram/Elected.java @@ -40,6 +40,11 @@ class Elected { private final String shortName; private final int score; + @Override + public String toString() { + return shortName + "/" + score; + } + public Elected(String shortName, int score) { this.shortName = shortName; this.score = score; diff --git a/src/net/sourceforge/plantuml/cucadiagram/EntityPort.java b/src/net/sourceforge/plantuml/cucadiagram/EntityPort.java index 741b08eb2..45ba7a03f 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/EntityPort.java +++ b/src/net/sourceforge/plantuml/cucadiagram/EntityPort.java @@ -48,9 +48,9 @@ public class EntityPort { } public String getFullString() { - if (portId != null) { + if (portId != null) return entityUid + ":" + portId; - } + return entityUid; } @@ -59,9 +59,9 @@ public class EntityPort { } public String getPrefix() { - if (isShielded()) { + if (isShielded()) return entityUid.substring(0, entityUid.length() - 2); - } + return entityUid; } diff --git a/src/net/sourceforge/plantuml/cucadiagram/MethodsOrFieldsArea.java b/src/net/sourceforge/plantuml/cucadiagram/MethodsOrFieldsArea.java index cc1edc1d8..8ef6c1f60 100644 --- a/src/net/sourceforge/plantuml/cucadiagram/MethodsOrFieldsArea.java +++ b/src/net/sourceforge/plantuml/cucadiagram/MethodsOrFieldsArea.java @@ -36,8 +36,11 @@ package net.sourceforge.plantuml.cucadiagram; import java.awt.geom.Rectangle2D; +import java.util.ArrayList; import java.util.Collection; -import java.util.HashSet; +import java.util.Collections; +import java.util.Comparator; +import java.util.List; import net.sourceforge.plantuml.Dimension2DDouble; import net.sourceforge.plantuml.EmbeddedDiagram; @@ -130,21 +133,37 @@ public class MethodsOrFieldsArea extends AbstractTextBlock implements TextBlock, return new Dimension2DDouble(x, y); } + private Collection sortBySize(Collection all) { + final List result = new ArrayList(all); + Collections.sort(result, new Comparator() { + @Override + public int compare(String s1, String s2) { + final int diff = s2.length() - s1.length(); + if (diff != 0) + return diff; + return s1.compareTo(s2); + } + }); + return result; + } + @Override public Ports getPorts(StringBounder stringBounder) { - final Ports result = new Ports(); + final Ports ports = new Ports(); double y = 0; + final Collection shortNames = sortBySize(leaf.getPortShortNames()); + for (CharSequence cs : members) { final TextBlock bloc = createTextBlock(cs); final Dimension2D dim = bloc.calculateDimension(stringBounder); - final Elected port = getElected(leaf.getPortShortNames(), convert(cs)); - if (port != null) - result.add(port.getShortName(), port.getScore(), y, dim.getHeight()); + final Elected elected = getElected(convert(cs), shortNames); + if (elected != null) + ports.add(elected.getShortName(), elected.getScore(), y, dim.getHeight()); y += dim.getHeight(); } - return result; + return ports; } private String convert(CharSequence cs) { @@ -153,16 +172,16 @@ public class MethodsOrFieldsArea extends AbstractTextBlock implements TextBlock, return cs.toString(); } - public Elected getElected(Collection shortNames, String cs) { - for (String shortName : new HashSet<>(shortNames)) { - final int score = getScore(shortName, cs); + public Elected getElected(String cs, Collection shortNames) { + for (String shortName : shortNames) { + final int score = getScore(cs, shortName); if (score > 0) return new Elected(shortName, score); } return null; } - private int getScore(String shortName, String cs) { + private int getScore(String cs, String shortName) { if (cs.matches(".*\\b" + shortName + "\\b.*")) return 100; diff --git a/src/net/sourceforge/plantuml/style/SName.java b/src/net/sourceforge/plantuml/style/SName.java index 7ac06353d..742d67bb9 100644 --- a/src/net/sourceforge/plantuml/style/SName.java +++ b/src/net/sourceforge/plantuml/style/SName.java @@ -41,6 +41,7 @@ public enum SName { activityDiagram, // actor, // agent, // + analog, // archimate, // arrow, // artifact, // diff --git a/src/net/sourceforge/plantuml/timingdiagram/PlayerAnalog.java b/src/net/sourceforge/plantuml/timingdiagram/PlayerAnalog.java index 341831ad7..ccfd23e3d 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/PlayerAnalog.java +++ b/src/net/sourceforge/plantuml/timingdiagram/PlayerAnalog.java @@ -35,6 +35,8 @@ package net.sourceforge.plantuml.timingdiagram; import java.awt.geom.Point2D; +import java.util.ArrayList; +import java.util.List; import java.util.Map; import java.util.Map.Entry; import java.util.SortedMap; @@ -45,6 +47,7 @@ import net.sourceforge.plantuml.ISkinParam; import net.sourceforge.plantuml.awt.geom.Dimension2D; import net.sourceforge.plantuml.command.Position; import net.sourceforge.plantuml.cucadiagram.Display; +import net.sourceforge.plantuml.cucadiagram.Stereotype; import net.sourceforge.plantuml.graphic.AbstractTextBlock; import net.sourceforge.plantuml.graphic.HorizontalAlignment; import net.sourceforge.plantuml.graphic.StringBounder; @@ -52,6 +55,7 @@ import net.sourceforge.plantuml.graphic.TextBlock; import net.sourceforge.plantuml.graphic.UDrawable; import net.sourceforge.plantuml.graphic.color.Colors; import net.sourceforge.plantuml.style.SName; +import net.sourceforge.plantuml.style.StyleSignature; import net.sourceforge.plantuml.style.StyleSignatureBasic; import net.sourceforge.plantuml.timingdiagram.graphic.IntricatedPoint; import net.sourceforge.plantuml.ugraphic.UGraphic; @@ -61,14 +65,17 @@ import net.sourceforge.plantuml.ugraphic.UTranslate; public class PlayerAnalog extends Player { private final SortedMap values = new TreeMap(); + + private final List constraints = new ArrayList<>(); + private final double ymargin = 8; private Double initialState; private Double start; private Double end; private Integer ticksEvery; - public PlayerAnalog(String code, ISkinParam skinParam, TimingRuler ruler, boolean compact) { - super(code, skinParam, ruler, compact, null); + public PlayerAnalog(String code, ISkinParam skinParam, TimingRuler ruler, boolean compact, Stereotype stereotype) { + super(code, skinParam, ruler, compact, stereotype); this.suggestedHeight = 100; } @@ -94,16 +101,17 @@ public class PlayerAnalog extends Player { } public double getFullHeight(StringBounder stringBounder) { - return suggestedHeight; + return getHeightForConstraints(stringBounder) + suggestedHeight; } public IntricatedPoint getTimeProjection(StringBounder stringBounder, TimeTick tick) { final double x = ruler.getPosInPixel(tick); - final double value = getValueAt(tick); - return new IntricatedPoint(new Point2D.Double(x, getYpos(value)), new Point2D.Double(x, getYpos(value))); + final double value = getValueAt(stringBounder, tick); + return new IntricatedPoint(new Point2D.Double(x, getYpos(stringBounder, value)), + new Point2D.Double(x, getYpos(stringBounder, value))); } - private double getValueAt(TimeTick tick) { + private double getValueAt(StringBounder stringBounder, TimeTick tick) { final Double result = values.get(tick); if (result != null) return result; @@ -155,14 +163,14 @@ public class PlayerAnalog extends Player { } } + @Override public void createConstraint(TimeTick tick1, TimeTick tick2, String message) { - throw new UnsupportedOperationException(); + this.constraints.add(new TimeConstraint(tick1, tick2, message, skinParam)); } - private double getYpos(double value) { - final double fullHeight = getFullHeight(null); - final double y = (value - getMin()) * (fullHeight - 2 * ymargin) / (getMax() - getMin()); - return fullHeight - ymargin - y; + private double getYpos(StringBounder stringBounder, double value) { + final double y = (value - getMin()) * (suggestedHeight - 2 * ymargin) / (getMax() - getMin()); + return getHeightForConstraints(stringBounder) + suggestedHeight - ymargin - y; } public TextBlock getPart1(final double fullAvailableWidth, final double specialVSpace) { @@ -224,7 +232,7 @@ public class PlayerAnalog extends Player { final TextBlock label = getTextBlock(value); final Dimension2D dim = label.calculateDimension(ug.getStringBounder()); ug = ug.apply(UTranslate.dx(fullAvailableWidth - dim.getWidth() - 2)); - label.drawU(ug.apply(UTranslate.dy(getYpos(value) - dim.getHeight() / 2))); + label.drawU(ug.apply(UTranslate.dy(getYpos(ug.getStringBounder(), value) - dim.getHeight() / 2))); } private TextBlock getTextBlock(double value) { @@ -239,7 +247,7 @@ public class PlayerAnalog extends Player { final ULine hline = ULine.hline(ruler.getWidth()); for (int i = first; i <= last; i++) if (i % ticksEvery == 0) - ug.apply(UTranslate.dy(getYpos(i))).draw(hline); + ug.apply(UTranslate.dy(getYpos(ug.getStringBounder(), i))).draw(hline); } @@ -253,14 +261,18 @@ public class PlayerAnalog extends Player { double lastx = 0; double lastValue = initialState == null ? 0 : initialState; for (Map.Entry ent : values.entrySet()) { - final double y1 = getYpos(lastValue); - final double y2 = getYpos(ent.getValue()); + final double y1 = getYpos(ug.getStringBounder(), lastValue); + final double y2 = getYpos(ug.getStringBounder(), ent.getValue()); final double x = ruler.getPosInPixel(ent.getKey()); ug.apply(new UTranslate(lastx, y1)).draw(new ULine(x - lastx, y2 - y1)); lastx = x; lastValue = ent.getValue(); } - ug.apply(new UTranslate(lastx, getYpos(lastValue))).draw(ULine.hline(ruler.getWidth() - lastx)); + ug.apply(new UTranslate(lastx, getYpos(ug.getStringBounder(), lastValue))) + .draw(ULine.hline(ruler.getWidth() - lastx)); + + drawConstraints(ug.apply(UTranslate.dy(getHeightForConstraints(ug.getStringBounder())))); + } }; } @@ -275,8 +287,19 @@ public class PlayerAnalog extends Player { } @Override - protected StyleSignatureBasic getStyleSignature() { - return StyleSignatureBasic.of(SName.root, SName.element, SName.timingDiagram); + protected StyleSignature getStyleSignature() { + return StyleSignatureBasic.of(SName.root, SName.element, SName.timingDiagram, SName.analog) + .withTOBECHANGED(stereotype); + } + + private void drawConstraints(final UGraphic ug) { + for (TimeConstraint constraint : constraints) { + constraint.drawU(ug, ruler); + } + } + + private double getHeightForConstraints(StringBounder stringBounder) { + return TimeConstraint.getHeightForConstraints(stringBounder, constraints); } } diff --git a/src/net/sourceforge/plantuml/timingdiagram/PlayerBinary.java b/src/net/sourceforge/plantuml/timingdiagram/PlayerBinary.java index fa3ddf3be..a14f2397b 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/PlayerBinary.java +++ b/src/net/sourceforge/plantuml/timingdiagram/PlayerBinary.java @@ -126,6 +126,7 @@ public class PlayerBinary extends Player { return LOW_STRING; } + @Override public void createConstraint(TimeTick tick1, TimeTick tick2, String message) { this.constraints.add(new TimeConstraint(tick1, tick2, message, skinParam)); } diff --git a/src/net/sourceforge/plantuml/timingdiagram/PlayerClock.java b/src/net/sourceforge/plantuml/timingdiagram/PlayerClock.java index 70cfc11e7..31778fe6b 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/PlayerClock.java +++ b/src/net/sourceforge/plantuml/timingdiagram/PlayerClock.java @@ -106,6 +106,7 @@ public class PlayerClock extends Player { throw new UnsupportedOperationException(); } + @Override public void createConstraint(TimeTick tick1, TimeTick tick2, String message) { throw new UnsupportedOperationException(); } diff --git a/src/net/sourceforge/plantuml/timingdiagram/TimingDiagram.java b/src/net/sourceforge/plantuml/timingdiagram/TimingDiagram.java index 08bb3d87d..8a8152f4b 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/TimingDiagram.java +++ b/src/net/sourceforge/plantuml/timingdiagram/TimingDiagram.java @@ -313,8 +313,8 @@ public class TimingDiagram extends UmlDiagram implements Clocks { return CommandExecutionResult.ok(); } - public PlayerAnalog createAnalog(String code, String full, boolean compact) { - final PlayerAnalog player = new PlayerAnalog(full, getSkinParam(), ruler, compactByDefault); + public PlayerAnalog createAnalog(String code, String full, boolean compact, Stereotype stereotype) { + final PlayerAnalog player = new PlayerAnalog(full, getSkinParam(), ruler, compactByDefault, stereotype); players.put(code, player); return player; } diff --git a/src/net/sourceforge/plantuml/timingdiagram/command/CommandAnalog.java b/src/net/sourceforge/plantuml/timingdiagram/command/CommandAnalog.java index a90697cd7..71e766f77 100644 --- a/src/net/sourceforge/plantuml/timingdiagram/command/CommandAnalog.java +++ b/src/net/sourceforge/plantuml/timingdiagram/command/CommandAnalog.java @@ -43,6 +43,7 @@ import net.sourceforge.plantuml.command.regex.RegexConcat; import net.sourceforge.plantuml.command.regex.RegexLeaf; import net.sourceforge.plantuml.command.regex.RegexOptional; import net.sourceforge.plantuml.command.regex.RegexResult; +import net.sourceforge.plantuml.cucadiagram.Stereotype; import net.sourceforge.plantuml.timingdiagram.PlayerAnalog; import net.sourceforge.plantuml.timingdiagram.TimingDiagram; @@ -61,6 +62,8 @@ public class CommandAnalog extends SingleLineCommand2 { new RegexLeaf("analog"), // RegexLeaf.spaceOneOrMore(), // new RegexLeaf("FULL", "[%g]([^%g]+)[%g]"), // + RegexLeaf.spaceZeroOrMore(), // + new RegexLeaf("STEREOTYPE", "(\\<\\<.*\\>\\>)?"), // RegexLeaf.spaceOneOrMore(), // new RegexOptional(// new RegexConcat( // @@ -74,7 +77,11 @@ public class CommandAnalog extends SingleLineCommand2 { RegexLeaf.spaceOneOrMore())), // new RegexLeaf("as"), // RegexLeaf.spaceOneOrMore(), // - new RegexLeaf("CODE", "([%pLN_.@]+)"), RegexLeaf.end()); + new RegexLeaf("CODE", "([%pLN_.@]+)"), // + RegexLeaf.spaceZeroOrMore(), // + new RegexLeaf("STEREOTYPE2", "(\\<\\<.*\\>\\>)?"), // + RegexLeaf.spaceZeroOrMore(), // + RegexLeaf.end()); } @Override @@ -82,7 +89,14 @@ public class CommandAnalog extends SingleLineCommand2 { final String compact = arg.get("COMPACT", 0); final String code = arg.get("CODE", 0); final String full = arg.get("FULL", 0); - final PlayerAnalog player = diagram.createAnalog(code, full, compact != null); + + Stereotype stereotype = null; + if (arg.get("STEREOTYPE", 0) != null) + stereotype = Stereotype.build(arg.get("STEREOTYPE", 0)); + else if (arg.get("STEREOTYPE2", 0) != null) + stereotype = Stereotype.build(arg.get("STEREOTYPE2", 0)); + + final PlayerAnalog player = diagram.createAnalog(code, full, compact != null, stereotype); final String start = arg.get("START", 0); final String end = arg.get("END", 0); if (start != null && end != null) { diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index 0c650fa8d..d8d94a7d7 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -80,7 +80,7 @@ public class Version { } public static int beta() { - final int beta = 1; + final int beta = 2; return beta; } From d926c4bfcb8eb6d5b8abafe69b08127c2e6dc3c3 Mon Sep 17 00:00:00 2001 From: PlantUML Date: Mon, 4 Jul 2022 12:23:41 +0200 Subject: [PATCH 12/14] Setting CORS --- src/net/sourceforge/plantuml/picoweb/PicoWebServer.java | 1 + 1 file changed, 1 insertion(+) diff --git a/src/net/sourceforge/plantuml/picoweb/PicoWebServer.java b/src/net/sourceforge/plantuml/picoweb/PicoWebServer.java index 5d4dddfa8..b23cfd118 100644 --- a/src/net/sourceforge/plantuml/picoweb/PicoWebServer.java +++ b/src/net/sourceforge/plantuml/picoweb/PicoWebServer.java @@ -223,6 +223,7 @@ public class PicoWebServer implements Runnable { write(out, "Cache-Control: no-cache"); write(out, "Server: PlantUML PicoWebServer " + Version.versionString()); write(out, "Date: " + new Date()); + write(out, "Access-Control-Allow-Origin: *"); write(out, "Content-type: " + fileFormatOption.getFileFormat().getMimeType()); write(out, "Content-length: " + fileData.length); write(out, "X-PlantUML-Diagram-Width: " + imageData.getWidth()); From 227045a4ae73a7f2707a6c339a25af03fd36a545 Mon Sep 17 00:00:00 2001 From: Arnaud Roques Date: Mon, 4 Jul 2022 18:40:37 +0200 Subject: [PATCH 13/14] fix https://github.com/plantuml/plantuml/issues/1053 --- .../sourceforge/plantuml/svg/SvgGraphics.java | 39 ++++++++++++++++++- .../sourceforge/plantuml/version/Version.java | 2 +- 2 files changed, 38 insertions(+), 3 deletions(-) diff --git a/src/net/sourceforge/plantuml/svg/SvgGraphics.java b/src/net/sourceforge/plantuml/svg/SvgGraphics.java index 7c01ae1bc..213a624e7 100644 --- a/src/net/sourceforge/plantuml/svg/SvgGraphics.java +++ b/src/net/sourceforge/plantuml/svg/SvgGraphics.java @@ -71,6 +71,7 @@ import net.sourceforge.plantuml.SignatureUtils; import net.sourceforge.plantuml.awt.geom.Dimension2D; import net.sourceforge.plantuml.code.Base64Coder; import net.sourceforge.plantuml.security.SImageIO; +import net.sourceforge.plantuml.security.SecurityProfile; import net.sourceforge.plantuml.security.SecurityUtils; import net.sourceforge.plantuml.tikz.TikzGraphics; import net.sourceforge.plantuml.ugraphic.UGroupType; @@ -641,8 +642,19 @@ public class SvgGraphics { } public void createXml(OutputStream os) throws TransformerException, IOException { - createXmlInternal(os); -// s = removeXmlHeader(s); + if (images.size() == 0) { + createXmlInternal(os); + return; + } + final ByteArrayOutputStream baos = new ByteArrayOutputStream(); + createXmlInternal(baos); + String s = new String(baos.toByteArray()); + for (Map.Entry ent : images.entrySet()) { + final String k = "<" + ent.getKey() + "/>"; + s = s.replace(k, ent.getValue()); + } + s = removeXmlHeader(s); + os.write(s.getBytes()); } private String removeXmlHeader(String s) { @@ -882,7 +894,30 @@ public class SvgGraphics { ensureVisible(x + image.getWidth(), y + image.getHeight()); } + private final Map images = new HashMap(); + + + private void svgImageUnsecure(UImageSvg image, double x, double y) { + if (hidden == false) { + String svg = manageScale(image); + final String pos = ""; + svg = pos + svg.substring(5); + final String key = "imagesvginlined" + image.getMD5Hex() + images.size(); + final Element elt = (Element) document.createElement(key); + getG().appendChild(elt); + images.put(key, svg); + } + ensureVisible(x, y); + ensureVisible(x + image.getData("width"), y + image.getData("height")); + } + + public void svgImage(UImageSvg image, double x, double y) { + if (SecurityUtils.getSecurityProfile() == SecurityProfile.UNSECURE) { + svgImageUnsecure(image, x, y); + return; + } + // https://developer.mozilla.org/fr/docs/Web/SVG/Element/image if (hidden == false) { final Element elt = (Element) document.createElement("image"); diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index d8d94a7d7..3de4de91b 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -80,7 +80,7 @@ public class Version { } public static int beta() { - final int beta = 2; + final int beta = 3; return beta; } From c6c2343ee95e21257bd1e9f8d88056acfe2e6a01 Mon Sep 17 00:00:00 2001 From: The-Lum <86879521+The-Lum@users.noreply.github.com> Date: Wed, 13 Jul 2022 23:39:29 +0000 Subject: [PATCH 14/14] add support for `Exception` in class diagram --- skin/plantuml.skin | 6 ++++++ .../plantuml/classdiagram/command/CommandCreateClass.java | 2 +- .../classdiagram/command/CommandCreateClassMultilines.java | 2 +- .../classdiagram/command/CommandHideShowByGender.java | 4 ++++ .../plantuml/classdiagram/command/CommandLinkLollipop.java | 2 +- src/net/sourceforge/plantuml/cucadiagram/LeafType.java | 5 +++-- src/net/sourceforge/plantuml/style/SName.java | 1 + .../plantuml/svek/image/EntityImageClassHeader.java | 4 ++++ 8 files changed, 21 insertions(+), 5 deletions(-) diff --git a/skin/plantuml.skin b/skin/plantuml.skin index 641e5e181..d2183accf 100644 --- a/skin/plantuml.skin +++ b/skin/plantuml.skin @@ -205,6 +205,9 @@ spot { spotEntity { BackgroundColor #ADD1B2 } + spotException { + BackgroundColor #D94321 + } } @@ -551,6 +554,9 @@ spot { spotEntity { BackgroundColor #2E5233 } + spotException { + BackgroundColor #7D0000 + } } diff --git a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClass.java b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClass.java index 980d3166f..f49233dad 100644 --- a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClass.java +++ b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClass.java @@ -80,7 +80,7 @@ public class CommandCreateClass extends SingleLineCommand2 { private static IRegex getRegexConcat() { return RegexConcat.build(CommandCreateClass.class.getName(), RegexLeaf.start(), // new RegexLeaf("TYPE", // - "(interface|enum|annotation|abstract[%s]+class|abstract|class|entity|circle|diamond|protocol|struct)"), // + "(interface|enum|annotation|abstract[%s]+class|abstract|class|entity|circle|diamond|protocol|struct|exception)"), // RegexLeaf.spaceOneOrMore(), // new RegexOr(// new RegexConcat(// diff --git a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java index 1274ab806..ee891ebce 100644 --- a/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java +++ b/src/net/sourceforge/plantuml/classdiagram/command/CommandCreateClassMultilines.java @@ -93,7 +93,7 @@ public class CommandCreateClassMultilines extends CommandMultilines2 { gender = EntityGenderUtils.byEntityType(LeafType.ABSTRACT_CLASS); } else if (arg1.equalsIgnoreCase("annotation")) { gender = EntityGenderUtils.byEntityType(LeafType.ANNOTATION); + } else if (arg1.equalsIgnoreCase("exception")) { + gender = EntityGenderUtils.byEntityType(LeafType.EXCEPTION); } else if (arg1.startsWith("<<")) { gender = EntityGenderUtils.byStereotype(arg1); } else { @@ -167,6 +169,8 @@ public class CommandHideShowByGender extends SingleLineCommand2 { gender = EntityGenderUtils.byEntityType(LeafType.PROTOCOL); } else if (arg1.equalsIgnoreCase("struct")) { gender = EntityGenderUtils.byEntityType(LeafType.STRUCT); + } else if (arg1.equalsIgnoreCase("exception")) { + gender = EntityGenderUtils.byEntityType(LeafType.EXCEPTION); } else if (arg1.startsWith("<<")) { gender = EntityGenderUtils.byStereotype(arg1); } else { diff --git a/src/net/sourceforge/plantuml/classdiagram/command/CommandLinkLollipop.java b/src/net/sourceforge/plantuml/classdiagram/command/CommandLinkLollipop.java index d9b1bd146..d8755c7c1 100644 --- a/src/net/sourceforge/plantuml/classdiagram/command/CommandLinkLollipop.java +++ b/src/net/sourceforge/plantuml/classdiagram/command/CommandLinkLollipop.java @@ -95,7 +95,7 @@ final public class CommandLinkLollipop extends SingleLineCommand2