Помогите автонаводка стрелы

  • Автор темы Автор темы KomapuK
  • Дата начала Дата начала

KomapuK

Активный участник
Пользователь
Баллы
76
Имя в Minecraft
KOMAP
При стрельбе из лука, стрела должна лететь в ближайшего моба или игрока, даже если тот кто выстрелил - промахнулся. Как реализовать?
 
При стрельбе из лука, стрела должна лететь в ближайшего моба или игрока, даже если тот кто выстрелил - промахнулся. Как реализовать?
Как вариант. При выстреле запомнить где то, например в хешмапе объект стрелы, а затем в шедулере, менять траекторию до ближайшего моба.
Но в таком случае тебе придется полностью скопировать логику полета стрелы из самой игры, ради простого изменения траектории до ближайшего моба.
 
Как вариант. При выстреле запомнить где то, например в хешмапе объект стрелы, а затем в шедулере, менять траекторию до ближайшего моба.
Но в таком случае тебе придется полностью скопировать логику полета стрелы из самой игры, ради простого изменения траектории до ближайшего моба.
То-есть реализовать это практически нереально по той схеме, которой я хочу? Обычный полёт стрелы по направлению в моба или игрока?
 
Как вариант. При выстреле запомнить где то, например в хешмапе объект стрелы, а затем в шедулере, менять траекторию до ближайшего моба.
Но в таком случае тебе придется полностью скопировать логику полета стрелы из самой игры, ради простого изменения траектории до ближайшего моба.

Вот то, что я хочу. Именно это и нужно мне, как это реализовать? СЫЛЛКА
 
Это очень легко!
При выстреле получаешь координаты стрелы и координаты сущности в которую хочешь попасть.
Далее путем вычитания координат стрелы из координат сущности получаешь вектор который будет направлен от стрелы до сущности. Далее его можно нормализовать и умножить для придания стреле определенной скорости и просто установить этот вектор движения для стрелы.
Также нужно учитывать что позиция моба находится у его ног чтобы стрела летела туда куда нужно следует перед получением позиции моба добавить к ее y координате 1.7f (примерный рост всех мобов). Тогда стрела будет лететь точному него а не в его ноги.
Также если ты хочешь чтобы стрела следовала за мообом как ракета с самонаведением то следует закинуть все выше сказаные действия в цыкличный поток и если стрела попала в моба то завершать поток.
 
Это очень легко!
При выстреле получаешь координаты стрелы и координаты сущности в которую хочешь попасть.
Далее путем вычитания координат стрелы из координат сущности получаешь вектор который будет направлен от стрелы до сущности. Далее его можно нормализовать и умножить для придания стреле определенной скорости и просто установить этот вектор движения для стрелы.
Также нужно учитывать что позиция моба находится у его ног чтобы стрела летела туда куда нужно следует перед получением позиции моба добавить к ее y координате 1.7f (примерный рост всех мобов). Тогда стрела будет лететь точному него а не в его ноги.
Также если ты хочешь чтобы стрела следовала за мообом как ракета с самонаведением то следует закинуть все выше сказаные действия в цыкличный поток и если стрела попала в моба то завершать поток.

блин, труднааа)
Можешь чуть подробнее кодом помочь пожалуйста? Вычитание координат, как их вычитать? Не догнал чегото я)
 
так, а как получить ближайшего моба? nearbyEntities?
Да можно так а потом сортировать список по дистанции. Только не забудь убрать из списка самого игрока А то сам по себе стрелять будешь
 
Да можно так а потом сортировать список по дистанции. Только не забудь убрать из списка самого игрока А то сам по себе стрелять будешь

Вот дважды перечитал темку твою с векторами, но так ничего и не понял, потестил методы различные с векторами, ничего не вышло. Можешь помочь пожалуйста кодом?
 
Вот дважды перечитал темку твою с векторами, но так ничего и не понял, потестил методы различные с векторами, ничего не вышло. Можешь помочь пожалуйста кодом?
С кодом а данный момент не могу. Не дома я.
В общем, чтобы рассчитать направление для стрелы (вектор) нужно вычесть из координат сущности(далее "e") координаты стрелы (Далее "a")
То есть
new Vector(e.x - a.x, e.y - a.y, e.z - a.z).
Таким образом мы получим вектор который будет направлен от стрелы на сущность.
Далее нам нужно присвоить этот вектор стреле чтобы она двигалась по нему
У стрелы должен быть метод setDirection(Vector);
Таким образом мы говорим стреле куда лететь и с какой скоростью.
Также чтобы можно было регулировать скорость стрелы можно нормализовать вектор перед тем как устанавливать его стреле.
(Нормализация вектора это приведение всех его координат к числу не более единицы)
У вектора есть метод normalizate или как То так. Который нормализует вектор.
Далее чтобы увеличить скорость стрелы мы можем умножить этот вектор на число, это тоже можно сделать при помощи встроенных методов
Vector# multiple() при умножение вектора на число увеличивается его длина и тем самым скорость и дальность полета стрелы (но будь осторожен в майнкрафте урон от стрелы полностью зависит от ее скорости. То есть если скорость очень большая то стрела просто ваншотнет сущность)
 
