# HG changeset patch
# Parent adcb59265f40ca1ad38814a4678415aaaf575ca8
RT-26277: add RegionInsets, which BackgroundFill, BorderStroke and BorderImage can use for their respective -fx-*-insets. RegionInsets allows for percentage values, but this means that the actual Insets values that NGRegion uses have to be calculated on the fly.
diff -r adcb59265f40 modules/graphics/src/main/java/com/sun/javafx/css/converters/InsetsConverter.java
--- a/modules/graphics/src/main/java/com/sun/javafx/css/converters/InsetsConverter.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/com/sun/javafx/css/converters/InsetsConverter.java Mon Nov 25 12:35:17 2013 -0500
@@ -26,6 +26,7 @@
package com.sun.javafx.css.converters;
import com.sun.javafx.css.Size;
+import com.sun.javafx.css.SizeUnits;
import com.sun.javafx.css.StyleConverterImpl;
import javafx.css.ParsedValue;
import javafx.css.StyleConverter;
@@ -58,11 +59,13 @@
@Override
public Insets convert(ParsedValue value, Font font) {
ParsedValue[] sides = value.getValue();
- double top = ((Size)sides[0].convert(font)).pixels(font);
- double right = (sides.length > 1) ? ((Size)sides[1].convert(font)).pixels(font) : top;
- double bottom = (sides.length > 2) ? ((Size)sides[2].convert(font)).pixels(font) : top;
- double left = (sides.length > 3) ? ((Size)sides[3].convert(font)).pixels(font) : right;
- return new Insets(top, right, bottom, left);
+ Size top = (Size)sides[0].convert(font);
+ Size right = (sides.length > 1) ? (Size)sides[1].convert(font) : top;
+ Size bottom = (sides.length > 2) ? (Size)sides[2].convert(font) : top;
+ Size left = (sides.length > 3) ? (Size)sides[3].convert(font) : right;
+ return new Insets(top.pixels(font), right.pixels(font), bottom.pixels(font), left.pixels(font),
+ top.getUnits() == SizeUnits.PERCENT, right.getUnits() == SizeUnits.PERCENT,
+ bottom.getUnits() == SizeUnits.PERCENT, left.getUnits() == SizeUnits.PERCENT);
}
@Override
diff -r adcb59265f40 modules/graphics/src/main/java/com/sun/javafx/css/parser/CSSParser.java
--- a/modules/graphics/src/main/java/com/sun/javafx/css/parser/CSSParser.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/com/sun/javafx/css/parser/CSSParser.java Mon Nov 25 12:35:17 2013 -0500
@@ -714,7 +714,7 @@
} else if ("-fx-background-image".equals(prop)) {
return parseURILayers(root);
} else if ("-fx-background-insets".equals(prop)) {
- return parseInsetsLayers(root);
+ return parseInsetsLayers(root);
} else if ("-fx-opaque-insets".equals(prop)) {
return parseInsetsLayer(root);
} else if ("-fx-background-position".equals(prop)) {
@@ -745,6 +745,9 @@
return parseURILayers(root);
} else if ("-fx-border-image-width".equals(prop)) {
return parseBorderImageWidthLayers(root);
+ } else if ("-fx-margin".equals(prop)) {
+ ParsedValueImpl,Size>[] sides = parseSizeSeries(root);
+ return new ParsedValueImpl(sides, InsetsConverter.getInstance());
} else if ("-fx-padding".equals(prop)) {
ParsedValueImpl,Size>[] sides = parseSizeSeries(root);
return new ParsedValueImpl(sides, InsetsConverter.getInstance());
@@ -2388,7 +2391,6 @@
return new ParsedValueImpl[], Margins[]>(layers, Margins.SequenceConverter.getInstance());
}
-
// http://www.w3.org/TR/css3-background/#the-border-radius
// {1,4} [ '/' {1,4}]? [',' {1,4} [ '/' {1,4}]?]?
private ParsedValueImpl[][],CornerRadii>[], CornerRadii[]> parseCornerRadius(Term root)
diff -r adcb59265f40 modules/graphics/src/main/java/com/sun/javafx/sg/prism/NGRegion.java
--- a/modules/graphics/src/main/java/com/sun/javafx/sg/prism/NGRegion.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/com/sun/javafx/sg/prism/NGRegion.java Mon Nov 25 12:35:17 2013 -0500
@@ -170,6 +170,14 @@
private float width, height;
/**
+ * Margins
+ */
+ private float marginTop = Float.NaN,
+ marginRight = Float.NaN,
+ marginBottom = Float.NaN,
+ marginLeft = Float.NaN;
+
+ /**
* Determined when a background is set on the region, this flag indicates whether this
* background can be cached. As of this time, the only backgrounds which can be cached
* are those where there are only solid fills or linear gradients.
@@ -270,7 +278,7 @@
// on the border objects is generally very fast (either for identity or
// for !equals. It is a bit longer for when they really are equal, but faster
// than a geometryChanged!)
- if (!border.getOutsets().equals(old.getOutsets())) {
+ if (!border.getOutsets(width, height).equals(old.getOutsets(width, height))) {
geometryChanged();
} else {
visualsChanged();
@@ -328,7 +336,7 @@
cacheKey = null;
// Only update the geom if the new background is geometrically different from the old
- if (!background.getOutsets().equals(old.getOutsets())) {
+ if (!background.getOutsets(width, height).equals(old.getOutsets(width, height))) {
geometryChanged();
} else {
visualsChanged();
@@ -358,6 +366,13 @@
invalidateOpaqueRegion();
}
+ public void setMargins(float top, float right, float bottom, float left) {
+ marginTop = top;
+ marginRight = right;
+ marginBottom = bottom;
+ marginLeft = left;
+ }
+
/**
* When cleaning the dirty tree, we also have to keep in mind
* the NGShape used by the NGRegion
@@ -516,7 +531,7 @@
// it if we absolutely have to. Specifically, if the background, shape, and size of the region
// has not changed since the last time we rendered we could skip all this and render
// directly out of a cache.
- final Insets outsets = background.getOutsets();
+ final Insets outsets = background.getOutsets(width, height);
final Shape outsetShape = resizeShape((float) -outsets.getTop(), (float) -outsets.getRight(),
(float) -outsets.getBottom(), (float) -outsets.getLeft());
final RectBounds outsetShapeBounds = outsetShape.getBounds();
@@ -601,8 +616,8 @@
// Instead, we just pass -1, telling setBorderStyle to just do a simple stroke
setBorderStyle(g, stroke, -1);
final Insets insets = stroke.getInsets();
- g.draw(resizeShape((float) insets.getTop(), (float) insets.getRight(),
- (float) insets.getBottom(), (float) insets.getLeft()));
+ g.draw(resizeShape((float) insets.getTop(this.height), (float) insets.getRight(this.width),
+ (float) insets.getBottom(this.height), (float) insets.getLeft(this.width)));
}
}
}
@@ -627,8 +642,8 @@
// Adjust the box within which we will fit the shape based on the
// insets. The resize shape method will resize the shape to fit
final Insets insets = fill.getInsets();
- g.fill(resizeShape((float) insets.getTop(), (float) insets.getRight(),
- (float) insets.getBottom(), (float) insets.getLeft()));
+ g.fill(resizeShape((float) insets.getTop(this.height), (float) insets.getRight(this.width),
+ (float) insets.getBottom(this.height), (float) insets.getLeft(this.width)));
}
// We now need to draw each background image. Only the "cover" property
@@ -707,7 +722,7 @@
cacheHeight = Math.min(cacheHeight, (int) (topInset + bottomInset));
}
- final Insets outsets = background.getOutsets();
+ final Insets outsets = background.getOutsets(width, height);
final int outsetsTop = roundUp(outsets.getTop());
final int outsetsRight = roundUp(outsets.getRight());
final int outsetsBottom = roundUp(outsets.getBottom());
@@ -990,18 +1005,18 @@
}
}
- private void renderBackgroundRectanglesDirectly(Graphics g, float width, float height) {
+ private void renderBackgroundRectanglesDirectly(Graphics g, float _width, float _height) {
final List fills = background.getFills();
for (int i = 0, max = fills.size(); i < max; i++) {
final BackgroundFill fill = fills.get(i);
final Insets insets = fill.getInsets();
- final float t = (float) insets.getTop(),
- l = (float) insets.getLeft(),
- b = (float) insets.getBottom(),
- r = (float) insets.getRight();
+ final float t = (float) insets.getTop( _height - marginTop - marginBottom) + marginTop,
+ l = (float) insets.getLeft(_width - marginLeft - marginRight) + marginLeft,
+ b = (float) insets.getBottom( _height - marginTop - marginBottom) + marginBottom,
+ r = (float) insets.getRight(_width - marginLeft - marginRight) + marginRight;
// w and h is the width and height of the area to be filled (width and height less insets)
- float w = width - l - r;
- float h = height - t - b;
+ float w = _width - l - r;
+ float h = _height - t - b;
// Only setup and paint for those areas which have positive width and height. This means, if
// the insets are such that the right edge is left of the left edge, then we have a negative
// width and will not paint it. TODO we need to document this fact (RT-26924)
@@ -1023,8 +1038,8 @@
g.fillRect(l, t, w, h);
} else {
// Fix the horizontal and vertical radii if they are percentage based
- if (radii.isTopLeftHorizontalRadiusAsPercentage()) tlhr = tlhr * width;
- if (radii.isTopLeftVerticalRadiusAsPercentage()) tlvr = tlvr * height;
+ if (radii.isTopLeftHorizontalRadiusAsPercentage()) tlhr = tlhr * _width;
+ if (radii.isTopLeftVerticalRadiusAsPercentage()) tlvr = tlvr * _height;
// The edges are rounded, so we need to compute the arc width and arc height
// and fill a round rect
float arcWidth = tlhr + tlhr;
@@ -1045,7 +1060,7 @@
// TODO document the issue number which will give us a fast path for rendering
// non-uniform corners, and that we want to implement that instead of createPath2
// below in such cases. (RT-26979)
- g.fill(createPath(width, height, t, l, b, r, normalize(radii)));
+ g.fill(createPath(_width, _height, t, l, b, r, normalize(radii)));
}
}
}
@@ -1065,10 +1080,10 @@
final javafx.scene.paint.Paint bottomStroke = stroke.getBottomStroke();
final javafx.scene.paint.Paint leftStroke = stroke.getLeftStroke();
- final float topInset = (float) insets.getTop();
- final float rightInset = (float) insets.getRight();
- final float bottomInset = (float) insets.getBottom();
- final float leftInset = (float) insets.getLeft();
+ final float topInset = (float) insets.getTop(this.height - marginTop - marginBottom) + marginTop;
+ final float rightInset = (float) insets.getRight(this.width - marginLeft - marginRight) + marginRight;
+ final float bottomInset = (float) insets.getBottom(this.height - marginTop - marginBottom) + marginBottom;
+ final float leftInset = (float) insets.getLeft(this.width - marginLeft - marginRight) + marginLeft;
final float topWidth = (float) (widths.isTopAsPercentage() ? height * widths.getTop() : widths.getTop());
final float rightWidth = (float) (widths.isRightAsPercentage() ? width * widths.getRight() : widths.getRight());
@@ -1260,10 +1275,10 @@
final BorderWidths slices = ib.getSlices();
// we will get gaps if we don't round to pixel boundaries
- final int topInset = (int) Math.round(insets.getTop());
- final int rightInset = (int) Math.round(insets.getRight());
- final int bottomInset = (int) Math.round(insets.getBottom());
- final int leftInset = (int) Math.round(insets.getLeft());
+ final int topInset = (int) Math.round(insets.getTop(this.height));
+ final int rightInset = (int) Math.round(insets.getRight(this.width));
+ final int bottomInset = (int) Math.round(insets.getBottom(this.height));
+ final int leftInset = (int) Math.round(insets.getLeft(this.width));
final int topWidth = widthSize(widths.isTopAsPercentage(), widths.getTop(), height);
final int rightWidth = widthSize(widths.isRightAsPercentage(), widths.getRight(), width);
@@ -1357,7 +1372,7 @@
}
/**
- * Visits each of the background fills and takes their raddi into account to determine the insets.
+ * Visits each of the background fills and takes their radii into account to determine the insets.
* The backgroundInsets variable is cleared whenever the fills change, or whenever the size of the
* region has changed (because if the size of the region changed and a radius is percentage based
* then we need to recompute the insets).
@@ -1373,10 +1388,10 @@
final BackgroundFill fill = fills.get(i);
final Insets insets = fill.getInsets();
final CornerRadii radii = normalize(fill.getRadii());
- top = (float) Math.max(top, insets.getTop() + Math.max(radii.getTopLeftVerticalRadius(), radii.getTopRightVerticalRadius()));
- right = (float) Math.max(right, insets.getRight() + Math.max(radii.getTopRightHorizontalRadius(), radii.getBottomRightHorizontalRadius()));
- bottom = (float) Math.max(bottom, insets.getBottom() + Math.max(radii.getBottomRightVerticalRadius(), radii.getBottomLeftVerticalRadius()));
- left = (float) Math.max(left, insets.getLeft() + Math.max(radii.getTopLeftHorizontalRadius(), radii.getBottomLeftHorizontalRadius()));
+ top = (float) Math.max(top, insets.getTop(this.height) + Math.max(radii.getTopLeftVerticalRadius(), radii.getTopRightVerticalRadius()));
+ right = (float) Math.max(right, insets.getRight(this.width) + Math.max(radii.getTopRightHorizontalRadius(), radii.getBottomRightHorizontalRadius()));
+ bottom = (float) Math.max(bottom, insets.getBottom(this.height) + Math.max(radii.getBottomRightVerticalRadius(), radii.getBottomLeftVerticalRadius()));
+ left = (float) Math.max(left, insets.getLeft(this.width) + Math.max(radii.getTopLeftHorizontalRadius(), radii.getBottomLeftHorizontalRadius()));
}
backgroundInsets = new Insets(roundUp(top), roundUp(right), roundUp(bottom), roundUp(left));
}
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/geometry/Insets.java
--- a/modules/graphics/src/main/java/javafx/geometry/Insets.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/geometry/Insets.java Mon Nov 25 12:35:17 2013 -0500
@@ -38,29 +38,113 @@
public static final Insets EMPTY = new Insets(0, 0, 0, 0);
/**
+ * Specifies whether the {@link #getTop() top} property should be interpreted as a
+ * percentage ({@code true}) or not ({@code false}).
+ */
+ public final boolean isTopAsPercentage() { return topAsPercentage; }
+ final boolean topAsPercentage;
+
+ /**
+ * Specifies whether the {@link #getRight() right} property should be interpreted as a
+ * percentage ({@code true}) or not ({@code false}).
+ */
+ public final boolean isRightAsPercentage() { return rightAsPercentage; }
+ final boolean rightAsPercentage;
+
+ /**
+ * Specifies whether the {@link #getBottom() bottom} property should be interpreted as a
+ * percentage ({@code true}) or not ({@code false}).
+ */
+ public final boolean isBottomAsPercentage() { return bottomAsPercentage; }
+ final boolean bottomAsPercentage;
+
+ /**
+ * Specifies whether the {@link #getLeft() left} property should be interpreted as a
+ * percentage ({@code true}) or not ({@code false}).
+ */
+ public final boolean isLeftAsPercentage() { return leftAsPercentage; }
+ final boolean leftAsPercentage;
+
+ /**
* The inset on the top side
*/
public final double getTop() { return top; }
+
+ /**
+ * The normalized inset on the top side
+ * @param height The height applied to percentage values
+ * @return If top is a percentage, {@code top*height} else {@code top}
+ */
+ public final double getTop(double height) {
+ return isTopAsPercentage() ? top * height : top;
+ }
private double top;
/**
* The inset on the right side
*/
public final double getRight() { return right; }
+
+ /**
+ * The normalized inset on the right side
+ * @param width The width applied to percentage values
+ * @return If right is a percentage, {@code right*width} else {@code right}
+ */
+ public final double getRight(double width) {
+ return isRightAsPercentage() ? right * width : right;
+ }
private double right;
/**
* The inset on the bottom side
*/
public final double getBottom() { return bottom; }
+
+ /**
+ * The normalized inset on the bottom side
+ * @param height The height applied to percentage values
+ * @return If bottom is a percentage, {@code bottom*height} else {@code bottom}
+ */
+ public final double getBottom(double height) {
+ return isBottomAsPercentage() ? bottom * height : bottom;
+ }
private double bottom;
/**
* The inset on the left side
*/
public final double getLeft() { return left; }
+
+ /**
+ * The normalized inset on the left side
+ * @param width The width applied to percentage values
+ * @return If left is a percentage, {@code left*width} else {@code left}
+ */
+ public final double getLeft(double width) {
+ return isLeftAsPercentage() ? left * width : left;
+ }
private double left;
+ public final boolean hasPercentBasedInsets() {
+ return topAsPercentage || rightAsPercentage || bottomAsPercentage || leftAsPercentage;
+
+ }
+
+ /**
+ * Return a new Insets from this Insets normalized to pixel values.
+ * @param width The width applied to percentage values
+ * @param height The height applied to percentage values
+ */
+ public final Insets normalize(double width, double height) {
+
+ final double _top = isTopAsPercentage() ? top * height : top;
+ final double _right = isRightAsPercentage() ? right * width : right;
+ final double _bottom = isBottomAsPercentage() ? bottom * height : bottom;
+ final double _left = isLeftAsPercentage() ? left * width : left;
+
+ return new Insets(_top, _right, _bottom, _left);
+ }
+
/**
* The cached hash code, used to improve performance in situations where
* we cache gradients, such as in the CSS routines.
@@ -69,6 +153,7 @@
/**
* Constructs a new Insets instance with four different offsets.
+ * The offsets are treated as pixel values.
*
* @param top the top offset
* @param right the right offset
@@ -76,41 +161,101 @@
* @param left the left offset
*/
public Insets(@NamedArg("top") double top, @NamedArg("right") double right, @NamedArg("bottom") double bottom, @NamedArg("left") double left) {
+ this(top, right, bottom, left, false, false, false, false);
+ }
+
+ /**
+ * Constructs a new Insets instance with same value for all four offsets.
+ * The offsets are treated as pixel values.
+ *
+ * @param topRightBottomLeft the value used for top, bottom, right and left
+ * offset
+ */
+ public Insets(@NamedArg("topRightBottomLeft") double topRightBottomLeft) {
+ this(topRightBottomLeft, topRightBottomLeft, topRightBottomLeft, topRightBottomLeft, false, false, false, false);
+ }
+
+ /**
+ * Constructs a new Insets instance with same value for all four offsets.
+ *
+ * @param topRightBottomLeft the value used for top, bottom, right and left
+ * @param topRightBottomLeftAsPercentage If true, topRightBottomLeft is treated as a percentage value
+ * offset
+ */
+ public Insets(@NamedArg("topRightBottomLeft") double topRightBottomLeft,
+ @NamedArg("topRightBottomLeftAsPercentage") boolean topRightBottomLeftAsPercentage) {
+ this(topRightBottomLeft, topRightBottomLeft, topRightBottomLeft, topRightBottomLeft,
+ topRightBottomLeftAsPercentage, topRightBottomLeftAsPercentage, topRightBottomLeftAsPercentage, topRightBottomLeftAsPercentage);
+ }
+
+ /**
+ * Creates a new Insets.
+ *
+ * @param top The offsets of the top.
+ * @param right The inset of the right.
+ * @param bottom The inset of the bottom.
+ * @param left The inset of the left.
+ * @param topAsPercentage Whether the top should be treated as a percentage.
+ * @param rightAsPercentage Whether the right should be treated as a percentage.
+ * @param bottomAsPercentage Whether the bottom should be treated as a percentage.
+ * @param leftAsPercentage Whether the left should be treated as a percentage.
+ */
+ public Insets(@NamedArg("top") double top, @NamedArg("right") double right,
+ @NamedArg("bottom") double bottom, @NamedArg("left") double left,
+ @NamedArg("topAsPercentage") boolean topAsPercentage, @NamedArg("rightAsPercentage") boolean rightAsPercentage,
+ @NamedArg("bottomAsPercentage") boolean bottomAsPercentage, @NamedArg("leftAsPercentage") boolean leftAsPercentage) {
+
this.top = top;
this.right = right;
this.bottom = bottom;
this.left = left;
+
+ this.topAsPercentage = topAsPercentage;
+ this.rightAsPercentage = rightAsPercentage;
+ this.bottomAsPercentage = bottomAsPercentage;
+ this.leftAsPercentage = leftAsPercentage;
+
+ long bits = 17L;
+ bits = 37L * bits + Double.doubleToLongBits(top);
+ bits = 37L * bits + Double.doubleToLongBits(right);
+ bits = 37L * bits + Double.doubleToLongBits(bottom);
+ bits = 37L * bits + Double.doubleToLongBits(left);
+ bits = 37L * bits + (this.topAsPercentage ? 1 : 0);
+ bits = 37L * bits + (this.rightAsPercentage ? 1 : 0);
+ bits = 37L * bits + (this.bottomAsPercentage ? 1 : 0);
+ bits = 37L * bits + (this.leftAsPercentage ? 1 : 0);
+ hash = (int) (bits ^ (bits >> 32));
}
- /**
- * Constructs a new Insets instance with same value for all four offsets.
- *
- * @param topRightBottomLeft the value used for top, bottom, right and left
- * offset
- */
- public Insets(@NamedArg("topRightBottomLeft") double topRightBottomLeft) {
- this.top = topRightBottomLeft;
- this.right = topRightBottomLeft;
- this.bottom = topRightBottomLeft;
- this.left = topRightBottomLeft;
- }
+
/**
- * Indicates whether some other object is "equal to" this one.
- *
- * @param obj the reference object with which to compare
- * @return true if this object is the same as the obj argument; false otherwise
- */
+ * Indicates whether some other object is "equal to" this one.
+ *
+ * @param obj the reference object with which to compare
+ * @return true if this object is the same as the obj argument; false otherwise
+ */
@Override public boolean equals(Object obj) {
if (obj == this) return true;
if (obj instanceof Insets) {
Insets other = (Insets) obj;
- return top == other.top
- && right == other.right
- && bottom == other.bottom
- && left == other.left;
- } else return false;
+ if (this.hash != other.hash) return false;
+
+ if (bottomAsPercentage != other.bottomAsPercentage) return false;
+ if (leftAsPercentage != other.leftAsPercentage) return false;
+ if (rightAsPercentage != other.rightAsPercentage) return false;
+ if (topAsPercentage != other.topAsPercentage) return false;
+
+ if (Double.compare(this.top, other.top) != 0) return false;
+ if (Double.compare(this.right, other.right) != 0) return false;
+ if (Double.compare(this.bottom, other.bottom) != 0) return false;
+ if (Double.compare(this.left, other.left) != 0) return false;
+
+ return true;
+ }
+
+ return false;
}
/**
@@ -118,14 +263,6 @@
* @return a hash code value for the insets.
*/
@Override public int hashCode() {
- if (hash == 0) {
- long bits = 17L;
- bits = 37L * bits + Double.doubleToLongBits(top);
- bits = 37L * bits + Double.doubleToLongBits(right);
- bits = 37L * bits + Double.doubleToLongBits(bottom);
- bits = 37L * bits + Double.doubleToLongBits(left);
- hash = (int) (bits ^ (bits >> 32));
- }
return hash;
}
@@ -134,7 +271,14 @@
* @return a string representation for the insets.
*/
@Override public String toString() {
- return "Insets [top=" + top + ", right=" + right + ", bottom="
- + bottom + ", left=" + left + "]";
+ return String.format("Insets [" +
+ "top=" + (isTopAsPercentage() ? "%1$.2f%%" : "%5$.2f") +
+ ",right=" + (isRightAsPercentage() ? "%2$.2f%%" : "%6$.2f") +
+ ",bottom=" + (isBottomAsPercentage() ? "%3$.2f%%" : "%7$.2f") +
+ ",left=" + (isLeftAsPercentage() ? "%4$.2f%%" : "%8$.2f") +
+ "]",
+ top*100, right*100, bottom*100, left*100,
+ top, right, bottom, left
+ );
}
}
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/scene/layout/Background.java
--- a/modules/graphics/src/main/java/javafx/scene/layout/Background.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/scene/layout/Background.java Mon Nov 25 12:35:17 2013 -0500
@@ -60,7 +60,7 @@
* both may be empty. Each defined {@link BackgroundFill} is rendered in order,
* followed by each defined {@link BackgroundImage}.
*
- * The Background's {@link #getOutsets() outsets} define any extension of the drawing area of a Region
+ * The Background's {@link #getOutsets(double, double) outsets} define any extension of the drawing area of a Region
* which is necessary to account for all background drawing. These outsets are strictly
* defined by the BackgroundFills that are specified on this Background, if any, because
* all BackgroundImages are clipped to the drawing area, and do not define it. The
@@ -152,9 +152,47 @@
* the distance from the edge of the Region outward. Any BackgroundImages
* which would extend beyond the outsets will be clipped. Only the
* BackgroundFills contribute to the outsets.
+ * @param width
+ * @param height
*/
- public final Insets getOutsets() { return outsets; }
- final Insets outsets;
+ public final Insets getOutsets(double width, double height) {
+
+ // This has to be calculated on the fly since the BackgroundFill's insets, which are RegionInsets,
+ // might be proportional.
+ if (fills == null || fills.isEmpty()) {
+ return Insets.EMPTY;
+ }
+
+ double outerTop = 0, outerRight = 0, outerBottom = 0, outerLeft = 0;
+
+ for (int i=0, iMax=fills.size(); i(noNulls, size);
}
- hasPercentageBasedFills = hasPercentFillRadii;
-
- // This ensures that we either have outsets of 0, if all the insets were positive,
- // or a value greater than zero if they were negative.
- outsets = new Insets(
- Math.max(0, -outerTop),
- Math.max(0, -outerRight),
- Math.max(0, -outerBottom),
- Math.max(0, -outerLeft));
+ hasPercentageBasedFills = hasPercentFill;
// An null or empty images array results in an empty list
if (images == null || images.length == 0) {
@@ -423,10 +444,10 @@
for (int i=0, max=fills.size(); i
+ * The RegionInsets will never be null, but the values may be negative
* in order to position the border beyond the natural bounds
* (that is, (0, 0, width, height)) of the Region.
*/
- public final Insets getInsets() { return insets; }
+ public final Insets getInsets() {
+ return insets;
+ }
final Insets insets;
+ final boolean hasPercentBasedFill;
/**
* A cached hash for improved performance on subsequent hash or
* equality look ups. It is expected that BackgroundFill will in
@@ -91,6 +95,8 @@
this.radii = radii == null ? CornerRadii.EMPTY : radii;
this.insets = insets == null ? Insets.EMPTY : insets;
+ hasPercentBasedFill = this.radii.hasPercentBasedRadii || this.insets.hasPercentBasedInsets();
+
// Pre-compute the hash code. NOTE: all variables are prefixed with "this" so that we
// do not accidentally compute the hash based on the constructor arguments rather than
// based on the fields themselves!
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/scene/layout/Border.java
--- a/modules/graphics/src/main/java/javafx/scene/layout/Border.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/scene/layout/Border.java Mon Nov 25 12:35:17 2013 -0500
@@ -60,15 +60,15 @@
* both may be empty. When rendering, if no images are specified or no
* image succeeds in loading, then all strokes will be rendered in order.
* If any image is specified and succeeds in loading, then no strokes will
- * be drawn, although they will still contribute to the {@link #getInsets() insets}
- * and {@link #getOutsets() outsets} of the Border.
+ * be drawn, although they will still contribute to the {@link #getInsets(double, double) insets}
+ * and {@link #getOutsets(double, double) outsets} of the Border.
*
- * The Border's {@link #getOutsets() outsets} define any extension of the drawing area of a Region
+ * The Border's {@link #getOutsets(double, double) outsets} define any extension of the drawing area of a Region
* which is necessary to account for all border drawing and positioning. These outsets are defined
* by both the {@link BorderStroke}s and {@link BorderImage}s specified on this Border.
* Outsets are strictly non-negative.
*
- * {@link #getInsets()} are used to define the inner-most edge of all of the borders. It also is
+ * {@link #getInsets(double, double)} are used to define the inner-most edge of all of the borders. It also is
* always strictly non-negative. The Region uses the insets of the {@link Background} and Border
* and the {@link javafx.scene.layout.Region#getPadding() Region's padding} to determine the
* Region {@link javafx.scene.layout.Region#getInsets() insets}, which define the content area
@@ -180,17 +180,141 @@
/**
* The outsets of the border define the outer-most edge of the border to be drawn.
* The values in these outsets are strictly non-negative.
+ * @param width
+ * @param height
*/
- public final Insets getOutsets() { return outsets; }
- final Insets outsets;
+ public final Insets getOutsets(double width, double height) {
+
+ // outsets have to be calculated on the fly since RegionInsets on strokes and images may be proportional
+ double outerTop = 0d;
+ double outerRight = 0d;
+ double outerBottom = 0d;
+ double outerLeft = 0d;
+
+ if (strokes != null) {
+ for (int i=0, iMax=strokes.size(); i= strokeOuterTop ? outerTop : strokeOuterTop;
+ outerRight = outerRight >= strokeOuterRight ? outerRight : strokeOuterRight;
+ outerBottom = outerBottom >= strokeOuterBottom ? outerBottom : strokeOuterBottom;
+ outerLeft = outerLeft >= strokeOuterLeft ? outerLeft : strokeOuterLeft;
+ }
+ }
+ }
+
+ if (images != null) {
+ for (int i=0, iMax=images.size(); i= imageOuterTop ? outerTop : imageOuterTop;
+ outerRight = outerRight >= imageOuterRight ? outerRight : imageOuterRight;
+ outerBottom = outerBottom >= imageOuterBottom ? outerBottom : imageOuterBottom;
+ outerLeft = outerLeft >= imageOuterLeft ? outerLeft : imageOuterLeft;
+ }
+ }
+ }
+
+ // Both the BorderStroke and BorderImage class make sure to return the outsets
+ // and insets in the right way, such that we don't have to worry about adjusting
+ // the sign, etc, unlike in the Background implementation.
+ return new Insets(outerTop, outerRight, outerBottom, outerLeft);
+ }
/**
* The insets define the distance from the edge of the Region to the inner-most edge
- * of the border, if that distance is non-negative. The values in these outsets
+ * of the border, if that distance is non-negative. The values in these insets
* are strictly non-negative.
+ * @param width
+ * @param height
*/
- public final Insets getInsets() { return insets; }
- final Insets insets;
+ public final Insets getInsets(double width, double height) {
+
+ if ((strokes == null || strokes.isEmpty()) && (images == null || images.isEmpty())) {
+ return Insets.EMPTY;
+ }
+
+ // insets have to be calculated on the fly since RegionInsets on strokes and images may be proportional
+ double innerTop = 0d;
+ double innerRight = 0d;
+ double innerBottom = 0d;
+ double innerLeft = 0d;
+
+ if (strokes != null) {
+ for (int i=0, iMax=strokes.size(); i= strokeInnerTop ? innerTop : strokeInnerTop;
+ innerRight = innerRight >= strokeInnerRight ? innerRight : strokeInnerRight;
+ innerBottom = innerBottom >= strokeInnerBottom ? innerBottom : strokeInnerBottom;
+ innerLeft = innerLeft >= strokeInnerLeft ? innerLeft : strokeInnerLeft;
+
+ }
+ }
+ }
+
+ if (images != null) {
+ for (int i=0, iMax=images.size(); i= imageInnerTop ? innerTop : imageInnerTop;
+ innerRight = innerRight >= imageInnerRight ? innerRight : imageInnerRight;
+ innerBottom = innerBottom >= imageInnerBottom ? innerBottom : imageInnerBottom;
+ innerLeft = innerLeft >= imageInnerLeft ? innerLeft : imageInnerLeft;
+
+ }
+ }
+ }
+
+ // Both the BorderStroke and BorderImage class make sure to return the outsets
+ // and insets in the right way, such that we don't have to worry about adjusting
+ // the sign, etc, unlike in the Background implementation.
+ return new Insets(innerTop, innerRight, innerBottom, innerLeft);
+ }
+ final boolean hasPercentBasedInsets;
/**
* Gets whether the Border is empty. It is empty if there are no strokes or images.
@@ -212,7 +336,7 @@
* Creates a new Border by supplying an array of BorderStrokes.
* This array may be null, or may contain null values. Any null values
* will be ignored and will not contribute to the {@link #getStrokes() strokes}
- * or {@link #getOutsets() outsets} or {@link #getInsets() insets}.
+ * or {@link #getOutsets(double, double) outsets} or {@link #getInsets(double, double) insets}.
*
* @param strokes The strokes. This may be null, and may contain nulls. Any
* contained nulls are filtered out and not included in the
@@ -230,7 +354,7 @@
* Creates a new Border by supplying an array of BorderImages.
* This array may be null, or may contain null values. Any null values
* will be ignored and will not contribute to the {@link #getImages() images}
- * or {@link #getOutsets() outsets} or {@link #getInsets() insets}.
+ * or {@link #getOutsets(double, double) outsets} or {@link #getInsets(double, double) insets}.
*
* @param images The images. This may be null, and may contain nulls. Any
* contained nulls are filtered out and not included in the
@@ -244,8 +368,8 @@
* Creates a new Border by supplying a List of BorderStrokes and BorderImages.
* These Lists may be null, or may contain null values. Any null values
* will be ignored and will not contribute to the {@link #getStrokes() strokes}
- * or {@link #getImages() images}, {@link #getOutsets() outsets}, or
- * {@link #getInsets() insets}.
+ * or {@link #getImages() images}, {@link #getOutsets(double, double) outsets}, or
+ * {@link #getInsets(double, double) insets}.
*
* @param strokes The strokes. This may be null, and may contain nulls. Any
* contained nulls are filtered out and not included in the
@@ -272,8 +396,8 @@
* Creates a new Border by supplying an array of BorderStrokes and BorderImages.
* These arrays may be null, or may contain null values. Any null values
* will be ignored and will not contribute to the {@link #getStrokes() strokes}
- * or {@link #getImages() images}, {@link #getOutsets() outsets}, or
- * {@link #getInsets() insets}.
+ * or {@link #getImages() images}, {@link #getOutsets(double, double) outsets}, or
+ * {@link #getInsets(double, double) insets}.
*
* @param strokes The strokes. This may be null, and may contain nulls. Any
* contained nulls are filtered out and not included in the
@@ -287,9 +411,8 @@
* final List of images. A null array becomes an empty List.
*/
public Border(@NamedArg("strokes") BorderStroke[] strokes, @NamedArg("images") BorderImage[] images) {
- double innerTop = 0, innerRight = 0, innerBottom = 0, innerLeft = 0;
- double outerTop = 0, outerRight = 0, outerBottom = 0, outerLeft = 0;
+ boolean hasPercentBasedInsets = false;
if (strokes == null || strokes.length == 0) {
this.strokes = Collections.emptyList();
} else {
@@ -299,34 +422,12 @@
final BorderStroke stroke = strokes[i];
if (stroke != null) {
noNulls[size++] = stroke;
-
- // Calculate the insets and outsets. "insets" are the distance
- // from the edge of the region to the inmost edge of the inmost border.
- // Outsets are the distance from the edge of the region out towards the
- // outer-most edge of the outer-most border.
- final double strokeInnerTop = stroke.innerEdge.getTop();
- final double strokeInnerRight = stroke.innerEdge.getRight();
- final double strokeInnerBottom = stroke.innerEdge.getBottom();
- final double strokeInnerLeft = stroke.innerEdge.getLeft();
-
- innerTop = innerTop >= strokeInnerTop ? innerTop : strokeInnerTop;
- innerRight = innerRight >= strokeInnerRight? innerRight : strokeInnerRight;
- innerBottom = innerBottom >= strokeInnerBottom ? innerBottom : strokeInnerBottom;
- innerLeft = innerLeft >= strokeInnerLeft ? innerLeft : strokeInnerLeft;
-
- final double strokeOuterTop = stroke.outerEdge.getTop();
- final double strokeOuterRight = stroke.outerEdge.getRight();
- final double strokeOuterBottom = stroke.outerEdge.getBottom();
- final double strokeOuterLeft = stroke.outerEdge.getLeft();
-
- outerTop = outerTop >= strokeOuterTop ? outerTop : strokeOuterTop;
- outerRight = outerRight >= strokeOuterRight? outerRight : strokeOuterRight;
- outerBottom = outerBottom >= strokeOuterBottom ? outerBottom : strokeOuterBottom;
- outerLeft = outerLeft >= strokeOuterLeft ? outerLeft : strokeOuterLeft;
+ hasPercentBasedInsets |= stroke.getInsets().hasPercentBasedInsets();
}
}
this.strokes = new UnmodifiableArrayList(noNulls, size);
}
+ this.hasPercentBasedInsets = hasPercentBasedInsets;
if (images == null || images.length == 0) {
this.images = Collections.emptyList();
@@ -337,39 +438,11 @@
final BorderImage image = images[i];
if (image != null){
noNulls[size++] = image;
-
- // The Image width + insets may contribute to the insets / outsets of
- // this border.
- final double imageInnerTop = image.innerEdge.getTop();
- final double imageInnerRight = image.innerEdge.getRight();
- final double imageInnerBottom = image.innerEdge.getBottom();
- final double imageInnerLeft = image.innerEdge.getLeft();
-
- innerTop = innerTop >= imageInnerTop ? innerTop : imageInnerTop;
- innerRight = innerRight >= imageInnerRight? innerRight : imageInnerRight;
- innerBottom = innerBottom >= imageInnerBottom ? innerBottom : imageInnerBottom;
- innerLeft = innerLeft >= imageInnerLeft ? innerLeft : imageInnerLeft;
-
- final double imageOuterTop = image.outerEdge.getTop();
- final double imageOuterRight = image.outerEdge.getRight();
- final double imageOuterBottom = image.outerEdge.getBottom();
- final double imageOuterLeft = image.outerEdge.getLeft();
-
- outerTop = outerTop >= imageOuterTop ? outerTop : imageOuterTop;
- outerRight = outerRight >= imageOuterRight? outerRight : imageOuterRight;
- outerBottom = outerBottom >= imageOuterBottom ? outerBottom : imageOuterBottom;
- outerLeft = outerLeft >= imageOuterLeft ? outerLeft : imageOuterLeft;
}
}
this.images = new UnmodifiableArrayList(noNulls, size);
}
- // Both the BorderStroke and BorderImage class make sure to return the outsets
- // and insets in the right way, such that we don't have to worry about adjusting
- // the sign, etc, unlike in the Background implementation.
- outsets = new Insets(outerTop, outerRight, outerBottom, outerLeft);
- insets = new Insets(innerTop, innerRight, innerBottom, innerLeft);
-
// Pre-compute the hash code. NOTE: all variables are prefixed with "this" so that we
// do not accidentally compute the hash based on the constructor arguments rather than
// based on the fields themselves!
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/scene/layout/BorderImage.java
--- a/modules/graphics/src/main/java/javafx/scene/layout/BorderImage.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/scene/layout/BorderImage.java Mon Nov 25 12:35:17 2013 -0500
@@ -111,15 +111,39 @@
final boolean filled;
/**
- * The insets of the BorderImage define where the border should be positioned
- * relative to the edge of the Region. This value will never be null.
+ * The Insets to use for this border image. Each inset indicates at what
+ * distance from the Region's bounds the drawing should begin.
+ *
+ * The Insets will never be null, but the values may be negative
+ * in order to position the border beyond the natural bounds
+ * (that is, (0, 0, width, height)) of the Region.
*/
- public final Insets getInsets() { return insets; }
+ public final Insets getInsets() {
+ return insets;
+ }
final Insets insets;
- // These two are used by Border to compute the insets and outsets of the border
- final Insets innerEdge;
- final Insets outerEdge;
+ // Compute the insets of the inner edge of the border
+ final Insets getInnerEdge(double width, double height) {
+
+ return new Insets(
+ insets.getTop(height) + (widths.isTopAsPercentage() ? height * widths.getTop() : widths.getTop()),
+ insets.getRight(width) + (widths.isRightAsPercentage() ? width * widths.getRight() : widths.getRight()),
+ insets.getBottom(height) + (widths.isBottomAsPercentage() ? width * widths.getBottom() : widths.getBottom()),
+ insets.getLeft(width) + (widths.isLeftAsPercentage() ? height * widths.getLeft() : widths.getLeft()));
+ }
+
+ // Compute the insets of the outer edge of the border
+ final Insets getOuterEdge(double width, double height) {
+
+ if (insets == Insets.EMPTY) return insets;
+
+ return new Insets(
+ Math.max(0, -insets.getTop(height)),
+ Math.max(0, -insets.getRight(width)),
+ Math.max(0, -insets.getBottom(height)),
+ Math.max(0, -insets.getLeft(width)));
+ }
/**
* A cached hash code for faster secondary usage. It is expected
@@ -134,11 +158,10 @@
* @param image The image to use. This must not be null.
* @param widths The widths of the border in each dimension. A null value results in Insets.EMPTY.
* @param insets The insets at which to place the border relative to the region.
- * A null value results in Insets.EMPTY.
+ * A null value results in Insets.EMPTY.
* @param slices The slices for the image. If null, defaults to BorderImageSlices.DEFAULT
* @param repeatX The repeat value for the border image in the x direction. If null, defaults to STRETCH.
* @param repeatY The repeat value for the border image in the y direction. If null, defaults to the same
- * value as repeatX.
*/
public BorderImage(
@NamedArg("image") Image image, @NamedArg("widths") BorderWidths widths, @NamedArg("insets") Insets insets, @NamedArg("slices") BorderWidths slices, @NamedArg("filled") boolean filled,
@@ -152,19 +175,6 @@
this.repeatX = repeatX == null ? BorderRepeat.STRETCH : repeatX;
this.repeatY = repeatY == null ? this.repeatX : repeatY;
- // Compute the inner & outer edge. The outer edge is insets.top,
- // while the inner edge is insets.top + widths.top
- outerEdge = new Insets(
- Math.max(0, -this.insets.getTop()),
- Math.max(0, -this.insets.getRight()),
- Math.max(0, -this.insets.getBottom()),
- Math.max(0, -this.insets.getLeft()));
- innerEdge = new Insets(
- this.insets.getTop() + this.widths.getTop(),
- this.insets.getRight() + this.widths.getRight(),
- this.insets.getBottom() + this.widths.getBottom(),
- this.insets.getLeft() + this.widths.getLeft());
-
// Pre-compute the hash code. NOTE: all variables are prefixed with "this" so that we
// do not accidentally compute the hash based on the constructor arguments rather than
// based on the fields themselves!
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/scene/layout/BorderStroke.java
--- a/modules/graphics/src/main/java/javafx/scene/layout/BorderStroke.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/scene/layout/BorderStroke.java Mon Nov 25 12:35:17 2013 -0500
@@ -149,16 +149,40 @@
final BorderWidths widths;
/**
- * Defines the insets of each side of the BorderStroke. This will never
- * be null, and defaults to EMPTY.
+ * The Insets to use for this border. Each inset indicates at what
+ * distance from the Region's bounds the drawing should begin.
+ *
+ * The Insets will never be null, but the values may be negative
+ * in order to position the border beyond the natural bounds
+ * (that is, (0, 0, width, height)) of the Region.
*/
- public final Insets getInsets() { return insets; }
+ public final Insets getInsets() {
+ return insets;
+ }
final Insets insets;
// These two are used by Border to compute the insets and outsets of the border
- final Insets innerEdge;
- final Insets outerEdge;
+ final Insets getInnerEdge(double width, double height) {
+ return new Insets(
+ insets.getTop(height) + innerEdge.getTop(height),
+ insets.getRight(width) + innerEdge.getRight(width),
+ insets.getBottom(height) + innerEdge.getBottom(height),
+ insets.getLeft(width) + innerEdge.getLeft(width)
+ );
+ }
+ private final Insets innerEdge;
+
+ final Insets getOuterEdge(double width, double height) {
+
+ return new Insets(
+ Math.max(0, outerEdge.getTop(height)) - insets.getTop(height),
+ Math.max(0, outerEdge.getRight(width)) - insets.getRight(width),
+ Math.max(0, outerEdge.getBottom(height))- insets.getBottom(height),
+ Math.max(0, outerEdge.getLeft(width)) - insets.getLeft(width)
+ );
+ }
+ private final Insets outerEdge;
/**
* Defines the radii for each corner of this BorderStroke. This will never
* be null, and defaults to CornerRadii.EMPTY.
@@ -291,17 +315,24 @@
// TODO these calculations are not accurate if we are stroking a shape. In such cases, we
// need to account for the mitre limit
+ // innerEdge and outerEdge are calculated without regard to the Insets. The
+ // Insets are accounted for in the getInnerEdge and getOuterEdge methods.
+ // TODO: if none of the Insets are proportional, then these could be pre-calculated.
innerEdge = new Insets(
- this.insets.getTop() + computeInside(this.topStyle.getType(), this.widths.getTop()),
- this.insets.getRight() + computeInside(this.rightStyle.getType(), this.widths.getRight()),
- this.insets.getBottom() + computeInside(this.bottomStyle.getType(), this.widths.getBottom()),
- this.insets.getLeft() + computeInside(this.leftStyle.getType(), this.widths.getLeft())
+ computeInside(this.topStyle.getType(), this.widths.getTop()),
+ computeInside(this.rightStyle.getType(), this.widths.getRight()),
+ computeInside(this.bottomStyle.getType(), this.widths.getBottom()),
+ computeInside(this.leftStyle.getType(), this.widths.getLeft()),
+ this.widths.isTopAsPercentage(), this.widths.isRightAsPercentage(),
+ this.widths.isBottomAsPercentage(), this.widths.isLeftAsPercentage()
);
outerEdge = new Insets(
- Math.max(0, computeOutside(this.topStyle.getType(), this.widths.getTop()) - this.insets.getTop()),
- Math.max(0, computeOutside(this.rightStyle.getType(), this.widths.getRight()) - this.insets.getRight()),
- Math.max(0, computeOutside(this.bottomStyle.getType(), this.widths.getBottom())- this.insets.getBottom()),
- Math.max(0, computeOutside(this.leftStyle.getType(), this.widths.getLeft()) - this.insets.getLeft())
+ computeOutside(this.topStyle.getType(), this.widths.getTop()),
+ computeOutside(this.rightStyle.getType(), this.widths.getRight()),
+ computeOutside(this.bottomStyle.getType(), this.widths.getBottom()),
+ computeOutside(this.leftStyle.getType(), this.widths.getLeft()),
+ this.widths.isTopAsPercentage(), this.widths.isRightAsPercentage(),
+ this.widths.isBottomAsPercentage(), this.widths.isLeftAsPercentage()
);
this.hash = preComputeHash();
}
diff -r adcb59265f40 modules/graphics/src/main/java/javafx/scene/layout/Region.java
--- a/modules/graphics/src/main/java/javafx/scene/layout/Region.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/main/java/javafx/scene/layout/Region.java Mon Nov 25 12:35:17 2013 -0500
@@ -568,6 +568,89 @@
public final ObjectProperty paddingProperty() { return padding; }
/**
+ * The top, right, bottom, and left margin which extends from the padding
+ * around the region's content. This space will be included in the calculation of the region's
+ * minimum and preferred sizes. By default margin is Insets.EMPTY. Setting the
+ * value to null should be avoided. Margins may be negative.
+ * @since JavaFX 8.0
+ */
+ private ObjectProperty margin = new StyleableObjectProperty(Insets.EMPTY) {
+ // Keep track of the last valid value for the sake of
+ // rollback in case margin is set to null. Note that
+ // Richard really does not like this pattern because
+ // it essentially means that binding the margin property
+ // is not possible since a binding expression could very
+ // easily produce an intermediate null value.
+
+ // Also note that because margin is set virtually everywhere via CSS, and CSS
+ // requires a property object in order to set it, there is no benefit to having
+ // lazy initialization here.
+
+ private Insets lastValidValue = Insets.EMPTY;
+
+ @Override public Object getBean() { return Region.this; }
+ @Override public String getName() { return "padding"; }
+ @Override public CssMetaData getCssMetaData() {
+ return StyleableProperties.PADDING;
+ }
+ @Override public void invalidated() {
+ final Insets newValue = get();
+ if (newValue == null) {
+ // rollback
+ if (isBound()) {
+ unbind();
+ }
+ set(lastValidValue);
+ throw new NullPointerException("cannot set padding to null");
+ } else if (!newValue.equals(lastValidValue)) {
+ lastValidValue = newValue;
+ insets.fireValueChanged();
+ }
+ }
+ };
+ public final void setMargin(Insets value) { marginProperty().set(value); }
+ public final Insets getMargin() { return margin == null ? Insets.EMPTY : margin.get(); }
+ public final ObjectProperty marginProperty() {
+ if (margin == null) {
+ margin = new StyleableObjectProperty(Insets.EMPTY) {
+ // Keep track of the last valid value for the sake of
+ // rollback in case margin is set to null. Note that
+ // Richard really does not like this pattern because
+ // it essentially means that binding the margin property
+ // is not possible since a binding expression could very
+ // easily produce an intermediate null value.
+
+ // Unlike padding, margin is not often used from CSS,
+ // so it is lazily instantiated here.
+
+ private Insets lastValidValue = Insets.EMPTY;
+
+ @Override public Object getBean() { return Region.this; }
+ @Override public String getName() { return "margin"; }
+ @Override public CssMetaData getCssMetaData() {
+ return StyleableProperties.MARGIN;
+ }
+ @Override public void invalidated() {
+ final Insets newValue = get();
+ if (newValue == null) {
+ // rollback
+ if (isBound()) {
+ unbind();
+ }
+ set(lastValidValue);
+ throw new NullPointerException("cannot set margin to null");
+ } else if (!newValue.equals(lastValidValue)) {
+ lastValidValue = newValue;
+ insets.fireValueChanged();
+ }
+ }
+ };
+
+ }
+ return margin;
+ }
+
+ /**
* The background of the Region, which is made up of zero or more BackgroundFills, and
* zero or more BackgroundImages. It is possible for a Background to be empty, where it
* has neither fills nor images, and is semantically equivalent to null.
@@ -585,7 +668,10 @@
final Background b = get();
if(old != null ? !old.equals(b) : b != null) {
// They are different! Both cannot be null
- if (old == null || b == null || !old.getOutsets().equals(b.getOutsets())) {
+ // getOutsets wants width and height. Here we just want to know if they are different
+ // so the actual width and height don't matter, but we need to pass 1 in case the
+ // outsets are proportional.
+ if (old == null || b == null || !old.getOutsets(1d,1d).equals(b.getOutsets(1d,1d))) {
// We have determined that the outsets of these two different background
// objects is different, and therefore the bounds have changed.
impl_geomChanged();
@@ -641,7 +727,10 @@
final Border b = get();
if(old != null ? !old.equals(b) : b != null) {
// They are different! Both cannot be null
- if (old == null || b == null || !old.getOutsets().equals(b.getOutsets())) {
+ // getOutsets wants width and height. Here we just want to know if they are different
+ // so the actual width and height don't matter, but we need to pass 1 in case the
+ // outsets are proportional.
+ if (old == null || b == null || !old.getOutsets(1d,1d).equals(b.getOutsets(1d,1d))) {
// We have determined that the outsets of these two different border
// objects is different, and therefore the bounds have changed.
impl_geomChanged();
@@ -784,26 +873,26 @@
// If there is no border or the border has no insets itself, then the only thing
// affecting the insets is the padding, so we can just return it directly.
final Border b = getBorder();
- if (b == null || Insets.EMPTY.equals(b.getInsets())) {
+ if (b == null) {
return getPadding();
}
// There is a border with some non-zero insets and we do not have a _shape, so we need
// to take the border's insets into account
if (cache == null) {
- // Combine the padding and the border insets.
- // TODO note that negative border insets were being ignored, but
- // I'm not sure that that made sense or was reasonable, so I have
- // changed it so that we just do simple math.
- // TODO Stroke borders should NOT contribute to the insets. Ensure via tests.
- final Insets borderInsets = b.getInsets();
+ // Combine the padding and the margin insets.
+ final Insets marginInsets = getMargin();
final Insets paddingInsets = getPadding();
- cache = new Insets(
- borderInsets.getTop() + paddingInsets.getTop(),
- borderInsets.getRight() + paddingInsets.getRight(),
- borderInsets.getBottom() + paddingInsets.getBottom(),
- borderInsets.getLeft() + paddingInsets.getLeft()
- );
+ if (!Insets.EMPTY.equals(marginInsets) || !Insets.EMPTY.equals(paddingInsets)) {
+ cache = new Insets(
+ marginInsets.getTop() + paddingInsets.getTop(),
+ marginInsets.getRight() + paddingInsets.getRight(),
+ marginInsets.getBottom() + paddingInsets.getBottom(),
+ marginInsets.getLeft() + paddingInsets.getLeft()
+ );
+ } else {
+ cache = Insets.EMPTY;
+ }
}
return cache;
}
@@ -820,17 +909,17 @@
/** Called to update the cached snapped insets */
private void updateSnappedInsets() {
- final Insets insets = getInsets();
+ final Insets _insets = getInsets();
if (_snapToPixel) {
- snappedTopInset = Math.ceil(insets.getTop());
- snappedRightInset = Math.ceil(insets.getRight());
- snappedBottomInset = Math.ceil(insets.getBottom());
- snappedLeftInset = Math.ceil(insets.getLeft());
+ snappedTopInset = Math.ceil(_insets.getTop());
+ snappedRightInset = Math.ceil(_insets.getRight());
+ snappedBottomInset = Math.ceil(_insets.getBottom());
+ snappedLeftInset = Math.ceil(_insets.getLeft());
} else {
- snappedTopInset = insets.getTop();
- snappedRightInset = insets.getRight();
- snappedBottomInset = insets.getBottom();
- snappedLeftInset = insets.getLeft();
+ snappedTopInset = _insets.getTop();
+ snappedRightInset = _insets.getRight();
+ snappedBottomInset = _insets.getBottom();
+ snappedLeftInset = _insets.getLeft();
}
}
@@ -2373,6 +2462,8 @@
final boolean sizeChanged = impl_isDirty(DirtyBits.NODE_GEOMETRY);
if (sizeChanged) {
pg.setSize((float)getWidth(), (float)getHeight());
+ Insets _margins = getMargin();
+ pg.setMargins((float)_margins.getTop(), (float)_margins.getRight(), (float)_margins.getBottom(), (float)_margins.getLeft());
}
// NOTE: The order here is very important. There is logic in NGRegion which determines
@@ -2590,7 +2681,7 @@
final List fills = background.getFills();
for (int i = 0, max = fills.size(); i < max; i++) {
final BackgroundFill bgFill = fills.get(i);
- if (contains(localX, localY, 0, 0, x2, y2, bgFill.getInsets(), bgFill.getRadii(), maxRadius)) {
+ if (contains(localX, localY, 0, 0, x2, y2, bgFill.getInsets().normalize(x2,y2), bgFill.getRadii(), maxRadius)) {
return true;
}
}
@@ -2606,7 +2697,7 @@
final List strokes = border.getStrokes();
for (int i=0, max=strokes.size(); i MARGIN =
+ new CssMetaData("-fx-margin",
+ InsetsConverter.getInstance(), Insets.EMPTY) {
+
+ @Override public boolean isSettable(Region node) {
+ return node.margin == null || !node.margin.isBound();
+ }
+
+ @Override public StyleableProperty getStyleableProperty(Region node) {
+ return (StyleableProperty)node.marginProperty();
+ }
+ };
+
private static final CssMetaData OPAQUE_INSETS =
new CssMetaData("-fx-opaque-insets",
InsetsConverter.getInstance(), null) {
@@ -3135,6 +3239,7 @@
final List> styleables =
new ArrayList>(Parent.getClassCssMetaData());
styleables.add(PADDING);
+ styleables.add(MARGIN);
styleables.add(BACKGROUND);
styleables.add(BORDER);
styleables.add(OPAQUE_INSETS);
diff -r adcb59265f40 modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundFillConverterTest.java
--- a/modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundFillConverterTest.java Mon Nov 25 10:00:45 2013 -0500
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,245 +0,0 @@
-/*
- * Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation. Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is 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
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.sun.javafx.scene.layout.region;
-
-import org.junit.Test;
-
-/**
- * Tests for the BackgroundFillConverter class
- */
-public class BackgroundFillConverterTest {
-
- @Test public void dummy() { }
- /*
- -fx-background-color:
- -fx-background-radius:
- -fx-background-insets:
- */
-// @Test public void scenario1() {
-// Map map = new HashMap();
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(0, fills.size());
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius:
-// -fx-background-insets:
-// */
-// @Test public void scenario2() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 0, 0, 0, 0, Insets.EMPTY);
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius: 10
-// -fx-background-insets:
-// */
-// @Test public void scenario3() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, Insets.EMPTY);
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius: 1 2 3 4
-// -fx-background-insets:
-// */
-// @Test public void scenario4() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(1.0, 2.0, 3.0, 4.0) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 1, 2, 3, 4, Insets.EMPTY);
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius: 10
-// -fx-background-insets: 1
-// */
-// @Test public void scenario5() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius: 10, 20
-// -fx-background-insets: 1
-// */
-// @Test public void scenario6() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10), new Insets(20) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue
-// -fx-background-radius: 10
-// -fx-background-insets: 1, 2
-// */
-// @Test public void scenario7() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1), new Insets(2) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(1, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue, green
-// -fx-background-radius: 10
-// -fx-background-insets: 1
-// */
-// @Test public void scenario8() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE, Color.GREEN });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(2, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-//
-// fill = fills.get(1);
-// expected = new BackgroundFill(Color.GREEN, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue, green
-// -fx-background-radius: 10, 20
-// -fx-background-insets: 1
-// */
-// @Test public void scenario9() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE, Color.GREEN });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10), new Insets(20) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(2, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-//
-// fill = fills.get(1);
-// expected = new BackgroundFill(Color.GREEN, 20, 20, 20, 20, new Insets(1));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: blue, green
-// -fx-background-radius: 10
-// -fx-background-insets: 1, 2
-// */
-// @Test public void scenario10() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Paint[] { Color.BLUE, Color.GREEN });
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[] { new Insets(10) });
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[] { new Insets(1), new Insets(2) });
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(2, fills.size());
-//
-// BackgroundFill fill = fills.get(0);
-// BackgroundFill expected = new BackgroundFill(Color.BLUE, 10, 10, 10, 10, new Insets(1));
-// assertEquals(expected, fill);
-//
-// fill = fills.get(1);
-// expected = new BackgroundFill(Color.GREEN, 10, 10, 10, 10, new Insets(2));
-// assertEquals(expected, fill);
-// }
-//
-// /*
-// -fx-background-color: null
-// -fx-background-radius: null
-// -fx-background-insets: null
-// */
-// @Test public void scenario11() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, null);
-// map.put(BackgroundFill.BACKGROUND_RADIUS, null);
-// map.put(BackgroundFill.BACKGROUND_INSETS, null);
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(0, fills.size());
-// }
-//
-// /*
-// -fx-background-color: []
-// -fx-background-radius: []
-// -fx-background-insets: []
-// */
-// @Test public void scenario12() {
-// Map map = new HashMap();
-// map.put(BackgroundFill.BACKGROUND_COLOR, new Color[0]);
-// map.put(BackgroundFill.BACKGROUND_RADIUS, new Insets[0]);
-// map.put(BackgroundFill.BACKGROUND_INSETS, new Insets[0]);
-// List fills = BackgroundFillConverter.getInstance().convert(map);
-// assertEquals(0, fills.size());
-// }
-
-}
diff -r adcb59265f40 modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundFillTest.java
--- a/modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundFillTest.java Mon Nov 25 10:00:45 2013 -0500
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation. Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is 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
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.sun.javafx.scene.layout.region;
-
-import javafx.geometry.Insets;
-import javafx.scene.layout.BackgroundFill;
-import javafx.scene.paint.Color;
-import org.junit.Test;
-
-import java.util.HashMap;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
-
-/**
- * Tests for the BackgroundFill class
- */
-public class BackgroundFillTest {
-
- @Test public void valuesAreSetCorrectly() {
-// BackgroundFill obj = new BackgroundFill(Color.ORANGE, 1, 2, 3, 4, new Insets(20));
-// assertEquals(Color.ORANGE, obj.getFill());
-// assertEquals(1, obj.getTopLeftCornerRadius(), 0);
-// assertEquals(2, obj.getTopRightCornerRadius(), 0);
-// assertEquals(3, obj.getBottomRightCornerRadius(), 0);
-// assertEquals(4, obj.getBottomLeftCornerRadius(), 0);
-// assertEquals(new Insets(20), obj.getOffsets());
- }
-
- @Test public void hashingReturnsSameObject() {
-// HashMap map = new HashMap();
-// BackgroundFill obj = new BackgroundFill(Color.ORANGE, 1, 2, 3, 4, new Insets(20));
-// map.put(obj, "YES");
-// assertEquals("YES", map.get(obj));
-//
-// BackgroundFill equivalent = new BackgroundFill(Color.ORANGE, 1, 2, 3, 4, new Insets(20));
-// assertEquals("YES", map.get(equivalent));
-//
-// BackgroundFill different = new BackgroundFill(Color.ORANGE, 1, /*different!*/3, 3, 4, new Insets(20));
-// assertFalse(map.containsKey(different));
- }
-
- @Test public void equality() {
-// BackgroundFill obj = new BackgroundFill(Color.ORANGE, 1, 2, 3, 4, new Insets(20));
-// BackgroundFill equivalent = new BackgroundFill(Color.ORANGE, 1, 2, 3, 4, new Insets(20));
-// assertTrue(obj.equals(equivalent));
-//
-// BackgroundFill different = new BackgroundFill(Color.ORANGE, 1, /*different!*/3, 3, 4, new Insets(20));
-// assertFalse(obj.equals(different));
- }
-}
diff -r adcb59265f40 modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundImageTest.java
--- a/modules/graphics/src/test/java/com/sun/javafx/scene/layout/region/BackgroundImageTest.java Mon Nov 25 10:00:45 2013 -0500
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,112 +0,0 @@
-/*
- * Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation. Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is 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
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.sun.javafx.scene.layout.region;
-
-import org.junit.Test;
-
-/**
- * Tests for the BackgroundImage class
- */
-public class BackgroundImageTest {
-
- @Test public void dummy() { }
-
-// @Test public void valuesAreSetCorrectly() {
-// Image image = new Image("http://dummyUrl", true);
-// BackgroundImage obj = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, true, false, true, false, true, false);
-//
-// assertEquals(image, obj.getImage());
-// assertEquals(Repeat.SPACE, obj.getRepeatX());
-// assertEquals(Repeat.ROUND, obj.getRepeatY());
-// assertEquals(1, obj.getTop(), 0);
-// assertEquals(2, obj.getRight(), 0);
-// assertEquals(3, obj.getBottom(), 0);
-// assertEquals(4, obj.getLeft(), 0);
-// assertEquals(5, obj.getWidth(), 0);
-// assertEquals(6, obj.getHeight(), 0);
-// assertTrue(obj.isProportionalHPos());
-// assertFalse(obj.isProportionalVPos());
-// assertTrue(obj.isProportionalWidth());
-// assertFalse(obj.isProportionalHeight());
-// assertTrue(obj.isContain());
-// assertFalse(obj.isCover());
-// }
-//
-// @Test public void valuesAreSetCorrectly2() {
-// Image image = new Image("http://dummyUrl", true);
-// BackgroundImage obj = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, false, true, false, true, false, true);
-//
-// assertEquals(image, obj.getImage());
-// assertEquals(Repeat.SPACE, obj.getRepeatX());
-// assertEquals(Repeat.ROUND, obj.getRepeatY());
-// assertEquals(1, obj.getTop(), 0);
-// assertEquals(2, obj.getRight(), 0);
-// assertEquals(3, obj.getBottom(), 0);
-// assertEquals(4, obj.getLeft(), 0);
-// assertEquals(5, obj.getWidth(), 0);
-// assertEquals(6, obj.getHeight(), 0);
-// assertFalse(obj.isProportionalHPos());
-// assertTrue(obj.isProportionalVPos());
-// assertFalse(obj.isProportionalWidth());
-// assertTrue(obj.isProportionalHeight());
-// assertFalse(obj.isContain());
-// assertTrue(obj.isCover());
-// }
-//
-// @Test public void hashingReturnsSameObject() {
-// Map map = new HashMap();
-// Image image = new Image("http://dummyUrl", true);
-// BackgroundImage obj = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, true, false, true, false, true, false);
-// map.put(obj, "YES");
-// assertEquals("YES", map.get(obj));
-//
-// BackgroundImage equivalent = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, true, false, true, false, true, false);
-// assertEquals("YES", map.get(equivalent));
-//
-// BackgroundImage different = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, false, true, false, true, false, true);
-// assertFalse(map.containsKey(different));
-// }
-//
-// @Test public void equality() {
-// Image image = new Image("http://dummyUrl", true);
-// BackgroundImage obj = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, true, false, true, false, true, false);
-//
-// BackgroundImage equivalent = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, true, false, true, false, true, false);
-//
-// assertEquals(obj, equivalent);
-//
-// BackgroundImage different = new BackgroundImage(image, Repeat.SPACE, Repeat.ROUND,
-// 1, 2, 3, 4, 5, 6, false, true, false, true, false, true);
-// assertFalse(obj.equals(different));
-// }
-}
diff -r adcb59265f40 modules/graphics/src/test/java/javafx/scene/layout/BackgroundTest.java
--- a/modules/graphics/src/test/java/javafx/scene/layout/BackgroundTest.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/test/java/javafx/scene/layout/BackgroundTest.java Mon Nov 25 12:35:17 2013 -0500
@@ -253,7 +253,7 @@
};
Background b = new Background(fills, null);
- assertEquals(new Insets(7, 2, 8, 8), b.getOutsets());
+ assertEquals(new Insets(7, 2, 8, 8), b.getOutsets(1,1));
}
@Test public void backgroundImagesDoNotContributeToOutsets() {
@@ -264,7 +264,7 @@
};
Background b = new Background(null, images);
- assertEquals(Insets.EMPTY, b.getOutsets());
+ assertEquals(Insets.EMPTY, b.getOutsets(1,1));
}
@Test public void equivalent() {
diff -r adcb59265f40 modules/graphics/src/test/java/javafx/scene/layout/BorderTest.java
--- a/modules/graphics/src/test/java/javafx/scene/layout/BorderTest.java Mon Nov 25 10:00:45 2013 -0500
+++ b/modules/graphics/src/test/java/javafx/scene/layout/BorderTest.java Mon Nov 25 12:35:17 2013 -0500
@@ -62,6 +62,9 @@
new BorderImage(IMAGE_4, new BorderWidths(3), Insets.EMPTY, new BorderWidths(3, 4, 5, 6), true, STRETCH, SPACE)
};
+ private static final int width = 0;
+ private static final int height = 0;
+
@Test public void instanceCreation() {
Border b = new Border(STROKES_1, IMAGES_1);
assertEquals(STROKES_1.length, b.getStrokes().size(), 0);
@@ -254,9 +257,9 @@
Border border = new Border(new BorderStroke[] { stroke }, null);
// This is a 2 pixel solid stroke painted on the OUTSIDE. This means that the
// outsets should be 2 pixel.
- assertEquals(new Insets(2), border.getOutsets());
+ assertEquals(new Insets(2), border.getOutsets(width,height));
// The insets should be 0, because the stroke is on the OUTSIDE
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelOuterStroke() {
@@ -265,9 +268,9 @@
Border border = new Border(new BorderStroke[] { stroke }, null);
// This is a 1 pixel solid stroke painted on the OUTSIDE. This means that the
// outsets should be 1 pixel.
- assertEquals(new Insets(1), border.getOutsets());
+ assertEquals(new Insets(1), border.getOutsets(width,height));
// The insets should be 0, because the stroke is on the OUTSIDE
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelCenteredStroke() {
@@ -276,9 +279,9 @@
Border border = new Border(new BorderStroke[] { stroke }, null);
// This is a 1 pixel solid stroke painted CENTERED. This means that the
// outsets should be .5 pixel.
- assertEquals(new Insets(.5), border.getOutsets());
+ assertEquals(new Insets(.5), border.getOutsets(width,height));
// The insets should be .5, because the stroke is CENTERED
- assertEquals(new Insets(.5), border.getInsets());
+ assertEquals(new Insets(.5), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelInnerStroke() {
@@ -287,101 +290,101 @@
Border border = new Border(new BorderStroke[] { stroke }, null);
// This is a 1 pixel solid stroke painted on the INSIDE. This means that the
// outsets should be 0 pixel.
- assertEquals(new Insets(0), border.getOutsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
// The insets should be 1, because the stroke is on the INSIDE
- assertEquals(new Insets(1), border.getInsets());
+ assertEquals(new Insets(1), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_twoPixelOuterStroke_PositiveInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.OUTSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(2), new Insets(1, 2, 3, 4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(1, 0, 0, 0), border.getOutsets());
- assertEquals(new Insets(1, 2, 3, 4), border.getInsets());
+ assertEquals(new Insets(1, 0, 0, 0), border.getOutsets(width,height));
+ assertEquals(new Insets(1, 2, 3, 4), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelOuterStroke_PositiveInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.OUTSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(1, 2, 3, 4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(0), border.getOutsets());
- assertEquals(new Insets(1, 2, 3, 4), border.getInsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
+ assertEquals(new Insets(1, 2, 3, 4), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelCenteredStroke_PositiveInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.CENTERED, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(1, 2, 3, 4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(0), border.getOutsets());
- assertEquals(new Insets(1.5, 2.5, 3.5, 4.5), border.getInsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
+ assertEquals(new Insets(1.5, 2.5, 3.5, 4.5), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelInnerStroke_PositiveInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.INSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(1, 2, 3, 4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(0), border.getOutsets());
- assertEquals(new Insets(2, 3, 4, 5), border.getInsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
+ assertEquals(new Insets(2, 3, 4, 5), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_twoPixelOuterStroke_NegativeInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.OUTSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(2), new Insets(-1, -2, -3, -4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(3, 4, 5, 6), border.getOutsets());
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(3, 4, 5, 6), border.getOutsets(width,height));
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelOuterStroke_NegativeInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.OUTSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(-1, -2, -3, -4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(2, 3, 4, 5), border.getOutsets());
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(2, 3, 4, 5), border.getOutsets(width,height));
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelCenteredStroke_NegativeInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.CENTERED, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(-1, -2, -3, -4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(1.5, 2.5, 3.5, 4.5), border.getOutsets());
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(1.5, 2.5, 3.5, 4.5), border.getOutsets(width,height));
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelInnerStroke_NegativeInsets() {
BorderStrokeStyle style = new BorderStrokeStyle(StrokeType.INSIDE, null, null, 0, 0, null);
BorderStroke stroke = new BorderStroke(Color.ORANGE, style, new CornerRadii(5), new BorderWidths(1), new Insets(-1, -2, -3, -4));
Border border = new Border(new BorderStroke[] { stroke }, null);
- assertEquals(new Insets(1, 2, 3, 4), border.getOutsets());
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(1, 2, 3, 4), border.getOutsets(width,height));
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelImageWidthNoInsets() {
BorderImage image = new BorderImage(IMAGE_1, new BorderWidths(1), new Insets(0), null, false, null, null);
Border border = new Border(null, new BorderImage[] { image });
- assertEquals(new Insets(0), border.getOutsets());
- assertEquals(new Insets(1), border.getInsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
+ assertEquals(new Insets(1), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelImageWidthWithPositiveInsets() {
BorderImage image = new BorderImage(IMAGE_1, new BorderWidths(1), new Insets(10), null, false, null, null);
Border border = new Border(null, new BorderImage[] { image });
- assertEquals(new Insets(0), border.getOutsets());
- assertEquals(new Insets(11), border.getInsets());
+ assertEquals(new Insets(0), border.getOutsets(width,height));
+ assertEquals(new Insets(11), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_singlePixelImageWidthWithNegativeInsets() {
BorderImage image = new BorderImage(IMAGE_1, new BorderWidths(1), new Insets(-10), null, false, null, null);
Border border = new Border(null, new BorderImage[] { image });
- assertEquals(new Insets(10), border.getOutsets());
- assertEquals(new Insets(0), border.getInsets());
+ assertEquals(new Insets(10), border.getOutsets(width,height));
+ assertEquals(new Insets(0), border.getInsets(width,height));
}
@Test public void insetsAndOutsets_triplePixelImageWidthWithNegativeInsets() {
BorderImage image = new BorderImage(IMAGE_1, new BorderWidths(3), new Insets(-1), null, false, null, null);
Border border = new Border(null, new BorderImage[] { image });
- assertEquals(new Insets(1), border.getOutsets());
- assertEquals(new Insets(2), border.getInsets());
+ assertEquals(new Insets(1), border.getOutsets(width,height));
+ assertEquals(new Insets(2), border.getInsets(width,height));
}
@Test public void equivalent() {