Author Topic: Useful Miscellaneous Code Snippets  (Read 56631 times)

Blargel

  • RAWR!
  • I'M AN ANGRY LOLI!
Re: Useful Miscellaneous Code Snippets
« Reply #30 on: April 06, 2010, 03:45:34 AM »
These functions should be useful to anyone who has to make a large amount of rectangular effect objects.



ObjEffect_InitializeRect(texture, layer)
Initializes an effect object with 4 vertices with the specified texture and on the specified layer.

Code: [Select]
function ObjEffect_InitializeRect(texture, layer){
  let obj = Obj_Create(OBJ_EFFECT);
  ObjEffect_SetTexture(obj, texture);
  ObjEffect_SetLayer(obj, layer);
  ObjEffect_SetPrimitiveType(obj, PRIMITIVE_TRIANGLEFAN);
  ObjEffect_CreateVertex(obj, 4);
  return obj;
}

ObjEffect_SetXYRect(id, left, top, right, bottom)
Sets the 4 XY vertices for an effect object created with the initialize function above.

Code: [Select]
function ObjEffect_SetXYRect(id, left, top, right, bottom){
  ObjEffect_SetVertexXY(id, 0, left, top);
  ObjEffect_SetVertexXY(id, 1, right, top);
  ObjEffect_SetVertexXY(id, 2, right, bottom);
  ObjEffect_SetVertexXY(id, 3, left, bottom);
}

ObjEffect_SetUVRect(id, left, top, right, bottom)
Sets the 4 UVvertices for an effect object created with the initialize function above.

Code: [Select]
function ObjEffect_SetUVRect(id, left, top, right, bottom){
  ObjEffect_SetVertexUV(id, 0, left, top);
  ObjEffect_SetVertexUV(id, 1, right, top);
  ObjEffect_SetVertexUV(id, 2, right, bottom);
  ObjEffect_SetVertexUV(id, 3, left, bottom);
}

ObjEffect_SetColor
Sets the alpha and color of all of an effect object's vertices in one go. You have to tell it how many vertices are in the effect though.

Code: [Select]
function ObjEffect_SetColor(id, vertexes, a, r, g, b){
  ascent(i in 0..vertexes){
    ObjEffect_SetVertexColor(id, i, a, r, g, b);
  }
}
« Last Edit: April 06, 2010, 03:47:12 AM by Blargel »
<WorkingKeine> when i get home i just go to the ps3 and beat people up in blazblue with a loli
<Azure> Keine: Danmakufu helper by day, violent loli by night.

Drake

  • *
Re: Useful Miscellaneous Code Snippets
« Reply #31 on: April 10, 2010, 09:21:11 PM »
DeleteShotInCircleEx(type, item, x, y, initradius, maxradius, accel)
Expands a circle of a specified radius at point (x,y) to maximum specified radius. Bullets in the circle are either deleted or turned to items. Can also activate player invincibility.

Code: [Select]
task DeleteShotInCircleEx(item, type, x, y, initradius, maxradius, grow, invincibility){
let currentradius = initradius;
while(currentradius!=maxradius){
if(item){
DeleteEnemyShotToItemInCircle(type,x,y,currentradius);
}else{
DeleteEnemyShotInCircle(type,x,y,currentradius);
}
currentradius+=grow;
if(invincibility){SetPlayerInvincibility(2);}
yield;
}
if(invincibility){SetPlayerInvincibility(0);}
}

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

RavenEngie

  • Now how'm I supposed to stop those mean ol' Mother Hubbards from tearin' me a structurally superfluous new behind? The answer, use a gun. If that don't work...
  • Gaming-Obsessed Illusionist
