adding a background image in flex 4.6 - apache-flex

Doing a Flex 4.6 mobile app I am trying to add an asset .png file to be displayed as the background to the application across all the different views and orientations. Has anyone worked out a way to do this yet?
Any help would be appreciated :)

I've been in this hole and I know the way out.
You'll need to create a skin class for your application. It doesn't have to be too complex here's what my file (appSkin.mxml) looks like.
<?xml version="1.0" encoding="utf-8"?><s:Skin xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark">
<fx:Metadata>
[HostComponent("spark.components.View")]
</fx:Metadata>
<!-- states -->
<s:states>
<s:State name="disabled" />
<s:State name="normal" />
</s:states>
<s:BitmapImage source="#Embed('assets/bg.png')" width="100%" height="100%" />
<s:Group id="contentGroup" width="100%" height="100%" minWidth="0" minHeight="0" />
<!-- SkinParts
name=contentGroup, type=spark.components.Group, required=false
-->
Then you'll need to declare that file as your application's skinClass in your application's opening tag…
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark" applicationDPI="320"
creationComplete="creationCompleteHandler()" xmlns:views="views.*" skinClass="skins.appSkin">
Then you'll have to do one final step. Each of your View components are carrying an opaque background layer so in each of them you'll want to explicitly set that backgroundAlpha value to 0.
<s:View xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark" title="Start" backgroundAlpha="0">
And that should accomplish your mission of maintaining a common background image for your application across multiple views.

Try something like this:
<s:View>
<fx:Script>
[Embed(source="myImage.gif")]
public var myImage :Class;
</fx:Script>
<s:Image source="myImage" width="100%" height="100%"/>
</s:View>
Info about Embedding images in Flex
However, I don't expect perfect results. A PNG is a pre-rendered bitmap. Most likely it will not look right across all views and orientations [and resolutions] because elements of the PNG may be skewed, stretched, or compressed, with it is resized on the fly; for example when switching from portrait to landscape.

Related

Spark Custom Grid Header Renderer Style

I am trying to create a Header for DataGrid which will show the Label and TextInput. The code is:
<?xml version="1.0" encoding="utf-8"?>
<s:DefaultGridHeaderRenderer xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<mx:VBox paddingLeft="5" paddingTop="5" paddingRight="5" paddingBottom="5">
<s:Label text="{data.headerText}"/>
<s:TextInput width="100%" />
</mx:VBox>
</s:DefaultGridHeaderRenderer>
It somehow works but the problem is I am loosing the styles on the headers and the background is showing as white instead of the nice grey gradient.
I think I have to add the styling manually. Is there an easy way to do so?
Thanks
Styles are handled by ActionScript code in the item renderer. It's up to you to write that code in your own item renderer. For an example view the source code for the default header renderer. Or you can ignore styles, and just add a Rect behind the Vbox and set its fill properties to whatever you like.

ItemRenderer Doesn't Resize with DataGrid Column

I have an item renderer tied to an mx:DataGrid column. The renderer used to be inline with the column, but I've moved it out to its own file so I can reuse it across multiple tables.
The problem is that now the renderer doesn't resize (grow/shrink) when the column is resized. So if the user makes the column very small, the contents displayed by the renderer just eat up space and show up over top other columns Any ideas how to make this work?
Code for Item Renderer:
<?xml version="1.0" encoding="utf-8"?>
<s:MXDataGridItemRenderer xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
focusEnabled="true">
<mx:HBox verticalScrollPolicy="auto" horizontalScrollPolicy="off" width="100%">
<mx:Spacer top="0" bottom="0" width="4" />
<mx:Image id="typeIcon" buttonMode="false" source="{data.type}" />
</mx:HBox>
</s:MXDataGridItemRenderer>
Code for column using that renderer:
<mx:DataGridColumn headerText="Type" dataField="type" itemRenderer="com.myCompany.myProject.TypeRenderer" />
Edit
Adding width=100% to the MXDataGridItemRender didn't work.
I posted my question on Adobe's flex forum -- the solution was to remove the outer s:MXDataGridItemRenderer and to just let the mx:HBox be the root control (no other changes were necessary.)
Strange that he Flex Builder app doesn't give you the option of defining the outermost control, it just plops an s:MXDataGridItemRenderer on top...

How to build efficient button skins with larger hitareas than visible area

