PDA

Volledige versie bekijken : removeChild werkt niet...


Jelmerholland
%Europe/Berlin %573 %2010, 14:45
Beste medemens en buitenlui.. ik ben nieuw op 't forum met de volgende vraag[:o)]

Ik ben bezig met een spelletje (let op! ik ben nieuw met flash) en daarbij moet je een vliegtuigje vliegen.. deze moet je verderop in het spel landen, en in de volgende stage moet je weeropstijgen, vliegen, landen.. en je krijgt steeds meer obstakels (dat is het plan) voorlopig heb ik alleen nog maar een vliegtuigje die vliegt en balletjes die als 'grond' dienen. Nou worden deze balletjes gespawned met de volgende code:

function addScene():void{
if(count == 3){
var High = 10;
var Low = -50;
// Create your variable and datatype it to the linkage id
var Lvl:MovieClip = new LevelClass();
Lvl.y = 700 + (Math.floor(Math.random()*(1+High-Low))+Low);
Lvl.x = 900;
Lvl.addEventListener(Event.ENTER_FRAME, moveScene);
stage.addChild (Lvl);
count = 1;
}else{
count++;
}
}
En deze wordt verplaatst met de volgende code:

function moveScene(e:Event):void{
// Tell Flash the event target is a MovieClip.
var target:MovieClip = e.target as MovieClip;
stage.setChildIndex(target,0);
target.x -= xvel * 3;
//if(target.x < 600){
target.parent.removeChild(target);
//}
}
nou loop ik alleen tegen een probleem aan. de target.parten.removeChild(target); werkt niet.. hoe kan ik dit oplossen?

Ik krijg deze error:

ArgumentError: Error #2025: The supplied DisplayObject must be a child of the caller.
at flash.display::DisplayObjectContainer/setChildIndex()
at flash.display::Stage/setChildIndex()
at MethodInfo-8()
Kan iemand mij uit de brand helpen?

eriknoorland
%Europe/Berlin %592 %2010, 15:13
Welkom op het forum.

probeer eens:

(e.target.parent as MovieClip).removeChild(e.target);

of

(e.target.parent as MovieClip).removeChild(e.target as MovieClip);

Jelmerholland
%Europe/Berlin %601 %2010, 15:26
Welkom op het forum.

probeer eens:

(e.target.parent as MovieClip).removeChild(e.target);
of

(e.target.parent as MovieClip).removeChild(e.target as MovieClip);

Methode 1:
1118: Implicit coercion of a value with static type Object to a possibly unrelated type flash.display:DisplayObject.


Methode 2:
TypeError: Error #1009: Cannot access a property or method of a null object reference.
at MethodInfo-8()


Ik ga d'r ff mee spelen.. misschien dat het ineens lukt.. als je nog suggesties hebt.. dan hoor ik ze graag!

eriknoorland
%Europe/Berlin %607 %2010, 15:34
ipv target kun je ook kijken naar currentTarget.

sidar
%Europe/Berlin %811 %2010, 20:28
zoals je het nu hebt staan...in die enterframe, het kan zo zijn dat ie het al heeft weg gegooid en weer probeert weg te gooien.

probeer anders

function moveScene(e:Event):void{
// Tell Flash the event target is a MovieClip.
var target:MovieClip = e.target as MovieClip;
stage.setChildIndex(target,0);
target.x -= xvel * 3;
if(target.x < 600){
if(target.parent)
{
target.parent.removeChild(target);
}
}
}

Als hij eenmaal is removed dan staat de parent op null. En dit kan de error veroorzaken.
(let wel ik heb je comment slashes verwijderd!)

jelmer91
%Europe/Berlin %168 %2010, 05:02
Hee =)

Klein vraagje, heb je les van Peter v/d Post?

Edit:

Misschien was t beetje slechte post, gezien het totaal niks met het onderwerp te maken heeft.

Wat je zou kunnen doen, is voor de removeChild() een trace() neerzetten, om te kijken of hetgene je probeert te removen wel bestaat, bestaat dit niet, weet je in elk geval waar de fout zit =)

sidar
%Europe/Berlin %440 %2010, 11:34
Hee =)

Klein vraagje, heb je les van Peter v/d Post?

Naar wie is deze vraag bedoelt?

jelmer91
%Europe/Berlin %524 %2010, 13:35
naar JelmerHolland :)

