Author Topic: Danmakufu Q&A/Problem Thread  (Read 172197 times)

Re: Danmakufu Q&A/Problem Thread
« Reply #330 on: July 19, 2009, 08:25:23 PM »
Also, this isn't a needed question, but I'm not really getting how people do the Particle of Wave and Particle spellcard because of all the crossing back.

CreateShot01(GetX, GetY, 3, angle, RED12, 10);
angle+=var;
var++;


Essentially you're just incrementing by an incrementing variable, which looks like it doubles back once it gets so high in value, but it really doesn't.


Also, what are the dimensions of the visible field?



The red area is where the player can move around freely, the black area is the visible playing field.

Cabblecorento

  • I'm a cat!
  • MEOW.
Re: Danmakufu Q&A/Problem Thread
« Reply #331 on: July 19, 2009, 09:11:33 PM »
2 things I noticed, which I'm going to try to fix by myself. One does not annoy me, the other one does.

1. It repeats. However , it's spread out over a long period of time.
2. The more streams you add, the faster it repeats, to where you can easily find safespots  >:(

Re: Danmakufu Q&A/Problem Thread
« Reply #332 on: July 19, 2009, 09:17:04 PM »
Yes, it does repeat, because when you're incrementing by a nice number it will eventually divide out evenly by 360. Usually I increment by about 0.1 or less to spread out the pattern more, as well as get rid of the safe spots. Incrementing by 1 is quite high for Border of Wave and Particle.

Cabblecorento

  • I'm a cat!
  • MEOW.
Re: Danmakufu Q&A/Problem Thread
« Reply #333 on: July 19, 2009, 09:37:13 PM »
Thanks for the help, and I have one more thing I need help with.
Code: [Select]
#TouhouDanmakufu
#Title[Queen's Demise "De-Coronation"]
#Text[De-Coronation]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
let imgExRumia=GetCurrentScriptDirectory~"img\ExRumia.png";
let imgExRumiaBack=GetCurrentScriptDirectory~"img\ExRumiaBack.png";
let frame=0;
    @Initialize {
        LoadGraphic(imgExRumia);
SetGraphicRect(1,1,64,64);
LoadGraphic(imgExRumiaBack);
        SetLife(100);
        SetDamageRate(1, 1);
        SetTimer(50);
        SetInvincibility(5);
CutIn(YOUMU, "Queen's Demise [De-Coronation]", imgExRumia, 0, 0, 50, 60);
        SetScore(500000);
        SetEnemyMarker(true);
        SetDurableSpellCard;
        MagicCircle(false);
        SetEffectForZeroLife(180, 100, 1);
SetMovePosition01(224,100,100)
    }

    @MainLoop {
        SetCollisionA(GetX, GetY, 32);
        SetCollisionB(GetX, GetY, 24);
if(frame==GetEnemyLife()){
CreateShot01(GetX, GetY, 3, rand(1,360), RED03, 10);
frame=0;
}
frame++;




    }

    @DrawLoop {
SetGraphicRect(64,64,127,127);
SetAlpha(255);
SetTexture(imgExRumia);
DrawGraphic(GetX(),GetY());
       
    }

    @Finalize {
    }
}

When I damage the enemy, it stops shooting.

Any help?

Stuffman

  • *
  • We're having a ball!
Re: Danmakufu Q&A/Problem Thread
« Reply #334 on: July 19, 2009, 10:52:45 PM »
Frame is an integer, but most players don't do damage in integers. For instance if a boss has 49.5 life, it won't shoot on either frame 49 or 50, and thus won't shoot at all.

