Print selected multiple item from tilelist in flex3 - actionscript-3

i'm working on flex 3 project. in which i have one tileList in which there are muliple images, every images put in different canvas in tileList. i will give allowmultipleSelection to true. now i need to print all that Images on print button click, which user select from TileList.
please give me proper suggestion, how i will DO.
Thanks,

I got my answer Here, I take Tile instead of TileList and i push all Selected Image into one Array. And in printer.printPage I will Pass that Array and It will work now.
/* MyCustomItemBox */
<mx:HBox id="hb" autoLayout="false">
<mx:Image id="img" source="{imageURL}"/>
</mx:HBox>
/* Print Script */
// Custom Component which will be added in to Tile.
var myCustomBox= new MyCustomItemBox();
thumbView.addChild(myCustomBox);
// On Print Button Click
protected function onPrintPages(event:MouseEvent):void
{
var printer:Printer = new Printer();
var arr:Array = new Array();
for(var i:int = 0;i<10;i++)
{
var bdi:MyCustomItemBox = thumbView.getChildAt(i) as MyCustomItemBox;
var hb:HBox = bdi.getChildByName("hb") as HBox;
arr.push( hb.getChildByName( 'img' ) as UIComponent );
}
if(arr.length > 0)
printer.printPage(arr,null, "showAll");
}
<mx:Tile id="thumbView" autoLayout="false" width="90%" height="90%" />

Related

How to remove child with same name if in same location or collision? AS3

So, in my script I have given the user the ability to make unlimited amount of a certain movieclip.
var square = new Square();
sqaure.x = mouseX;
sqaure.y = mouseY;
addChild(square);
However, I would like to have the script remove any extra children added to the same X and Y coordinates. I need to make sure it removes the extra child even if they click and move the cursor away and then click back to an already populated location later. Either in the .class file or in the main script itself.
Any ideas? Thanks
At the moment of click you can obtain a list of all the things under the mouse cursor with the getObjectsUnderPoint(...) method and remove any subset of them upon criteria of your liking.
// Stage, because if user clicks the current container
// into the empty area, the click won't register.
stage.addEventListener(MouseEvent.MOUSE_DOWN, onDown);
function onDown(e:MouseEvent):void
{
var aPoint:Point = new Point;
// Set it to the mouse coordinates.
aPoint.x = mouseX;
aPoint.y = mouseY;
// Convert it to Stage coordinates.
aPoint = localToGlobal(aPoint);
// The returned list will contain only descendants
// of the current DisplayObjectContainer.
var aList:Array = getObjectsUnderPoint(aPoint);
// Iterate through the results.
for each (var aChild:DiaplayObject in aList)
{
// Now, filter the results to match certain criteria.
// Don't bother with the grandchildren.
if (aChild.parent != this) continue;
// Ignore things if they are not of the right class.
if (!(aChild is Square)) continue;
// ...etc.
// Remove those ones that have passed all the checks.
removeChild(aChild);
}
// Add the new one here.
var aSq:Square = new Square;
aSq.x = mouseX;
aSq.y = mouseY;
addChild(aSq);
}
One thing that Organis said, the "addEventListener" is something you can take a look at using the search terms "as3 event listener api". the "api" searches will come up with adobe specific code and property examples.
You can try to put in small input text boxes and a button with an event listener to set x and y to the values of the input text boxes
Another thing, I've always done it best with arrays to hold every item that you are adding to the stage.
//global variables
var nameSprite:Sprite;
var name2Array:Array = new Array();
var id:Number = 0;
//initial function
nameSprite = new Sprite();
addChild(nameSprite);
name2Array = new Array();//seems redundant but has been what I've had to do to make it work
//other function to add items to the array
var sqaure:objectName = new objectName();
sqaure.x = mouseX;
sqaure.y = mouseY;
square.id = id;//I like to add an id to be able to better sort things
nameSprite.addChild(sqaure);
name2Array.push(sqaure);
id++;
//function to remove items
IndexPH = j;//j would be the index in the for loop to identify the entry to be removed
nameSprite.removeChild(name2Array[IndexPH]);//removes from stage
name2Array.splice(IndexPH,1);//removes from array
//function to sort the array after an item has been removed
name2Array.sortOn(["id"], Array.NUMERIC);
So this is a bunch of things that you can mess around with if you need ideas. I tend to search and search and then find a little bit of code to incorporate into my projects while not necessarily using every part of a specific code example.

ActionBar in pure Actionscript

