Reputation: 3810
I am trying for a minimal program that can draw a line, in a new Flex project (using Flash Builder 4.6):
But when it is run in a web browser (Chrome or Firefox), and the button myButton
is clicked on, no line is drawn -- does anybody know how to make it work, and how to make it so that it will draw without needing to click on the button?
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<fx:Script>
<![CDATA[
public function drawLine():void
{
var canvas:Shape = new Shape();
canvas.graphics.lineStyle(3, 0xff);
canvas.graphics.moveTo (0,0);
canvas.graphics.lineTo(300,300);
this.addChild(canvas);
}
]]>
</fx:Script>
<s:Button label="myButton" click="drawLine()" />
</s:Application>
Upvotes: 1
Views: 1580
Reputation: 11912
A much easier way to draw a simple line (or more complex lines too, if you wish) in a Flex application, is to use FXG graphics. This little snippet should draw the same line as in your example immediately when tha application starts up:
<s:Path data="M 0 0 L 300 300 Z">
<s:stroke>
<s:SolidColorStroke color="0xff" weight="3" />
</s:stroke>
</s:Path>
Done!
Now if you absolutely wish to stick with the Shape
class from your example (which I wouldn't recommend in a Flex app), you will need a way to add it to the displayList of a Spark Flex 4 app. Shape
is not an IVisualElement
, which is the only interface the addElement()
method accepts.
You can use the SpriteVisualElement class, which serves exactly this purpose. Note that in an mx (Flex 3) application, you wouldn't need this because you could simply use the addChild()
method. (I know this may be confusing for newcomers: it's a matter of backwards compatibility.)
private function drawLine():void {
var shape:Shape = new Shape();
shape.graphics.lineStyle(3, 0xff);
shape.graphics.moveTo (0,0);
shape.graphics.lineTo(300,300);
var sve:SpriteVisualElement = new SpriteVisualElement();
sve.addChild(shape);
addElement(sve);
}
Now, to avoid the button click, just call drawLine()
when the Application's creationComplete event fires:
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
minWidth="955" minHeight="600"
creationComplete="drawLine()">
Upvotes: 4
Reputation: 39408
The Spark Application tag extends SkinnableComponent which will throw a runtime error when using the AddChild() method. Make sure that you have the Debug Version of the Flash Player installed so that you can see the error. It'll help you in debugging a great many things.
Here is some code that works:
<?xml version="1.0" encoding="utf-8"?>
<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<fx:Script>
<![CDATA[
public function drawLine():void
{
drawingArea.graphics.lineStyle(3, 0x000000);
drawingArea.graphics.moveTo (0,0);
drawingArea.graphics.lineTo(300,300);
}
]]>
</fx:Script>
<s:Button label="myButton" click="drawLine()" />
<s:Group width="100%" height="100%" id="drawingArea">
</s:Group>
</s:WindowedApplication>
I gave the app it's own drawing area, in MXML, and drew to that area. This is an AIR app; but the same code should work in a web based app.
Here is another sample, which does not create the drawing area in MXML; but ActionSCript:
<?xml version="1.0" encoding="utf-8"?>
<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<fx:Script>
<![CDATA[
import mx.core.UIComponent;
public function drawLine():void
{
var canvas :UIComponent = new UIComponent;
canvas.graphics.lineStyle(3, 0xff);
canvas.graphics.moveTo (0,0);
canvas.graphics.lineTo(300,300);
this.addElement(canvas);
}
]]>
</fx:Script>
<s:Button label="myButton" click="drawLine()" />
</s:WindowedApplication>
Note; I used a UIComponent as the drawing element here. I believe UIComponent is the "highest" component up the hierarchy chain which implements IVisualElement and can be passed into the addElement method.
Upvotes: 1