Try the floor() function, which removes any decimals.
if(frame==floor(GetEnemyLife())){...

EDIT: Actually ceil() would be better since it won't make the boss stop shooting with less than 1 life. (It rounds up instead of down)
« Last Edit: July 19, 2009, 10:54:54 PM by Stuffman »

Henry

  • The observer
  • Exploring to the new world of Danmaku
Re: Danmakufu Q&A/Problem Thread
« Reply #335 on: July 20, 2009, 02:28:12 PM »
I am a totally newbie on Shot Objects...

Code: [Select]
#TouhouDanmakufu
#Title[QED "Ripples of 495 Years"]
#Text[Test script]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    let ImgBoss = "script\img\ExRumia.png";
    let frame = -120;
    let i;
    let angle=[];
    @Initialize {
       SetLife(3000);
       SetTimer(120);
       SetScore(1000000);
       SetDurableSpellCard();
       SetDamageRate(50,0);
       SetMovePosition02(GetCenterX, GetClipMinY+120, 120);
       SetInvincibility(120);
       Concentration01(120);
       PlaySE(GetCurrentScriptDirectory~"SFX\Charge.wav");
       CutIn(YOUMU, "QED "\""Ripples of 495 Years"\", "", 0, 0, 0, 0);
       LoadGraphic(ImgBoss);
       SetTexture(ImgBoss);
       SetGraphicRect(0, 0, 64, 64);
       LoadUserShotData(GetCurrentScriptDirectory~"images\shot_All.txt");
    }

    @MainLoop {
        SetCollisionA(GetX, GetY, 32);
        SetCollisionB(GetX, GetY, 16);
        if(frame==10) {
           ascent(i in 0..64){
             Obj_Create(OBJ_SHOT);
             Obj_SetPosition(i, GetX, GetY);
             Obj_SetSpeed=1;
             angle=angle~(i*360/64);
             Obj_SetAngle(i, angle[i]);
             ObjShot_SetGraphic(i, 45);
           }
        }
        if(frame>10){
           ascent(i in 0..64){
              if(Obj_GetX(i)==GetClipMaxX||Obj_GetX(i)==GetClipMaxX){
                 angle[i]=180-angle[i];
                 Obj_SetAngle(i, angle[i]);
              }
              if(Obj_GetY(i)==GetClipMaxY||Obj_GetY(i)==GetClipMaxY){
                 angle[i]=-angle[i];
                 Obj_SetAngle(i, angle[i]);
              }
           }
        }
        frame++;
    }

    @DrawLoop {
        DrawGraphic(GetX, GetY);
    }

    @Finalize {
        DeleteGraphic(ImgBoss);
    }
}
Why when I run this script, after the boss show up, it freezes?
Old/Forgotten member.

Old Patchouli Project was outdated but new one is in progress.

Iryan

  • Ph?nglui mglw?nafh
  • Cat R?lyeh wgah?nagl fhtagn.
Re: Danmakufu Q&A/Problem Thread
« Reply #336 on: July 20, 2009, 02:47:25 PM »
Well...

Your code contains the nonsensical command Obj_SetSpeed=1; for once. It should read Obj_SetSpeed(i, 1);, and even then I am not entirely shure it will work. While it is possible to code objects in the main loop, this is not recommended unkess you want to refer to a specific object colliding with another specific object, which you don't. Instead, you tell danmakufu to create a minor script that runs beside the main loop which is called a task. How tasks are coded and how you create object bullets using them can be found in the Intermediate Danmakufu Tutorial anout one third down the page. It even directly explains how you create a bullet that bounces off of the borders of the playing field. ;)
Old Danmakufu stuff can be found here!

"As the size of an explosion increases, the numbers of social situations it is incapable of solving approaches zero."

Nuclear Cheese

  • Relax and enjoy the danmaku.
    • My homepage
Re: Danmakufu Q&A/Problem Thread
« Reply #337 on: July 21, 2009, 02:08:56 AM »
Well...

Your code contains the nonsensical command Obj_SetSpeed=1; for once. It should read Obj_SetSpeed(i, 1);, and even then I am not entirely shure it will work. While it is possible to code objects in the main loop, this is not recommended unkess you want to refer to a specific object colliding with another specific object, which you don't. Instead, you tell danmakufu to create a minor script that runs beside the main loop which is called a task. How tasks are coded and how you create object bullets using them can be found in the Intermediate Danmakufu Tutorial anout one third down the page. It even directly explains how you create a bullet that bounces off of the borders of the playing field. ;)

While I'm not trying to be an elitist jerk ... I highly recommend against using tasks in the manner you're suggesting.  It's very inefficient, and will start to bring down the game's performance before too long.

Instead, I recommend using an array to keep track of object shots, as demonstrated in my object shot tutorial.  It's a bit harder to chew at first, but its a much better approach in the long run.

To be fair, you could use a single task to control all object shots as in the tutorial, but honestly, I prefer to just do it in @MainLoop directly.
« Last Edit: July 21, 2009, 02:10:51 AM by Nuclear Cheese »
to quote Naut:
"I can see the background, there are too many safespots."
:V

Zengar Zombolt

  • Space-Time Tuning Circle - Wd/Fr
  • Green-Red Divine Clock
Re: Danmakufu Q&A/Problem Thread
« Reply #338 on: July 21, 2009, 02:26:51 AM »
I recommend using an array
Now that you mention this, is it posible to use Linked Lists?
(A list made of Nodes, that works like an array but without a limit of objects)

Nuclear Cheese

  • Relax and enjoy the danmaku.
    • My homepage
Re: Danmakufu Q&A/Problem Thread
« Reply #339 on: July 21, 2009, 03:10:41 AM »
I am a totally newbie on Shot Objects...

Code: [Select]
t3h codezWhy when I run this script, after the boss show up, it freezes?

I got a chance to look over your code, and I've found a few issues.

1) As Iryan pointed out, Obj_SetSpeed = 1 isn't the way to set object speed.  Instead, use Obj_SetSpeed(i, 1)

2) More importantly, when you use Obj_Create(OBJ_SHOT) you need to store the value that it returns, and use that as the object ID to pass the other Obj_ functions.  Have you seen the object shot tutorial I made (linked in my previous post)?  It might help you get a better grip on using these.


Overall, it looks like you're trying to assume that the object shots you create are given the IDs 0 through 64 ... this is a bad assumption and is very likely what is causing the crash.  You need to use and store the IDs returned from Obj_Create(OBJ_SHOT) in order to properly refer to the object shots.  Again, you can reference my object shot tutorial (linked in my previous post) for some basis on this.

Another hint - you don't need to store the angle of each shot.  You can get is using the shot's ID with the function Obj_GetAngle().