I have this MXML that I would like to express as actionscript:
<s:titleContent>
<s:Label text="Title" fontWeight="bold" fontSize="20" height="20" verticalAlign="top" />
<s:Label text=".com" fontSize="12" height="17" verticalAlign="bottom" />
</s:titleContent>
I've tried this with no success:
var chrome:ActionBar = new ActionBar();
chromeTitle.text = "Title";
chrome.setStyle("fontSize", 20);
chrome.title = "Title";
chrome.title = chromeTitle;
How can I add css styled text to the action bar (multiple labels)? Also is it possible to make other views inherit this action bar so that I dont't have to duplicate code (all vies would have common elements)?
This syntax:
<s:titleContent>
...
</s:titleContent>
Means that you are setting the titleContent property on the component that this resides under. You can tell the difference between properties and new class instances from the case. Class names always start with an uppercase; whereas property names start with a lowercase. You didn't specify which class this is a property on; but since you're dealing with mobile I assume it is a view. the titleContent property is an array.
So; you must do this:
// create the first label and set properties
var tempLabel :Label = new Label();
tempLabel.text = 'Title';
tempLabel.setStyle('fontWeight','bold');
tempLabel.setStyle('fontSize',20);
tempLabel.height = 20;
tempLabel.setStyle('verticalAlign','top');
// add label to titleContent array
this.titleContent.push(tempLabel);
// create next label
tempLabel :Label = new Label();
tempLabel.text = '.com';
tempLabel.setStyle('fontSize',12);
tempLabel.height = 17;
tempLabel.setStyle('verticalAlign','bottom');
// add second label to titleContent array
this.titleContent.push(tempLabel);
That is the proper way to convert the MXML code you provided into ActionScript. Since your own code tried to create a new ActionBar() I'm not sure what you if this is really what you wanted.

Flex getElementByName

I know that there is no such function as getElementByName in Flex but I also now that you can do this["object_id"] to get the element of the application u're in.
What about getting an element inside another element?
I've tried making element["id"] ? But in my try-catch it always runs the "catch" part =\
So: how do I get an element inside another element just having it's id in dynamically created string form?
Thank you in advance
It depends on what kind of element you are trying to access.
A child display object can be accessed by calling DisplayObjectContainer#getChildByName:
element.getChildByName("name");
A public variable (which could be set to also contain a child display object) can be accessed by using bracket syntax:
element["name"];
or simply using dot syntax:element.name
(where name is the name of the property you are trying to access).
Note that any instance you drag to the stage in the Flash IDE will automatically be assigned to a public variable, if you have the "automatically declare stage instances" option checked in your export settings. That is why using this[name]works.
If I understand correctly, you're asking for a way to get all the "elements" in a Flex application that have a certain name.
Here's an example (Flex 3):
<?xml version="1.0"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" xmlns="*">
<mx:Script>
<![CDATA[
private function testIt():void
{
var arr:Array = getDisplayObjectsByName(this, "foo");
for each (var e:* in arr)
trace(e);
}
private static function getDisplayObjectsByName(node:DisplayObjectContainer,
name:String, recurse:Boolean = true):Array
{
var n:int = node.numChildren;
var a:Array = [];
for (var i:int = 0; i < n; i++) {
var c:DisplayObject = node.getChildAt(i);
if (c.name == name)
a.push(c);
if (recurse) {
if (c is DisplayObjectContainer)
a = a.concat(getDisplayObjectsByName(DisplayObjectContainer(c),
name, true));
}
}
return a;
}
]]>
</mx:Script>
<mx:VBox name="foo">
<mx:HBox>
<mx:Button name="foo" label="Test" click="testIt()" />
</mx:HBox>
</mx:VBox>
<mx:Label text="Ignore Me" />
<mx:VBox name="bar">
</mx:VBox>
</mx:Application>
Here we're looking for all the elements called "foo" when the user clicks the "Test" button.
Output:
main0.foo
main0.foo.HBox5.foo
You'll notice that getDisplayObjectsByName() is static. All it does is traverse the display list (depth-first) and pick out all the objects with the specified name.
If you're looking for the element in a Group, you can use this function:
static function getElementByName(group:GroupBase, name:String):IVisualElement {
const child:DisplayObject = group.getChildByName(name);
const index:int = group.getChildIndex(child);
return group.getElementAt(index);
}

How to create dynamic variable vbox in actionscript

I have to create several vbox-es in a for each loop.
Now I want to do something like this.
formsArray["vb"+counter] = new VBox;
formsArray["vb"+counter].visible = true;
add labels etc.
I can't get this thing to work. Anybody any idea how to create dynamic variable names for my vbox-es?
Thanks
First off, to use an associative array, you need to use an Object and not an Array (perhaps you already are, then never mind).
You can achieve what you want to do the following way:
var vbox:VBox;
var formsArray:Object = new Object();
var counter:int = 0;
for each(<statement>)
{
vbox = new VBox();
formsArray[("vb" + counter.toString())] = vbox;
counter++;
}
The VBox's visible property is true by default, so no need to explicitly set it.
Answer to additional question in comments:
You don't really need to make use of dynamic references to do what you want to do. You'd be best of creating a custom component for this, extending the VBox class, by creating a new MXML class with VBox as the root tag. Something along these lines:
<mx:VBox ... >
<mx:Button ... click="btnClickHandler()"/>
<mx:Script>
<![CDATA[
// Toggles visibility of the VBox
private function btnClickHandler():void
{
visible = !visible;
}
]]>
</mx:Script>
</mx:VBox>
Then you can just instantiate as many of these custom VBox:es as you need. However, making the VBox invisible will make the contained button invisible as well, making it difficult to click it again. :) You probably want to address that. Anyways, I hope this will point you in the right direction.