С кодом а данный момент не могу. Не дома я.
В общем, чтобы рассчитать направление для стрелы (вектор) нужно вычесть из координат сущности(далее "e") координаты стрелы (Далее "a")
То есть
new Vector(e.x - a.x, e.y - a.y, e.z - a.z).
Таким образом мы получим вектор который будет направлен от стрелы на сущность.
Далее нам нужно присвоить этот вектор стреле чтобы она двигалась по нему
У стрелы должен быть метод setDirection(Vector);
Таким образом мы говорим стреле куда лететь и с какой скоростью.
Также чтобы можно было регулировать скорость стрелы можно нормализовать вектор перед тем как устанавливать его стреле.
(Нормализация вектора это приведение всех его координат к числу не более единицы)
У вектора есть метод normalizate или как То так. Который нормализует вектор.
Далее чтобы увеличить скорость стрелы мы можем умножить этот вектор на число, это тоже можно сделать при помощи встроенных методов
Vector# multiple() при умножение вектора на число увеличивается его длина и тем самым скорость и дальность полета стрелы (но будь осторожен в майнкрафте урон от стрелы полностью зависит от ее скорости. То есть если скорость очень большая то стрела просто ваншотнет сущность)

то?
PHP:
@EventHandler
    public void onEvent(ProjectileLaunchEvent e) {
        Player p = (Player) e.getEntity().getShooter();
      
        Location a = e.getLocation();
        Location v = (Location) p.getNearbyEntities(15, 15, 15);
      
      
      
        Vector vec = new Vector(v.getX()-a.getX(), v.getY()-a.getY(), v.getZ()-a.getZ());
        v.setDirection(vec);

    }
 
то?
PHP:
@EventHandler
    public void onEvent(ProjectileLaunchEvent e) {
        Player p = (Player) e.getEntity().getShooter();
     
        Location a = e.getLocation();
        Location v = (Location) p.getNearbyEntities(15, 15, 15);
     
     
     
        Vector vec = new Vector(v.getX()-a.getX(), v.getY()-a.getY(), v.getZ()-a.getZ());
        v.setDirection(vec);

    }
Нет. Я домой приеду напишу тебе нормальный метод.
 
то?
PHP:
@EventHandler
    public void onEvent(ProjectileLaunchEvent e) {
        Player p = (Player) e.getEntity().getShooter();
 
        Location a = e.getLocation();
        Location v = (Location) p.getNearbyEntities(15, 15, 15);
 
 
 
        Vector vec = new Vector(v.getX()-a.getX(), v.getY()-a.getY(), v.getZ()-a.getZ());
        v.setDirection(vec);

    }
Дирекшен вот так устанавливается. targetLocation.setDirection(targetLocation.toVector().subtract(location.toVector()));
и getNearbyEntities возвращает лист ентити.
 
Тут можно еще использовать Skript, функция on event <событие>: должна сработать
Вот накидал по быстрому.
Будет стрелять по ближайшему мобу к курсору;
PHP:
@EventHandler
public void onAimShoot(EntityShootBowEvent e){
    int aimRadius = 30; //радиус действия аим бота
    float arrowSpeed = 3; // дальность и скорость полета стрелы


    // если стрелок не игрок тогда ничего не делаем
    // Мы же не хотим чтобы скелеты бегали тоже с аимом
    if(!(e.getEntity() instanceof Player)) return;

    //получение всех сущностей в радиусе действия аимбота
    ArrayList<LivingEntity> nearEntities = (ArrayList<LivingEntity>) e.getProjectile().getLocation().getNearbyLivingEntities(aimRadius);

    //если в списке есть игрок который стрелял то убираем его чтобы сам себя не застрелил.
    if(nearEntities.contains(e.getEntity())) nearEntities.remove(e.getEntity());

    //если список пуст то есть рядом нет ни 1 моба то мы ничего не делаем.
    if(nearEntities.size() == 0) return;

    //сортировка списка по скалярному произведению. тоесть будет выстрел по моду который ближе всего к прицелу.
    //про скалярное произведение векторов почитай сам.
    Collections.sort(nearEntities, (e1, e2) ->{
        double dot1 = e.getEntity().getLocation().getDirection().dot(setDirection(e.getEntity().getLocation(), e1.getLocation()));
        double dot2 = e.getEntity().getLocation().getDirection().dot(setDirection(e.getEntity().getLocation(), e2.getLocation()));
        if(dot1 > dot2) return -1;
        else return 1;
    });
   
    //получение самого ближайшего моба к прицелу.
    LivingEntity aimEntity = nearEntities.get(0);
   
    //получение локации от куда ведется выстрел
    Location shootLocation = e.getEntity().getLocation();
   
    //установка направления и скорости стреле
    e.getProjectile().setVelocity(setDirection(shootLocation, aimEntity.getLocation()).multiply(arrowSpeed));
}