Unfortunately, I don't really have the time to get into a more in-dept debugging of it.  I need to at least try and get some sleep for work :-\
If you're still having trouble, I might be able to help out at a more detailed level sometime later in the week, assuming work leaves me with a decent amount of thought capacity :P


Hope this helps!


I recommend using an array
Now that you mention this, is it posible to use Linked Lists?
(A list made of Nodes, that works like an array but without a limit of objects)

Linked lists, by the standard definition, are not possible in Danmakufu.  You'd need a reference type (pointers) to achieve this.

However, this is a moot point, since arrays in Danmakufu are dynamically resizable* (in that regard, they kind of are like linked lists).

The linked tutorial above gives a quick rundown of it, but here's the basics:

Declare your initial array:
Code: [Select]
let zomg_array = [999, 1234, 55555];You probably know this by now.

Add an element to the end of the array:
Code: [Select]
zomg_array = zomg_array ~ [7];Effectively, the ~ combines the two lists into one, larger list.

Remove an element from an array:
Code: [Select]
zomg_array = erase(zomg_array, 2);erase gives the list, with the indexed element removed.


You can do lots of complex stuff with arrays like this.  However, one limitation, if I remember correctly, is that arrays must be homogenous - that is, all elements of the array must be the same type.  So having an array such as:
Code: [Select]
let bad_array = [123, 'lol', 456, ':V', 789];wouldn't work.



*Technicality: okay, so really they're not, but you can easily create 'derivatives', so it works practically the same :V
to quote Naut:
"I can see the background, there are too many safespots."
:V

Zengar Zombolt

  • Space-Time Tuning Circle - Wd/Fr
  • Green-Red Divine Clock
Re: Danmakufu Q&A/Problem Thread
« Reply #340 on: July 21, 2009, 03:13:05 AM »
And I was starting to overthink stuff due to the limits arrays can have :V
Thanks!

Henry

  • The observer
  • Exploring to the new world of Danmaku
Re: Danmakufu Q&A/Problem Thread
« Reply #341 on: July 21, 2009, 12:03:26 PM »
This is the modified version of the buggy script (your guess is correct, Danmakufu still freezes)