Jelmerholland
%Europe/Berlin %755 %2010, 19:08
Sidar,
Nee dat werkt niet helaas :( Dan krijg ik namelijk de volgende error...

DisplayObject must be a child of the caller.
at flash.display::DisplayObjectContainer/setChildIndex()
at flash.display::Stage/setChildIndex()
at MethodInfo-8()
Jelmer,
Als ik: "trace(target.parent);" doe dan krijg ik dit terug: "[object Stage]"..
Wat moet ik nu doen dan? Want de stage is dus de parent van target?
Hoe moet ik dan verder?


Het gekke is ook dat hij ze wel verwijderd als de target.x < 600 is.. dat vind ik zo raar.. dus het werkt wel, maar het werkt niet8~



http://www.actionscript.org/forums/showthread.php3?t=180084
Dat ga ik is toepassen, mocht iemand nog suggesties hebben! graag

[edit2.1]
Nee, dit werkt ook niet :(
[/edit2.1]

cornedor
%Europe/Berlin %875 %2010, 22:01
Werkt stage.removeChild() niet?

Jelmerholland
%Europe/Berlin %879 %2010, 22:06
Nope.. :( Kan het er misschien aan liggen dat ik het 'level' maak in de eerste functie, en dat ik 'm verplaats en verwijder in de 2e funtie? (Lijkt me toch niet, aangezien de stage.setChildIndex(target,0) wel werkt..)

Ik kan ook wel de file naar je/iemand toesturen? Mocht dat werken? (waarschijnlijk zal je gek worden van m'n code en manier van doen, maarja.. ik ben nieuw XD (telt dat als een goed excuus? ))

cornedor
%Europe/Berlin %882 %2010, 22:11
en addChild (Lvl); ipv stage.addChild (Lvl); en dan removeChild(Lvl);?

Jelmerholland
%Europe/Berlin %887 %2010, 22:18
Oké, ik heb wat debugging gedaan... als ik de code van 'stage.setChildIndex(target,0)' even als comment zet (dus gewoon weg haal) dan is er niks aan de hand. Dan werkt de code naar behoren.. Waarom vern**kt de setChildIndex de removeChild? Is daar iets veranderd aan de 'target' ofzo?
Hoe kan dat?

cornedor
%Europe/Berlin %902 %2010, 22:39
Je zou het evt kunnen proberen om alles in een movieclip te zetten. maar dit is inderdaad raar probleem.

Jelmerholland
%Europe/Berlin %927 %2010, 23:15
http://www.jdwebdesign.nl/flash/Spel 3.swf (http://www.jdwebdesign.nl/flash/Spel%203.swf)

Tja.. meer kan ik er nu even niet van maken ;) Ik zal kijken of ik morgen de .fla naar je stuur.. uploaden doe ik sws niet.. wil 't toch enigszins voor mezelf houden :P totdat ie af is XD

LET OP!, is m'n eerste échte flash project ;)

Controls: pijltjes

sidar
%Europe/Berlin %854 %2010, 21:30
"DisplayObject must be a child of the caller."

Betekend dat de child die je wilt hebben niet bekend is in het object waar je het wilt aanspreken.

1: Hij is al verwijderd en probeert hem nog een keer te verwijderen.
of
2: Je spreekt de verkeerde parent aan.

"Waarom vern**kt de setChildIndex de removeChild? Is daar iets veranderd aan de 'target' ofzo?
Hoe kan dat?"

Puur om de zelfde reden als boven beschreven.
Als Target niet in de parent zit die je wilt aanspreken krijg je een fout.

En waarom verwijder je die groene blobs?
Waarom reset je het begin punt niet? Is veel efficienter.

Jelmerholland
%Europe/Berlin %924 %2010, 23:11
Dan moet ik even uitleggen wat die groene bolletjes doen:

De file, het spel dus, is 600px of 800px breed, weet 't niet precies, kheb de file niet bij de hand ;).
Voor het gemak pak ik even de 600px breedte.

De blobs worden 'gemaakt' op 700px, dus je ziet ze niet gemaakt worden,
Op -100 worden ze verwijderd. Als ik ze laat staan, dan blijven ze maar komen en komen en worden ze niet verwijderd. Gevolg, na een pixeltje of 10.000 afgelegd te hebben wordt het spel toch wel wat traag. Snap je waar ik heen wil?

Dus de vraag is nu: zou je je nader kunnen verklaren met 'het beginpunt resetten' ? Ik snap niet wat je daar mee bedoelt ;)

cornedor
%Europe/Berlin %258 %2010, 07:12
de mc's weer terug zetten naar zijn begin punt ipv verwijderen, if(mc.x <= -50)
{
mc.x = stage.stageWidth+50;
}

sidar
%Europe/Berlin %399 %2010, 10:35
Gebruik een forloop om die blobs van tevoren aan te maken. Verdeeld over het veld.
Laat ze allen de richting in bewegen zoals je nu doet, maar inplaats van verwijderen doe je wat cornedor heeft uitgelegt.

!!!! Je maakt GEEN nieuwe objecten aan!!!!

Maar inplaats dat je alleen de x aanpast, pas ook de y waarde aan zodat je niet het zelfde patroon in hoogte krijgt.
Gebruik Math.random om voor de y een willekeurige plek te pakken( vergeet je marge niet!)
[Dit is natuurlijk weer details over het design zelf =P just helping out]

Vertraging kan veroozaakt worden omdat je de referentie ergens vast houd(in een Array bijvoorbeeld). Het is maar een idee.

Jelmerholland
%Europe/Berlin %414 %2010, 10:56
Mag je écht geen nieuwe objecten aanmaken? Want ik heb het nu al opgelost door bij de else van de if(x < -100) de setChildIndex neer te zetten.. dus het werkt nou wel naar behoren..

Maar is dit dus niet de bedoeling? Maakt dit uit voor de snelheid van je spelletje?

sidar
%Europe/Berlin %584 %2010, 15:01
Het mag wel, maar de methode die ik je probeer te geven is bedoeld om bestaande sets te hergebruiken.
Dus het hele nut word een beetje onnodig als je toch nieuwe objecten aanmaakt.

In jouw game is het niet zo erg, maar verder in de praktijk zul je merken dat als je spelletjes aan het bouwen bent dat " hergebruik " een belangrijk onderdeel word van je design, en met design bedoel ik niet het uiterlijk, maar meer de technische achtergrond.

Het geeft zeker een boost aangezien het aanmaken van een nieuw object een zware taak is. Daarnaast kan je ook meer geheugen besparen en hoef je niet te wachten op de "garbagecollector" om geheugen vrij te maken.

Gevaar is wel, maar meestal ook snel op te lossen, als je de objecten ergens vast houd als referentie. Je gooit ze wel uit je displaylist (http://www.adobe.com/devnet/flash/quickstart/display_list_programming_as3/), maar ze zitten dan nog wel in het geheugen. Dit is gevaarlijk omdat je na een tijdje gaat merken dat je game opeens traag loopt.

Kogels bijvoorbeeld in een -shoot'm up- (http://cache.kotaku.com/assets/resources/2006/08/250px-Mushi-ST3boss.jpg)(zoals de gekkere variant uit japan) kun je beter 1000'en van te voren aanmaken, en dan een aan zetten als je een kogel wilt gebruiken. Dit zorgt voor een veel betere performance. Het is namelijk efficienter want de objecten zijn er al, je gebruikt ze alleen opnieuw.

Jelmerholland
%Europe/Berlin %589 %2010, 15:08
Oké, dat is een tip waar ik zeker wat mee kan ;) Ik ga er mee aan de slag. Merci boekoep ^^

Jelmerholland
%Europe/Berlin %738 %2010, 18:43
Okay, dan heb ik nou toch nog even jullie hulp nodig.

Ik ben dus aan het ombouwen naar die for-loop die de scenery maakt, maar nou wil ik het dus nog wel laten bewegen.

Dit werd gedaan door een addEventListener in de functie 'addScene', maar omdat die addScene nu in frame 1 staat, waar alle variabelen worden gemaakt en waar dus de scenery wordt gemaakt, werkt het niet meer. Omdat daar een EventListener op de 'Lvl' stond met een ENTER_FRAME, die moveScene functie keek wie dat aanriep, maar nou werkt hij niet meer.

want daarin staat een e:Event in de functie en ik krijg 'm niet werkende. Moet ik iets verwijderen ofzo? Als jullie de code nodig hebben hoor ik 't wel ;)

sidar
%Europe/Berlin %581 %2010, 14:57
Maak een Array aan als een globale variabele( dus niet binnen een functie).
In die forloop waar je de objecten aanmaakt moet je de objecten "pushen" in die array.

Vervolgens in je enterframe, maak je een forloop die door de hele array gaat.
dus
for(var i:int =0; i<jouwArray.length;i++)
{
jouArray[i].x -= //jouw snelheid;

if(jouArray[i].x < jouwLimit)
{
//zet hier de gevolgen van de if.
}
}




Houd er wel rekening mee dat deze Array een referentie vast houd naar all deze objecten.
Als jij ze totaal wilt verwijderen dan moet je ze ook uit de array gooien.

Als je deze lijst toch keer op keer opnew gaat gebruiken.
Dan kun je beter in je forloop waar je de objecten aan maakt, checken of deze lijst niet leeg is.
En mocht ie niet leeg zijn, dat je dan door de array heen gaat en ze opnew verdeelt over het veld.