1) I need to make a baddie that moves along (platform) and shoots at you when you get too close it it. I've worked out the AI but I can only put one moster in because it uses a fast loop and stuffs up if there more then one. So yeah is it possible to give an object its own group of events?
2) I have an object that moves <---left---right---> at the bottom of the screen. I need to make it so it randomly shoots a fireball up at a random height and falls down again?
- Thanks heaps -
theonecardgame.com
DaVince This fool just HAD to have a custom rating
For 2:
- Value A of object = 0: set value B to 100+Random(50) (you can change the 100 and 50 to how many frames you want to wait before randomly shooting. 50 frames = 1 second.)
- Always: add 1 to value A
- value A >= value B: create ball; set value A to 0
DaVince, could he also use behavior events? I've never got it to work right but it sounds like he wants each monster to have the same set of events doesn't it?
--
"Del Duio has received 0 trophies. Click here to see them all."
"To be a true ninja you must first pick the most stealthy of our assorted combat suits. Might I suggest the bright neon orange?"
DXF Games, coming next: Hasslevania 2- This Space for Rent!
DaVince This fool just HAD to have a custom rating
Registered 04/09/2004
Points 7998
28th September, 2007 at 10:44:36 -
Funny, I just wanted to edit my post to suggest the usage of using object behaviours.
How do behaviour events work? What I mean is, does it work like global events do? I don't put too much stock in global events for the most part. How would you tie an enemy to a set of behaviour events?
--
"Del Duio has received 0 trophies. Click here to see them all."
"To be a true ninja you must first pick the most stealthy of our assorted combat suits. Might I suggest the bright neon orange?"
DXF Games, coming next: Hasslevania 2- This Space for Rent!
1) I've never used behaviours, so I'm not completely sure how they work, but here's what I usually do:
* Always
- Monster: Spread 0 in Value A
* Always
- Start loop "foo" NObjects("Monster") times
* On loop "foo"
* Value A of Monster == LoopIndex("foo")
- [Insert code here]
2) Use an alterable value to store the Y velocity of the fireball:
* [event]
- Create Fireball at (0;0) from SomeObject
- Fireball: Set Value A to (0 - (Random(21) + 10)) (Generates a random number between -10 and -30, you can change it if you want)
* Always
- Fireball: Add 1 to Value A
- Fireball: Set Y position to Y("Fireball") + Alterable Value A("Fireball")
In relation to question 2, thanks Axel, it's beautiful... it brought tears to my eyes and it's only two events. Thanks.
Question 1 I don't understand: what do you mean by [Insert code here]. There are alot of events under my Baddie with its fast loop for gravity and all that.
So, in regards to question 1 you're trying to make multiple baddies use a fast loop platform engine? As far as I know, not going to happen.
Instead, try making the fast-looping platform engine for a Qualifier/Group, and then throw the baddie in the group. Thats the only way I can think of overcoming such madness.
Originally Posted by »xerus So, in regards to question 1 you're trying to make multiple baddies use a fast loop platform engine? As far as I know, not going to happen.
Noes! I've done it many times before, and it's very much possible. Simply use the code I posted above.
Originally Posted by Edwin Street
Question 1 I don't understand: what do you mean by [Insert code here]. There are alot of events under my Baddie with its fast loop for gravity and all that.
It's quite simple: Copy/paste those two conditions into every enemy-related line of code. Note that the "On loop" condition always has to be checked first. It may requite some tweaking though, depending on how your movement engine works, but I can help you out if you struggle.
PS: The "spread a value" and "start loop" actions have to be on two separate events, due to an annoying MMF bug. I learned that the hard way =(
Actually, I think I'll just make an example file, so you can have a look at the full source yourself. It might take a while though, because my home internets are sort of BROKEN at the moment =P
n/a
Deleted User
29th September, 2007 at 13:59:55 -
Something you might want to consider is the fact that normal events run first, then global events and then behaviours. If your events are interconnected, you might want to do code your game in the normal events, or in the behaviours (which work just as well). Global events don't handle Qualifiers =/
I've added my Baddie's movement here of what I mean for you guys can see.
Anyone who wants to use it feel free. It's pretty much just DavidN's platform tutorial with a bit of added AI.
But yeah if you just grab another baddie and place it in the level you'll see what I mean about it stuffing up.
I've also added the fire balls level of what we were talking about in case anyone else needs the same thing. Just one thing, I can't figure out how to make a fire ball shoot up randomly between 3 and 6 seconds. So if anyone knows how please let me know or just fill it in.
Axel, if you want to add the events you were talking about into this example you're more than welcome.
Okay, here's why your example file isn't working properly:
- The number of loops is being determined by the alterable value of one of your enemies. Just one. The last one placed, I believe. This means that if that one enemy has a Gravity value of 1, the other enemy won't be moving very far.
- You're stopping the loop once the enemy hits an obstacle. Since there's only one loop going for all of your enemies, this stops everyone's movement once anyone hits a wall or floor.
- You can't use a detector like that for the enemy unless you want to go through the trouble of spreading values and running fastloops to get that detector to work for every single enemy.
Anyway, those are the things I noticed. I'd say ditch the detector, make the gravity loop run a set number of times each time, and give the enemies an additional gravity value that's assigned before the loop is initialized and that depletes with every loop step.
I know it's late to be replying to this forum (since October last year) but I was just wondering if Axel ever did end up making that example file. I really need it so I can figure out the A.I. for my baddies.
Otherwise, if there anyone here who is a master at platform AI?
Basically I need a baddie with gravity who shoots when close. I know how to do the shooting when close part. But I can't place anymore than 1 baddie because I don't know how to run 1 fast loop that covers all the baddie placed in the level. Have a look at my example: http://eyeangle.sitesled.com/baddie_movement.zip - 15.39KB and you'll see what I mean.
Heh, sorry, I must've forgotten about this thread. But I'm quite sure I posted an example file just like that in another thread. I'll have a look on my webspace and see if I can find it...
Edit: Meh, I just remembered: I did a major cleanup a few weeks ago, removing most of the stuff I had on my webspace. The example, if I ever made it, probably went along with the rest of all the crap I had there. Nevermind that though, I'll download your engine and see what I can do.
I've been trying to find a good substitute for this whole "you need an index value to iterate through objects", since in TGF you only get 3 of those total. To be exact, I've been trying to figure out exactly why:
+Always
=Object: Set Flag 1 Off
=Loop: Start Loop 1 for (Number of "Object") Loops
+Loop: On Loop #1
+Object: Flag 1 is off
+Object: Pick an "Object" at random
=Object: Set Flag 1 On
=Object: Set Flag 2 On
+Loop: On Loop #1
+Object: Flag 2 is on
=(INSERT CODE HERE)
+Loop: On Loop #1
+Object: Flag 2 is on
=Object: Set Flag 2 off
theoretically, this should always pick one of the remaining objects and thus iterate through them, however for some reason when used in TGF, it will only refer to the very last created object, as if it were a dumb "always" event, with no iteration.
I've discovered that klik pretty much just sucks for multiple condition events concerning objects that have multiple instances. I usually do something like this for each event:
>Always
-set val A to 0 // val A keeps track of individual conditions for an event. For each condition that is true in the event block, add 1 to value A. If value A = the sum of the conditions at the end, execute that event's actions with that object.
> // condition 1
- add 1 to val A
> // condition 2
- add 1 to val A
...
> if val A = (sum of conditions)
-perform actions with object.
// repeat for different events (divide them into similar event blocks, all reseting the objects' val A to 0 first)
it takes several event lines to do this, but it will work. This is why scripting > klik.
I know it sucks, but it does so with very odd rules, and even after like a decade of beating it with a stick, I am yet to master all of its secrets. Its like trying to program in Malbolge sometimes.
The general rule is- given any single event, it starts off with by default ALL copies of an object selected.
So if you do this code:
*ALWAYS:
=Destroy Object
it will destroy EVERY copy of that object
however, what it seems to do is read top to bottom through the event conditions, and narrow the selected objects by that criterion. So for example;
*ALWAYS
+Object Flag 1 is off
+Object Value A = 0
=Destroy Object
it will first take ALL objects (always is non-specific)
then it will take only the remaining objects with flag 1 is off
then it will narrow those down to the ones with A = 0
so overall only the objects with BOTH Flag 1 on, and Value 1 = 0 will be destroyed.
However, I'm yet to figure out alot of the nuances, like how the "Pick an object at random" really works.
If I take that code outside of a loop, and instead modify it to run every X frames, for example:
*COUNTER = 0
=SET COUNTER TO (NUMBER OF OBJECTS)
=SET OBJECT FLAG 0 OFF
*COUNTER > 0
+OBJECT FLAG 0 IS OFF
+PICK AN OBJECT AT RANDOM
=SUB 1 TO COUNTER
=SET OBJECT FLAG 0 ON
=SET OBJECT FLAG 1 ON
*OBJECT FLAG 1 IS ON
=SET OBJECT POSX to (OBJECT POSX + 1)
=SET OBJECT FLAG 1 OFF
this will work as intended; the objects, regardless of how many there are, will move along at a uniform rate, although a little awkwardly so since they will take turns moving forward one step. However, they will always be within 1 pixel of each other. Hence it works EXACTLY as intended.
For all I can tell, what this is means is that somehow, the fastloop object in TGF completely screws up the "Pick an object at random" command, be it called from an object or called directly from the global.
I think the whole 'multiple conditioning arguments for multiple instances of an object' as you put it, is probably the #1 turnoff I've seen for newbies trying out click. Its extremely poorly set up for iterating through objects like a normal programming language does, and since the event stack and all that is basically a whole bunch of hocus pocus completely hidden from the programmer by the editor, it makes it very tough to explain to people. I dunno how many times I've seen questions like "how do I make more then one enemy respond to my event"
only problem for them is that if they're really serious about making some advanced games later on, they're going to have to learn all the "hocus-pocus." (i.o.w. study programming languages and experiment with the MMF's engine) That's why I became a wizard.
Yeah I've studied enough programming languages that I understand most of it, but several parts of TGF/MMF might as well be done by gremlins in my computer. Its sometimes impossible to predict how some things will work; for example why would my code properly pick objects outside of a loop but not function inside of a loop? Theres alot iffy parts like that, added to the lack of support for memory allocation (I get a set amount of variables to store in each object? *great*), and pisspoor iteration (I'd kill for a .getIterator command, or built in N-dimension arrays), it really stops it from being a 'professional' language. I just happen to like beating it with a stick, since while it might be more *difficult*, it sure does take less *time* then its counterparts.
Yeah, I've never had a problem with it outside of loops, but I just tested it with looks and it goes all screwy.
The pick one at random event is one of the most useful conditions in TGF, if used right (as in, you're not using to pick something randomly). Be warned, it doesn't like working with groups though.
Actually, I just tested it out a little further, and hit it over the head with a stick.
It looks like the problem IS NOT with picking an object at random, but rather how its applying the events on the same queue as the "Start loop 1 for x loops" event.
Even though I have the "Set object flag 1 off" listed BEFORE the start the loop action, it doesn't seem to occur like that. Either its happening not at all, at some funky different time, or only affecting a single object, because if I simply create a new event:
*Always
=Set object flag 0 off
and put it on top of the stack, it will solve the problem. According to the structure of TGF, it shouldn't operate like that, but it seems like the fast loop object is causing some funny business.
I know I had used this "Choose an object at random inside of a loop to iterate through all of them" approach inside gridquest, and it sure works there. So it must just be something funny with fastloop. I've found its usually good practice to put a loop initalization event seperate from the rest, or it might screw up the order.
if I put that ALWAYS event before the loop is initalized, it works fine, and if I put it AFTER the loop, it works fine (resetting the flags either way)
however, if I put it BEFORE the loop is initalized, but in the same horizontal row, it will not work. It seems that for some reason, activating a loop will all the object specifiers in that condition for no apparent reason. Now thats odd stuff