Code: [Select]
#TouhouDanmakufu
#Title[QED "Ripples of 495 Years"]
#Text[Test script]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    let ImgBoss = "script\img\ExRumia.png";
    let frame = -120;
    let i;
    let angle=[];
    let no=[];
    @Initialize {
       SetLife(3000);
       SetTimer(120);
       SetScore(1000000);
       SetDurableSpellCard();
       SetDamageRate(50,0);
       SetMovePosition02(GetCenterX, GetClipMinY+120, 120);
       SetInvincibility(120);
       Concentration01(120);
       PlaySE(GetCurrentScriptDirectory~"SFX\Charge.wav");
       CutIn(YOUMU, "QED "\""Ripples of 495 Years"\", "", 0, 0, 0, 0);
       LoadGraphic(ImgBoss);
       SetTexture(ImgBoss);
       SetGraphicRect(0, 0, 64, 64);
       LoadUserShotData(GetCurrentScriptDirectory~"images\shot_All.txt");
    }

    @MainLoop {
        SetCollisionA(GetX, GetY, 32);
        SetCollisionB(GetX, GetY, 16);
        if(frame==10) {
           ascent(i in 0..64){
             no=no~(Obj_Create(OBJ_SHOT));
             Obj_SetPosition(no[i], GetX, GetY);
             Obj_SetSpeed(no[i],1);
             angle=angle~(i*360/64);
             Obj_SetAngle(no[i], angle[i]);
             ObjShot_SetGraphic(no[i], 45);
           }
        }
        if(frame>10){
           ascent(i in 0..64){
              if(Obj_GetX(no[i])==GetClipMaxX||Obj_GetX(no[i])==GetClipMaxX){
                 angle[i]=180-angle[i];
                 Obj_SetAngle(no[i], angle[i]);
              }
              if(Obj_GetY(no[i])==GetClipMaxY||Obj_GetY(no[i])==GetClipMaxY){
                 angle[i]=-angle[i];
                 Obj_SetAngle(no[i], angle[i]);
              }
           }
        }
        frame++;
    }

    @DrawLoop {
        DrawGraphic(GetX, GetY);
    }

    @Finalize {
        DeleteGraphic(ImgBoss);
    }
}
(Replying Iryan's comment)Also, can I use a function instead of a task to make shot obj as function is faster than tasks...
Old/Forgotten member.

Old Patchouli Project was outdated but new one is in progress.

Iryan

  • Ph?nglui mglw?nafh
  • Cat R?lyeh wgah?nagl fhtagn.
Re: Danmakufu Q&A/Problem Thread
« Reply #342 on: July 21, 2009, 02:16:56 PM »
@ Henry:
Well, to make your bullets bounce off of something, properties of the bullet have to be checked after it has been fired. The advantage of tasks compared to mere functions is that you can have them work along the main loop for a desired amount of time, which enables you to check these properties. A function is a one-shot command. You call it once and it is executed on the frame it is called without a recurring effect later on that could check for the object's properties.
So no, you cannot just take a task, turn it into a function and expect it to do the same work.

What you can do is define several functions that are called inside your main loop each frame and which check for the properties of your bullets, basically just like the script you already posted, only with functions. However, I don't think this is neccessary as it wouldn't make your code any shorter, I think.

@ NC:
While I'm not trying to be an elitist jerk ... I highly recommend against using tasks in the manner you're suggesting.  It's very inefficient, and will start to bring down the game's performance before too long.

Instead, I recommend using an array to keep track of object shots, as demonstrated in my object shot tutorial.  It's a bit harder to chew at first, but its a much better approach in the long run.

To be fair, you could use a single task to control all object shots as in the tutorial, but honestly, I prefer to just do it in @MainLoop directly.
Hum? Having about 60 object bullets on the screen simultaneously that don't even have complex code to perform every frame will slow down the game too much? I never had problems or noticed other people's complains regarding performance on cards that had a nothing but a relativley high count of simple object bullets. 64 isn't even that high of a number...

I guess I am misinterpreting what you say, because I don't understand how using tasks for object bullets which don't interact with one another is such a huge disadvantage. Everyone does it, to my knowledge. They don't seem to slow the game down by a noticable margin compared to otherwise identical bullets coded into the main loop. On the other hand, the reduced complexity and improved clarity of the script strikes me as an advantage of the task bullets. The only reason for me to code the objects in the main loop is if you want to refer to specific bullets, especially if you want two or more objects to interact.

I frankly don't quite understand you here.  :-\
Old Danmakufu stuff can be found here!

"As the size of an explosion increases, the numbers of social situations it is incapable of solving approaches zero."

Henry

  • The observer
  • Exploring to the new world of Danmaku
Re: Danmakufu Q&A/Problem Thread
« Reply #343 on: July 21, 2009, 02:48:11 PM »
I think NC was trying to mean that if your computer's performance is not very well, 64 obj bullets does make a difference.

Sorry if I mis-interpreted NC's words.

P.S. I am not so familiar with tasks... even looked at the Intermediate Tutorial
Old/Forgotten member.

Old Patchouli Project was outdated but new one is in progress.

Re: Danmakufu Q&A/Problem Thread
« Reply #344 on: July 21, 2009, 08:38:30 PM »
I find that coding them in tasks only affects performance when the bullets are actually doing something (reflecting, detecting collision with other bullets, whatever). Otherwise the difference is negligable, at best. This is with (semi-)extensive testing on both an 8GHz/4GB Ram/Vista 64bit and a 2.66Ghz/1GB Ram/XP 32bit/7 years old. Neither detected noticable differences in processing speed whether or not things were processed using yield; trees in tasks or using conditional statements in the @MainLoop.

I bold collision with other bullets just because it batshit's up processing speed no matter what you do.

So uh, unless you've got some other testing going on then I'm seeing no disadvantage to using tasks (even though the wiki also says they slow down your computer.... I've yet to see proof). As far as I know, the math and memory involved with task creation/maintaining is not very heavy at all, since so far the only thing I've seen that affects computer performance by a fair degree is object property changing (you know, reflecting, collision...) and additive blending.

Unless I'm horribly mistaken and my computers just run abnormally fast for no real reason.

Nuclear Cheese

  • Relax and enjoy the danmaku.
    • My homepage
Re: Danmakufu Q&A/Problem Thread
« Reply #345 on: July 22, 2009, 12:32:31 AM »
I find that coding them in tasks only affects performance when the bullets are actually doing something (reflecting, detecting collision with other bullets, whatever). Otherwise the difference is negligable, at best. This is with (semi-)extensive testing on both an 8GHz/4GB Ram/Vista 64bit and a 2.66Ghz/1GB Ram/XP 32bit/7 years old. Neither detected noticable differences in processing speed whether or not things were processed using yield; trees in tasks or using conditional statements in the @MainLoop.

I bold collision with other bullets just because it batshit's up processing speed no matter what you do.

So uh, unless you've got some other testing going on then I'm seeing no disadvantage to using tasks (even though the wiki also says they slow down your computer.... I've yet to see proof). As far as I know, the math and memory involved with task creation/maintaining is not very heavy at all, since so far the only thing I've seen that affects computer performance by a fair degree is object property changing (you know, reflecting, collision...) and additive blending.

Unless I'm horribly mistaken and my computers just run abnormally fast for no real reason.

Okay, I admit I probably exaggerated the effect that using tasks like that would have in Danmakufu.  Probably comes from the fact that threads (which tasks are supposed to be like) in programming are non-trivial.


detecting collision with other bullets

But this is where the most fun can be had with object bullets!


Hum? Having about 60 object bullets on the screen simultaneously that don't even have complex code to perform every frame will slow down the game too much? I never had problems or noticed other people's complains regarding performance on cards that had a nothing but a relativley high count of simple object bullets. 64 isn't even that high of a number...

I guess I am misinterpreting what you say, because I don't understand how using tasks for object bullets which don't interact with one another is such a huge disadvantage. Everyone does it, to my knowledge. They don't seem to slow the game down by a noticable margin compared to otherwise identical bullets coded into the main loop. On the other hand, the reduced complexity and improved clarity of the script strikes me as an advantage of the task bullets. The only reason for me to code the objects in the main loop is if you want to refer to specific bullets, especially if you want two or more objects to interact.

I frankly don't quite understand you here.  :-\

Honestly, I disagree with you on the clarity point.  Using yield to switch between tasks suddenly creates multiple "entry points" for each piece of code (including the @MainLoop) - this makes it harder to track where the code goes.
Plus, as with any multi-threaded processing, it opens you up to ambiguity in the overall execution order of all pieces of code running.  Not as much as preemptive threading/multitasking, but the risk is still there.

As far as basic code clarity is concerned, this can be dealt with pretty easily with a few things:
1) Proper and consistent code structure and indentation.
2) Break up your functionality into functions that are called from @MainLoop, and it'll look a lot more like your divided-into-tasks approach.
3) Comments.  Properly commented messy code is, in most cases, more readable than uncommented structured code.