//метод который вернет нам вектор с углами от 1 позиции до другой
private Vector setDirection(Location point1, Location point2){
    return point2.clone().subtract(point1.clone()).toVector().normalize();
}
Почитай комментарии и попробуй разобраться.

Дирекшен вот так устанавливается. targetLocation.setDirection(targetLocation.toVector().subtract(location.toVector()));
и getNearbyEntities возвращает лист ентити.
Хз мне удобнее вычесть из 1 позиции вычесть другую. Так понятнее что происходит.
 
Вот накидал по быстрому.
Будет стрелять по ближайшему мобу к курсору;
PHP:
@EventHandler
public void onAimShoot(EntityShootBowEvent e){
    int aimRadius = 30; //радиус действия аим бота
    float arrowSpeed = 3; // дальность и скорость полета стрелы


    // если стрелок не игрок тогда ничего не делаем
    // Мы же не хотим чтобы скелеты бегали тоже с аимом
    if(!(e.getEntity() instanceof Player)) return;

    //получение всех сущностей в радиусе действия аимбота
    ArrayList<LivingEntity> nearEntities = (ArrayList<LivingEntity>) e.getProjectile().getLocation().getNearbyLivingEntities(aimRadius);

    //если в списке есть игрок который стрелял то убираем его чтобы сам себя не застрелил.
    if(nearEntities.contains(e.getEntity())) nearEntities.remove(e.getEntity());

    //если список пуст то есть рядом нет ни 1 моба то мы ничего не делаем.
    if(nearEntities.size() == 0) return;

    //сортировка списка по скалярному произведению. тоесть будет выстрел по моду который ближе всего к прицелу.
    //про скалярное произведение векторов почитай сам.
    Collections.sort(nearEntities, (e1, e2) ->{
        double dot1 = e.getEntity().getLocation().getDirection().dot(setDirection(e.getEntity().getLocation(), e1.getLocation()));
        double dot2 = e.getEntity().getLocation().getDirection().dot(setDirection(e.getEntity().getLocation(), e2.getLocation()));
        if(dot1 > dot2) return -1;
        else return 1;
    });
  
    //получение самого ближайшего моба к прицелу.
    LivingEntity aimEntity = nearEntities.get(0);
  
    //получение локации от куда ведется выстрел
    Location shootLocation = e.getEntity().getLocation();
  
    //установка направления и скорости стреле
    e.getProjectile().setVelocity(setDirection(shootLocation, aimEntity.getLocation()).multiply(arrowSpeed));
}

//метод который вернет нам вектор с углами от 1 позиции до другой
private Vector setDirection(Location point1, Location point2){
    return point2.clone().subtract(point1.clone()).toVector().normalize();
}
Почитай комментарии и попробуй разобраться.


Хз мне удобнее вычесть из 1 позиции вычесть другую. Так понятнее что происходит.



PHP:
  ArrayList<LivingEntity> nearEntities = (ArrayList<LivingEntity>)
 e.getProjectile().getLocation().getNearbyLivingEntities(aimRadius);
просит создать объект, но после его создания просит сделать тоже самое.
 
PHP:
  ArrayList<LivingEntity> nearEntities = (ArrayList<LivingEntity>)
 e.getProjectile().getLocation().getNearbyLivingEntities(aimRadius);
просит создать объект, но после его создания просит сделать тоже самое.
Скинь скриншотом на что ругается. У меня этот кусок кода нормально работает.
 
Скинь скриншотом на что ругается. У меня этот кусок кода нормально работает.
II5UkJX.png
 
Назад
Верх