Re: Useful Miscellaneous Code Snippets
« Reply #32 on: April 16, 2010, 07:11:10 PM »
RoughlyEqualTo
Sometimes you're off by a tiny amount, and danmakufu doesn't pick up on it when you need to see if two numbers are equal. This is a bugger to sort out, sometimes.
num1 , num2 : The two numbers you want to compare
errormargin : How far apart they've to be to be considered 'equal' (Use something with a decimal point and a few zero's in front. Otherwise it'll be ridiculous. :V)
Examples :
RoughlyEqualTo(4.5, 4.4999, 0.0125) = true
RoughlyEqualTo(20, 10, 1) = false
RoughlyEqualTo(2, 1, 50) = true  (Don't. :V)
Code: [Select]
function RoughlyEqualTo(num1, num2, errormargin)
{
    if(num1 >= num2 - errormargin && num1 <= num2 + errormargin)
    {
        return true;
    } else
    {
        return false;
    }
}
WALUIGI BACK! NOW THIS SIG IS FUNNY AGAIN!
Mah arts! :3

Blargel

  • RAWR!
  • I'M AN ANGRY LOLI!
Re: Useful Miscellaneous Code Snippets
« Reply #33 on: April 16, 2010, 10:05:18 PM »
I know I'm being really anal about this, but this sort of unnecessary stuff really bugs me.  :V
Code: [Select]
function RoughlyEqualTo(num1, num2, errormargin){
    return absolute(num1-num2) <= errormargin;
}

The big offender in my mind was how you used an if else construction when a comparison already gives you true or false, but I also had a simpler way to do the math.



EDIT: More geometry. With terrible function names, but I have no idea what the hell I should call them.

YOnLineFromX(x1, y1, x2, y2, x3)
Gets the y-coordinate of the point that has an x-coordinate of x3 and that is on the line defined by the points (x1, y1) and (x2, y2). Returns y2 if x1 is equal to x2.

Code: [Select]
function YOnLineFromX(x1, y1, x2, y2, x3){
  let a_numerator = y2-y1;
  let a_denominator = x2-x1;
  if(a_denominator==0){
    return y2;
  }
  else {
    let a = a_numberator/a_denominator;
    let xDist = x3-x2;
    let yDist = xDist*a;
    let y3 = y2+yDist;
    return y3;
  }
}


XOnLineFromY(x1, y1, x2, y2, y3)
Gets the x-coordinate of the point that has a y-coordinate of y3 and that is on the line defined by the points (x1, y1) and (x2, y2). Returns x2 if y1 is equal to y2.

Code: [Select]
function XOnLineFromY(x1, y1, x2, y2, y3){
  let a_numerator = y2-y1;
  let a_denominator = x2-x1;
  if(a_numerator==0){
    return x2;
  }
  else {
    let a = a_numberator/a_denominator;
    let yDist = y3-y2;
    let xDist = yDist/a;
    let x3 = x2+xDist;
    return x3;
  }
}
« Last Edit: April 17, 2010, 06:02:54 PM by Blargel »
<WorkingKeine> when i get home i just go to the ps3 and beat people up in blazblue with a loli
<Azure> Keine: Danmakufu helper by day, violent loli by night.

RavenEngie

  • Now how'm I supposed to stop those mean ol' Mother Hubbards from tearin' me a structurally superfluous new behind? The answer, use a gun. If that don't work...
  • Gaming-Obsessed Illusionist
Re: Useful Miscellaneous Code Snippets
« Reply #34 on: April 17, 2010, 10:10:22 PM »
I know I'm being really anal about this, but this sort of unnecessary stuff really bugs me.  :V

The big offender in my mind was how you used an if else construction when a comparison already gives you true or false, but I also had a simpler way to do the math.

Yes. Yes you are.
And gimme a break. I'm recovering from an incredibly over-exaggerated serious bout of the flu. Hell, I can't even beat my own scripts these days.
'Sides, I didn't know about that absolute thingy.

But meh, learned something new there.
WALUIGI BACK! NOW THIS SIG IS FUNNY AGAIN!
Mah arts! :3

Re: Useful Miscellaneous Code Snippets
« Reply #35 on: May 10, 2010, 03:02:45 AM »
old code
« Last Edit: May 15, 2010, 06:10:46 PM by Naut »

Drake

  • *
Re: Useful Miscellaneous Code Snippets
« Reply #36 on: May 10, 2010, 03:34:51 AM »
Just going to add "No bitching about how simple the hitbox is" here. Take it, change image, screw around with code. Do it yourself. It's an outline, basically.

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

Re: Useful Miscellaneous Code Snippets
« Reply #37 on: May 15, 2010, 06:10:21 PM »
Improved the hitbox code a bit, since Drake said it was too simple >: |



Here's some code to add in a working Touhou-style hitbox to your player characters, simply by copy/pasting.

Save this image in the same directory as your player script as thHitbox.png (alternatively, change the image pathname in the script):


Copy and paste this code inside script_player_main (preferably towards the beginning of it):
Code: [Select]
let objHitbox = NULL;
let objHitboxCopy = NULL;
let objHitboxGraphic = GetCurrentScriptDirectory~"thHitbox.png";
let objHitboxScale = 0;
let objHitboxAngle = 0;
let objHitboxAngleVel = 103;
let objHitboxCopyScale = 1.45;

sub CreateHitbox{
LoadGraphic(objHitboxGraphic);
objHitbox = Obj_Create(OBJ_EFFECT);
ObjEffect_SetTexture(objHitbox, objHitboxGraphic);
ObjEffect_SetRenderState(objHitbox, ALPHA);
ObjEffect_SetLayer(objHitbox, 4);
ObjEffect_SetPrimitiveType(objHitbox, PRIMITIVE_TRIANGLEFAN);
ObjEffect_CreateVertex(objHitbox, 4);
ObjEffect_SetVertexUV(objHitbox, 0, 0, 0);
ObjEffect_SetVertexUV(objHitbox, 1, 63, 0);
ObjEffect_SetVertexUV(objHitbox, 2, 63, 63);
ObjEffect_SetVertexUV(objHitbox, 3, 0, 63);
ObjEffect_SetVertexXY(objHitbox, 0, -32, -32);
ObjEffect_SetVertexXY(objHitbox, 1, 32, -32);
ObjEffect_SetVertexXY(objHitbox, 2, 32, 32);
ObjEffect_SetVertexXY(objHitbox, 3, -32, 32);
objHitboxCopy = Obj_Create(OBJ_EFFECT);
ObjEffect_SetTexture(objHitboxCopy, objHitboxGraphic);
ObjEffect_SetRenderState(objHitboxCopy, ALPHA);
ObjEffect_SetLayer(objHitboxCopy, 4);
ObjEffect_SetPrimitiveType(objHitboxCopy, PRIMITIVE_TRIANGLEFAN);
ObjEffect_CreateVertex(objHitboxCopy, 4);
ObjEffect_SetVertexUV(objHitboxCopy, 0, 0, 0);
ObjEffect_SetVertexUV(objHitboxCopy, 1, 63, 0);
ObjEffect_SetVertexUV(objHitboxCopy, 2, 63, 63);
ObjEffect_SetVertexUV(objHitboxCopy, 3, 0, 63);
ObjEffect_SetVertexXY(objHitboxCopy, 0, -32, -32);
ObjEffect_SetVertexXY(objHitboxCopy, 1, 32, -32);
ObjEffect_SetVertexXY(objHitboxCopy, 2, 32, 32);
ObjEffect_SetVertexXY(objHitboxCopy, 3, -32, 32);
}

sub DrawHitbox{
if(GetKeyState(VK_SLOWMOVE)==KEY_PUSH || GetKeyState(VK_SLOWMOVE)==KEY_HOLD){
if(GetKeyState(VK_SLOWMOVE)==KEY_PUSH){
objHitboxCopyScale = 1.45;
}
if(objHitboxAngleVel>3){
objHitboxAngleVel -= 5;
}
if(objHitboxScale<1){
objHitboxScale += 0.2;
}
if(objHitboxCopyScale>1){
objHitboxCopyScale-=0.05;
}
objHitboxAngle += objHitboxAngleVel;
ObjEffect_SetAngle(objHitbox, 0, 0, objHitboxAngle);
ObjEffect_SetScale(objHitbox, objHitboxScale, objHitboxScale);
ObjEffect_SetAngle(objHitboxCopy, 0, 0, -objHitboxAngle);
ObjEffect_SetScale(objHitboxCopy, objHitboxCopyScale, objHitboxCopyScale);
Obj_SetPosition(objHitbox, GetPlayerX, GetPlayerY);
Obj_SetPosition(objHitboxCopy, GetPlayerX, GetPlayerY);
}else{
if(objHitboxScale>0){
objHitboxScale -= 0.2;
}else{
objHitboxScale = 0;
}
if(objHitboxCopyScale>0){
objHitboxCopyScale -= 0.2;
}else{
objHitboxCopyScale = 0;
}

objHitboxAngleVel = 103;
ObjEffect_SetAngle(objHitbox, 0, 0, objHitboxAngle);
ObjEffect_SetScale(objHitbox, objHitboxScale, objHitboxScale);
ObjEffect_SetAngle(objHitboxCopy, 0, 0, -objHitboxAngle);
ObjEffect_SetScale(objHitboxCopy, objHitboxCopyScale, objHitboxCopyScale);
}
}

Put this in @Initialize:
Code: [Select]
CreateHitbox;

Put this in @DrawLoop:
Code: [Select]
DrawHitbox;

Hooray you now have a Touhou-style hitbox!


Henry

  • The observer
  • Exploring to the new world of Danmaku
Re: Useful Miscellaneous Code Snippets
« Reply #38 on: May 16, 2010, 02:42:38 PM »
I had a try on the reflect function on Touhou Wiki add find that it has bugs which automatically delete lasers when it's head merely pass the border.

Therefore, here is a revised version of that function. Additional features also added.
Parameters:
v stands for velocity, that is speed in daily language  :D
maxLen is the length of laser it is the "max" due to lengthening effect present
delay is the time interval between call of function and firing of laser, esp. useful when a spiral pattern is produced.
count is the number of time of allowed reflection.


Usage:
Call TReflectionalLaser only, the other 2 functions just helps this function and has no meaning when used alone.


Here is the code:
Code: [Select]
task TReflectionLaser(x, y, v, angle, maxLen, width, graphic, delay, count){
   //adjust the angle
   while(angle>=180){angle-=360;}
   while(angle<-180){angle+=360;}

   loop(delay){yield;}
   //bullet object
   let obj=Obj_Create(OBJ_LASER);

   //initial settings
   Obj_SetPosition(obj, x, y);
   Obj_SetAngle(obj, angle);
   ObjLaser_SetWidth(obj, width);
   ObjShot_SetGraphic(obj, graphic);
   Obj_SetAutoDelete(obj, false);
   ObjLaser_SetSource(obj, false);
   TReflectionLaser_Lengthen(obj, maxLen, v);
   TReflectionLaser_Move(obj, x, y, v, angle);

   while(!Obj_BeDeleted(obj)){
      if(x>GetClipMaxX&&x+maxLen*cos(angle)>GetClipMaxX||x<GetClipMinX&&x+maxLen*cos(angle)<GetClipMinX||y<GetClipMinY&&y+maxLen*sin(angle)<GetClipMinY){Obj_Delete(obj);}
      x=Obj_GetX(obj);
      y=Obj_GetY(obj);
      // reflection detection
      if(angle<0 && y<GetClipMinY && x>GetClipMinX && x<GetClipMaxX){
         //ceil
         if(count>0){TReflectionLaser(x, y, v, -angle, maxLen, width, graphic, 0, count-1);}
         break;
      }else
      if(((-90<angle && angle<90) && x>GetClipMaxX)||((angle<-90 || 90<angle) && x <GetClipMinX) && y>GetClipMinY && y<GetClipMaxY){
         //wall
         if(count>0){TReflectionLaser(x, y, v, 180 - angle, maxLen, width, graphic, 0, count-1);}
         break;
      }
      yield;
   }
}

//lengthen the object laser
task TReflectionLaser_Lengthen(obj, maxLen, v) {
   let len=0;
   let max=floor(maxLen/v);
   let i=0;
   while(!Obj_BeDeleted(obj)) {
      //When the length is negative,
      //the laser extends backward.
      ObjLaser_SetLength(obj, -len);
      yield;
      if(i<max){
         len+=v;
         i++;
      }else
      if(i==max){
         ObjLaser_SetLength(obj, -maxLen);
         break;
      }
   }
}

// move the object laser
// Since Obj_SetSpeed is ignored in case of object laser,
// the motion needs to be controlled by Obj_SetPosition.
task TReflectionLaser_Move(obj, x, y, v, angle) {
   let vx=v*cos(angle);
   let vy=v*sin(angle);
   while(!Obj_BeDeleted(obj)){
      Obj_SetPosition(obj, x, y);
      yield;
      x+=vx;
      y+=vy;
   }
}
Old/Forgotten member.

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

Re: Useful Miscellaneous Code Snippets
« Reply #39 on: May 16, 2010, 06:33:13 PM »
lol nope
« Last Edit: June 19, 2010, 01:33:53 AM by Naut »

Blargel

  • RAWR!
  • I'M AN ANGRY LOLI!
Re: Useful Miscellaneous Code Snippets
« Reply #40 on: May 25, 2010, 11:11:30 AM »
GetPreviousScriptDirectory
Gets the directory that the current script's directory is in. Example: if the script is in "script\folder1\folder2\hi.txt", it'll return "script\folder1\"

Code: [Select]
function GetPreviousScriptDirectory(){
  let current = GetCurrentScriptDirectory();
  current = erase(current, length(current)-1);
  while(current[length(current)-1] != '\'){
    current = erase(current, length(current)-1);
  }
  return current;
}



GetPreviousScriptDirectoryEx
Similar to the previous function, but now you can specify how many levels to go up. Putting 1 will have the same effect as the last function. Putting 0 will return the exact same thing as GetCurrentScriptDirectory().

Code: [Select]
function GetPreviousScriptDirectoryEx(num){
  let current = GetCurrentScriptDirectory();
  loop(num){
    current = erase(current, length(current)-1);
    while(current[length(current)-1] != '\'){
      current = erase(current, length(current)-1);
    }
  }
  return current;
}
« Last Edit: May 25, 2010, 09:33:55 PM by Blargel »
<WorkingKeine> when i get home i just go to the ps3 and beat people up in blazblue with a loli
<Azure> Keine: Danmakufu helper by day, violent loli by night.

Drake

  • *
Re: Useful Miscellaneous Code Snippets
« Reply #41 on: May 25, 2010, 05:27:01 PM »
ilu blargel

You people better use that.

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

Chronojet ⚙ Dragon

  • The Oddity
  • 今コソ輝ケ、我ガ未来、ソノ可能性!!
Re: Useful Miscellaneous Code Snippets
« Reply #42 on: June 09, 2010, 05:54:28 AM »
Code: (Stage functions) [Select]
function WaitForNoEnemy { while(GetEnemyNum!=0) { yield; } }
function WaitToNumOfEnemy(num) { while(GetEnemyNum!=num) { yield; } }
function WaitForFrames(framestowait) { loop(framestowait) { yield; } }
function WaitForNoBomb { while(OnBomb) { yield; } }
function WaitForAlive { while(OnPlayerMissed) { yield; } }
function WaitForDead { while(!OnPlayerMissed) { yield; } }
function WaitForNoInvincibility { while(GetTimeOfSuperNaturalBorder != 0 && GetTimeOfPlayerInvincibility != 0) { yield; } }
function WaitForNoEvent { while(OnEvent) { yield; } }

Seriolusly, no one ever bothered? :getdown:
« Last Edit: June 13, 2010, 05:52:00 PM by μ⑨ »

Chronojet ⚙ Dragon

  • The Oddity
  • 今コソ輝ケ、我ガ未来、ソノ可能性!!
Re: Useful Miscellaneous Code Snippets
« Reply #43 on: June 13, 2010, 05:53:02 PM »
Is there a function to get the largest value in a number array?

* Mewkyuu needs it for a "thing" he's making for a certain other project

Iryan

  • Ph?nglui mglw?nafh
  • Cat R?lyeh wgah?nagl fhtagn.
Re: Useful Miscellaneous Code Snippets
« Reply #44 on: June 13, 2010, 06:09:45 PM »
Is there a function to get the largest value in a number array?

* Mewkyuu needs it for a "thing" he's making for a certain other project
Shouldn't be a problem.

Edit: Fixed the code.

Function name: ArrMax(array);

Use: Returns the highest value of all the values in the chosen array.

Parameters: array = name of the array




Code: [Select]
function ArrMax(array){
let n = 0;
let value=array[0];
while( n<length(array) ){
if(array[n]>value){ value=array[n]; }
n++;
}
return(value);
}
« Last Edit: June 15, 2011, 10:50:14 PM by Iryan »
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."

Chronojet ⚙ Dragon

  • The Oddity
  • 今コソ輝ケ、我ガ未来、ソノ可能性!!
Re: Useful Miscellaneous Code Snippets
« Reply #45 on: June 13, 2010, 10:25:29 PM »
Shouldn't be a problem.

Edit: Fixed the code.

<code description>
<long code>

OH YES.
* Mew9 goes to make mini PMD-related thing

EDIT: Wait, wait, wait.
What will happen if there are two or more "largest values"?
« Last Edit: June 14, 2010, 12:12:39 AM by μ⑨ »

Iryan

  • Ph?nglui mglw?nafh
  • Cat R?lyeh wgah?nagl fhtagn.
Re: Useful Miscellaneous Code Snippets
« Reply #46 on: June 14, 2010, 12:31:46 AM »
Look at the code, it is not that huge or difficult, and you will be able to answer that question yourself.

Why would that make a difference? Or did you actually want the function to return the spot in the array that holds the largest value instead of the value itself?  :/
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."

Re: Useful Miscellaneous Code Snippets
« Reply #47 on: June 16, 2010, 06:12:48 AM »
LineToLinePoint
Eight parameters. Returns the intersection point between two lines formed by four points. First two parameters are the coordinates of a point on line one, second two parameters a different coordinate on line one. Next four parameters are the coordinates of points on line two. Returns an array [x, y]. Remember that a line is infinite, this code does not use line segments, so the line will stretch past the points you specify.

Code: [Select]
function LineToLinePoint(let x1, let y1, let x2, let y2, let x3, let y3, let x4, let y4){
let point = [0, 0];
point[0] = ( ((x1*y2 - y1*x2)*(x3 - x4) - (x1 - x2)*(x3*y4 - y3*x4)) / ((x1 - x2)*(y3 - y4) - (y1 - y2)*(x3 - x4)) );
point[1] = ( ((x1*y2 - y1*x2)*(y3 - y4) - (y1 - y2)*(x3*y4 - y3*x4)) / ((x1 - x2)*(y3 - y4) - (y1 - y2)*(x3 - x4)) );
return point;
}

Can be used something like this:

let point = LineToLinePoint(100, 240, 500, 240, 224, 100, 224, 500);
CreateShot01(point[0], point[1], 3, 90, RED01, 10);


Spawns a bullet on the intersection point between the two lines made up by (100, 240), (500, 240) and (224, 100), (224, 500). The intersection point would be (224, 240).

Works great if you need to find the point at which an object installation laser collides with another line, or something of that sort.

Kylesky

  • *The Unknown*
  • Local Unbalanced Danmakufu Idiot Scripter
    • My useless youtube account... (will be useful in the future *I promise*)
Re: Useful Miscellaneous Code Snippets
« Reply #48 on: June 16, 2010, 11:44:41 AM »
Quote
*insert naut's megacode here*
NICE!!!
I've been looking for/trying to figure out something like this :]

EDIT: :/ that code's giving me a headache XD don't want to even analyze it... 2 questions though
1)what returns when the 2 lines don't intersect (i.e. parallel)
2)what returns when the 2 lines are the same lines/on top of each other
???