In the end, though, it probably just all comes down to personal bias.  Personally, I don't really like Danmakufu's tasks setup to begin with.  Using tasks (specifically, yield) changes the semantics of the @MainLoop from a function that gets called once per frame to a function that loops on its own.  This strikes me as kind-of odd in its own way, if you ask me.

Secondly (and somewhat related to the first point), is the whole use of the yield statement to switch tasks.  The way I see it, if you've created a bunch of tasks, you're going to want them all working in parallel, right?  So why do we need to explicitly say, in each one, "okay, time to let the next one on the CPU"?
to quote Naut:
"I can see the background, there are too many safespots."
:V

Henry

  • The observer
  • Exploring to the new world of Danmaku
Re: Danmakufu Q&A/Problem Thread
« Reply #346 on: July 22, 2009, 01:35:57 AM »
If I use tasks for obj bullets, should I use these statements for the Mainloop?

Code: [Select]
@MainLoop{
   SetCollisionA(...);
   SetCollisionB(...);
   yield;
}
Old/Forgotten member.

Old Patchouli Project was outdated but new one is in progress.

Chronojet ⚙ Dragon

  • The Oddity
  • 今コソ輝ケ、我ガ未来、ソノ可能性!!
Re: Danmakufu Q&A/Problem Thread
« Reply #347 on: July 22, 2009, 03:09:53 AM »
There aren't any measurements of Power in Danmakufu, so if you're aiming to make a player with different capabilities at different levels, you're going to have to make custom objects.
Like effect objects or something?
I see it in the official games and Touhou Mushuugeki (CtC), so yeah.

Re: Danmakufu Q&A/Problem Thread
« Reply #348 on: July 22, 2009, 03:39:21 AM »
Secondly (and somewhat related to the first point), is the whole use of the yield statement to switch tasks.  The way I see it, if you've created a bunch of tasks, you're going to want them all working in parallel, right?  So why do we need to explicitly say, in each one, "okay, time to let the next one on the CPU"?

I think of it more like "okay, take a break from this and move on to this, then you can continue where you left off the next frame". This way I can easily plan out what happens, in order, during a spellcard. As a matter of fact, my @MainLoops nowadays only have the two necessary lines of collision detection, as well as yield;. I have everything planned out in order, frame by frame (with intense use of the God tier loop function).

detecting collision with other bullets

But this is where the most fun can be had with object bullets!