AS3 How to remove previous loaders

In Flash CS4, I'm creating a photo gallery. My goal is to load different thumbnails from a number of images. I have managed that when one clicks an image, a number of thumbnails are being displayed, but when one clicks another image, the new thumbnails are placed on top of the old ones. Can someone help me on how to get rid of the old thumbnails?
Here is the code:
for (var i:int = 0; i < thumbnails.length(); i++) {
imgLoader.unload();
imgLoader = new Loader();
imgLoader.load(new URLRequest(thumbnails[i]));
imgLoader.name= i;
imgLoader.x = 95 * columns;
imgLoader.y = 80 * rows;
imgLoader.alpha = 0;
details.gallery.addChild(imgLoader);
if (columns+1< 5) {
columns++;
} else {
columns = 0;
rows++;
}
}
This is where an Array is your friend. You could do this without an array by merely using a while loop to remove every last child from the sprite or movieclip that you added the thumbs to. The reason we use arrays is so that we can reuse the thumbs, instead of reloading them we merely remove them from the display list. You push a reference to each object into an array for each thumb as you add it to the display list. Each thumbContainer node in the XML gets its own array which get added to the main array. The main array holds references to thumbnail arrays. Thumbnail arrays hold references to loaded thumbnails so that they can be added and removed from the display list. If you plan to never use the thumbs after they have been seen once you may set it's reference equal to null, otherwise merely remove it from the display list; There is no reason to load it many times. When you are ready to add the new thumbs you must clear out previous thumbs. The easiest way to do this is with a while loop.
//Assuming the thumbs were loaded into container
while(container.numChildren > 0)
{
//Remove the first child until there are none.
container.removeChildAt(0);
}
//The XML / 2 Containers / thumbContainer[0] and thumbContainer[1]
<?xml version="1.0" encoding="utf-8"?>
<xml>
<thumbContainer>
<thumb path="path/to/file" />
<thumb path="path/to/file" />
<thumb path="path/to/file" />
</thumbContainer>
<thumbContainer>
<thumb path="path/to/file" />
<thumb path="path/to/file" />
<thumb path="path/to/file" />
</thumbContainer>
</xml>
package
{
import flash.display.Sprite;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.net.URLLoader;
import flash.net.URLRequest;
public class DocumentClass extends Sprite
{
private var _container:Sprite;
private var _mainArray:Array;
private var _xml:XML;
private var _urlLoader:URLLoader;
private var _urlRequest:URLRequest;
public function DocumentClass():void
{
if(stage) _init();
else addEventListener(Event.ADD_TO_STAGE, _init, false, 0 , true);
}
private function _init(e:Event = null):void
{
//Will contain arrays for each thumbContainer in the XML.
_mainArray = [];
_urlRequest = new URLRequest('path/to/xml');
_urlLoader = new URLLoader();
_urlLoader.addEventListener(Event.COMPLETE, _onXMLComplete, false, 0, true);
}
private function _onXMLComplete(e:Event):void
{
_xml = new XML(e.target.data);
_loadThumbs(0);
}
private function _loadThumbs(pIndex:int):void
{
_clearThumbs();
//Find out how many sets of thumbs there and add to _mainArray
for(var i:int = 0; i < _xml.thumbContainer.length(); i++)
{
var tempArray:Array = new Array();
for(var j:int = 0; j < _xml.thumbContainer[i].thumb.length; j++)
{
tempArray[i].push(_xml.thumbContainer[i].thumb[j].#path);
}
_mainArray.push(tempArray);
}
//Here is where we add the new content to container, or you can call a function to do it.
}
private function _clearThumbs():void
{
while(container.numChildren > 0)
{
//Remove the first child until there are none.
container.removeChildAt(0);
}
}
}
}
Again, it is good practice to hold a reference to something that is reusable and to simply remove it from the display list instead of setting to null and prepping for garbage collection only to be loaded again later. I already have written more than I intended and wasn't able to slap in all the code I wanted. It is important to setup the code that makes sure it only loads a particular set of thumbs once; That is the whole idea. As for removing them, it's as simple as the while loop I showed you, you just need to know the name of the DisplayObjectContainer that parents them.
You are adding new thumbnails to your gallery object via the addChild() methods, so you should call a method that removes all thumbnails from the gallery before adding new ones.
I believe it is removeChild() you should use.
I had some very weird problems with this not long ago, causing all sorts of crazy hit collisions and what not. My solution were to call removeChild() on the object I wanted to remove, and then I set it to "null". Prior to this I had a check if the object were null (can't removeChild something that's null).
Can't guarantee this is how you "should" do it, as I'm pretty newbie to the Actionscript scene myself. Hope it solves your problem.
You can remove them by passing the object into details.gallery.removeChild(object) or by index using details.gallery.removeChildAt(index). If you use removeChild(), be sure to check for a null or it will throw an error.
Make sure to check out the flash help files, they're by far the best resource you can use.
This will remove all children within a movieclip called gallery:
while( gallery.numChildren > 0) { gallery.removeChildAt(0); };