What I'm trying to do: build a super simple button skin (say a small circle when in up state, slightly larger circle when in over / down states) that has a larger mouse hit area than visible area. In other words, I'd like the button to look like a 5x5 circle when in up state, but transition to over state when the mouse is in a 15x15 pixel area around such circle - in order to make clicking on the button easier.
What I've done in the past is to use a transparent ellipse behind the the visible ellipse. This works nicely but seems like a waste of memory (not much, although if you start having a lot of these buttons it adds up) and rendering cycles (transparency). I thought I could avoid this by wrapping the ellipse in a group with a given size and listen to its mouse events, but somehow no mouse events seem to fire on such a group - not sure why.
I guess I'd love to know if anyone knows an efficient way to do this. Also would love to know why such a group won't fire mouse events, but I guess that's secondary. Simple code snippet below:
the application:
<?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">
<s:Button x="100" y="100" skinClass="mySkin"/>
</s:Application>
the button skin:
<?xml version="1.0" encoding="utf-8"?>
<s:SparkSkin xmlns:fx="http://ns.adobe.com/mxml/2009" xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:fb="http://ns.adobe.com/flashbuilder/2009">
<fx:Metadata>[HostComponent("spark.components.Button")]</fx:Metadata>
<fx:Script>
<![CDATA[
import mx.states.OverrideBase;
protected function group1_rollOverHandler(event:MouseEvent):void
{
trace("roll over");
}
]]>
</fx:Script>
<s:states>
<s:State name="up"/>
<s:State name="over"/>
<s:State name="down"/>
<s:State name="disabled"/>
</s:states>
<s:Group width="15" height="15" rollOver="group1_rollOverHandler(event)">
<s:Ellipse height.up="5" height="12" width="12" width.up="5"
x="0" y="0" x.up="3" y.up="3">
<s:fill>
<s:SolidColor color="0x222222"/>
</s:fill>
</s:Ellipse>
</s:Group>
</s:SparkSkin>
I wouldn't worry about the memory of an Ellipse inside of a SparkSkin. If you are that concerned about memory, you would want to roll your own Button
However, there are a couple of very minor performance enhancements that won't effect the implementation:
Use Skin instead of SparkSkin. it is lighter weight.
Use Rect for the hitarea. It is lighter weight than Ellipse

Setting background image in Flex 4.5

I have written a custom skin in Flex 4.5, which shows a custom image. I want this to my background image, so how can I set this skin to the application container?
Thanks
You skin the application like any other component, the skinClass attribute of course! :)
How?
Here is my app.mxml :
<?xml version="1.0"?>
<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"
skinClass="MyAppSkin">
</s:Application>
Now, here I make a simple skin with a background image stretched to fit!
Full source of my MyAppSkin.mxml file here (too big to post here): http://pastebin.com/Hwu9tc1Y
Here is the important part (only part really customized - rest is standard) :
<s:Group id="backgroundRect">
<s:BitmapImage source="#Embed('beach.jpg')" left="0" right="0" top="0" bottom="0" scaleMode="stretch"/>
</s:Group>
What happens when you apply a skin is that it searches for certain elements by id (backgroundRect being the one we're interested in) and applying them. To customize, simply change the parts of the skin you want. I replaced the standard background solid color fill with this group with an image.
Piece of cake sir!
Make sense?
How about this:
<s:BitmapImage source="#Embed('paper1.jpg')"
left="0" right="0"
width="100%" height="100%"
/>
Set background image and add components
<mx:VBox width="100%" height="100%" horizontalAlign="center" verticalAlign="middle">
<s:List>
<s:ArrayCollection>
<fx:String>One</fx:String>
<fx:String>Two</fx:String>
<fx:String>Three</fx:String>
<fx:String>Four</fx:String>
<fx:String>Five</fx:String>
</s:ArrayCollection>
</s:List>
</mx:VBox>
</s:Group>

modularity and flex view states

I've seen some similar questions, but nothing quite like what I'm trying to figure out, so here goes. I have a flex app with many view states, some of which are used frequently, some of which are not. Currently all these states reside in one mxml file so that only one swf file is generated and loaded in the client browser. I would like to modularize these view states by separating them out into different source files and just loading states from one file into another, however, I still want the user to only have to load one swf file. My main reason for this is to avoid having source files in excess of 10,000 lines. Is there a standard way of addressing this issue?
Thanks.
There are two ways of doing what you ask. The first is what it sounds like you are asking, the second is what I would recommend.
First:
Create your main.mxml application and then create separate component1.mxml and component2.mxml files for each of your states. Then in your application set it up like this:
<?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" xmlns:local="*">
<s:states>
<s:State name="State1"/>
<s:State name="State2"/>
</s:states>
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<local:Component1 includeIn="State1"/>
<local:Component2 includeIn="State2"/>
</s:Application>
The second way, and the one I recommend because of your description of the application breaks it down into multiple swf modules with one swf application. This way the user only downloads what they plan to use. In this scenario do the same as before but create modules instead of components.
<?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" xmlns:local="*">
<s:states>
<s:State name="State1"/>
<s:State name="State2"/>
</s:states>
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<mx:ModuleLoader url="Component1.swf" includeIn="State1"/>
<mx:ModuleLoader url="Component2.swf" includeIn="State2"/>
</s:Application>

Resources