Reference with static type error - actionscript-3

I have an ActionScript 3 function looking like this:
private function removeEntry(myT:Vector.<MyType>):void
{
for (var i:Number; = myT.length - 1; i >= 0; i--)
{
if(!myT[i].condition)
{
removeChild(myT[i]);
myT.removeAt(i);
}
}
}
Unfortunately I get the following nasty error:
Description Resource Path Location Type Call to a possibly undefined
method removeAt through a reference with static type
Vector.. (...) Flex Problem
What am I missing here?

I solved this by using slice instead of removeAt:
private function removeEntry(myT:Vector.<MyType>):void
{
for (var i:Number; = myT.length - 1; i >= 0; i--)
{
if(!myT[i].condition)
{
removeChild(myT[i]);
myT.slice(i, 1);
}
}
}

Related

Block property ActionScript 3

I don't know why I'm getting this error in AS3, "Access of undefined property Block.".
I was following a tutorial and copied the code as it is,
function mainLoop (e:Event) {
for (var i = 0; i < numChildren; i++){
if (getChildAt(i) is Block)
{
var bb = getChildAt(i) as Block;
if (bb.hitTestPoint(mouseX, mouseY))
{
trace("hit");
}
}
}
}
Maybe a missing import? Although FlashDevelop didn't automatically add as it does sometimes so I'm a bit clueless
You should have class definition for Block. It could be exported as part of .swc library or defined in code. Without definition of Block class of cause you will have errors.
Also you could improve your main loop, you shouldn't perform several times same lookup with getChildAt and operations is and as also could be optimised:
function mainLoop(e:Event) {
var block:Block, len:int = numChildren, i:int;
for (i = 0; i < len; i++) {
block = getChildAt(i) as Block;
if (block != null) {
if (block.hitTestPoint(mouseX, mouseY)) {
trace("hit");
}
}
}
}

How to sort objects in a sprite without blinking?

public function resort():void {
while (tickets.numChildren > 0) {
tickets.removeChildAt(tickets.numChildren - 1);
}
for(var i:int = 0; i < ticketsBought.length; i++)
{
var t:TicketCard = ticketsBought[i] as TicketCard;
tickets.addChild(t);
}
}
after this function executes, the tickets are blinking visually, but I don't want that, is there a way to sort objects in the stage without blinking?
I think you can use the setChildIndex method of the DisplayObjectContainer class (see documentation) to reorder your objects without removing and then re-adding them.
Unfortunately I'm not in a position to test this at the moment, but I think the following should work:
public function resort():void {
for(var i:int = 0; i < ticketsBought.length; i++)
{
var t:TicketCard = ticketsBought[i] as TicketCard;
tickets.setChildIndex(t, i);
}
}

Loop a function name in as3

How would I create a simple loop to create these functions:
function hello1(e:Event):void
{
trace("hi");
}
function hello2(e:Event):void
{
trace("hi");
}
The function name goes in order until it stops at
function hello10(e:Event):void
{
trace("hi");
}
I know I can just use one function but I am using this as an example for a larger project.
Functions are just like any other object is ActionScript 3, so you can pass them by reference.
Try something like this.
var functionList:Array = [];
var func:Function;
var numFunctions:int = 10;
for (var i:int = 0; i < numFunctions; i++)
{
func = function(num:Number):void
{
trace(num);
};
functionList.push(func);
}
for (var j:int = 0; j < functionList.length; j++)
{
func = functionList[j] as Function;
func(Math.random()* 100);
}
There are many way to accomplish this.
You could store all function in an array, then call Function pointers.
Or, maybe something like:
package
{
import flash.display.Sprite;
import flash.events.Event;
public class HelloLoop extends Sprite
{
public function hello1(event:Event):void
{
trace("hi - 1");
}
public function hello2(event:Event):void
{
trace("hi - 2");
}
public function hello3(event:Event):void
{
trace("hi - 3");
}
public function HelloLoop()
{
// not sure what event you are passing
var event:Event = new Event("unknown");
for (var i:uint = 1; i <= 3; i++)
{
this["hello" + i](event);
}
}
}
}

Removing array-objects from DisplayList

