Solved Particle Math

Discussion in 'Plugin Development' started by ollinator01, Oct 14, 2016.

Thread Status:
Not open for further replies.
  1. Offline

    ollinator01

    Hey,
    i got the problem if i spawn the particle, i mean the black little particle in the middle, spawning with an wrong distance each other.
    If you can help to get the black little particle in the middle opposite to each other, its really cool. :D

    Greetings

    Code for the black Particle:
    Code:
    public void coneEffect1(final Player p) {
            new BukkitRunnable() {
                double t4 = 0;
                public void run() {
                    if (!part.contains(p)) {
                        cancel();
                    }
                    if(part.size() == 0) {
                        cancel();
                    }
    
                    t4 += Math.PI/32;
                    Location l = p.getLocation();
                    for(double phi6 = 0; phi6 <= Math.PI/2; phi6 += Math.PI/2){
                        double x3 = 0.15*(4*Math.PI) * Math.cos(t4  + phi6);
                        double y3 = 0.2;
                        double z3 = 0.15*(4*Math.PI) * Math.sin(t4  + phi6);
                        l.add(x3, y3, z3);
                        ParticleEffect.REDSTONE.display(0.0F, 0.0F, 0.0F, 0.0009F, 8, l, 12.0D);
                        l.subtract(x3, y3, z3);
    
    
    
                    }
                    if(t4 >= 4*Math.PI){
                        coneEffect1(p);
                        cancel();
                  
                    }
                }
            }.runTaskTimer(this, 0L, 3L);
        }
     
  2. Offline

    Whoneedspacee

    You're adding pi / 2, or 90 degrees, add just pi and you'll get 180 degrees, look up about radians and degrees and you should understand.
     
  3. Offline

    ollinator01

    Ok thank you so much @Whoneedspacee, it works! :D
    Have a nice day!

    Ok, i got a new problem on a different plugin.
    I want that to do it like this, thanks:


    Heres the current code:
    Code:
    package fr;
    
    
    import java.util.ArrayList;
    
    import org.bukkit.Location;
    import org.bukkit.Sound;
    import org.bukkit.command.Command;
    import org.bukkit.command.CommandSender;
    import org.bukkit.entity.Player;
    import org.bukkit.plugin.Plugin;
    import org.bukkit.plugin.java.JavaPlugin;
    import org.bukkit.scheduler.BukkitRunnable;
    
    public class frMain extends JavaPlugin {
      
        public static ArrayList<Player> part = new ArrayList<>();
        public static ArrayList<Player> part1 = new ArrayList<>();
      
        public boolean onCommand(CommandSender sender, Command cmd, String label, String[] agrs) {
            if (label.equalsIgnoreCase("ptest")) {
                if (!(sender instanceof Player)) {
                    sender.sendMessage( "§4Du musst ein Spieler sein!");
                    return true;
                }
                Player p = (Player) sender;
                if (!part.contains(p)) {
                    if (part1.contains(p)) {
                        p.sendMessage( "§cBitte warte 10 Sekunden, bevor du deinen Helix togglest!.");
                        p.playSound(p.getLocation(), Sound.ENTITY_ITEM_BREAK, 1.8F, 1.4F);
                        return true;
                    }
                    part.add(p);
                    p.sendMessage( "§f§lDeine Frost Lord Partikel wurden aktiviert!");
                    coneEffect(p);
                    return true;
                }
             
                part.remove(p);
                return true;
            }
            return false;
        }
      
    
            public void coneEffect(final Player p) {
                new BukkitRunnable() {
                    double t = 0;
                    double t2 = 0;
                    public void run() {
                        if (!part.contains(p)) {
                            p.sendMessage("§8§lDeine Frost Lord Partikel wurden deaktiviert!");
                            cancel();
                        }
                        if(part.size() == 0) {
                            cancel();
                        }
    
                        t += Math.PI/16;
                        t2 += Math.PI/8;
                        Location l = p.getLocation();
                        for(double phi = 0; phi <= 2*Math.PI; phi += Math.PI/2){
                            double x = 0.3*(2*Math.PI - t) * Math.cos(t * 2.5 + phi);
                            double y = 2.0*t2;
                            double z = 0.3*(2*Math.PI - t) * Math.sin(t * 2.5 + phi);
                            l.add(x, y, z);
                            ParticleEffect.FLAME.display(0.0F, 0.0F, 0.0F, 0.0F, 2 ,l ,12.0D);
                            l.subtract(x, y, z);
    
    
    
                        }
                        if(t >= Math.PI/2){
                            coneEffect(p);
                            cancel();
                        }
                    }
                  
                }.runTaskTimer(this, 0L, 1L);
            }
    
    }
    EDIT by Moderator: merged posts, please use the edit button instead of double posting.
     
    Last edited: Oct 19, 2016
  4. Offline

    Whoneedspacee

    If you want it to spiral up into the air and go back up in down, you're going to want to have an incrementing up variable for y's degrees, then you want to get the sin of those degrees and then set it say to, the players location, then multiply it for how many blocks you want it to go up, then absolute value the whole thing so it can't go negative, that's the math I'd do, tell me if it works.
     
  5. Offline

    ollinator01

    @Whoneedspacee , sorry i cant do this.
    Can you please send me an example or something? ^^
    Thanks for your answere!
     
  6. Offline

    Whoneedspacee

    It's pretty much exactly what you already did, you want to have a int value that increases over time, and then you want to get the sin of that value and multiply it by the amount of blocks you want it to go up, since sin 90 = 1, which is the maximum it can be, if you multiply it by 3, then sin 90 = 3, which is 3 blocks up, then you want to use that as the y coordinate for the player, but since sin 270 = -1, and it goes negative, you want to absolute value the entire thing so it doesn't go negative, then you set the particles y coordinate to the value you just got + the players y coordinate, so it will be relative to the players location, this is how the pseudocode would look.

    particleY = abs(sin(incrementingDegrees) * blocksHigh + player.location.y)

    should look something like that, let me know if you have any further problems.
     
  7. Offline

    ollinator01

    Hmm @Whoneedspacee i cant imagine how to do this.
    But i found out, if i change the ParticleEffect.FIREWORKS_SPARK.display(0.0F, 0.0F, 0.0F, 0.0F, 0, location, 12.0D);
    to ParticleEffect.FIREWORKS_SPARK.display(1.0F, 0.0F, 1.0F, 0.1F, 0, location, 12.0D);
    It creates a little "shoot" of particles.
    Thanks for your help.
    /Edit: I added examples.

    http://imgur.com/a/TQXrr
     
  8. Offline

    ollinator01

    /push Need help! Thanks
     
  9. Offline

    mythbusterma

    ollinator01 likes this.
  10. Offline

    ollinator01

    Hey @mythbusterma , i want the Particle like in the second Video. They Particle should "spray" and dont spawn like in the first Video!
    Thanks for your answere.
     
  11. Offline

    ChipDev

    For the white particles:
    You add velocity to the particle in the direction of your wanting, you can find that by subtracting the destination by the base location (loc2 - loc1) to get the vector in-between, then we can normalize that value. Subtract the location of the particle to the location of the player, normalize it, and add that velocity to the particle. Play around with it and you can multiply it and see how far it will go at what speed.
     
  12. Offline

    ollinator01

    Anybody know it, how i can do this particle like in the second video?
     
  13. @ollinator01 Did you completely ignore the post replying to you? @ChipDev posted how to do it...
     
  14. Offline

    ollinator01

    @bwfcwalshy No, i asked him with an pn that he can help me with that, but he ignore me and it passed now a long time without an response. So i asked again and wait for another response that can help me or show me a better way how i can do it.
     
  15. @ollinator01 Let me message him, he doesn't come on here much anymore neither do I so we can miss things.
     
  16. Offline

    ollinator01

    Ok, thank you. Have a nice day!
     
  17. Offline

    ChipDev

    Ask me your question here so people on Google can see it.
     
  18. Offline

    I Al Istannen

    @ollinator01
    Do you want it to look like this?
    ying yang.gif

    If yes, I can help you :p
     
    ollinator01 likes this.
  19. Offline

    ChipDev

    Aren't you just making a circle, and then making another with the velocity of the amount from the center?
     
  20. Offline

    I Al Istannen

    @ChipDev
    Code:java
    1.  
    2. // This is in a class I made, which takes care of invoking this every few ticks.
    3. // It is quite similiar to the "run" method in a BukkitRunnable
    4. @Override
    5. public void display(Location center) {
    6. // increase the time passed to correctly animate it
    7. time += getGranularity();
    8.  
    9. // spawn some black particles
    10. // "time" is the angle theta. It uses polar coordinates. Quite easy to understand, google them if needed
    11. // radBlack is the radius of the circle
    12. spawnParticle(time, radBlack, Particle.SMOKE_NORMAL, center);
    13. // The same as above, but now we add PI to the angle. This is the same as adding 180 degrees, just in radian
    14. // And where does adding 180 degree get you? At the opposite side.
    15. // So this will spawn the same particle, just on the opposite side!
    16. spawnParticle(time + PI, radBlack, Particle.SMOKE_NORMAL, center);
    17.  
    18. {
    19. // Now modify our angle a bit. This is because the white particles should be slightly in front of the black
    20. // PI / 2 is an amount figured out by trial and error and looked nice.
    21. double theta = time + Math.PI / 2;
    22.  
    23. // The xOffset. This is basically the x coordinate of the point on the outer circle where it should land
    24. // These next 3 lines just convert a point fromt he polar (theta=theta, radius=0.4) to the cartesian coordinate system (x,y,z), which we need
    25. double xOffset = Math.cos(theta) * 0.4;
    26. double yOffset = 0;
    27. double zOffset = Math.sin(theta) * 0.4;
    28. // Spawn the particles. Set the amount to 0, so that there is no randomness involved. This is an exception in the client render code
    29. // Passing xOffset,yOffset and zOffset as well as setting the speed to one will let the particles land on the point on the outer circle.
    30. center.getWorld().spawnParticle(Particle.FIREWORKS_SPARK, center, 0, xOffset, yOffset, zOffset, 1);
    31.  
    32. // the same, but again on the opposite side
    33. xOffset = Math.cos(theta + PI) * 0.4;
    34. zOffset = Math.sin(theta + PI) * 0.4;
    35. center.getWorld().spawnParticle(Particle.FIREWORKS_SPARK, center, 0, xOffset, yOffset, zOffset, 1);
    36. }
    37. }
    38.  
    39. private void spawnParticle(double theta, double rad, Particle particle, Location center) {
    40. // convert polar (theta, radius) to cartesian (x,y)
    41. double x = Math.cos(theta) * rad;
    42. double z = Math.sin(theta) * rad;
    43.  
    44. // add that to the center
    45. Location point = center.clone().add(x, 0, z);
    46.  
    47. // display it. Amount is 10 to make it more dense and speed is 0 to make them stay at one point
    48. center.getWorld().spawnParticle(particle, point, 10, 0, 0, 0, 0);
    49. }


    Count up a variable time.
    Display a point on the circle using polar coords and the same on the opposite side (black ones)

    Then do roughly the same and set it as the x and z offset of the firesparks particle. Minecraft will use a special handling if count is 0 (took me a while to find out), which involves no randomness (as count 1+ do). This can be used to make them shoot off in the direction you want. Just convert the angle to cartesian coords.
    Do the same on both sides and you are good.


    Took me longer to figure out than I would like to admit :p
     
    Last edited: Nov 11, 2016
  21. Offline

    ChipDev

    May want to explain to OP ;)
    (Or not, your choice)
    *I mean variables, etc. He most likely copied code
     
    I Al Istannen likes this.
  22. Offline

    I Al Istannen

    @ChipDev
    Sorry, forgot that while explaining what I did to you :p

    Below it is roughly written how it works and I will add comments to it, to ease understanding.

    Thanks!
     
  23. Offline

    ChipDev

    Thanks for the notes! I hope the OP enjoy's :)
     
  24. Offline

    I Al Istannen

    @ChipDev
    Added some. Feel free to explain things I missed!
     
  25. Offline

    ollinator01

    Oh yeah @I Al Istannen. :D
    Thank you so much, i gonna try this out in the next hours. ^^
    But i really i dont know what to do with the time (where i can find it). :I
     
    Last edited: Nov 12, 2016
  26. Offline

    I Al Istannen

    @ollinator01
    I do not understand you. You just make a field called "time" of type double and increase that.

    If you are able to follow the math, feel free to say so. Just copying the code will not completly work and wasn't my intention, as that will not help you the slightest.

    The math is actually not that hard, so I am probabyl capable of explaining it, it if you say what you didn't get.
     
  27. Offline

    ollinator01

    Oh @I Al Istannen i found the problem and it works now with an little problem.
    The firework particle aren't spinning without an curve. ^^
     
  28. Offline

    I Al Istannen

    @ollinator01
    What does "The firework particle aren't spinning without an curve. ^^" mean?
     
  29. Offline

    ollinator01

    I mean this:
    [​IMG]
     
  30. Offline

    I Al Istannen

Thread Status:
Not open for further replies.

Share This Page