return;
}
- gc.setLineWidth(1);
- gc.setLineStyle(IGraphics.LineStyle.LINE_SOLID);
- def olgBg = gc.getBackground();
- gc.setBackground(gc.getForeground());
- gc.setAlpha(64);
+ gc.useStyle(DrawingStyle.SELECTION_FILL);
gc.fillRect(r);
- gc.setBackground(olgBg);
- gc.setAlpha(255);
+ gc.useStyle(DrawingStyle.SELECTION_BORDER);
gc.drawRect(r);
if (displayName == null || isMultipleSelection) {
Rect rc = childNode.getBounds();
if (rp.isValid() && rc.isValid()) {
- gc.setLineWidth(1);
- gc.setLineStyle(IGraphics.LineStyle.LINE_DOT);
+ gc.useStyle(DrawingStyle.ANCHOR);
// top line
int m = rc.x + rc.w / 2;
}
// Highlight the receiver
- gc.setForeground(gc.registerColor(0x00FFFF00));
- gc.setLineStyle(IGraphics.LineStyle.LINE_SOLID);
- gc.setLineWidth(2);
+ gc.useStyle(DrawingStyle.DROP_RECIPIENT);
gc.drawRect(b);
+ gc.useStyle(DrawingStyle.DROP_ZONE);
gc.setLineStyle(IGraphics.LineStyle.LINE_DOT);
gc.setLineWidth(1);
def currY = feedback.userData.currY;
if (currX != null && currY != null) {
+ gc.useStyle(DrawingStyle.DROP_ZONE_ACTIVE);
+
int x = currX;
int y = currY;
addInnerElements(newChild, element, idMap);
}
}
-
-
}
}
return;
}
- def color = gc.registerColor(0x00FF9900);
- gc.setForeground(color);
-
- gc.setLineStyle(IGraphics.LineStyle.LINE_SOLID);
- gc.setLineWidth(2);
+ gc.useStyle(DrawingStyle.DROP_RECIPIENT);
gc.drawRect(b);
- gc.setLineStyle(IGraphics.LineStyle.LINE_DOT);
- gc.setLineWidth(1);
+ gc.useStyle(DrawingStyle.DROP_ZONE);
def data = feedback.userData;
}
if (data.curr) {
+ gc.useStyle(DrawingStyle.DROP_ZONE_ACTIVE);
gc.setAlpha(200);
- gc.setBackground(color);
gc.fillRect(data.curr.rect);
gc.setAlpha(255);
y += h;
}
- gc.setLineStyle(IGraphics.LineStyle.LINE_SOLID);
- gc.setLineWidth(2);
-
def mark = data.curr.get("mark");
if (mark) {
def black = gc.registerColor(0);
if (data.rejected) {
def br = data.rejected;
- gc.setForeground(gc.registerColor(0x000000FF));
- gc.setLineStyle(IGraphics.LineStyle.LINE_SOLID);
- gc.setLineWidth(4);
+ gc.useStyle(DrawingStyle.INVALID);
gc.drawLine(br.x, br.y , br.x + br.w, br.y + br.h);
gc.drawLine(br.x, br.y + br.h, br.x + br.w, br.y );
}
--- /dev/null
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Eclipse Public License, Version 1.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.eclipse.org/org/documents/epl-v10.php
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.ide.eclipse.adt.editors.layout.gscripts;
+
+/**
+ * Drawing styles are used to distinguish the visual appearance of selection,
+ * hovers, anchors, etc. Each style may have different colors, line thickness,
+ * dashing style, transparency, etc.
+ */
+public enum DrawingStyle {
+ /**
+ * The style used for the border of a selected view
+ */
+ SELECTION_BORDER,
+
+ /**
+ * The style used for the interior of a selected view
+ */
+ SELECTION_FILL,
+
+ /**
+ * The style used for hovered views (e.g. when the mouse is directly on top
+ * of the view)
+ */
+ HOVER,
+
+ /**
+ * The style used to draw anchors (lines to the other views the given view
+ * is anchored to)
+ */
+ ANCHOR,
+
+ /**
+ * The style used to draw outlines (the structure of views)
+ */
+ OUTLINE,
+
+ /**
+ * The style used to draw the recipient/target View of a drop. This is
+ * typically going to be the bounding-box of the view into which you are
+ * adding a new child.
+ */
+ DROP_RECIPIENT,
+
+ /**
+ * The style used to draw a potential drop area <b>within</b> a
+ * {@link #DROP_RECIPIENT}. For example, if you are dragging into a view
+ * with a LinearLayout, the {@link #DROP_RECIPIENT} will be the view itself,
+ * whereas each possible insert position between two children will be a
+ * {@link #DROP_ZONE}. If the mouse is over a {@link #DROP_ZONE} it should
+ * be drawn using the style {@link #DROP_ZONE_ACTIVE}.
+ */
+ DROP_ZONE,
+
+ /**
+ * The style used to draw a currently active drop zone within a drop
+ * recipient. See the documentation for {@link #DROP_ZONE} for details on
+ * the distinction between {@link #DROP_RECIPIENT}, {@link #DROP_ZONE} and
+ * {@link #DROP_ZONE_ACTIVE}.
+ */
+ DROP_ZONE_ACTIVE,
+
+ /**
+ * The style used to raw illegal/error/invalid markers
+ */
+ INVALID,
+
+ /**
+ * A style used for unspecified purposes; can be used by a client to have
+ * yet another color that is domain specific; using this color constant
+ * rather than your own hardcoded value means that you will be guaranteed to
+ * pick up a color that is themed properly and will look decent with the
+ * rest of the colors
+ */
+ CUSTOM1,
+
+ /**
+ * A second styled used for unspecified purposes; see {@link #CUSTOM1} for
+ * details.
+ */
+ CUSTOM2
+}
public interface IGraphics {
/**
- * Registers a color using 0x00rrggbb where each component is
- * 0..0xFF.
+ * Draws a line between 2 points, using the current foreground color and
+ * alpha.
+ */
+ void drawLine(int x1, int y1, int x2, int y2);
+
+ /**
+ * Draws a line between 2 points, using the current foreground color and
+ * alpha.
+ */
+ void drawLine(Point p1, Point p2);
+
+ /**
+ * Draws a rectangle outline between 2 points, using the current foreground
+ * color and alpha.
+ */
+ void drawRect(int x1, int y1, int x2, int y2);
+
+ /**
+ * Draws a rectangle outline between 2 points, using the current foreground
+ * color and alpha.
+ */
+ void drawRect(Point p1, Point p2);
+
+ /**
+ * Draws a rectangle outline between 2 points, using the current foreground
+ * color and alpha.
+ */
+ void drawRect(Rect r);
+
+ /**
+ * Fills a rectangle outline between 2 points, using the current background
+ * color and alpha.
+ */
+ void fillRect(int x1, int y1, int x2, int y2);
+
+ /**
+ * Fills a rectangle outline between 2 points, using the current background
+ * color and alpha.
+ */
+ void fillRect(Point p1, Point p2);
+
+ /**
+ * Fills a rectangle outline between 2 points, using the current background
+ * color and alpha.
+ */
+ void fillRect(Rect r);
+
+ /**
+ * Draws the given string, using the current foreground color. No tab
+ * expansion or carriage return processing will be performed.
+ *
+ * @param string the string to be drawn.
+ * @param x the x coordinate of the top left corner of the text.
+ * @param y the y coordinate of the top left corner of the text.
+ */
+ void drawString(String string, int x, int y);
+
+ /**
+ * Draws the given string, using the current foreground color. No tab
+ * expansion or carriage return processing will be performed.
+ *
+ * @param string the string to be drawn.
+ * @param topLeft the top left corner of the text.
+ */
+ void drawString(String string, Point topLeft);
+
+ /**
+ * Set up the graphics context to use the given style for subsequent drawing
+ * operations.
+ *
+ * @param style The drawing style to be used. May not be null.
+ */
+ void useStyle(DrawingStyle style);
+
+ /**
+ * Registers a color using 0x00rrggbb where each component is 0..0xFF.
* <p/>
* Transparency is handled separately using {@link #setAlpha(int)}.
* <p/>
- * If the same color is registered twice, the same object will
- * be returned.
+ * If the same color is registered twice, the same object will be returned.
+ * <p/>
+ * NOTE: It's preferable to use {@link #useStyle(DrawingStyle)} if possible
+ * to ensure that your colors work properly across multiple current and
+ * future themes.
*/
IColor registerColor(int rgb);
IColor getForeground();
/**
- * Returns the current background color.
- * The background color is used for fill operations.
+ * Sets the foreground color. The foreground color is used for drawing
+ * operations including when text is drawn.
*/
- IColor getBackground();
+ void setForeground(IColor color);
/**
- * Sets the foreground color. The foreground color is used
- * for drawing operations including when text is drawn.
+ * Returns the current background color. The background color is used for
+ * fill operations.
*/
- void setForeground(IColor color);
+ IColor getBackground();
/**
- * Sets the background color. The background color is used
- * for fill operations.
+ * Sets the background color. The background color is used for fill
+ * operations.
*/
void setBackground(IColor color);
/**
+ * Returns the current alpha value (varies between 0 for transparent and 255
+ * for opaque).
+ *
+ * @return The current alpha value in use
+ */
+ int getAlpha();
+
+ /**
* Sets the receiver's alpha value which must be
* between 0 (transparent) and 255 (opaque).
* <p>
* The operation is ignored if <var>width</var> is less than 1.
*/
void setLineWidth(int width);
-
- /**
- * Draws a line between 2 points, using the current foreground
- * color and alpha.
- */
- void drawLine(int x1, int y1, int x2, int y2);
- /**
- * Draws a line between 2 points, using the current foreground
- * color and alpha.
- */
- void drawLine(Point p1, Point p2);
-
- /**
- * Draws a rectangle outline between 2 points, using the current
- * foreground color and alpha.
- */
- void drawRect(int x1, int y1, int x2, int y2);
- /**
- * Draws a rectangle outline between 2 points, using the current
- * foreground color and alpha.
- */
- void drawRect(Point p1, Point p2);
- /**
- * Draws a rectangle outline between 2 points, using the current
- * foreground color and alpha.
- */
- void drawRect(Rect r);
-
- /**
- * Fills a rectangle outline between 2 points, using the current
- * background color and alpha.
- */
- void fillRect(int x1, int y1, int x2, int y2);
- /**
- * Fills a rectangle outline between 2 points, using the current
- * background color and alpha.
- */
- void fillRect(Point p1, Point p2);
- /**
- * Fills a rectangle outline between 2 points, using the current
- * background color and alpha.
- */
- void fillRect(Rect r);
-
- /**
- * Draws the given string, using the current foreground color.
- * No tab expansion or carriage return processing will be performed.
- *
- * @param string the string to be drawn.
- * @param x the x coordinate of the top left corner of the text.
- * @param y the y coordinate of the top left corner of the text.
- */
- void drawString(String string, int x, int y);
-
- /**
- * Draws the given string, using the current foreground color.
- * No tab expansion or carriage return processing will be performed.
- *
- * @param string the string to be drawn.
- * @param topLeft the top left corner of the text.
- */
- void drawString(String string, Point topLeft);
}
* the requested FQCN.
*
* @param fqcn The target View FQCN to find.
- * @param descriptors A list of cildren descriptors to iterate through.
+ * @param descriptors A list of children descriptors to iterate through.
* @param visited A set we use to remember which descriptors have already been visited,
* necessary since the view descriptor hierarchy is cyclic.
* @return Either a matching {@link ViewElementDescriptor} or null.
package com.android.ide.eclipse.adt.internal.editors.layout.gle2;
+import com.android.ide.eclipse.adt.editors.layout.gscripts.DrawingStyle;
import com.android.ide.eclipse.adt.editors.layout.gscripts.IColor;
import com.android.ide.eclipse.adt.editors.layout.gscripts.IGraphics;
import com.android.ide.eclipse.adt.editors.layout.gscripts.IViewRule;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.FontMetrics;
import org.eclipse.swt.graphics.GC;
+import org.eclipse.swt.graphics.RGB;
+import java.util.EnumMap;
import java.util.HashMap;
+import java.util.Map;
/**
* Wraps an SWT {@link GC} into an {@link IGraphics} interface so that {@link IViewRule} objects
/** A map of registered colors. All these colors must be disposed at the end. */
private final HashMap<Integer, ColorWrapper> mColorMap = new HashMap<Integer, ColorWrapper>();
+ /**
+ * A map of the {@link SwtDrawingStyle} colors that we have actually used
+ * (to be disposed)
+ */
+ private final Map<DrawingStyle, Color> mStyleColorMap = new EnumMap<DrawingStyle, Color>(
+ DrawingStyle.class);
+
/** The cached pixel height of the default current font. */
private int mFontHeight = 0;
c.getColor().dispose();
}
mColorMap.clear();
+
+ for (Color c : mStyleColorMap.values()) {
+ c.dispose();
+ }
+ mStyleColorMap.clear();
}
//-------------
return new ColorWrapper(c);
}
+ public int getAlpha() {
+ return getGc().getAlpha();
+ }
+
public void setForeground(IColor color) {
checkGC();
getGc().setForeground(((ColorWrapper) color).getColor());
public void drawString(String string, Point topLeft) {
drawString(string, topLeft.x, topLeft.y);
}
+
+ // Styles
+
+ public void useStyle(DrawingStyle style) {
+ checkGC();
+
+ // Look up the specific SWT style which defines the actual
+ // colors and attributes to be used for the logical drawing style.
+ SwtDrawingStyle swtStyle = SwtDrawingStyle.of(style);
+ RGB fg = swtStyle.getForeground();
+ if (fg != null) {
+ Color color = getStyleColor(style, fg);
+ mGc.setForeground(color);
+ }
+ RGB bg = swtStyle.getBackground();
+ if (bg != null) {
+ Color color = getStyleColor(style, bg);
+ mGc.setBackground(color);
+ }
+ mGc.setLineWidth(swtStyle.getLineWidth());
+ mGc.setLineStyle(swtStyle.getLineStyle());
+ mGc.setAlpha(swtStyle.getAlpha());
+ }
+
+ /**
+ * Get the SWT color to use for the given style, using the provided color
+ * description if we haven't seen this color yet. The color will also be
+ * placed in the {@link #mStyleColorMap} such that it can be disposed of at
+ * cleanup time.
+ *
+ * @param style The drawing style for which we want a color
+ * @param defaultColorDesc The RGB values to initialize the color to if we
+ * haven't seen this color before
+ * @return The color object
+ */
+ private Color getStyleColor(DrawingStyle style, RGB defaultColorDesc) {
+ Color color = mStyleColorMap.get(style);
+ if (color == null) {
+ color = new Color(getGc().getDevice(), defaultColorDesc);
+ mStyleColorMap.put(style, color);
+ }
+
+ return color;
+ }
}
mGCWrapper = new GCWrapper(mHScale, mVScale);
Display d = getDisplay();
- mSelectionFgColor = d.getSystemColor(SWT.COLOR_RED);
- mHoverFgColor = new Color(d, 0xFF, 0x99, 0x00); // orange
- mOutlineColor = d.getSystemColor(SWT.COLOR_GREEN);
+ mSelectionFgColor = new Color(d, SwtDrawingStyle.SELECTION_BORDER.getForeground());
+ mHoverFgColor = new Color(d, SwtDrawingStyle.HOVER.getForeground());
+ mOutlineColor = new Color(d, SwtDrawingStyle.OUTLINE.getForeground());
mFont = d.getSystemFont();
if (mShowOutline && mLastValidViewInfoRoot != null) {
gc.setForeground(mOutlineColor);
- gc.setLineStyle(SWT.LINE_DOT);
+ gc.setLineStyle(SwtDrawingStyle.OUTLINE.getLineStyle());
drawOutline(gc, mLastValidViewInfoRoot);
}
if (mHoverRect != null) {
gc.setForeground(mHoverFgColor);
- gc.setLineStyle(SWT.LINE_DOT);
+ gc.setLineStyle(SwtDrawingStyle.HOVER.getLineStyle());
int x = mHScale.translate(mHoverRect.x);
int y = mVScale.translate(mHoverRect.y);
--- /dev/null
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Eclipse Public License, Version 1.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.eclipse.org/org/documents/epl-v10.php
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.ide.eclipse.adt.internal.editors.layout.gle2;
+
+import com.android.ide.eclipse.adt.editors.layout.gscripts.DrawingStyle;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.graphics.RGB;
+
+/**
+ * Description of the drawing styles with specific color, line style and alpha
+ * definitions. This class corresponds to the more generic {@link DrawingStyle}
+ * class which defines the drawing styles but does not introduce any specific
+ * SWT values to the API clients.
+ * <p>
+ * TODO: This class should eventually pick up theme preferences.
+ */
+public enum SwtDrawingStyle {
+ /**
+ * The style used for the border of a selected view
+ */
+ SELECTION_BORDER(new RGB(0xFF, 0x00, 0x00), null, 1, SWT.LINE_SOLID, 255),
+
+ /**
+ * The style used for the interior of a selected view
+ */
+ SELECTION_FILL(null, new RGB(0xFF, 0x00, 0x00), 1, SWT.LINE_SOLID, 64),
+
+ /**
+ * The style used for hovered views (e.g. when the mouse is directly on top
+ * of the view)
+ */
+ HOVER(new RGB(0xFF, 0x99, 0x00), null, 1, SWT.LINE_DOT, 255),
+
+ /**
+ * The style used to draw anchors (lines to the other views the given view
+ * is anchored to)
+ */
+ ANCHOR(new RGB(0xFF, 0x00, 0x00), null, 1, SWT.LINE_SOLID, 255),
+
+ /**
+ * The style used to draw outlines (the structure of views)
+ */
+ OUTLINE(new RGB(0x00, 0xFF, 0x00), null, 1, SWT.LINE_DOT, 255),
+
+ /**
+ * The style used to draw the recipient/target View of a drop. This is
+ * typically going to be the bounding-box of the view into which you are
+ * adding a new child.
+ */
+ DROP_RECIPIENT(new RGB(0xFF, 0x99, 0x00), new RGB(0xFF, 0x99, 0x00), 1, SWT.LINE_SOLID, 255),
+
+ /**
+ * The style used to draw a potential drop area <b>within</b> a
+ * {@link #DROP_RECIPIENT}. For example, if you are dragging into a view
+ * with a LinearLayout, the {@link #DROP_RECIPIENT} will be the view itself,
+ * whereas each possible insert position between two children will be a
+ * {@link #DROP_ZONE}. If the mouse is over a {@link #DROP_ZONE} it should
+ * be drawn using the style {@link #DROP_ZONE_ACTIVE}.
+ */
+ DROP_ZONE(new RGB(0xFF, 0x99, 0x00), new RGB(0xFF, 0x99, 0x00), 1, SWT.LINE_DOT, 255),
+
+ /**
+ * The style used to draw a currently active drop zone within a drop
+ * recipient. See the documentation for {@link #DROP_ZONE} for details on
+ * the distinction between {@link #DROP_RECIPIENT}, {@link #DROP_ZONE} and
+ * {@link #DROP_ZONE_ACTIVE}.
+ */
+ DROP_ZONE_ACTIVE(new RGB(0xFF, 0x99, 0x00), new RGB(0xFF, 0x99, 0x00), 1, SWT.LINE_SOLID, 255),
+
+ /**
+ * The style used to raw illegal/error/invalid markers
+ */
+ INVALID(new RGB(0x00, 0x00, 0xFF), null, 3, SWT.LINE_SOLID, 255),
+
+ /**
+ * A style used for unspecified purposes; can be used by a client to have
+ * yet another color that is domain specific; using this color constant
+ * rather than your own hardcoded value means that you will be guaranteed to
+ * pick up a color that is themed properly and will look decent with the
+ * rest of the colors
+ */
+ CUSTOM1(new RGB(0xFF, 0x00, 0xFF), null, 1, SWT.LINE_SOLID, 255),
+
+ /**
+ * A second styled used for unspecified purposes; see {@link #CUSTOM1} for
+ * details.
+ */
+ CUSTOM2(new RGB(0x00, 0xFF, 0xFF), null, 1, SWT.LINE_DOT, 255);
+
+ /**
+ * Construct a new style value with the given foreground, background, width,
+ * linestyle and transparency.
+ *
+ * @param fg A color descriptor for the foreground color, or null if no
+ * foreground color should be set
+ * @param bg A color descriptor for the background color, or null if no
+ * foreground color should be set
+ * @param width The line width, in pixels, or 0 if no line width should be
+ * set
+ * @param lineStyle The SWT line style - such as {@link SWT#LINE_SOLID}.
+ * @param alpha The alpha value, an integer in the range 0 to 255 where 0 is
+ * fully transparent and 255 is fully opaque.
+ */
+ private SwtDrawingStyle(RGB fg, RGB bg, int width, int lineStyle, int alpha) {
+ mFg = fg;
+ mBg = bg;
+ mWidth = width;
+ mLineStyle = lineStyle;
+ mAlpha = alpha;
+ }
+
+ /**
+ * Return the foreground RGB color description to be used for this style, or
+ * null if none
+ */
+ public RGB getForeground() {
+ return mFg;
+ }
+
+ /**
+ * Return the background RGB color description to be used for this style, or
+ * null if none
+ */
+ public RGB getBackground() {
+ return mBg;
+ }
+
+ /** Return the line width to be used for this style */
+ public int getLineWidth() {
+ return mWidth;
+ }
+
+ /** Return the SWT line style to be used for this style */
+ public int getLineStyle() {
+ return mLineStyle;
+ }
+
+ /** Return the alpha value (in the range 0,255) to be used for this style */
+ public int getAlpha() {
+ return mAlpha;
+ }
+
+ /**
+ * Return the corresponding SwtDrawingStyle for the given
+ * {@link DrawingStyle}
+ */
+ public static SwtDrawingStyle of(DrawingStyle style) {
+ switch (style) {
+ case SELECTION_BORDER:
+ return SELECTION_BORDER;
+ case SELECTION_FILL:
+ return SELECTION_FILL;
+ case HOVER:
+ return HOVER;
+ case ANCHOR:
+ return ANCHOR;
+ case OUTLINE:
+ return OUTLINE;
+ case DROP_ZONE:
+ return DROP_ZONE;
+ case DROP_ZONE_ACTIVE:
+ return DROP_ZONE_ACTIVE;
+ case DROP_RECIPIENT:
+ return DROP_RECIPIENT;
+ case INVALID:
+ return INVALID;
+ case CUSTOM1:
+ return CUSTOM1;
+ case CUSTOM2:
+ return CUSTOM2;
+
+ // Internal error
+ default:
+ throw new IllegalArgumentException("Unknown style " + style);
+ }
+ }
+
+ private final RGB mFg;
+
+ private final RGB mBg;
+
+ private final int mWidth;
+
+ private final int mLineStyle;
+
+ private final int mAlpha;
+}