I'm working on a game for the iPhone using flash, and since memory is crucial i want to clean up displayObjects not needed. All the objects i need to delete is MovieClips taken from some array to another using splice(). Here is the code.
public function onTick(e:TimerEvent):void
{
randomNr = Math.random();
if ( randomNr > 0.9 )
{
var newFriend:Friend = new Friend( randomX, -15 );
newFriend.cacheAsBitmap = true;
army.push(newFriend);
addChild(newFriend);
}
for (var i:int = 0; i < army.length;i++)
{
army[i].y += 3;
if (avatar.hitTestObject(army[i]))
{
mood = false;
TweenLite.to(army[i], .3, {x:308, y:458, scaleX:.7, scaleY:.7, ease:Expo.easeOut, onComplete:fadeFace, onCompleteParams:[army[i],mood]});
deleted.push(army.splice(i,1));
}
}
}
private function cleanUp(e:MouseEvent):void
{
var totalDel:int = deleted.length;
for(var i:int = 0; i < totalDel ;i++)
{
removeChild(deleted[i]);
}
trace(totalDel + " Dele from deleted");
}
My problem is that i get an error when trying to use the CleanUp function.
I can trace all objects in the array and they show as [object Friend], but when trying to remove then from the displayList i get this Error: Error #1034: Type Coercion failed: cannot convert []#2c11309 to flash.display.DisplayObject.
Might be the wrong method im using!? Need some guidance please :)
Try casting each "Friend" as a Display Object:
var totalDel:int = deleted.length;
for(var i:int = 0; i < totalDel ;i++) {
var toDelete:DisplayObject = deleted[i] as DisplayObject;
removeChild(toDelete);
trace(totalDel + "Dele from deleted");
}
A friend coder ended up handing me the perfect solution:
private function cleanUp(arr:Array):void
{
var toDelete:DisplayObject;
var totalDel:int = 0;
while(arr.length >0)
{
toDelete = arr[0];
toDelete.parent.removeChild(toDelete);
arr.shift();
totalDel++
}
//trace(totalDel + "deleted from array " + arr.length + " left");
}
This way all objects gets deleted without any collapsing the array, which is exactly what i needed... Hope this will help someone withe the same problem.

Actionscript 3.0: display object walker in strict mode

This is a document class for a display object walker. Make sure to turn off the strict mode (howto here) when testing the class. Also put some stuff on the stage. When the strict mode is turned off the object walker works just fine. However, I want to make it work in strict mode too. I have tried changing the problematic parts, and addig (dispObj as DisplayObject), with no luck.
package {
import flash.display.MovieClip;
import flash.display.DisplayObject;
import flash.display.DisplayObjectContainer;
public class DisplayWalker extends MovieClip {
public function DisplayWalker() {
showChildren(stage, 0);
}
private function padIndent(indents:int):String {
var indent:String = "";
for (var i:uint = 0; i < indents; i++) {
indent += " ";
}
return indent;
}
private function showChildren(dispObj:DisplayObject, indentLevel:Number):void {
for (var i:uint = 0; i < dispObj.numChildren; i++) {
var obj:DisplayObject = dispObj.getChildAt(i);
if (obj is DisplayObjectContainer) {
trace(padIndent(indentLevel), obj, obj.name);
showChildren(obj, indentLevel + 1);
} else {
trace(padIndent(indentLevel), obj);
}
}
}
}
}
Your class will generate compile time errors in Strict mode because you're trying to access the numChildren and getChildAt methods, which aren't available on the DisplayObject class, but first on one of it's subclasses, DisplayObjectContainer.
The reason it is working in non-Strict mode is that, at runtime, you're effectively passing in subclasses of DisplayObjectContainer (Stage, Sprite, etc).
Just replace DisplayObject with DisplayObjectContainer as the type for dispObj in your showChildren method. DisplayObjects cannot have children and are always leafs in the display object tree, something your showChildren method will have to account for.
Stiggler is on the right track, but properly didn't see that you already check for DisplayObjectContainers.
You just need to modify your code slightly. I didn't test the code, but in any case you should be able to figure it out ;)
private function showChildren(dispObj:DisplayObject, indentLevel:Number):void
{
var dOC:DisplayObjectContainer = dispObj as DisplayObjectContainer;
if(dOC == null)
{
trace(padIndent(indentLevel),obj);
}
else
{
trace(padIndent(indentLevel), obj, obj.name);
var obj:DisplayObject = null;
for (var i:uint = 0; i < dispObj.numChildren; i++)
{
obj = dOC.getChildAt(i);
showChildren(obj, indentLevel + 1);
}
}
}