Author: rwhitcomb Date: Mon Mar 22 06:29:02 2021 New Revision: 1887917 URL: http://svn.apache.org/viewvc?rev=1887917&view=rev Log: PIVOT-1056,PIVOT-1014: First POC commit of the Color, Font, Insets, and CornerRadii "fromObject" methods, used now in LabelSkin and BorderSkin. Coupled with their default styles being moved to "terra_theme_defaults.json", this finishes the conversion work in these two components.
Modified: pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraBorderSkin.java pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraLabelSkin.java pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_defaults.json pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_styles.json pivot/trunk/wtk/src/org/apache/pivot/wtk/CornerRadii.java pivot/trunk/wtk/src/org/apache/pivot/wtk/Insets.java pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/BorderSkin.java pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/ComponentSkin.java pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/LabelSkin.java Modified: pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraBorderSkin.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraBorderSkin.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraBorderSkin.java (original) +++ pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraBorderSkin.java Mon Mar 22 06:29:02 2021 @@ -19,22 +19,16 @@ package org.apache.pivot.wtk.skin.terra; import org.apache.pivot.wtk.skin.BorderSkin; /** - * Terra Border skin. Deals with colors that depend on - * the current theme. + * Terra Border skin. Nothing to do here. */ public class TerraBorderSkin extends BorderSkin { - public TerraBorderSkin() { - setBackgroundColor(4); - setColor(7); - setTitleColor(12); - } - public final void setColor(int color) { - setColor(getColor(color)); - } - - public final void setTitleColor(int titleColor) { - setTitleColor(getColor(titleColor)); + /** + * Specific constructor with nothing to do. + * <p> Default colors, etc. set by call to {@link TerraTheme#setDefaultStyles} + * from {@link BorderSkin#install}. + */ + public TerraBorderSkin() { } } Modified: pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraLabelSkin.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraLabelSkin.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraLabelSkin.java (original) +++ pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/TerraLabelSkin.java Mon Mar 22 06:29:02 2021 @@ -16,32 +16,19 @@ */ package org.apache.pivot.wtk.skin.terra; -import org.apache.pivot.wtk.Theme; import org.apache.pivot.wtk.skin.LabelSkin; /** - * Terra Label skin. Only deals with colors that depend on - * the current theme. + * Terra Label skin. Nothing to do here. */ public class TerraLabelSkin extends LabelSkin { - public TerraLabelSkin() { - setColor(1); - setDisabledColor(7); - } - - public final void setColor(int color) { - Theme theme = currentTheme(); - setColor(theme.getColor(color)); - } - public final void setDisabledColor(int color) { - Theme theme = currentTheme(); - setDisabledColor(theme.getColor(color)); - } - - public final void setBackgroundColor(int backgroundColor) { - Theme theme = currentTheme(); - setBackgroundColor(theme.getColor(backgroundColor)); + /** + * Specific constructor with nothing to do. + * <p> Default colors, etc. set by call to {@link TerraTheme#setDefaultStyles} + * from {@link LabelSkin#install}. + */ + public TerraLabelSkin() { } } Modified: pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_defaults.json URL: http://svn.apache.org/viewvc/pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_defaults.json?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_defaults.json (original) +++ pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_defaults.json Mon Mar 22 06:29:02 2021 @@ -40,21 +40,24 @@ }, TerraSeparatorSkin : { - // TODO: conflicts between SeparatorSkin and TerraSeparatorSkin - - // color = defaultForegroundColor(); - // headingColor = defaultForegroundColor(); - font : { bold : true }, thickness : 1, padding : [ 4, 0, 4, 4 ], - // These are from TerraSeparatorSkin + // TODO: conflicts between SeparatorSkin and TerraSeparatorSkin + // color = defaultForegroundColor(); + // headingColor = defaultForegroundColor(); + + // While these are from TerraSeparatorSkin color : 7, headingColor : 12 }, TerraTextAreaSkin : { + margin : 4, + wrapText : true, + tabWidth : 4, + // TODO: conflicts here b/w TextAreaSkin and TerraTextAreaSkin: // This is what TextAreaSkin says right now: // color = defaultForegroundColor(); @@ -67,13 +70,8 @@ // selectionColor = Color.DARK_GRAY; // inactiveSelectionColor = Color.DARK_GRAY; // } - - // These were taken from TextAreaSkin (after the preceding code): - backgroundColor : 'null', - inactiveColor : 'GRAY', - margin : 4, - wrapText : true, - tabWidth : 4, + // backgroundColor = null; + // inactiveColor = Color.GRAY; // But, the colors below were taken from TerraTextAreaSkin... color : 1, @@ -113,6 +111,22 @@ backgroundColor : 4 }, + TerraLabelSkin : { + // These are set only in LabelSkin + backgroundColor : null, + textDecoration : null, + horizontalAlignment : 'LEFT', + verticalAlignment : 'TOP', + padding : 0, + wrapText : false, + // Conflict: LabelSkin has: + // color = defaultForegroundColor() + // disabledColor = Color.GRAY + // While these are from TerraLabelSkin... + color : 1, + disabledColor : 7 + }, + TerraTreeViewSkin : { // Taken from TerraTreeViewSkin constructor... color : 1, @@ -134,6 +148,20 @@ branchControlInactiveSelectionColor : 14, gridColor : 11, showGridLines : false + }, + + TerraBorderSkin : { + // Taken from BorderSkin constructor + // setBackgroundColor(defaultBackgroundColor()); + // color = defaultForegroundColor(); + // titleColor = defaultForegroundColor(); + thickness : 1, + padding : 0, + cornerRadii : 0, + // Taken from TerraBorderSkin constructor + backgroundColor : 4, + color : 7, + titleColor : 12 } /* More to come ... */ Modified: pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_styles.json URL: http://svn.apache.org/viewvc/pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_styles.json?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_styles.json (original) +++ pivot/trunk/wtk-terra/src/org/apache/pivot/wtk/skin/terra/terra_theme_styles.json Mon Mar 22 06:29:02 2021 @@ -14,7 +14,8 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -{ commandButton: { +{ + commandButton: { font: {bold:true}, color: 4, backgroundColor: 14, Modified: pivot/trunk/wtk/src/org/apache/pivot/wtk/CornerRadii.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk/src/org/apache/pivot/wtk/CornerRadii.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk/src/org/apache/pivot/wtk/CornerRadii.java (original) +++ pivot/trunk/wtk/src/org/apache/pivot/wtk/CornerRadii.java Mon Mar 22 06:29:02 2021 @@ -30,14 +30,30 @@ import org.apache.pivot.util.Utils; public final class CornerRadii implements Serializable { private static final long serialVersionUID = -433469769555042467L; + /** + * Radius of the top left corner. + */ public final int topLeft; + /** + * Radius of the top right corner. + */ public final int topRight; + /** + * Radius of the bottom left corner. + */ public final int bottomLeft; + /** + * Radius of the bottom right corner. + */ public final int bottomRight; + /** Dictionary key for the top left value. */ public static final String TOP_LEFT_KEY = "topLeft"; + /** Dictionary key for the top right value. */ public static final String TOP_RIGHT_KEY = "topRight"; + /** Dictionary key for the bottom left value. */ public static final String BOTTOM_LEFT_KEY = "bottomLeft"; + /** Dictionary key for the bottom right value. */ public static final String BOTTOM_RIGHT_KEY = "bottomRight"; /** @@ -45,50 +61,91 @@ public final class CornerRadii implement */ public static final CornerRadii NONE = new CornerRadii(0); - public CornerRadii(int radius) { + /** + * Construct with a single value for all four corners. + * + * @param radius The single value for all corners. + */ + public CornerRadii(final int radius) { this(radius, radius, radius, radius); } - public CornerRadii(Number radius) { + /** + * Construct with a single value for all corners. + * + * @param radius The (integer) value for all corners. + */ + public CornerRadii(final Number radius) { Utils.checkNull(radius, "radius"); int radii = radius.intValue(); Utils.checkNonNegative(radii, "radii"); - this.topLeft = radii; - this.topRight = radii; - this.bottomLeft = radii; - this.bottomRight = radii; + topLeft = radii; + topRight = radii; + bottomLeft = radii; + bottomRight = radii; } - private void check(CornerRadii radii) { + /** + * Check for valid values for all corners. + * + * @param radii The complete object to check all its values. + * @throws IllegalArgumentException if any of the values are negative. + */ + private void check(final CornerRadii radii) { check(radii.topLeft, radii.topRight, radii.bottomLeft, radii.bottomRight); } - private void check(int topLeft, int topRight, int bottomLeft, int bottomRight) { - Utils.checkNonNegative(topLeft, "topLeft"); - Utils.checkNonNegative(topRight, "topRight"); - Utils.checkNonNegative(bottomLeft, "bottomLeft"); - Utils.checkNonNegative(bottomRight, "bottomRight"); + /** + * Check the individual corner radius values. + * + * @param tL The top left value. + * @param tR The top right value. + * @param bL The bottom left value. + * @param bR The bottom right value. + * @throws IllegalArgumentException if any of the values are negative. + */ + private void check(final int tL, final int tR, final int bL, final int bR) { + Utils.checkNonNegative(tL, "topLeft"); + Utils.checkNonNegative(tR, "topRight"); + Utils.checkNonNegative(bL, "bottomLeft"); + Utils.checkNonNegative(bR, "bottomRight"); } - public CornerRadii(CornerRadii cornerRadii) { + /** + * "Copy" constructor from another corner radii object. + * + * @param cornerRadii The other object to copy from. + * @throws IllegalArgumentException if the object is {@code null}. + */ + public CornerRadii(final CornerRadii cornerRadii) { Utils.checkNull(cornerRadii, "cornerRadii"); check(cornerRadii); - this.topLeft = cornerRadii.topLeft; - this.topRight = cornerRadii.topRight; - this.bottomLeft = cornerRadii.bottomLeft; - this.bottomRight = cornerRadii.bottomRight; + topLeft = cornerRadii.topLeft; + topRight = cornerRadii.topRight; + bottomLeft = cornerRadii.bottomLeft; + bottomRight = cornerRadii.bottomRight; } - public CornerRadii(int topLeft, int topRight, int bottomLeft, int bottomRight) { - check(topLeft, topRight, bottomLeft, bottomRight); - - this.topLeft = topLeft; - this.topRight = topRight; - this.bottomLeft = bottomLeft; - this.bottomRight = bottomRight; + /** + * Construct given the individual corner radius values. + * + * @param topLeftValue The new top left radius value. + * @param topRightValue The new top right radius value. + * @param bottomLeftValue The new bottom left radius. + * @param bottomRightValue The bottom right radius value. + * @throws IllegalArgumentException if any of the values are negative. + */ + public CornerRadii(final int topLeftValue, final int topRightValue, + final int bottomLeftValue, final int bottomRightValue) { + check(topLeftValue, topRightValue, bottomLeftValue, bottomRightValue); + + topLeft = topLeftValue; + topRight = topRightValue; + bottomLeft = bottomLeftValue; + bottomRight = bottomRightValue; } /** @@ -100,7 +157,7 @@ public final class CornerRadii implement * {@value #BOTTOM_RIGHT_KEY}, all with numeric values. Omitted values are * treated as zero. */ - public CornerRadii(Dictionary<String, ?> cornerRadii) { + public CornerRadii(final Dictionary<String, ?> cornerRadii) { Utils.checkNull(cornerRadii, "cornerRadii"); topLeft = cornerRadii.getInt(TOP_LEFT_KEY, 0); @@ -111,7 +168,15 @@ public final class CornerRadii implement check(this); } - public CornerRadii(Sequence<?> cornerRadii) { + /** + * Construct from a sequence of four numeric values. + * + * @param cornerRadii Sequence of values in the order of: + * top left, top right, bottom left, bottom right. + * @throws IllegalArgumentException if the input is {@code null} or if any + * of the values are negative. + */ + public CornerRadii(final Sequence<?> cornerRadii) { Utils.checkNull(cornerRadii, "cornerRadii"); topLeft = ((Number) cornerRadii.get(0)).intValue(); @@ -123,7 +188,7 @@ public final class CornerRadii implement } @Override - public boolean equals(Object object) { + public boolean equals(final Object object) { boolean equals = false; if (object instanceof CornerRadii) { @@ -153,6 +218,37 @@ public final class CornerRadii implement } /** + * Convert any of our supported object sources into a {@code CornerRadii} object. + * + * @param source Any supported object ({@code Integer}, {@code Number}, {@code String}, etc.). + * @return The constructed {@code CornerRadii} object. + * @throws IllegalArgumentException if the source if {@code null} or we can't + * figure out how to convert. + */ + public static CornerRadii fromObject(final Object source) { + Utils.checkNull(source, "cornerRadii"); + + if (source instanceof CornerRadii) { + return (CornerRadii) source; + } else if (source instanceof String) { + return decode((String) source); + } else if (source instanceof Integer) { + return new CornerRadii((Integer) source); + } else if (source instanceof Number) { + return new CornerRadii((Number) source); + } else if (source instanceof Dictionary) { + @SuppressWarnings("unchecked") + Dictionary<String, ?> dictionary = (Dictionary<String, ?>) source; + return new CornerRadii(dictionary); + } else if (source instanceof Sequence) { + return new CornerRadii((Sequence<?>) source); + } else { + throw new IllegalArgumentException("Unable to convert " + + source.getClass().getSimpleName() + " to CornerRadii!"); + } + } + + /** * Convert a string into corner radii. * <p> If the string value is a JSON map, then parse the map * and construct using the {@link #CornerRadii(Dictionary)} method. @@ -174,7 +270,7 @@ public final class CornerRadii implement * a JSON map, or if it starts with <code>"["</code> but cannot be parsed * as a JSON list. */ - public static CornerRadii decode(String value) { + public static CornerRadii decode(final String value) { Utils.checkNullOrEmpty(value, "value"); CornerRadii cornerRadii; Modified: pivot/trunk/wtk/src/org/apache/pivot/wtk/Insets.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk/src/org/apache/pivot/wtk/Insets.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk/src/org/apache/pivot/wtk/Insets.java (original) +++ pivot/trunk/wtk/src/org/apache/pivot/wtk/Insets.java Mon Mar 22 06:29:02 2021 @@ -238,6 +238,50 @@ public final class Insets implements Ser } /** + * Convert any of our supported object sources into a {@code Insets} object. + * + * @param source Any supported object ({@code Integer}, {@code Number}, {@code String}, etc.). + * @return The constructed {@code Insets} object. + * @throws IllegalArgumentException if the source if {@code null} or we can't + * figure out how to convert. + */ + public static Insets fromObject(final Object source) { + return fromObject(source, null); + } + + /** + * Convert any of our supported object sources into a {@code Insets} object. + * + * @param source Any supported object ({@code Integer}, {@code Number}, {@code String}, etc.). + * @param message Description of the setting we are converting (eg, "margin", "padding", etc.). + * @return The constructed {@code Insets} object. + * @throws IllegalArgumentException if the source if {@code null} or we can't + * figure out how to convert. + */ + public static Insets fromObject(final Object source, final String message) { + Utils.checkNull(source, message); + + if (source instanceof String) { + return decode((String) source); + } else if (source instanceof Integer) { + return new Insets((Integer) source); + } else if (source instanceof Number) { + return new Insets((Number) source); + } else if (source instanceof Dictionary) { + @SuppressWarnings("unchecked") + Dictionary<String, ?> dictionary = (Dictionary<String, ?>) source; + return new Insets(dictionary); + } else if (source instanceof Sequence) { + return new Insets((Sequence<?>) source); + } else if (source instanceof Dimensions) { + return new Insets((Dimensions) source); + } else { + throw new IllegalArgumentException("Unable to convert " + + source.getClass().getSimpleName() + " to " + ((message == null) ? "Insets" : message) + "!"); + } + } + + /** * Decode a possible Insets value. The value can be in one of the * following forms: * <ul> Modified: pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/BorderSkin.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/BorderSkin.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/BorderSkin.java (original) +++ pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/BorderSkin.java Mon Mar 22 06:29:02 2021 @@ -27,8 +27,6 @@ import java.awt.geom.Area; import java.awt.geom.Rectangle2D; import java.awt.geom.RoundRectangle2D; -import org.apache.pivot.collections.Dictionary; -import org.apache.pivot.collections.Sequence; import org.apache.pivot.util.Utils; import org.apache.pivot.wtk.Border; import org.apache.pivot.wtk.BorderListener; @@ -38,7 +36,6 @@ import org.apache.pivot.wtk.Dimensions; import org.apache.pivot.wtk.GraphicsUtilities; import org.apache.pivot.wtk.Insets; import org.apache.pivot.wtk.Platform; -import org.apache.pivot.wtk.Theme; /** * Border skin. <p> TODO Add styles to support different border styles (e.g. @@ -54,42 +51,55 @@ public class BorderSkin extends Containe private Insets padding; private CornerRadii cornerRadii; + /** + * Default constructor. + */ public BorderSkin() { font = getThemeFont().deriveFont(Font.BOLD); + // Note: these get overridden by "setDefaultStyles" in "install" setBackgroundColor(defaultBackgroundColor()); color = defaultForegroundColor(); titleColor = defaultForegroundColor(); - - thickness = 1; - padding = Insets.NONE; - cornerRadii = CornerRadii.NONE; } + /** + * @return Our component, cast to a {@link Border} object, for use internally. + */ private Border getBorder() { return (Border) getComponent(); } @Override - public void install(Component component) { + public void install(final Component component) { super.install(component); + setDefaultStyles(); + Border border = (Border) component; border.getBorderListeners().add(this); calculateTitleSize(); } + /** + * @return The total padding width plus twice the thickness, for use in + * width calculations. + */ private int paddingThicknessWidth() { return padding.getWidth() + (thickness * 2); } + /** + * @return The total padding height plus top and bottom thickenss, for use in + * height calculations. + */ private int paddingThicknessHeight() { return padding.getHeight() + (topThickness + thickness); } @Override - public int getPreferredWidth(int height) { + public int getPreferredWidth(final int trialHeight) { int preferredWidth = 0; Border border = getBorder(); @@ -103,7 +113,7 @@ public class BorderSkin extends Containe Component content = border.getContent(); if (content != null) { - int heightUpdated = height; + int heightUpdated = trialHeight; if (heightUpdated != -1) { heightUpdated = Math.max(heightUpdated - paddingThicknessHeight(), 0); } @@ -117,14 +127,14 @@ public class BorderSkin extends Containe } @Override - public int getPreferredHeight(int width) { + public int getPreferredHeight(final int trialWidth) { int preferredHeight = 0; Border border = getBorder(); Component content = border.getContent(); if (content != null) { - int widthUpdated = width; + int widthUpdated = trialWidth; if (widthUpdated != -1) { widthUpdated = Math.max(widthUpdated - paddingThicknessWidth(), 0); } @@ -165,7 +175,7 @@ public class BorderSkin extends Containe } @Override - public int getBaseline(int width, int height) { + public int getBaseline(final int trialWidth, final int trialHeight) { int baseline = -1; Border border = getBorder(); @@ -173,8 +183,8 @@ public class BorderSkin extends Containe // Delegate baseline calculation to the content component Component content = border.getContent(); if (content != null) { - int clientWidth = Math.max(width - paddingThicknessWidth(), 0); - int clientHeight = Math.max(height - paddingThicknessHeight(), 0); + int clientWidth = Math.max(trialWidth - paddingThicknessWidth(), 0); + int clientHeight = Math.max(trialHeight - paddingThicknessHeight(), 0); baseline = content.getBaseline(clientWidth, clientHeight); } @@ -206,7 +216,7 @@ public class BorderSkin extends Containe } @Override - public void paint(Graphics2D graphics) { + public void paint(final Graphics2D graphics) { Border border = getBorder(); String title = border.getTitle(); @@ -282,7 +292,6 @@ public class BorderSkin extends Containe * <p> Caches the {@link #topThickness} and {@link #titleAscent} values for painting. */ private void calculateTitleSize() { - // Redo the top thickness calculation when the title changes topThickness = thickness; titleAscent = 0.0f; @@ -305,35 +314,16 @@ public class BorderSkin extends Containe /** * Sets the font used in rendering the title. * - * @param font The new font to use for the border title. + * @param fontValue The new font to use for the border title of a type supported by + * {@link fontFromObject(Object)}. */ - public void setFont(Font font) { - Utils.checkNull(font, "font"); - - this.font = font; + public void setFont(final Object fontValue) { + font = fontFromObject(fontValue); calculateTitleSize(); invalidateComponent(); } /** - * Sets the font used in rendering the title. - * - * @param font A {@linkplain ComponentSkin#decodeFont(String) font specification}. - */ - public final void setFont(String font) { - setFont(decodeFont(font)); - } - - /** - * Sets the font used in rendering the title. - * - * @param font A dictionary {@linkplain Theme#deriveFont describing a font}. - */ - public final void setFont(Dictionary<String, ?> font) { - setFont(Theme.deriveFont(font)); - } - - /** * @return The color of the border. */ public Color getColor() { @@ -343,40 +333,30 @@ public class BorderSkin extends Containe /** * Sets the color of the border. * - * @param color The new color for the border. + * @param colorValue The new color for the border. */ - public void setColor(Color color) { - Utils.checkNull(color, "color"); - - this.color = color; + public void setColor(final Object colorValue) { + color = colorFromObject(colorValue, "color"); repaintComponent(); } /** - * Sets the color of the border. - * - * @param color Any of the {@linkplain GraphicsUtilities#decodeColor color - * values recognized by Pivot}. + * @return The color for the title on the border. */ - public final void setColor(String color) { - setColor(GraphicsUtilities.decodeColor(color, "color")); - } - public Color getTitleColor() { return titleColor; } - public void setTitleColor(Color titleColor) { - Utils.checkNull(titleColor, "titleColor"); - - this.titleColor = titleColor; + /** + * Sets the color for the border title. + * + * @param colorValue The new color for the title. + */ + public void setTitleColor(final Object colorValue) { + titleColor = colorFromObject(colorValue, "titleColor"); repaintComponent(); } - public final void setTitleColor(String titleColor) { - setTitleColor(GraphicsUtilities.decodeColor(titleColor, "titleColor")); - } - /** * @return The thickness of the border. */ @@ -387,102 +367,46 @@ public class BorderSkin extends Containe /** * Sets the thickness of the border. * - * @param thickness The border thickness (in pixels). + * @param thicknessValue The border thickness (in pixels). */ - public void setThickness(int thickness) { - Utils.checkNonNegative(thickness, "thickness"); - - this.thickness = thickness; + public void setThickness(final int thicknessValue) { + Utils.checkNonNegative(thicknessValue, "thickness"); + thickness = thicknessValue; calculateTitleSize(); - invalidateComponent(); } /** * Sets the thickness of the border. * - * @param thickness The border thickness (integer value in pixels). + * @param thicknessValue The border thickness (integer value in pixels). */ - public void setThickness(Number thickness) { - Utils.checkNull(thickness, "thickness"); + public void setThickness(final Number thicknessValue) { + Utils.checkNull(thicknessValue, "thickness"); - setThickness(thickness.intValue()); + setThickness(thicknessValue.intValue()); } /** - * @return The amount of space between the edge of the Border and its - * content. + * @return The amount of space between the edge of the Border and its content. */ public Insets getPadding() { return padding; } /** - * Sets the amount of space to leave between the edge of the Border and its - * content. + * Sets the amount of space to leave between the edge of the Border and its content. * - * @param padding The set of padding values. + * @param paddingValues The set of padding values of any type supported by + * {@link Insets#fromObject}. */ - public void setPadding(Insets padding) { - Utils.checkNull(padding, "padding"); - - this.padding = padding; + public void setPadding(final Object paddingValues) { + padding = Insets.fromObject(paddingValues, "padding"); invalidateComponent(); } /** - * Sets the amount of space to leave between the edge of the Border and its - * content. - * - * @param padding A dictionary with keys in the set {top, left, bottom, right}. - */ - public final void setPadding(Dictionary<String, ?> padding) { - setPadding(new Insets(padding)); - } - - /** - * Sets the amount of space to leave between the edge of the Border and its - * content. - * - * @param padding A sequence with values in the order [top, left, bottom, right]. - */ - public final void setPadding(Sequence<?> padding) { - setPadding(new Insets(padding)); - } - - /** - * Sets the amount of space to leave between the edge of the Border and its - * content, uniformly on all four edges. - * - * @param padding The padding value (in pixels) to use for all four sides. - */ - public final void setPadding(int padding) { - setPadding(new Insets(padding)); - } - - /** - * Sets the amount of space to leave between the edge of the Border and its - * content, uniformly on all four edges. - * - * @param padding The padding value (integer value in pixels) to use for all four sides. - */ - public void setPadding(Number padding) { - setPadding(new Insets(padding)); - } - - /** - * Sets the amount of space to leave between the edge of the Border and its - * content. - * - * @param padding A string containing an integer or a JSON dictionary with - * keys left, top, bottom, and/or right. - */ - public final void setPadding(String padding) { - setPadding(Insets.decode(padding)); - } - - /** * @return A {@link CornerRadii}, describing the radius of each of the * Border's corners. */ @@ -493,63 +417,23 @@ public class BorderSkin extends Containe /** * Sets the radii of the Border's corners. * - * @param cornerRadii The radii for each of the corners. + * @param cornerRadiiValues The radii for each of the corners of any type + * supported by {@link CornerRadii#fromObject}. */ - public void setCornerRadii(CornerRadii cornerRadii) { - Utils.checkNull(cornerRadii, "cornerRadii"); - - this.cornerRadii = cornerRadii; + public void setCornerRadii(final Object cornerRadiiValues) { + cornerRadii = CornerRadii.fromObject(cornerRadiiValues); repaintComponent(); } - /** - * Sets the radii of the Border's corners. - * - * @param cornerRadii A Dictionary - * {@linkplain CornerRadii#CornerRadii(Dictionary) specifying the four corners}. - */ - public final void setCornerRadii(Dictionary<String, ?> cornerRadii) { - setCornerRadii(new CornerRadii(cornerRadii)); - } - - /** - * Sets the radii of the Border's four corners to the same value. - * - * @param cornerRadii The integer value to set all four corners' radii. - */ - public final void setCornerRadii(int cornerRadii) { - setCornerRadii(new CornerRadii(cornerRadii)); - } - - /** - * Sets the radii of the Border's four corners to the same value. - * - * @param cornerRadii The value for the radii (integer value in pixels). - */ - public final void setCornerRadii(Number cornerRadii) { - setCornerRadii(new CornerRadii(cornerRadii)); - } - - /** - * Sets the radii of the Border's corners. - * - * @param cornerRadii A single integer value, or a JSON dictionary - * {@linkplain CornerRadii#CornerRadii(Dictionary) specifying the four corners}. - */ - public final void setCornerRadii(String cornerRadii) { - setCornerRadii(CornerRadii.decode(cornerRadii)); - } - // Border events @Override - public void titleChanged(Border border, String previousTitle) { + public void titleChanged(final Border border, final String previousTitle) { calculateTitleSize(); - invalidateComponent(); } @Override - public void contentChanged(Border border, Component previousContent) { + public void contentChanged(final Border border, final Component previousContent) { invalidateComponent(); } } Modified: pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/ComponentSkin.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/ComponentSkin.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/ComponentSkin.java (original) +++ pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/ComponentSkin.java Mon Mar 22 06:29:02 2021 @@ -19,7 +19,9 @@ package org.apache.pivot.wtk.skin; import java.awt.Color; import java.awt.Font; +import org.apache.pivot.collections.Dictionary; import org.apache.pivot.collections.EnumSet; +import org.apache.pivot.util.Utils; import org.apache.pivot.wtk.Bounds; import org.apache.pivot.wtk.Component; import org.apache.pivot.wtk.ComponentKeyListener; @@ -30,6 +32,7 @@ import org.apache.pivot.wtk.ComponentMou import org.apache.pivot.wtk.ComponentStateListener; import org.apache.pivot.wtk.ComponentTooltipListener; import org.apache.pivot.wtk.Container; +import org.apache.pivot.wtk.CSSColor; import org.apache.pivot.wtk.Cursor; import org.apache.pivot.wtk.Dimensions; import org.apache.pivot.wtk.Display; @@ -37,6 +40,7 @@ import org.apache.pivot.wtk.DragSource; import org.apache.pivot.wtk.DropTarget; import org.apache.pivot.wtk.FocusTraversalDirection; import org.apache.pivot.wtk.FontUtilities; +import org.apache.pivot.wtk.GraphicsUtilities; import org.apache.pivot.wtk.Keyboard; import org.apache.pivot.wtk.Keyboard.KeyCode; import org.apache.pivot.wtk.Keyboard.KeyLocation; @@ -484,6 +488,33 @@ public abstract class ComponentSkin impl } /** + * Convert any object we support into its corresponding font. + * <p> Uses {@link FontUtilities#decodeFont} or {@link Theme#deriveFont} + * to do the work. + * + * @param fontValue The object to be converted to a font. + * @return The converted font. + * @throws IllegalArgumentException if the value is {@code null} or + * cannot be converted. + */ + public Font fontFromObject(final Object fontValue) { + Utils.checkNull(fontValue, "font"); + + if (fontValue instanceof Font) { + return (Font) fontValue; + } else if (fontValue instanceof String) { + return FontUtilities.decodeFont((String) fontValue); + } else if (fontValue instanceof Dictionary) { + @SuppressWarnings("unchecked") + Dictionary<String, ?> fontDictionary = (Dictionary<String, ?>) fontValue; + return Theme.deriveFont(fontDictionary); + } else { + throw new IllegalArgumentException("Unable to convert " + + fontValue.getClass().getSimpleName() + " to Font!"); + } + } + + /** * Returns the current Theme. * * @return The currently loaded theme. @@ -557,6 +588,89 @@ public abstract class ComponentSkin impl } /** + * Interpret an object as a color value. + * + * @param colorValue One of a {@link String} (interpreted by {@link GraphicsUtilities#decodeColor(String,String)}), + * a straight {@link Color}, one of our {@link CSSColor} values, or an integer index into the theme's + * color palette. + * @return The real {@link Color} value. + * @throws IllegalArgumentException if the {@code colorValue} is {@code null} or of a type we don't recognize. + */ + public final Color colorFromObject(final Object colorValue) { + return colorFromObject(colorValue, null, false); + } + + /** + * Interpret an object as a color value. + * + * @param colorValue One of a {@link String} (interpreted by {@link GraphicsUtilities#decodeColor(String,String)}), + * a straight {@link Color}, one of our {@link CSSColor} values, or an integer index into the theme's + * color palette. + * @param allowNull Whether or not to allow a null color. + * @return The real {@link Color} value. + * @throws IllegalArgumentException if the {@code colorValue} is {@code null} (unless {@code allowNull} + * is {@code true}), or of a type we don't recognize. + */ + public final Color colorFromObject(final Object colorValue, final boolean allowNull) { + return colorFromObject(colorValue, null, allowNull); + } + + /** + * Interpret an object as a color value. + * + * @param colorValue One of a {@link String} (interpreted by {@link GraphicsUtilities#decodeColor(String,String)}), + * a straight {@link Color}, one of our {@link CSSColor} values, or an integer index into the theme's + * color palette. + * @param description An optional description for the call to {@link Utils#checkNull} in case of a null input value. + * @return The real {@link Color} value. + * @throws IllegalArgumentException if the {@code colorValue} is {@code null}, or of a type we don't recognize. + */ + public final Color colorFromObject(final Object colorValue, final String description) { + return colorFromObject(colorValue, description, false); + } + + /** + * Interpret an object as a color value. + * + * @param colorValue One of a {@link String} (interpreted by {@link GraphicsUtilities#decodeColor(String,String)}), + * a straight {@link Color}, one of our {@link CSSColor} values, or an integer index into the theme's + * color palette. + * @param description An optional description for the call to {@link Utils#checkNull} in case of a null input value. + * @param allowNull Whether or not to allow a null color. + * @return The real {@link Color} value. + * @throws IllegalArgumentException if the {@code colorValue} is {@code null} (unless {@code allowNull} + * is {@code true}), or of a type we don't recognize. + */ + public final Color colorFromObject(final Object colorValue, final String description, final boolean allowNull) { + if (!allowNull) { + Utils.checkNull(colorValue, description); + } + + Color color; + + if (allowNull && colorValue == null) { + color = null; + } else if (colorValue instanceof Color) { + color = (Color) colorValue; + } else if (colorValue instanceof String) { + Color decodedColor = GraphicsUtilities.decodeColor((String) colorValue); + if (!allowNull) { + Utils.checkNull(decodedColor, description); + } + color = decodedColor; + } else if (colorValue instanceof CSSColor) { + color = ((CSSColor) colorValue).getColor(); + } else if (colorValue instanceof Number) { + color = getColor(((Number) colorValue).intValue()); + } else { + throw new IllegalArgumentException("Object of type " + + colorValue.getClass().getName() + " cannot be converted to a Color."); + } + + return color; + } + + /** * Returns the current font setting for the theme. * * @return The default font for the theme. Modified: pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/LabelSkin.java URL: http://svn.apache.org/viewvc/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/LabelSkin.java?rev=1887917&r1=1887916&r2=1887917&view=diff ============================================================================== --- pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/LabelSkin.java (original) +++ pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/LabelSkin.java Mon Mar 22 06:29:02 2021 @@ -30,19 +30,15 @@ import java.awt.geom.Rectangle2D; import java.text.StringCharacterIterator; import org.apache.pivot.collections.ArrayList; -import org.apache.pivot.collections.Dictionary; -import org.apache.pivot.collections.Sequence; import org.apache.pivot.util.Utils; import org.apache.pivot.wtk.Component; import org.apache.pivot.wtk.Dimensions; -import org.apache.pivot.wtk.GraphicsUtilities; import org.apache.pivot.wtk.HorizontalAlignment; import org.apache.pivot.wtk.Insets; import org.apache.pivot.wtk.Label; import org.apache.pivot.wtk.LabelListener; import org.apache.pivot.wtk.Platform; import org.apache.pivot.wtk.TextDecoration; -import org.apache.pivot.wtk.Theme; import org.apache.pivot.wtk.VerticalAlignment; /** @@ -62,29 +58,36 @@ public class LabelSkin extends Component private ArrayList<GlyphVector> glyphVectors = null; private float textHeight = 0; + /** + * Default constructor. + */ public LabelSkin() { - font = currentTheme().getFont(); + font = getThemeFont(); + // Note: the following are overridden by "setDefaultStyles" in "install" color = defaultForegroundColor(); disabledColor = Color.GRAY; - backgroundColor = null; - textDecoration = null; - horizontalAlignment = HorizontalAlignment.LEFT; - verticalAlignment = VerticalAlignment.TOP; - padding = Insets.NONE; - wrapText = false; + } + + /** + * @return Our component cast to a {@link Label} object, for use internally. + */ + private Label getLabel() { + return (Label) getComponent(); } @Override public void install(final Component component) { super.install(component); - Label label = (Label) getComponent(); + setDefaultStyles(); + + Label label = (Label) component; label.getLabelListeners().add(this); } @Override public int getPreferredWidth(final int height) { - Label label = (Label) getComponent(); + Label label = getLabel(); String text = label.getText(); int preferredWidth = 0; @@ -114,7 +117,7 @@ public class LabelSkin extends Component @Override public int getPreferredHeight(final int width) { - Label label = (Label) getComponent(); + Label label = getLabel(); String text = label.getText(); float preferredHeight; @@ -175,7 +178,7 @@ public class LabelSkin extends Component @Override public Dimensions getPreferredSize() { - Label label = (Label) getComponent(); + Label label = getLabel(); String text = label.getText(); FontRenderContext fontRenderContext = Platform.getFontRenderContext(); @@ -248,9 +251,28 @@ public class LabelSkin extends Component return baseline; } + /** + * Internal method used by {@link #layout} to setup values for each individual line + * of text (assuming we're wrapping). + * + * @param text The complete text of the label. + * @param start Starting offset (inclusive) of the text for this line. + * @param end The ending offset (exclusive) of the text for this line. + * @param fontRenderContext The context used for font measurement. + */ + private void appendLine(final String text, final int start, final int end, + final FontRenderContext fontRenderContext) { + StringCharacterIterator line = new StringCharacterIterator(text, start, end, start); + GlyphVector glyphVector = font.createGlyphVector(fontRenderContext, line); + glyphVectors.add(glyphVector); + + Rectangle2D textBounds = glyphVector.getLogicalBounds(); + textHeight += textBounds.getHeight(); + } + @Override public void layout() { - Label label = (Label) getComponent(); + Label label = getLabel(); String text = label.getText(); glyphVectors = new ArrayList<>(); @@ -313,19 +335,9 @@ public class LabelSkin extends Component } } - private void appendLine(final String text, final int start, final int end, - final FontRenderContext fontRenderContext) { - StringCharacterIterator line = new StringCharacterIterator(text, start, end, start); - GlyphVector glyphVector = font.createGlyphVector(fontRenderContext, line); - glyphVectors.add(glyphVector); - - Rectangle2D textBounds = glyphVector.getLogicalBounds(); - textHeight += textBounds.getHeight(); - } - @Override public void paint(final Graphics2D graphics) { - Label label = (Label) this.getComponent(); + Label label = getLabel(); int width = getWidth(); int height = getHeight(); @@ -446,38 +458,15 @@ public class LabelSkin extends Component /** * Sets the font used in rendering the Label's text. * - * @param font The new font to use to render the text. + * @param fontValue The new font to use to render the text of a type supported + * by {@link fontFromObject(Object)}. */ - public void setFont(final Font font) { - Utils.checkNull(font, "font"); - - this.font = font; + public void setFont(final Object fontValue) { + font = fontFromObject(fontValue); invalidateComponent(); } /** - * Sets the font used in rendering the Label's text. - * - * @param font A {@linkplain ComponentSkin#decodeFont(String) font specification}. - */ - public final void setFont(final String font) { - Utils.checkNull(font, "font"); - - setFont(decodeFont(font)); - } - - /** - * Sets the font used in rendering the Label's text. - * - * @param font A dictionary {@linkplain Theme#deriveFont describing a font}. - */ - public final void setFont(final Dictionary<String, ?> font) { - Utils.checkNull(font, "font"); - - setFont(Theme.deriveFont(font)); - } - - /** * @return The foreground color of the text of the label. */ public Color getColor() { @@ -487,28 +476,15 @@ public class LabelSkin extends Component /** * Sets the foreground color of the text of the label. * - * @param color The new foreground color for the label text. + * @param colorValue The new foreground color for the label text, which can + * be interpreted by {@link colorFromObject(Object)}. */ - public void setColor(final Color color) { - Utils.checkNull(color, "color"); - - this.color = color; + public void setColor(final Object colorValue) { + color = colorFromObject(colorValue, "color"); repaintComponent(); } /** - * Sets the foreground color of the text of the label. - * - * @param color Any of the {@linkplain GraphicsUtilities#decodeColor color - * values recognized by Pivot}. - */ - public final void setColor(final String color) { - Utils.checkNull(color, "color"); - - setColor(GraphicsUtilities.decodeColor(color, "color")); - } - - /** * @return The foreground color of the text of the label when disabled. */ public Color getDisabledColor() { @@ -518,28 +494,15 @@ public class LabelSkin extends Component /** * Sets the foreground color of the text of the label when disabled. * - * @param color The new disabled text color. + * @param colorValue The new disabled text color, which can be interpreted by + * {@link colorFromObject(Object)}. */ - public void setDisabledColor(final Color color) { - Utils.checkNull(color, "disabledColor"); - - this.disabledColor = color; + public void setDisabledColor(final Object colorValue) { + disabledColor = colorFromObject(colorValue, "disabledColor"); repaintComponent(); } /** - * Sets the foreground color of the text of the label when disabled. - * - * @param color Any of the {@linkplain GraphicsUtilities#decodeColor color - * values recognized by Pivot}. - */ - public final void setDisabledColor(final String color) { - Utils.checkNull(color, "disabledColor"); - - setDisabledColor(GraphicsUtilities.decodeColor(color, "disabledColor")); - } - - /** * @return The background color of the label. */ public Color getBackgroundColor() { @@ -549,126 +512,91 @@ public class LabelSkin extends Component /** * Sets the background color of the label. * - * @param backgroundColor The new background color for the label - * (can be {@code null} to let the parent background show through). + * @param colorValue The new background color for the label + * (can be {@code null} to let the parent background show through), or + * a value that can be interpreted by {@link colorFromObject(Object)}. */ - public void setBackgroundColor(final Color backgroundColor) { - this.backgroundColor = backgroundColor; + public final void setBackgroundColor(final Object colorValue) { + backgroundColor = colorFromObject(colorValue, "backgroundColor", true); repaintComponent(); } /** - * Sets the background color of the label. - * - * @param backgroundColor Any of the - * {@linkplain GraphicsUtilities#decodeColor color values recognized by - * Pivot}. + * @return The current text decoration (strikethrough, underline, etc) for the label + * (can be {@code null}). */ - public final void setBackgroundColor(final String backgroundColor) { - setBackgroundColor(GraphicsUtilities.decodeColor(backgroundColor, "backgroundColor")); - } - public TextDecoration getTextDecoration() { return textDecoration; } - public void setTextDecoration(final TextDecoration textDecoration) { - this.textDecoration = textDecoration; - repaintComponent(); - } - - public HorizontalAlignment getHorizontalAlignment() { - return horizontalAlignment; - } - - public void setHorizontalAlignment(final HorizontalAlignment horizontalAlignment) { - Utils.checkNull(horizontalAlignment, "horizontalAlignment"); - - this.horizontalAlignment = horizontalAlignment; - repaintComponent(); - } - - public VerticalAlignment getVerticalAlignment() { - return verticalAlignment; - } - - public void setVerticalAlignment(final VerticalAlignment verticalAlignment) { - Utils.checkNull(verticalAlignment, "verticalAlignment"); - - this.verticalAlignment = verticalAlignment; + /** + * Sets the text decoration (eg, strikethrough, underline, etc) for this label. + * + * @param textDecorationValue The new setting (can be {@code null} to cancel + * any decoration for the label). + */ + public void setTextDecoration(final TextDecoration textDecorationValue) { + textDecoration = textDecorationValue; repaintComponent(); } /** - * @return The amount of space to leave between the edge of the Label and - * its text. + * @return The horizontal alignment for the label to use when drawing the text + * inside the label's total width. */ - public Insets getPadding() { - return padding; + public HorizontalAlignment getHorizontalAlignment() { + return horizontalAlignment; } /** - * Sets the amount of space to leave between the edge of the Label and its - * text. + * Set the horizontal alignment for the text inside the label's total width. * - * @param padding The new value of the padding for each edge. + * @param horizontalAlignmentValue The new setting. + * @throws IllegalArgumentException if the value is {@code null}. */ - public void setPadding(final Insets padding) { - Utils.checkNull(padding, "padding"); + public void setHorizontalAlignment(final HorizontalAlignment horizontalAlignmentValue) { + Utils.checkNull(horizontalAlignmentValue, "horizontalAlignment"); - this.padding = padding; - invalidateComponent(); + horizontalAlignment = horizontalAlignmentValue; + repaintComponent(); } /** - * Sets the amount of space to leave between the edge of the Label and its - * text. - * - * @param padding A dictionary with keys in the set {top, left, bottom, right}. + * @return The vertical alignment used to draw the text inside the label's total height. */ - public final void setPadding(final Dictionary<String, ?> padding) { - setPadding(new Insets(padding)); + public VerticalAlignment getVerticalAlignment() { + return verticalAlignment; } /** - * Sets the amount of space to leave between the edge of the Label and its - * text. + * Set the new vertical alignment value for the text inside the label's height. * - * @param padding A sequence with values in the order [top, left, bottom, right]. + * @param verticalAlignmentValue The new setting. + * @throws IllegalArgumentException if the new value is {@code null}. */ - public final void setPadding(final Sequence<?> padding) { - setPadding(new Insets(padding)); - } + public void setVerticalAlignment(final VerticalAlignment verticalAlignmentValue) { + Utils.checkNull(verticalAlignmentValue, "verticalAlignment"); - /** - * Sets the amount of space to leave between the edge of the Label and its - * text, uniformly on all four edges. - * - * @param padding The new single padding value to use for all edges. - */ - public final void setPadding(final int padding) { - setPadding(new Insets(padding)); + verticalAlignment = verticalAlignmentValue; + repaintComponent(); } /** - * Sets the amount of space to leave between the edge of the Label and its - * text, uniformly on all four edges. - * - * @param padding The new (integer) padding value to use for all edges. + * @return The amount of space to leave between the edge of the Label and its text. */ - public final void setPadding(final Number padding) { - setPadding(new Insets(padding)); + public Insets getPadding() { + return padding; } /** - * Sets the amount of space to leave between the edge of the Label and its - * text. + * Sets the amount of space to leave between the edge of the Label and its text. * - * @param padding A string containing an integer or a JSON dictionary with - * keys left, top, bottom, and/or right. + * @param paddingValues The new value of the padding for each edge, of any + * type supported by {@link Insets#fromObject}. */ - public final void setPadding(final String padding) { - setPadding(Insets.decode(padding)); + public void setPadding(final Object paddingValues) { + padding = Insets.fromObject(paddingValues, "padding"); + invalidateComponent(); } /** @@ -686,10 +614,10 @@ public class LabelSkin extends Component * <p>Also note that newline characters (if wrapping is set true) will cause a * hard line break. * - * @param wrapText Whether or not to wrap the Label's text within its width. + * @param wrapTextValue Whether or not to wrap the Label's text within its width. */ - public void setWrapText(final boolean wrapText) { - this.wrapText = wrapText; + public void setWrapText(final boolean wrapTextValue) { + wrapText = wrapTextValue; invalidateComponent(); }