Vector Victor - This is confusing me

Discussion in 'Plugin Development' started by MonsieurApple, Mar 8, 2011.

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

    MonsieurApple

    Hi everyone, recently I saw the setVelocity() option for vehicles and i thought "lets set the y value positive and make flying things!"

    Believe it or not, it worked. Then I got to thinking... hey this could be a mode of transport around my server. So I got out my java compiler and started writing.

    Anyways, after a few hours of digging around the interwebs for formulas and coding, I got something that compiled (yay) and made sense (yay) but didn't work (booo).

    So I'm posting my code for everyone to take a look at and tell me what I'm doing wrong.

    Theres a command /ft (for fly test) and it takes <x1> <z1> <x2> <z2>. You should set x1 and z1 to your current coordinates and x2 z2 to your destination. I have no idea how to work in y values, so those are just a random value for now.

    Also, there are some random debug statements

    Anyways, please help ;(

    Code:
    package net.serenity.flight;
    
    import java.io.File;
    import java.util.HashMap;
    import java.io.File;
    import java.util.logging.Logger;
    import java.util.HashSet;
    import java.util.Set;
    import java.util.Arrays;
    import java.lang.Math;
    import org.bukkit.command.Command;
    import org.bukkit.command.CommandSender;
    import org.bukkit.entity.Player;
    import org.bukkit.Server;
    import org.bukkit.event.Event.Priority;
    import org.bukkit.event.Event;
    import org.bukkit.plugin.PluginDescriptionFile;
    import org.bukkit.plugin.PluginLoader;
    import org.bukkit.plugin.java.JavaPlugin;
    import org.bukkit.plugin.PluginManager;
    import org.bukkit.util.Vector;
    
    /**
     * Flight WIP
     *
     * @author MonsieurApple
     */
    public class Flight extends JavaPlugin {
    
        protected static final Logger log = Logger.getLogger("Minecraft");
    
        public void onDisable()
        {
            PluginDescriptionFile pdfFile = this.getDescription();
               log.info( pdfFile.getName() + " version " + pdfFile.getVersion() + " is disabled!" );
        }
    
        public void onEnable()
        {
            PluginDescriptionFile pdfFile = this.getDescription();
            log.info( pdfFile.getName() + " version " + pdfFile.getVersion() + " is enabled!" );
        }
    
        @Override
        public boolean onCommand(CommandSender sender, Command command, String commandLabel, String[] args){
            String commandName = command.getName();
            Player player;
            Integer x1 = Integer.valueOf(args[0]);
            Integer z1 = Integer.valueOf(args[1]);
            Integer x2 = Integer.valueOf(args[2]);
            Integer z2 = Integer.valueOf(args[3]);
    
            if (sender instanceof Player)
            {
                player = (Player) sender;
            }
            else
            {
                return false;
            }
    
            player.sendMessage(" X1: " + args[0] + " Z1: " + args[1] + " X2: " + args[2] + " Z2: " + args[3]);
    
            float d2d = Distance(new Vector(x1, 0, z1), new Vector(x2, 0, z2));
            player.sendMessage("Our distance is:" + String.valueOf(d2d));
            float distanceFinal = (float)Math.sqrt(Math.pow((double)d2d, 2.0) + Math.pow((double)(0), 2.0));
            player.sendMessage("Our distance is:" + String.valueOf(distanceFinal));
            Vector vector1 = new Vector(x1, 0, z1);
            float heading = Heading(new Vector(x2, 0, z2), new Vector(x1, 0, z1));
            player.sendMessage("Our new heading is " + String.valueOf(heading));
            Vector reposition = Reposition(vector1, heading, distanceFinal);
            // OMG!
            player.sendMessage("X: " + String.valueOf(reposition.getX()) + " Z: " + String.valueOf(reposition.getZ()));
            player.getVehicle().setVelocity(reposition);
    
            return true;
        }
    
        public static float Distance(Vector Pos1, Vector Pos2)
        {
            return (float)Math.sqrt(Math.pow((double)(Pos2.getX() - Pos1.getX()), 2.0) + Math.pow((double)(Pos2.getZ() - Pos1.getZ()), 2.0));
        }
    
        public static Vector Reposition(Vector Pos, float Ang, float Hyp)
        {
            float r = (float)Math.toRadians(Ang);
            float a = (float)(Math.sin(r)) * Hyp;
            float b = (float)(Math.cos(r)) * Hyp;
            return new Vector((double)(Pos.getX() + b), 3, (double)(Pos.getZ() + a));
        }
    
        public static float Heading(Vector Origin, Vector Dest)
        {
            double ang = (double)Math.atan2((Dest.getZ() - Origin.getZ()), (Dest.getX() - Origin.getX()));
            return (float)Math.toDegrees(ang);
        }
    }
     
  2. Offline

    Afforess

    There is a built in vector method to compute the distance between two vectors. vector.distance(vector v).

    Anyway, what do you mean by "doesn't work"?
     
  3. Offline

    MonsieurApple

    Well I fly places but never to the right place and sometimes in the opposite direction :(

    Also, a good proof that theres something wrong in my logic is /ft 1 1 1 1 (which should not move at all, same position) shoots me somewhere >.<
    [MERGETIME="1299651765"][/MERGETIME]
    Ok I changed the first part of the Reposition function to
    float r = Ang * (float)Math.PI / 180.0f;
    and it works a little more reliably, but not perfectly.
    [MERGETIME="1299651855"][/MERGETIME]
    Something is up. /ft 0 0 10 10 gives me -10 x and z

    /ft 10 10 20 20 gives me 0 x 0 z!?
    [MERGETIME="1299684584"][/MERGETIME]
    Well I know someone that is good with 3D space and could probably figure this out. I'll email him later today.
     
  4. Offline

    Raphfrk

    Are you just trying to get the player to move in a particular direction?

    That should just be

    Code:
    
    // Assumes that targetLoc is the location of the target
    
    double speed = 0.1; // whatever
    
    Location loc = player.getLocation();
    
    Vector target = new Vector(targetLoc.getX(), targetLoc.getY(), targetLoc.getZ());
    
    Vector velocity = target.clone().subtract(new Vector(loc.getX(), loc.getY(), loc.getZ()));
    
    velocity.multiply(speed/velocity.length());
    
    player.setVelocity(velocity);
    
    This doesn't take into account gravity though.

    In theory, that could be taken into account. (assuming gravity is known :) )
     
  5. Offline

    MonsieurApple

    I'll have to test that :p

    As for gravity, it's explained here :D http://www.minecraftforum.net/viewtopic.php?f=3&t=167836&p=2413341
    [MERGETIME="1299772994"][/MERGETIME]
    Tested: all it managed to do was smack me around the world :p
     
  6. Offline

    Raphfrk

    However, did it send you in the right direction :) ?
     
  7. Offline

    MonsieurApple

    Sometimes, sometimes not.
     
  8. Offline

    Raphfrk

    Unless there is a coding error if the target is above the player, it should work :) If the target is below they there could be a problem with being pushed into the ground.
     
  9. Offline

    MonsieurApple

    On a separate note, it turns out there is a limit on how high of a velocity you can set. I'll investigate more tomorrow when I'm not half falling asleep.
     
  10. Offline

    Afforess

    Yep. Found that myself. Even though the data is stored as doubles, I believe Notch treats them like Floats, and it overflows when Floats overflow.
     
  11. Offline

    MonsieurApple

  12. Offline

    Afforess

    Actually, I find this most damning:

    Code:
            if (Math.abs(this.motX) > 10.0D) {
                 this.motX = 0.0D;
             }
             if (Math.abs(this.motY) > 10.0D) {
                 this.motY = 0.0D;
             }
              if (Math.abs(this.motZ) > 10.0D) {
                 this.motZ = 0.0D;
             }
    
     
  13. Offline

    MonsieurApple

    Isn't that what lines 825-835 are? :p
     
  14. Offline

    phaed


    This worked wonderfully for me. Check it out in action in my two new pstones, Sky Bouncer and Launch Pad. They have a couple of added twists. The vertical height of the jump is determined by the vertical aim of the player, and they can be redstone activated.

    http://forums.bukkit.org/threads/se...-sky-bouncer-and-launch-pad-pstones-556.1034/
     
Thread Status:
Not open for further replies.

Share This Page