diff --git a/src/net/sourceforge/plantuml/decoration/symbol/USymbolActorBusiness.java b/src/net/sourceforge/plantuml/decoration/symbol/USymbolActorBusiness.java new file mode 100644 index 000000000..501afd463 --- /dev/null +++ b/src/net/sourceforge/plantuml/decoration/symbol/USymbolActorBusiness.java @@ -0,0 +1,57 @@ +/* ======================================================================== + * PlantUML : a free UML diagram generator + * ======================================================================== + * + * (C) Copyright 2009-2024, Arnaud Roques + * + * Project Info: https://plantuml.com + * + * If you like this project or if you find it useful, you can support us at: + * + * https://plantuml.com/patreon (only 1$ per month!) + * https://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.decoration.symbol; + +import net.sourceforge.plantuml.klimt.Fashion; +import net.sourceforge.plantuml.klimt.shape.TextBlock; +import net.sourceforge.plantuml.skin.ActorStyle; +import net.sourceforge.plantuml.style.SName; + +public class USymbolActorBusiness extends USymbolSimpleAbstract { + + private final ActorStyle actorStyle = ActorStyle.STICKMAN_BUSINESS; + + @Override + public SName getSName() { + return SName.business; + } + + @Override + protected TextBlock getDrawing(Fashion symbolContext) { + return actorStyle.getTextBlock(symbolContext); + } + +} \ No newline at end of file diff --git a/src/net/sourceforge/plantuml/decoration/symbol/USymbols.java b/src/net/sourceforge/plantuml/decoration/symbol/USymbols.java index a4f62aa2e..b2f64a4a2 100644 --- a/src/net/sourceforge/plantuml/decoration/symbol/USymbols.java +++ b/src/net/sourceforge/plantuml/decoration/symbol/USymbols.java @@ -77,8 +77,7 @@ public abstract class USymbols { public final static USymbol COLLECTIONS = record("COLLECTIONS", new USymbolCollections()); public final static USymbol AGENT = record("AGENT", new USymbolRectangle(SName.agent)); public final static USymbol ACTOR_STICKMAN = record("ACTOR_STICKMAN", new USymbolActor(ActorStyle.STICKMAN)); - public final static USymbol ACTOR_STICKMAN_BUSINESS = record("ACTOR_STICKMAN_BUSINESS", - new USymbolActor(ActorStyle.STICKMAN_BUSINESS)); + public final static USymbol ACTOR_STICKMAN_BUSINESS = record("ACTOR_STICKMAN_BUSINESS", new USymbolActorBusiness()); public final static USymbol ACTOR_AWESOME = record("ACTOR_AWESOME", new USymbolActor(ActorStyle.AWESOME)); public final static USymbol ACTOR_HOLLOW = record("ACTOR_HOLLOW", new USymbolActor(ActorStyle.HOLLOW)); public final static USymbol USECASE = null; diff --git a/src/net/sourceforge/plantuml/descdiagram/DescriptionDiagram.java b/src/net/sourceforge/plantuml/descdiagram/DescriptionDiagram.java index b301585ba..e8f2f0a4a 100644 --- a/src/net/sourceforge/plantuml/descdiagram/DescriptionDiagram.java +++ b/src/net/sourceforge/plantuml/descdiagram/DescriptionDiagram.java @@ -58,6 +58,10 @@ public class DescriptionDiagram extends AbstractEntityDiagram { return null; if (id.startsWith("()")) id = StringUtils.trin(id.substring(2)); + if (id.startsWith(":") && id.endsWith(":/")) + return id.substring(1, id.length() - 2); + if (id.startsWith("(") && id.endsWith(")/")) + return id.substring(1, id.length() - 2); return super.cleanId(id); } diff --git a/src/net/sourceforge/plantuml/descdiagram/command/CommandLinkElement.java b/src/net/sourceforge/plantuml/descdiagram/command/CommandLinkElement.java index 98a364e9e..69f48f068 100644 --- a/src/net/sourceforge/plantuml/descdiagram/command/CommandLinkElement.java +++ b/src/net/sourceforge/plantuml/descdiagram/command/CommandLinkElement.java @@ -57,6 +57,7 @@ import net.sourceforge.plantuml.regex.RegexConcat; import net.sourceforge.plantuml.regex.RegexLeaf; import net.sourceforge.plantuml.regex.RegexOptional; import net.sourceforge.plantuml.regex.RegexResult; +import net.sourceforge.plantuml.skin.ActorStyle; import net.sourceforge.plantuml.stereo.Stereotype; import net.sourceforge.plantuml.utils.Direction; import net.sourceforge.plantuml.utils.LineLocation; @@ -77,9 +78,13 @@ public class CommandLinkElement extends SingleLineCommand2 { static IRegex getRegexConcat() { return RegexConcat.build(CommandLinkElement.class.getName(), RegexLeaf.start(), // getGroup("ENT1"), // + RegexLeaf.spaceZeroOrMore(), // new RegexOptional(new RegexLeaf("FIRST_LABEL", "[%g]([^%g]+)[%g]")), // RegexLeaf.spaceZeroOrMore(), // +// new RegexOptional(new RegexLeaf("STEREO1", "(\\<\\<.*\\>\\>)")), // +// RegexLeaf.spaceZeroOrMore(), // + new RegexLeaf("HEAD2", "(0\\)|<<|<_|[<^*+#0@)]|<\\|[\\|\\:]?|[%s]+o)?"), // new RegexLeaf("BODY1", "([-=.~]+)"), // new RegexLeaf("ARROW_STYLE1", "(?:\\[(" + LINE_STYLE_MUTILPLES + ")\\])?"), // @@ -88,11 +93,16 @@ public class CommandLinkElement extends SingleLineCommand2 { new RegexLeaf("ARROW_STYLE2", "(?:\\[(" + LINE_STYLE + ")\\])?"), // new RegexLeaf("BODY2", "([-=.~]*)"), // new RegexLeaf("HEAD1", "(\\(0|>>|_>|[>^*+#0@(]|[\\:\\|]?\\|>|\\\\\\\\|o[%s]+)?"), // + RegexLeaf.spaceZeroOrMore(), // new RegexOptional(new RegexLeaf("SECOND_LABEL", "[%g]([^%g]+)[%g]")), // RegexLeaf.spaceZeroOrMore(), // + getGroup("ENT2"), // RegexLeaf.spaceZeroOrMore(), // +// new RegexOptional(new RegexLeaf("STEREO2", "(\\<\\<.*\\>\\>)")), // +// RegexLeaf.spaceZeroOrMore(), // + color().getRegex(), // RegexLeaf.spaceZeroOrMore(), // new RegexLeaf("STEREOTYPE", "(\\<\\<.*\\>\\>)?"), // @@ -229,11 +239,11 @@ public class CommandLinkElement extends SingleLineCommand2 { "|" + // "\\(\\)[%s]*[%g][^%g]+[%g]" + // "|" + // - ":[^:]+:" + // + ":[^:]+:/?" + // "|" + // "(?!\\[\\*\\])\\[[^\\[\\]]+\\]" + // "|" + // - "\\((?!\\*\\))[^)]+\\)" + // + "\\((?!\\*\\))[^)]+\\)/?" + // ")"); } @@ -244,14 +254,6 @@ public class CommandLinkElement extends SingleLineCommand2 { final String ent2 = arg.get("ENT2", 0); final String ent1clean = diagram.cleanId(ent1); final String ent2clean = diagram.cleanId(ent2); -// final String ent1 = StringUtils.eventuallyRemoveStartingAndEndingDoubleQuote(ent1String); -// final String ent2 = StringUtils.eventuallyRemoveStartingAndEndingDoubleQuote(ent2String); -// final Quark ident1 = diagram.buildFullyQualified(ent1); -// final Quark ident2 = diagram.buildFullyQualified(ent2); -// Quark ident1pure = diagram.getPlasma().root().child(ent1); -// Quark ident2pure = diagram.getPlasma().root().child(ent2); -// final Quark code1 = diagram.buildFromFullPath(ent1String); -// final Quark code2 = diagram.buildFromFullPath(ent2String); final LinkType linkType = getLinkType(arg); final Direction dir = getDirection(arg); @@ -308,6 +310,7 @@ public class CommandLinkElement extends SingleLineCommand2 { } final char codeChar = ident.length() > 2 ? ident.charAt(0) : 0; + final boolean endWithSlash = ident.endsWith("/"); ident = diagram.cleanId(ident); final Quark quark = diagram.quarkInContext(ident, false); @@ -318,10 +321,18 @@ public class CommandLinkElement extends SingleLineCommand2 { final Display display = Display.getWithNewlines(quark.getName()); if (codeChar == '(') { - return diagram.reallyCreateLeaf(quark, display, LeafType.USECASE, USymbols.USECASE); + if (endWithSlash) + return diagram.reallyCreateLeaf(quark, display, LeafType.USECASE_BUSINESS, USymbols.USECASE); + else + return diagram.reallyCreateLeaf(quark, display, LeafType.USECASE, USymbols.USECASE); } else if (codeChar == ':') { - return diagram.reallyCreateLeaf(quark, display, LeafType.DESCRIPTION, - diagram.getSkinParam().actorStyle().toUSymbol()); + if (endWithSlash) + return diagram.reallyCreateLeaf(quark, display, LeafType.DESCRIPTION, + ActorStyle.STICKMAN_BUSINESS.toUSymbol()); + else + return diagram.reallyCreateLeaf(quark, display, LeafType.DESCRIPTION, + diagram.getSkinParam().actorStyle().toUSymbol()); + } else if (codeChar == '[') { final USymbol sym = diagram.getSkinParam().componentStyle().toUSymbol(); return diagram.reallyCreateLeaf(quark, display, LeafType.DESCRIPTION, sym); diff --git a/src/net/sourceforge/plantuml/klimt/font/FontConfiguration.java b/src/net/sourceforge/plantuml/klimt/font/FontConfiguration.java index b672aed0d..7f8057470 100644 --- a/src/net/sourceforge/plantuml/klimt/font/FontConfiguration.java +++ b/src/net/sourceforge/plantuml/klimt/font/FontConfiguration.java @@ -53,12 +53,6 @@ import net.sourceforge.plantuml.style.Style; public class FontConfiguration { - // ::uncomment when __HAXE__ -// public UFont getFont() { -// return null; -// } - // ::done__ - public static FontConfiguration create(UFont font, HColor color, HColor hyperlinkColor, UStroke hyperlinkUnderlineStroke, int tabSize) { return new FontConfiguration(getStyles(font), font, color, font, color, null, FontPosition.NORMAL, @@ -87,7 +81,6 @@ public class FontConfiguration { private FontConfiguration(EnumSet styles, UFont motherFont, HColor motherColor, UFont currentFont, HColor currentColor, HColor extendedColor, FontPosition fontPosition, SvgAttributes svgAttributes, HColor hyperlinkColor, UStroke hyperlinkUnderlineStroke, int tabSize) { - // ::comment when __HAXE__ this.styles = styles; this.currentFont = currentFont; this.motherFont = motherFont; @@ -99,10 +92,16 @@ public class FontConfiguration { this.hyperlinkColor = hyperlinkColor; this.hyperlinkUnderlineStroke = hyperlinkUnderlineStroke; this.tabSize = tabSize; - // ::done } - // ::comment when __HAXE__ + public UFont getFont() { + UFont result = currentFont; + for (FontStyle style : styles) + result = style.mutateFont(result); + + return fontPosition.mute(result); + } + private final EnumSet styles; private final UFont currentFont; private final UFont motherFont; @@ -117,6 +116,7 @@ public class FontConfiguration { private final int tabSize; + // ::comment when __HAXE__ public String toStringDebug() { return getFont().toStringDebug() + " " + styles.toString(); // return "" + currentFont + " " + styles.toString() + currentColor + extendedColor + hyperlinkColor @@ -303,14 +303,6 @@ public class FontConfiguration { svgAttributes, hyperlinkColor, hyperlinkUnderlineStroke, tabSize); } - public UFont getFont() { - UFont result = currentFont; - for (FontStyle style : styles) - result = style.mutateFont(result); - - return fontPosition.mute(result); - } - public HColor getColor() { return currentColor; } diff --git a/src/net/sourceforge/plantuml/klimt/font/FontPosition.java b/src/net/sourceforge/plantuml/klimt/font/FontPosition.java index 1471f2934..3b2e6d910 100644 --- a/src/net/sourceforge/plantuml/klimt/font/FontPosition.java +++ b/src/net/sourceforge/plantuml/klimt/font/FontPosition.java @@ -48,8 +48,6 @@ public enum FontPosition { return 0; } - // ::comment when __HAXE__ - public UFont mute(UFont font) { if (this == NORMAL) return font; @@ -61,6 +59,7 @@ public enum FontPosition { return font.withSize((float) size); } + // ::comment when __HAXE__ public String getHtmlTag() { if (this == EXPOSANT) return "sup"; diff --git a/src/net/sourceforge/plantuml/skin/ActorStyle.java b/src/net/sourceforge/plantuml/skin/ActorStyle.java index 461cf2559..dd24bf039 100644 --- a/src/net/sourceforge/plantuml/skin/ActorStyle.java +++ b/src/net/sourceforge/plantuml/skin/ActorStyle.java @@ -51,6 +51,8 @@ public enum ActorStyle { return USymbols.ACTOR_AWESOME; else if (this == HOLLOW) return USymbols.ACTOR_HOLLOW; + else if (this == STICKMAN_BUSINESS) + return USymbols.ACTOR_STICKMAN_BUSINESS; throw new IllegalStateException(); } diff --git a/src/net/sourceforge/plantuml/style/SName.java b/src/net/sourceforge/plantuml/style/SName.java index 80c15537d..aa74331bb 100644 --- a/src/net/sourceforge/plantuml/style/SName.java +++ b/src/net/sourceforge/plantuml/style/SName.java @@ -49,6 +49,7 @@ public enum SName { boundary, // box, // boxless, // + business, // caption, // card, // circle, // diff --git a/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java b/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java index 737c1d65e..3dc9daf2d 100644 --- a/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java +++ b/src/net/sourceforge/plantuml/svek/image/EntityImageDescription.java @@ -49,6 +49,7 @@ import net.sourceforge.plantuml.abel.Link; import net.sourceforge.plantuml.cucadiagram.BodyFactory; import net.sourceforge.plantuml.cucadiagram.PortionShower; import net.sourceforge.plantuml.decoration.symbol.USymbol; +import net.sourceforge.plantuml.decoration.symbol.USymbolActorBusiness; import net.sourceforge.plantuml.decoration.symbol.USymbols; import net.sourceforge.plantuml.klimt.Fashion; import net.sourceforge.plantuml.klimt.Shadowable; @@ -67,7 +68,6 @@ import net.sourceforge.plantuml.klimt.geom.HorizontalAlignment; import net.sourceforge.plantuml.klimt.geom.MagneticBorder; import net.sourceforge.plantuml.klimt.geom.MagneticBorderNone; import net.sourceforge.plantuml.klimt.geom.XDimension2D; -import net.sourceforge.plantuml.klimt.geom.XPoint2D; import net.sourceforge.plantuml.klimt.shape.TextBlock; import net.sourceforge.plantuml.klimt.shape.TextBlockUtils; import net.sourceforge.plantuml.klimt.shape.UComment; @@ -131,8 +131,13 @@ public class EntityImageDescription extends AbstractEntityImage { final Colors colors = entity.getColors(); - final StyleSignatureBasic tmp = StyleSignatureBasic.of(SName.root, SName.element, styleName, symbol.getSName(), - SName.title); + final StyleSignatureBasic tmp; + if (symbol instanceof USymbolActorBusiness) + tmp = StyleSignatureBasic.of(SName.root, SName.element, styleName, SName.actor, SName.business, + SName.title); + else + tmp = StyleSignatureBasic.of(SName.root, SName.element, styleName, symbol.getSName(), SName.title); + final Stereotype stereotype = entity.getStereotype(); final Style styleTitle = tmp.withTOBECHANGED(stereotype).getMergedStyle(getSkinParam().getCurrentStyleBuilder()) .eventuallyOverride(colors); diff --git a/src/net/sourceforge/plantuml/svek/image/EntityImageUseCase.java b/src/net/sourceforge/plantuml/svek/image/EntityImageUseCase.java index 3792c74b7..7b66c1d9d 100644 --- a/src/net/sourceforge/plantuml/svek/image/EntityImageUseCase.java +++ b/src/net/sourceforge/plantuml/svek/image/EntityImageUseCase.java @@ -194,6 +194,11 @@ public class EntityImageUseCase extends AbstractEntityImage { } private StyleSignature getDefaultStyleDefinition() { + final LeafType type = getEntity().getLeafType(); + if (type == LeafType.USECASE_BUSINESS) + return StyleSignatureBasic + .of(SName.root, SName.element, SName.componentDiagram, SName.usecase, SName.business) + .withTOBECHANGED(getStereo()); return StyleSignatureBasic.of(SName.root, SName.element, SName.componentDiagram, SName.usecase) .withTOBECHANGED(getStereo()); } diff --git a/src/net/sourceforge/plantuml/tim/EaterAffectation.java b/src/net/sourceforge/plantuml/tim/EaterAffectation.java index fb2df9583..1c7297580 100644 --- a/src/net/sourceforge/plantuml/tim/EaterAffectation.java +++ b/src/net/sourceforge/plantuml/tim/EaterAffectation.java @@ -49,25 +49,26 @@ public class EaterAffectation extends Eater { checkAndEatChar("!"); skipSpaces(); String varname = eatAndGetVarname(); - TVariableScope scope = null; + TVariableScope scope = TVariableScope.lazzyParse(varname); + if (scope != null) { + skipSpaces(); + if (peekChar() == '?' || peekChar() == '=') { + // The variable itself is "local" or "glocal", which is not a good idea by the way + scope = null; + } else + varname = eatAndGetVarname(); + } skipSpaces(); boolean conditional = false; if (peekChar() == '?') { checkAndEatChar('?'); conditional = true; } - if (peekChar() != '=') { - scope = TVariableScope.valueOf(varname.toUpperCase()); - varname = eatAndGetVarname(); - skipSpaces(); - } checkAndEatChar('='); - if (conditional) { - final TValue already = memory.getVariable(varname); - if (already != null) { + if (conditional) + if (memory.getVariable(varname) != null) return; - } - } + skipSpaces(); final TValue value = eatExpression(context, memory); memory.putVariable(varname, value, scope); diff --git a/src/net/sourceforge/plantuml/tim/TVariableScope.java b/src/net/sourceforge/plantuml/tim/TVariableScope.java index 78c4b0f01..065bc8975 100644 --- a/src/net/sourceforge/plantuml/tim/TVariableScope.java +++ b/src/net/sourceforge/plantuml/tim/TVariableScope.java @@ -35,5 +35,13 @@ package net.sourceforge.plantuml.tim; public enum TVariableScope { - LOCAL, GLOBAL + LOCAL, GLOBAL; + + public static TVariableScope lazzyParse(String value) { + if ("local".equalsIgnoreCase(value)) + return LOCAL; + if ("global".equalsIgnoreCase(value)) + return GLOBAL; + return null; + } } diff --git a/src/net/sourceforge/plantuml/version/Version.java b/src/net/sourceforge/plantuml/version/Version.java index 0faf631cc..549a431a4 100644 --- a/src/net/sourceforge/plantuml/version/Version.java +++ b/src/net/sourceforge/plantuml/version/Version.java @@ -82,7 +82,7 @@ public class Version { } public static int beta() { - final int beta = 0; + final int beta = 1; return beta; }