I want to have a dashed line border around my component, but Flex does not offer dashed lines in borders. I also want to be able to control the length of the dash and the length of the gap between dashes.
Implement a custom border class that extends the RectangularBorder class. Implement custom style properties for the custom border class.
Implementing a dash border starts with extending the UIComponent class.
The custom style properties are set in a <mx:Style> tag, though you could set them in ActionScript as well.
Run this code and examine the test app VBox borders to see what happens with various combinations of borderThickness, dashlen, and gaplen.
--------------------------------- DashBorder.as ----------------------------------------
package
{
import mx.core.UIComponent;
public class DashBorder extends UIComponent{
private var dashlen:Number = 5;
private var gaplen:Number = 5;
public function DashBorder(){
super();
}
override protected function updateDisplayList
(unscaledWidth:Number, unscaledHeight:Number):void{
super.updateDisplayList(unscaledWidth, unscaledHeight);
var borderThickness:int = getStyle("borderThickness");
var borderColor:int = getStyle("borderColor");
var backgroundColor:int = getStyle("backgroundColor");
var backgroundAlpha:Number = getStyle("backgroundAlpha");
graphics.clear();
graphics.beginFill(backgroundColor, backgroundAlpha);
graphics.drawRect(0, 0, unscaledWidth, unscaledHeight);
graphics.lineStyle(borderThickness, borderColor, 1)
if (getStyle("dashlen")) {
this.dashlen = getStyle("dashlen");
}
if (getStyle("gaplen")) {
this.gaplen = getStyle("gaplen");
}
drawBorder(this.x, this.y, unscaledWidth, unscaledHeight,
this.dashlen, this.gaplen);
}
public function drawLine(x1:Number, y1:Number, x2:Number,
y2:Number,
dashlen:Number, gaplen:Number): void {
if((x1 != x2) || (y1 != y2)){
var incrlen:Number = dashlen + gaplen;
var len:Number = Math.sqrt((x1 - x2) * (x1 - x2) + (y1 -
y2) * (y1 - y2));
var angle:Number = Math.atan((y2 - y1) / (x2 - x1));
var steps:uint = len / (dashlen + gaplen);
var dashstepx:Number = dashlen * Math.cos(angle);
if (x2 < x1) dashstepx *= -1;
var dashstepy:Number = dashlen * Math.sin(angle);
var gapstepx:Number = gaplen * Math.cos(angle);
if (x2 < x1) gapstepx *= -1;
var gapstepy:Number = gaplen * Math.sin(angle);
var stepcount:uint = 0;
while ((stepcount++) < steps) {
var dashstartx:Number;
var dashstarty:Number;
var dashendx:Number;
var dashendy:Number;
if(x1 == x2 && y1 != y2){
dashstartx = dashendx = x1;
if(y2 > y1){
dashstarty = y1 + ((stepcount-1) * (dashlen +
gaplen));
dashendy = dashstarty + dashlen;
}else{
dashstarty = y1 - ((stepcount-1) * (dashlen +
gaplen));
dashendy = dashstarty - dashlen;
}
}else if(y1 == y2 && x1 != x2){
dashstarty = dashendy = y1;
if(x2 > x1){
dashstartx = x1 + ((stepcount-1) * (dashlen +
gaplen));
dashendx = dashstartx + dashlen;
}else{
dashstartx = x1 - ((stepcount-1) * (dashlen +
gaplen));
dashendx = dashstartx - dashlen;
}
}
graphics.moveTo(dashstartx, dashstarty);
graphics.lineTo(dashendx, dashendy);
}
}
}
private function drawBorder(x1:Number, y1:Number, width:Number,
height:Number,
dashlen:Number, gaplen:Number) : void {
drawLine(x1, y1, x1 + width, y1, dashlen, gaplen);
drawLine(x1 + width, y1, x1 + width, y1 + height, dashlen,
gaplen);
drawLine(x1 + width, y1 + height, x1, y1 + height, dashlen,
gaplen);
drawLine(x1, y1 + height, x1, y1, dashlen, gaplen);
}
}
}
----------------------------------- DashBorderExample.mxml ----------------------------------
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
verticalGap="20" backgroundGradientColors="0xFFFFFF, 0xFFFFFF"
backgroundColor="0xFFFFFF">
<mx:Style>
DashBorder {
dashlen: 20;
gaplen: 20;
}
.tightDashBorder {
dashlen: 2;
gaplen: 2;
}
.tightDashWideGapBorder {
dashlen: 2;
gaplen: 20;
}
.wideDashTightGapBorder {
dashlen: 20;
gaplen: 2;
}
</mx:Style>
<mx:VBox borderStyle="solid" width="250" height="200"
borderThickness="1" borderColor="0x000000"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="default solid 1px thick border"/>
</mx:VBox>
<mx:HBox horizontalGap="30">
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="1" borderColor="0x000000"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="1px thick DashBorder"/>
<mx:Label text="20px dash length / 20px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="1" borderColor="0x000000"
styleName="tightDashBorder" backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="1px thick DashBorder"/>
<mx:Label text="2px dash length / 2px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="1" borderColor="0x000000"
styleName="tightDashWideGapBorder"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="1px thick DashBorder"/>
<mx:Label text="2px dash length / 20px gap length"/>
</mx:VBox>
</mx:HBox>
<mx:HBox horizontalGap="30">
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="2" borderColor="0x000000"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="2px thick DashBorder"/>
<mx:Label text="20px dash length / 20px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="2" borderColor="0x000000"
styleName="tightDashBorder" backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="2px thick DashBorder"/>
<mx:Label text="2px dash length / 2px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="2" borderColor="0x000000"
styleName="tightDashWideGapBorder"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="2px thick DashBorder"/>
<mx:Label text="2px dash length / 20px gap length"/>
</mx:VBox>
</mx:HBox>
<mx:HBox horizontalGap="30">
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="3" borderColor="0x000000"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="3px thick DashBorder"/>
<mx:Label text="20px dash length / 20px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="3" borderColor="0x000000"
styleName="tightDashBorder" backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="3px thick DashBorder"/>
<mx:Label text="2px dash length / 2px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="3" borderColor="0x000000"
styleName="tightDashWideGapBorder"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="3px thick DashBorder"/>
<mx:Label text="2px dash length / 20px gap length"/>
</mx:VBox>
</mx:HBox>
<mx:HBox horizontalGap="30">
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="10" borderColor="0x000000"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="10px thick DashBorder"/>
<mx:Label text="20px dash length / 20px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="10" borderColor="0x000000"
styleName="tightDashBorder" backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="10px thick DashBorder"/>
<mx:Label text="2px dash length / 2px gap length"/>
</mx:VBox>
<mx:VBox borderSkin="DashBorder" width="250" height="200"
borderThickness="10" borderColor="0x000000"
styleName="tightDashWideGapBorder"
backgroundColor="0xFFFFFF"
horizontalAlign="center" verticalAlign="middle">
<mx:Label text="10px thick DashBorder"/>
<mx:Label text="2px dash length / 20px gap length"/>
</mx:VBox>
</mx:HBox>
</mx:Application>