EDIT2(so I don't double post): Some random functions :V


ObjShot_Reflect(id, dist)
Basic reflection code for object bullets. dist is a number determining how past the edges of the screen will the bullet reflect, since different people like reflecting them at different distances. (Must be called every frame)
Code: [Select]
function ObjShot_Reflect(id, dist){
    if(Obj_GetX(id)<GetClipMinX-dist || Obj_GetX(id)>GetClipMaxX+dist){Obj_SetAngle(id, 180-Obj_GetAngle(id));}
    if(Obj_GetY(id)<GetClipMinY-dist || Obj_GetY(id)>GetClipMaxY+dist){Obj_SetAngle(id, 0-Obj_GetAngle(id));}
}

InField(x, y)
Detects if the said point is on the screen.
Code: [Select]
function InField(x, y){
if(x<GetClipMaxX && x>GetClipMinX && y<GetClipMaxY && y>GetClipMinY)
{
return true;
}else{
return false;
}
}

and expanding Naut's LineToLinePoint function

SegmentToSegmentCollision
Detects if 2 segments intersect.
Code: [Select]
function SegmentToSegmentCollision(let x1, let y1, let x2, let y2, let x3, let y3, let x4, let y4){
    let PoI=LineToLinePoint(x1, y1, x2, y2, x3, y3, x4, y4);
    if(Collision_Line_Circle(x1, y1, x2, y2, 1, PoI[0], PoI[1], 1)==true && Collision_Line_Circle(x3, y3, x4, y4, 1, PoI[0], PoI[1], 1)==true){
        return true;
    }else{
        return false;
    }
}

SegmentToSegmentPoint
If the 2 segments intersect, it returns the point of intersection. If they don't, it returns an array [-1000, 1000]. (yes, that was a random value)
Code: [Select]
function SegmentToSegmentPoint(let x1, let y1, let x2, let y2, let x3, let y3, let x4, let y4){
    if(SegmentToSegmentCollision(x1, y1, x2, y2, x3, y3, x4, y4)==true){
        return LineToLinePoint(x1, y1, x2, y2, x3, y3, x4, y4);
    }else{
        return [-1000, -1000];
    }
}

Haven't tested some of them, but if my logic's right, they should work...

EDIT3:
LineToLinePointB
I THINK I fixed it up to "fit" my 2 functions better and to remove dividing by 0. (maybe wrongly, or not 100% of the time...)
Code: [Select]
function LineToLinePointB(let x1, let y1, let x2, let y2, let x3, let y3, let x4, let y4){
        let slope=(y1-y2)/(x1-x2);
        let slopeb=(y3-y4)/(x3-x4);
let point = [0, 0];
        if(slope==slopeb || x1-x2==0 || x3-x4==0){
            return [-1000, 1000];
        }else{
          point[0] = ( ((x1*y2 - y1*x2)*(x3 - x4) - (x1 - x2)*(x3*y4 - y3*x4)) / ((x1 - x2)*(y3 - y4) - (y1 - y2)*(x3 - x4)) );
    point[1] = ( ((x1*y2 - y1*x2)*(y3 - y4) - (y1 - y2)*(x3*y4 - y3*x4)) / ((x1 - x2)*(y3 - y4) - (y1 - y2)*(x3 - x4)) );
    return point;
        }
}
« Last Edit: June 16, 2010, 02:11:04 PM by Kylesky »
Danmakufu Script Thread :V Latest Script: Intertwining Mechanical Intervention (temp name)

Yooooouuutuuuubeeee Channel Latest Video: Contest #8 Entry

Iryan

  • Ph?nglui mglw?nafh
  • Cat R?lyeh wgah?nagl fhtagn.
Re: Useful Miscellaneous Code Snippets
« Reply #49 on: June 19, 2010, 10:36:30 AM »
Gnahahahahaha!

Although testing is a little difficult, I am ~90% certain that his code here is functional:

Function name: EllipseCollision(px, py, x, y, r, s, ang);

What it does: Checks if the point (px|py) is inside the defined ellipse. Returns "true" if it is and "false" if it isn't.

Parameters:

px, py: coordinates of the seperate point
x, y: center of the ellipse
r: maximum radius
s: minimum radius
ang: angular alignment of the ellipse




Code: [Select]
function EllipseCollision(px, py, x, y, r, s, ang){
if(
( ( (y+((r^2 - s^2)^0.5)*sin(ang) - py)^2 + (x+((r^2 - s^2)^0.5)*cos(ang) - px)^2 )^0.5
+( (y-((r^2 - s^2)^0.5)*sin(ang) - py)^2 + (x-((r^2 - s^2)^0.5)*cos(ang) - px)^2 )^0.5 )< 2*r){
return(true);
} else{ return(false);
}
}

 :dragonforce:
« Last Edit: June 19, 2010, 10:40:33 AM by Iryan »
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."

Re: Useful Miscellaneous Code Snippets
« Reply #50 on: July 20, 2010, 12:48:17 PM »
Microthread that making curving laser look smoothly.

task Beam( parameters ){ // Microthread that controls the movement of a curving laser.
   let obj=Obj_Create(OBJ_SHOT);
   CurveLaserBase02(obj,parameters); // curving laser effects will appear following the movement of an object "obj".
   while(!Obj_BeDeleted(obj)){
      // Put codes that control bullet movement you want.
      yield;
   }
}

task CurveLaserBase02(let object,let X,let Y,let spd,let wid,let ang,let grap,let killtime){ // Microthread that set basic parameters and commands to draw laser graphic.
   Obj_SetPosition(object,X,Y); // Set a starting position of laser.
   Obj_SetSpeed(object,spd); // Set a starting speed of laser.
   Obj_SetAngle(object,ang); // Set a starting angle of laser.
   ObjShot_ToItem(object,false);
   ObjShot_SetBombResist(object,true);
   while(!Obj_BeDeleted(object)){
      EffectForLaser02(object,Obj_GetX(object),Obj_GetY(object),Obj_GetSpeed(object),wid,Obj_GetAngle(object),grap,killtime);  // Create laser effect every 2 frames until starting bullet (microthread Beam) disappears.
      wait(1);
      yield;}
}

task EffectForLaser02(let obj1,let X,let Y,let spd,let wid,let ang,let grap,let killtime){ // Microthread that draws laser graphic.[/i]
   let obj=Obj_Create(OBJ_LASER); // Creates laser graphic object.
   let alpha=0;
   let length=(int(200/3*spd))/10; // Laser graphic length. If this parameter is too long, laser will look like chainsaw when spinning or so. If too short, laser will look like a rosary.
   let width=wid;
   Obj_SetPosition(obj,X,Y);
   Obj_SetAngle(obj,ang);
   ObjShot_SetGraphic(obj,grap);
   ObjLaser_SetSource(obj,false);
   ObjLaser_SetLength(obj,0); // If this parameter is not set 0, front tip of a laser will look too sharp.
   ObjLaser_SetWidth(obj,width);
   Obj_SetCollisionToPlayer(obj,true);
   Obj_SetAutoDelete(obj,true);
   ObjShot_ToItem(obj,false);
   ObjShot_SetBombResist(obj,true);
   Obj_SetAlpha(obj,alpha);
   loop(5){ // First 5 frames. This also makes front tip of a laser look smoothly.
      alpha+=(255)/5;
      Obj_SetAlpha(obj,alpha);
      yield;}
   Obj_SetAlpha(obj,alpha);
   ObjLaser_SetLength(obj,length);
   let tAngle=Obj_GetAngle(obj1);
   Obj_SetAngle(obj,(ang+tAngle)/2); // To make the line of a laser smoothly.
   let fac=Collision_Line_Circle(Obj_GetX(obj),Obj_GetY(obj),Obj_GetX(obj)+spd*4*cos(Obj_GetAngle(obj)),Obj_GetY(obj)+spd*4*sin(Obj_GetAngle(obj)),ObjLaser_GetWidth(obj)*0.5,GetPlayerX,GetPlayerY,6); // There was a error that laser don't hit characters, so I had to add this parameter. This parameter determines whether your character hit by this laser.
   let k=0;
   let wi=0;
   let gtime=0;
   loop(killtime-5){
      if(fac && GetTimeOfPlayerInvincibility==0){ShootDownPlayer;} // Bang! You're dead. Not when you're using a bomb or just ressurected.
      k++;
      wi=int(width*(0.75+0.25*cos(k*90/(killtime-5)))); // Just adjusting the width of a laser to look pretty.
      Obj_SetAlpha(obj,alpha);
      ObjLaser_SetLength(obj,ObjLaser_GetLength(obj));
      ObjLaser_SetWidth(obj,wi);
      yield;}
   Obj_Delete(obj);
}

Fujiwara no Mokou

  • Hourai Incarnate
  • Oh, so this trial of guts is for ME?
    • Profile
Re: Useful Miscellaneous Code Snippets
« Reply #51 on: August 16, 2010, 09:18:27 PM »
Load all Graphics/Images
-This is a very useful function if you want to load a large number of images (300+) for a cinematic/effect/whatever you want that requires a lot of images.
(example- 0001.png, 0002.png, 0003.png ...2401.png, 2042.png)
-Replace all strings/paths and/or variables to the desired directories.
-'PLAYING' those effects uses a similar function to this one. Note however, that delays due to lowered frames per second may be caused by a large number of object effects all present at once.
-You can prevent this delay by using only one object to do all of the animation (refreshing the Obj_SetTexture(string); directory and XY/UV vertices by using a loop in the object) and timing each frame by real-time-que instead of frame-sequential (you can do this by pairing the image number with the GetTime; function)


-if you need help recording a video-to-PNG, iwisoft Video Converter is a free program with no watermark that can do the job. You can get the link HERE

Code: [Select]
task load{

let totalnumberofpictures=9999;
let imgnum=1;
let numberofdigitsneeded=6; ////for the parameter of the name '000001.png', which is in the 'PNG' folder


   while(imgnum<=totalnumberofpictures){
   let arrnum=0;
   let string=""~ToString(imgnum);
   let loadstring="";

   
   loop((numberofdigitsneeded-1)-floor(log10(imgnum))){ loadstring=loadstring~ToString('0'); }  ////here, the correct number of zeros are added to loadstring before the number (ex. '0'1, '00'2, '0000'4) to get the correct parameter name of the image

   while(string[arrnum]!='.'){   loadstring=loadstring~ToString(string[arrnum]);   arrnum++; }  ///here, the actual number  is added to loadstring. (ex. 0'1', 00'2', 0000'4')

    LoadGraphic(GetCurrentScriptDirectory~"PNG\EFFECT_"~loadstring~".png");      imgnum++;  } ///LoadGraphic function is called. In this first loop, it's path would be "PNG\EFFECT_000001.png"

  //////if you have 100+ pictures loading and the game freezes, give it time. It will unfreeze and play like normal when the task is done.

}
[/code ]
« Last Edit: August 16, 2010, 09:28:51 PM by Fujiwara no Mokou »

Areylie

  • Cirno's Sister
    • Lymia's Website
Re: Useful Miscellaneous Code Snippets
« Reply #52 on: September 01, 2010, 02:43:19 AM »
GetPreviousScriptDirectory
Gets the directory that the current script's directory is in. Example: if the script is in "script\folder1\folder2\hi.txt", it'll return "script\folder1\"

(code here)

GetPreviousScriptDirectoryEx
Similar to the previous function, but now you can specify how many levels to go up. Putting 1 will have the same effect as the last function. Putting 0 will return the exact same thing as GetCurrentScriptDirectory().

(code here)

Fixed this for you:
Code: [Select]
function GetPreviousScriptDirectory()  {
return GetCurrentScriptDirectory()~"..\";
}
function GetPreviousScriptDirectoryEx(i) {
let s = GetCurrentScriptDirectory();
loop(i) { s = s~"..\"; }
return s;
}
« Last Edit: September 01, 2010, 02:52:02 AM by Cirno-chan »
[Geek code (3.12): GCS/H/M d+(-) s+:->--:- a--->? C+(++++)>$ UL++@ P+(++) L+++ E- W++ N o K? w-@ O- M- V? PS++@ PE>- Y+ PGP++ t- 5? X? R+@ tv- b+(++) DI D-- G? e>+++(++++) h! r++ x-]
[Furry code (1.3): FFm1r A !C D? H+++ M? P++++ R-- T W !Z Sf! RLCT a- cl+~++++>$ d--- e>+++ f? h* i++/+++ j+ p+ sf!]

Azure Lazuline

  • Looooove!!
  • PM me for free huggles and love!
    • Entanma Project - indie game development
Re: Useful Miscellaneous Code Snippets
« Reply #53 on: September 01, 2010, 04:32:53 AM »
While that works in some situations, it doesn't in others. I really don't want to go into the technical detail, but take it from me that if you use that version instead of Blargel's, you'll eventually run into some problems if you're using graphics loaded from a different directory (loading ..\img\graphic.png from a script in a folder named "stage," then calling ..\img\graphic.png from a script in a folder named "boss" will NOT work). Blame it on Danmakufu's bad path handling.

Areylie

  • Cirno's Sister
    • Lymia's Website
Re: Useful Miscellaneous Code Snippets
« Reply #54 on: September 01, 2010, 09:54:41 AM »
Yes, yes. Danmakufu refers to images by file path, blah blah. Fixed.

Code: [Select]
function BindTexture(target,file,width,height) {
    LoadGraphic(file);
    CreateRenderTarget(target,next_power(width),next_power(height));
    let rt = SetRenderTarget(target);
    SetTexture(file);
    SetGraphicRect(0,0,width,height);
    DrawGraphic(width/2,height/2);
    SetRenderTarget(rt);
    function next_power(n) {
        let t = 1;
        while(t<n){t*=2;}
        return t;
    }
}
« Last Edit: September 01, 2010, 09:56:59 AM by Cirno-chan »
[Geek code (3.12): GCS/H/M d+(-) s+:->--:- a--->? C+(++++)>$ UL++@ P+(++) L+++ E- W++ N o K? w-@ O- M- V? PS++@ PE>- Y+ PGP++ t- 5? X? R+@ tv- b+(++) DI D-- G? e>+++(++++) h! r++ x-]
[Furry code (1.3): FFm1r A !C D? H+++ M? P++++ R-- T W !Z Sf! RLCT a- cl+~++++>$ d--- e>+++ f? h* i++/+++ j+ p+ sf!]

Azure Lazuline

  • Looooove!!
  • PM me for free huggles and love!
    • Entanma Project - indie game development
Re: Useful Miscellaneous Code Snippets
« Reply #55 on: September 01, 2010, 06:26:10 PM »
Using ..\ in general is a bad idea. I guess it's time to go into the technical detail. Assume your folder setup is like this:

script
    |-bosses
    |      '-boss.txt
    |
    |-stages
    |      '-stage.txt
    |
    '-images
          '-image.png

Then, in stage.txt, you call LoadGraphic(GetCurrentScriptDirectory~"..\images\image.png");. The path is stored as "script\stages\..\images\image.png". Then, in boss.txt, you SetTexture(GetCurrentScriptDirectory~"..\images\image.png");, which presumably is the exact same graphic that you loaded. However, Danmakufu sees this as  "script\bosses\..\images\image.png", which is NOT the same as the path of the graphic you loaded. Therefore, it does not know that graphic is loaded, and the texture is not set. Blargel's GetPreviousScriptDirectory function fixes this issue, while yours does not.
I'm sorry if I sound harsh here, but I pretty much tore my hair out over this issue. I don't want others to have the same problems.

Marco

  • DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI
  • DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI
Re: Useful Miscellaneous Code Snippets
« Reply #56 on: September 01, 2010, 09:24:25 PM »
I used Kimoblager's GetPlayerMoveAngleto move the boss, but it can go outside the field do I correct the script:
Code: [Select]
function GetPlayerMoveAngle {
  let angle = NULL;
  if(GetKeyState(VK_DOWN)==KEY_HOLD){
    if(GetKeyState(VK_RIGHT)==KEY_HOLD){
     if((GetEnemyY < 464)&& GetEnemyX <416){   angle = 45;
    }}
    else if(GetKeyState(VK_LEFT)==KEY_HOLD){
if((GetEnemyY < 464)&& GetEnemyX >32){
      angle = 135;
    }}
    else {if(GetEnemyY < 464){
      angle = 90;
    }}
  }
  else if(GetKeyState(VK_UP)==KEY_HOLD){
    if(GetKeyState(VK_RIGHT)==KEY_HOLD){if((GetEnemyY > 16)&& GetEnemyX <416){
      angle = 315;
    }}
    else if(GetKeyState(VK_LEFT)==KEY_HOLD){if((GetEnemyY > 16)&& GetEnemyX >32){
      angle = 225;
    }}
    else {if(GetEnemyY > 16){
      angle = 270;
    }}
  }
  else if(GetKeyState(VK_RIGHT)==KEY_HOLD){if(GetEnemyX <416){
    angle = 0;
  }}
  else if(GetKeyState(VK_LEFT)==KEY_HOLD){if(GetEnemyX >32){
    angle = 180;
  }}
  return angle;
}
THIS CODE IS NOT MINE IS (feel good) BLAGER'S!
Still I havn't do anything special but.... maybe can be useful...
DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI DANZAI

Kylesky

  • *The Unknown*
  • Local Unbalanced Danmakufu Idiot Scripter
    • My useless youtube account... (will be useful in the future *I promise*)
Re: Useful Miscellaneous Code Snippets
« Reply #57 on: September 02, 2010, 11:32:39 AM »
I used Kimoblager's GetPlayerMoveAngleto move the boss, but it can go outside the field do I correct the script:
Code: [Select]
blah blah blah
}
THIS CODE IS NOT MINE IS (feel good) BLAGER'S!
Still I havn't do anything special but.... maybe can be useful...

you bwoke it :/

change all the GetEnemyX to GetPlayerX and GetEnemyY to GetPlayerY... you're getting the player's position, not the boss' :V
Danmakufu Script Thread :V Latest Script: Intertwining Mechanical Intervention (temp name)

Yooooouuutuuuubeeee Channel Latest Video: Contest #8 Entry

GenericTouhouFailure

  • WHAT DO YOU MEAN IT'S NOT CALLED UNL? *boom*
Re: Useful Miscellaneous Code Snippets
« Reply #58 on: September 05, 2010, 11:57:16 AM »
I am bored :V
Using CREATESHOTA? Lazy to play Sound Effects?

Code: [Select]
task PlayDelaySE(se,delay){
        loop(delay){yield;}
        PlaySE(se);
}
Example: PlayDelaySE("se\se1UP.wav",20);
This waits 20 frames then plays the 1up sound effect.


Wanna make your score counter run up gradually? (like the stage clear bonuses or something)
Code: [Select]
task AddScoreEx(amount,increment){
        let c = 0;
        while(c<amount){
                AddScore(increment);
                c+=increment;
                yield;
        }
        if(c-amount>0){
                AddScore(c-amount);
        }
}
eg: AddScoreEx(23000000,100000);
This increases the score by 10000 each frame until 23000000 points are added to score.

DISCLAIMER: HAVE NOT TESTED THIS CODE SO IT MAY CONTAIN MISTAKES.

tatsu011

Re: Useful Miscellaneous Code Snippets
« Reply #59 on: September 10, 2010, 08:35:14 AM »
Heres some functions that I am suprised havent been seen neither on the Wiki nor in this thread (yet)
Code: [Select]
Obj_GetAngleToPlayer(obj);
Obj_SetAngleToPlayer(obj);
Code: [Select]
function Obj_GetAngleToPlayer(obj) {
return atan2(GetPlayerY - Obj_GetY(obj), GetPlayerX - Obj_GetX(obj));
}

Code: [Select]
Obj_SetAngleToPlayer(obj) {
Obj_SetAngle(obj, Obj_GetAngleToPlayer(obj);
}

Easier code = Less math to remember