The most fun, as well as the most CPU annihilating. I agree completely though, easily the best function in regards to object coding (even though I don't use it much...).

In the end, though, it probably just all comes down to personal bias.

Considering the negligable difference in processing speed, I would have to agree with you there. Too much is set on personal preference in Danmakufu (didn't I rant about this somewhere else?), but I guess it's good and bad. Good that you have your own code, bad that you can't read anybody else's.


There aren't any measurements of Power in Danmakufu, so if you're aiming to make a player with different capabilities at different levels, you're going to have to make custom objects.
Like effect objects or something?
I see it in the official games and Touhou Mushuugeki (CtC), so yeah.

Hmmm, if you can't think of how you could accomplish a power system in Danmakufu then I would suggest not trying it. This is only because it would require some massive amount of interlaced coding between player scripts and spell card/stage scripts (we're talking CommonData up the yingyang), so it would require a plethora of time, planning and worst of all: thinking. Chances are if you can't think of how to do it right now then you haven't done enough of the latter two, which can be fixed by pouring more effort into the foremost listed. Think Stuffman's PoSR, he made custom point items, could you not make custom power items?

If I use tasks for obj bullets, should I use these statements for the Mainloop?

Code: [Select]
@MainLoop{
   SetCollisionA(...);
   SetCollisionB(...);
   yield;
}

Technically you could get away with only those three lines of code in your @MainLoop (seriously), but have a task start in @Initialize that plans out your whole attack (this is actually my method of coding nowadays, so feel free to ask questions about it if you'd like to try it out).

Usually people just do the standard frame++;, if(frame==60){spawn object bullets that run seperately in tasks alongside the @MainLoop}.
« Last Edit: July 22, 2009, 03:44:25 AM by Naut »

Drake

  • *
Re: Danmakufu Q&A/Problem Thread
« Reply #349 on: July 22, 2009, 03:55:53 AM »
It should be possible to make working power items. Once I'm finished most of Reimu I was going to attempt it myself, as you could just leave a default Power setting for most cards and have a dynamic Power with spellcards made for it. Shuffling through stages and spellcards shouldn't be a problem as most coding would be done in the player script.

You would have a CommonData of Power that initializes in the player script. The CommonData would change if you died. Then a task in the spellcard would spawn power items and when they're hit, get the data and increase it. [EDIT: considering the objects would disappear after the spellcard finishes, you would have them spawn at the beginning, so when played it would look as if they appeared because you beat the card. Incidentally, this might require more CommonData if you need to track whether or not it was captured, etc) A per-frame task in the player script would be constantly getting the data and change a variable that controls your shot patterns and such. If there's a spellcard with no CommonData in it it, GetCommonData would return the string "NoData". You check in the same per-frame task if there is NoData, and if so your CommonData just stays at the default.
\(゜∀゜)/

Effect Objects would be ideal considering you can put them on a high graphic level, check player collision and other such things. You could use Shot Objects if you find it easier, though it might require a few workarounds.
« Last Edit: July 22, 2009, 04:00:58 AM by Drake »

A Colorful Calculating Creative and Cuddly Crafty Callipygous Clever Commander
- original art by Aiけん | ウサホリ -

Hat

  • Just an unassuming chapeau.
  • I will never be ready.
Re: Danmakufu Q&A/Problem Thread
« Reply #350 on: July 23, 2009, 12:39:57 AM »
Time for a durr durr moment for me. =D Okay, first off, as I'm just curious: is it possible to make C Lasers with Object Shots (read: object lasers)?

And to the meat of the issue: how exactly would one code a gradually homing shot? I... ew, I deleted it, so I'll try to summarize below. I'll just list what's in the 'while(Obj_BeDeleted(obj)==false){}' statement.
Code: [Select]
while(Obj_BeDeleted(obj)==false){
let p_angle = atan2(Obj_GetY(obj)-GetPlayerY, Obj_GetX(obj)-GetPlayerX);
if(p_angle > Obj_GetAngle(obj)-5){
  Obj_SetAngle(obj, Obj_GetAngle(obj)+5);
}
if(p_angle < Obj_GetAngle(obj)-5){
  Obj_SetAngle(obj, Obj_GetAngle(obj)-5);
}
}
I know the bullet won't home in fully, I had a more complex code that incremented the bullet's turn more if the player was waaay out of the way of the bullet, but that's not where the problem lies. There's this weird little problem in that if I pass by a certain... point of the bullet, I'm not entirely sure where, it will basically freak out. It will curve away from me, and eventually drifts in the complete opposite direction. I tried putting absolute value signs around the two arguments in atan2, but that didn't do the trick. That just made it WORSE (it would start drifting away with even less provocation).

Re: Danmakufu Q&A/Problem Thread
« Reply #351 on: July 23, 2009, 03:12:04 AM »
Try inputting something to normalize the angles to a positive value:

while(p_angle < 0){ p_angle+=360; }
while(p_angle > 360){ p_angle-=360; }

Not entirely sure if this will help, but I know that this is a recurring problem with homing shots and this code is always involved, so yeah.

Hat

  • Just an unassuming chapeau.
  • I will never be ready.
Re: Danmakufu Q&A/Problem Thread
« Reply #352 on: July 23, 2009, 04:01:57 AM »
Oh, good thinking! Yeah, that would definitely confuse the code... heh, this is totally the root of my problem. Naut, you're the greatest. =D

Oh, right, and something that's been bugging me... are variables global? i.e. if I call 'var' in @Initialize, will it be recognized in @Mainloop (or more importantly, will 'var' in, say, a hypothetical Task1 overlap with a 'var' called in a hypothetical Task2?)

EDIT: Bleh, that didn't fix it after all. Now the bullets chase after a mystery angle that is directly away from me if I'm outside this weird 'line of sight' they seem to have. I think it may have something to do with the 'homing' part of the script...
Code: [Select]
#TouhouDanmakufu
#Title[Homing Shots]
#Text[Test script]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    let ImgBoss = "script\img\ExRumia.png";
T1;

    @Initialize {
        SetLife(2000);
        SetTimer(50);
        SetScore(1000000);

        SetMovePosition02(GetCenterX, GetClipMinY + 120, 120);
        CutIn(YOUMU, "Test Sign "\""Test"\", "", 0, 0, 0, 0);

        LoadGraphic(ImgBoss);
        SetTexture(ImgBoss);
        SetGraphicRect(0, 0, 64, 64);
    }

    @MainLoop {
        SetCollisionA(GetX, GetY, 32);
        SetCollisionB(GetX, GetY, 16);
yield;

    }

    @DrawLoop {
        DrawGraphic(GetX, GetY);
    }

    @Finalize {
        DeleteGraphic(ImgBoss);
    }
task T1{
loop(120){yield;}
loop{
TMain;
loop(120){yield;}
}
}
task TMain{
loop(120){yield;}
loop{
let obj = Obj_Create(OBJ_SHOT);
Obj_SetPosition(obj, GetX, GetY);
Obj_SetSpeed(obj, 3);
Obj_SetAngle(obj, rand(135, 215));
ObjShot_SetGraphic(obj, WHITE02);
while(Obj_BeDeleted(obj) == false){
let p_angle = atan2((|Obj_GetY(obj)-GetPlayerY|), (|Obj_GetX(obj)-GetPlayerX|));
if(p_angle > Obj_GetAngle(obj)-5){
Obj_SetAngle(obj, Obj_GetAngle(obj)+5);
}
if(p_angle < Obj_GetAngle(obj)-5){
Obj_SetAngle(obj, Obj_GetAngle(obj)-5);
}
while(p_angle < 0){ p_angle+=360; }
while(p_angle > 360){ p_angle-=360; }
yield;
}
}
}
}
This was kind of a lift-and-paste, I just wanted to see if it would work. o-o I'd puzzle over it some more myself, but I know it's been done somewhere on this board, and I was never that good at geometry (especially in the weird coordinate system Danmakufu uses, which always trips me up). Oh, and I know that in this code it waits to generate the next few bullets until Obj_BeDeleted(obj) becomes true and the while statement is broken, but I was gonna fix that by using a function to trip the TMain housed in the Mainloop. For now, I just want these damn bullets to follow my ass! D=<
« Last Edit: July 23, 2009, 04:24:44 AM by Karfloozly »

Re: Danmakufu Q&A/Problem Thread
« Reply #353 on: July 23, 2009, 04:23:23 AM »
Variables are contained within the braces you declare them in. So if you declare a variable in @Initialize, it can only be used in @Initialize and will raise an error if used outside. If you declare them in script_enemy_main, then they are used in script_enemy_main (what we refer to as "global variables"). This is a very good thing though, because if you need to run multiple of the same task and not worry about variables adding multiple times, you can simply declare the variable inside the task and it will only exist inside of that one task, even if multiple instances of the task are running simultaneously.

So I can make a task that runs something like this:

task Bullats(speed){
    let a = GetAngleToPlayer;
    loop(20){
        CreateShot01(GetX, GetY, speed, a, RED01, 0);
        a+=18;
        yield;
    }
}

and then say somewhere in @MainLoop:

if(frame==60){
    Bullats(3);
    Bullats(4);
    Bullats(5);
    frame = 0;
}

And not have to worry about the variable "a" stacking three times every frame, since to Danmakufu it only exists inside of those individual tasks.

Edit: And uh, here's some homing bullet code for you to steal: http://touhou.wikia.com/wiki/Touhou_Danmakufu:_Object_Bullets

AND! You were supposed to put that code I mentioned inbetween the declaration and the if statements. But whatever, it still probably wont work.
« Last Edit: July 23, 2009, 04:28:22 AM by Naut »

Hat

  • Just an unassuming chapeau.
  • I will never be ready.
Re: Danmakufu Q&A/Problem Thread
« Reply #354 on: July 23, 2009, 04:26:54 AM »
Okay, that's a relief (I've been renaming variables over and over again to make sure that wouldn't happen). Now, to work on these bullets.

puremrz

  • Can't stop playing Minecraft!
Re: Danmakufu Q&A/Problem Thread
« Reply #355 on: July 23, 2009, 06:53:31 AM »
It's been a while, but I got another burning question:
I want to create tasks so I can do reflecting shots and indestructable bullets, but the tutorial on this board doesn't have a full script example, just bits and pieces you have to glue together. And that just won't work, no matter how I try it.
Can someone post a full sample file that has a reflection and/or indestructable-bullet script in it?
Full Danmakufu game "Juuni Jumon - Summer Interlude" is done!
By the same person who made Koishi Hell 1,2 (except this game is serious)
Topic: http://www.shrinemaiden.org/forum/index.php/topic,9647.0.html

Helepolis

  • Charisma!
  • *
  • O-ojousama!?
Re: Danmakufu Q&A/Problem Thread
« Reply #356 on: July 23, 2009, 07:44:18 AM »
That is odd, the tutorial posted here on Motk is not bits of pieces glued together but a step by step explaining understanding how an object task is build.

You can also checkthe Touhou Wiki of Danmakufu where an copy/past able example of lasers and bullets are written.

puremrz

  • Can't stop playing Minecraft!
Re: Danmakufu Q&A/Problem Thread
« Reply #357 on: July 23, 2009, 10:38:51 AM »
The thing is, there's no complete script as an end-result in that tutorial, only the Task part.
Also, some contents keep changing. One moment it's:
Code: [Select]
task NameOfTheTask(put, variables, here) {
And the next it's:
Code: [Select]
task Testtask(a, b, c) {Which confuses me even more D:

Ah, but someone has got to have a script on their computer which uses tasks in the way I wanted, so I'd appreciate it if you would share it with me.


Oh, while I'm here. Is there a command that can relocate the player? I was trying to make reversed movement (left=right), but I could not find a way to change the player's location and/or movement.
« Last Edit: July 23, 2009, 10:42:12 AM by puremrz »
Full Danmakufu game "Juuni Jumon - Summer Interlude" is done!
By the same person who made Koishi Hell 1,2 (except this game is serious)
Topic: http://www.shrinemaiden.org/forum/index.php/topic,9647.0.html

Helepolis

  • Charisma!
  • *
  • O-ojousama!?
Re: Danmakufu Q&A/Problem Thread
« Reply #358 on: July 23, 2009, 02:11:27 PM »
The thing is, there's no complete script as an end-result in that tutorial, only the Task part.
Also, some contents keep changing. One moment it's:
Code: [Select]
task NameOfTheTask(put, variables, here) {
And the next it's:
Code: [Select]
task Testtask(a, b, c) {Which confuses me even more D:

Ah, but someone has got to have a script on their computer which uses tasks in the way I wanted, so I'd appreciate it if you would share it with me.

What do you mean it is not complete or endresult? It is the entire code for the reflection laser or bullet. You just need to call/spawn the bullet by using the Taskname inside a loop/seperate task.

I'll post my code I used for my Uwabami Breakers - Dance contest non-card when I am at home as I am currently at work. (Or if you are impatient, you can download the scripts and check 'Afro03.txt' in there. )

Thaws

  • _m廿廿m_
Re: Danmakufu Q&A/Problem Thread
« Reply #359 on: July 23, 2009, 02:33:17 PM »
Oh, while I'm here. Is there a command that can relocate the player? I was trying to make reversed movement (left=right), but I could not find a way to change the player's location and/or movement.

I made one just a few days ago O_O!
Code: [Select]
#TouhouDanmakufu
#Title[Mirror Sign"Reverse Direction"]
#Text[]
#BackGround[Default]
#PlayLevel[Normal]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
#include_function "lib\SHOT_REPLACE\shot_replace.dnh"
let ImgBoss = "script\img\ExRumia.png";

let frame = 0;
let framem = 0;
let phase = 1;

let playerv;
let dista = 20;
let pic = WHITEI02;

let bullets = [ ];


    @Initialize {
        shotinit;
        LoadGraphic(ImgBoss);
        CutIn(YOUMU, "Mirror Sign"\""Reverse Direction"\", "", 0, 0, 0, 0);
        SetLife(2000);
        SetDamageRate(100, 100);
        SetTimer(40);
        SetInvincibility(120);
        SetScore(500000);
        SetEnemyMarker(true);
        Concentration02(60);
        SetMovePosition03(GetCenterX, 100, 10, 10);
    }

    @MainLoop {
SetCollisionA(GetX, GetY, 32);
SetCollisionB(GetX, GetY, 24);

if(phase >= 1)
{
if(frame == 2)
{
ascent(i in -1..2)
{
let obj=Obj_Create(OBJ_SHOT);
Obj_SetPosition(obj, GetX, GetY);
Obj_SetAngle(obj, GetAngleToPlayer+i*dista);
Obj_SetSpeed(obj, 7);
ObjShot_SetGraphic(obj, pic);
ObjShot_SetDelay(obj, 0);
bullets = bullets ~ [obj];
}
dista -= 0.1;
frame = 0;
}

if(phase == 2)
{
if((GetKeyState(VK_SLOWMOVE) == KEY_HOLD) || (GetKeyState(VK_SLOWMOVE) == KEY_PUSH))
{
playerv = GetPlayerInfo(PLAYER_SPEED_LOW);
}else
{
playerv = GetPlayerInfo(PLAYER_SPEED_HIGH);
}
if((GetKeyState(VK_LEFT) == KEY_HOLD) || (GetKeyState(VK_LEFT) == KEY_PUSH))
{
SetPlayerX(GetPlayerX + playerv*2);
}
if((GetKeyState(VK_RIGHT) == KEY_HOLD) || (GetKeyState(VK_RIGHT) == KEY_PUSH))
{
SetPlayerX(GetPlayerX - playerv*2);
}
}

if(framem == 160)
{
    Concentration02(30);
}
if(framem == 200)
{
ascent(i in 0..length(bullets))
{
Obj_SetPosition(bullets[i], 448-Obj_GetX(bullets[i]), Obj_GetY(bullets[i]));
Obj_SetAngle(bullets[i], 180-Obj_GetAngle(bullets[i]));
ObjShot_SetGraphic(bullets[i], WHITE02);
}
dista = 20;
pic = WHITE02;
phase = 2;
}
if(framem == 360)
{
    Concentration02(30);
}
if(framem == 400)
{
ascent(i in 0..length(bullets))
{
Obj_SetPosition(bullets[i], 448-Obj_GetX(bullets[i]), Obj_GetY(bullets[i]));
Obj_SetAngle(bullets[i], 180-Obj_GetAngle(bullets[i]));
ObjShot_SetGraphic(bullets[i], WHITEI02);
}
dista = 20;
pic = WHITEI02;
phase = 1;
framem = 0;
}
framem ++;
frame ++;
}

yield;
}


    @DrawLoop {
SetTexture(ImgBoss);
SetGraphicRect(0, 0, 64, 64);
DrawGraphic(GetX, GetY);
    }

    @Finalize {
    }

}

Hope it helped.