Исходник Пример кода антифристенда.

Модератор форума
Участник
Статус
Оффлайн
Регистрация
26 Янв 2020
Сообщения
378
Реакции[?]
157
Поинты[?]
9K
Warning: этот код представлен исключительно в образовательных целях. Он требует дальнейшей доработки.
C++:
//Это демонстрационный код антифристенд ресольвера, работающего на довольно простых и базовых принципах.
          
           //получаем левую и правую позу игрока исходя из матриц
            auto leftPose = GetHitboxPos(player, left_matrixes, HITBOX_HEAD);
            auto rightPose = GetHitboxPos(player, right_matrixes, HITBOX_HEAD);

            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.
            float left_damage = g_AutoWall.Think(leftPose , player, HITGROUP_HEAD).m_damage;
            float right_damage = g_AutoWall.Think(rightPose , player, HITGROUP_HEAD).m_damage;
            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.

            CTraceFilter filter;

            trace_t tr;

            Ray_t RayToleft, RayToRight;

            Vector CurrentLocalPose;

            //получаем начальный угол глаз откуда будет выпускаться луч. В данном случае это eyeAngles локала.
            CurrentLocalPose = csgo->local->GetEyeAngles();

             /*есть моя недоработка, что использую макс десинк дельту, это не есть хорошо, т.к эта функция дает максимально возможную дельту игрока при заданных параметрах,
            а не ту, которая есть на самом деле.*/

            //Сетапим позицию плеера Для начала его правую сторону.
            Vector RightPose(player->GetEyeAngles().x, player->GetEyeAngles().y - player->GetDSYDelta(), player->GetEyeAngles().z);
            //опять сетапим позицию плеера, теперь уже его левую сторону.
            Vector LeftPose(player->GetEyeAngles().x, player->GetEyeAngles().y + player->GetDSYDelta(), player->GetEyeAngles().z);

            //Фильтр, чтоб игнорировать локал плеера и не трейсить самого себя.
            filter.pSkip = csgo->local;

            //Получаем дистанцию до игрока.
            float Distance = std::floor(csgo->local->GetAbsOrigin().DistTo(player->GetAbsOrigin()));

            float RightDistance, LeftDistance;
       
            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToRight.Init(CurrentLocalPose, RightPose);
            interfaces.trace->TraceRay(RayToRight, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в правую позу противника.
            RightDistance = (tr.endpos - tr.startpos).Length();

            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToleft.Init(CurrentLocalPose, LeftPose);
            interfaces.trace->TraceRay(RayToleft, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в левую позу противника.
            LeftDistance = (tr.endpos - tr.startpos).Length();
       
            //Здесь мы делаем проверку, на то, что есть ли на челика аволл дамаг. Если есть, то энеми за стеной, вычисляем сайд путем простой логики.
            //Если аволл рассчитал что может нанести дамага в левую сторону больше чем в правую, то логично что у чела позитив сайд. И наоборот.
            //P.s почему бы не юзать просто трейсера?? А потому, что если энеми за непростреливаемой стенкой, то лучи просто уткнутся в стенку и вы не получите корректные данные.
            //Именно за этим и нужен автоволл метод.
            if (left_damage > 0.0f && right_damage > 0.0f) {

                if (left_damage > right_damage)
                    FreestandSide[idx] = 1;
                else if (left_damage < right_damage)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
            else {

            //how it works. В энеми выпускаются лучи. В лефт позу и райт позу. Если длинна луча больше чем дистанция до энеми, то он прошел сковзь модель, значит она фейковая.
            //методом инверсии легко догадаться что сайд будет противоположным от того куда мы ротейтили.

                if (fabsf(RightDistance) > Distance)
                    FreestandSide[idx] = 1;
                else if (fabsf(LeftDistance) > Distance)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
Внимание, ошибка в коде, через пару минут пофикшу.
P.s ошибка пофикшена.
 
Последнее редактирование:
Модератор форума
Участник
Статус
Оффлайн
Регистрация
26 Янв 2020
Сообщения
378
Реакции[?]
157
Поинты[?]
9K
Пример функции, получающей позу хитбокса.
C++:
Vector GetHitboxPos(IBasePlayer* player, matrix* mat, int hitbox_id)
{
    if (!player)
        return Vector();

    auto hdr = interfaces.models.model_info->GetStudioModel(player->GetModel());

    if (!hdr)
        return Vector();

    auto hitbox_set = hdr->pHitboxSet(player->GetHitboxSet());

    if (!hitbox_set)
        return Vector();

    auto hitbox = hitbox_set->pHitbox(hitbox_id);

    if (!hitbox)
        return Vector();

    Vector min, max;

    Math::VectorTransform(hitbox->bbmin, mat[hitbox->bone], min);
    Math::VectorTransform(hitbox->bbmax, mat[hitbox->bone], max);

    return (min + max) * 0.5f;
}
 
Эксперт
Статус
Оффлайн
Регистрация
30 Дек 2019
Сообщения
1,970
Реакции[?]
958
Поинты[?]
19K
Warning: этот код представлен исключительно в образовательных целях. Он требует дальнейшей доработки.
C++:
//Это демонстрационный код антифристенд ресольвера, работающего на довольно простых и базовых принципах.
         
           //получаем левую и правую позу игрока исходя из матриц
            auto leftPose = GetHitboxPos(player, left_matrixes, HITBOX_HEAD);
            auto rightPose = GetHitboxPos(player, right_matrixes, HITBOX_HEAD);

            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.
            float left_damage = g_AutoWall.Think(leftPose , player, HITGROUP_HEAD).m_damage;
            float right_damage = g_AutoWall.Think(rightPose , player, HITGROUP_HEAD).m_damage;
            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.

            CTraceFilter filter;

            trace_t tr;

            Ray_t RayToleft, RayToRight;

            Vector CurrentLocalPose;

            //получаем начальный угол глаз откуда будет выпускаться луч. В данном случае это eyeAngles локала.
            CurrentLocalPose = csgo->local->GetEyeAngles();

             /*есть моя недоработка, что использую макс десинк дельту, это не есть хорошо, т.к эта функция дает максимально возможную дельту игрока при заданных параметрах,
            а не ту, которая есть на самом деле.*/

            //Сетапим позицию плеера Для начала его правую сторону.
            Vector RightPose(player->GetEyeAngles().x, player->GetEyeAngles().y - player->GetDSYDelta(), player->GetEyeAngles().z);
            //опять сетапим позицию плеера, теперь уже его левую сторону.
            Vector LeftPose(player->GetEyeAngles().x, player->GetEyeAngles().y + player->GetDSYDelta(), player->GetEyeAngles().z);

            //Фильтр, чтоб игнорировать локал плеера и не трейсить самого себя.
            filter.pSkip = csgo->local;

            //Получаем дистанцию до игрока.
            float Distance = std::floor(csgo->local->GetAbsOrigin().DistTo(player->GetAbsOrigin()));

            float RightDistance, LeftDistance;
      
            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToRight.Init(CurrentLocalPose, RightPose);
            interfaces.trace->TraceRay(RayToRight, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в правую позу противника.
            RightDistance = (tr.endpos - tr.startpos).Length();

            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToleft.Init(CurrentLocalPose, LeftPose);
            interfaces.trace->TraceRay(RayToleft, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в левую позу противника.
            LeftDistance = (tr.endpos - tr.startpos).Length();
      
            //Здесь мы делаем проверку, на то, что есть ли на челика аволл дамаг. Если есть, то энеми за стеной, вычисляем сайд путем простой логики.
            //Если аволл рассчитал что может нанести дамага в левую сторону больше чем в правую, то логично что у чела позитив сайд. И наоборот.
            //P.s почему бы не юзать просто трейсера?? А потому, что если энеми за непростреливаемой стенкой, то лучи просто уткнутся в стенку и вы не получите корректные данные.
            //Именно за этим и нужен автоволл метод.
            if (left_damage > 0.0f && right_damage > 0.0f) {

                if (left_damage > right_damage)
                    FreestandSide[idx] = 1;
                else if (left_damage < right_damage)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
            else {

            //how it works. В энеми выпускаются лучи. В лефт позу и райт позу. Если длинна луча больше чем дистанция до энеми, то он прошел сковзь модель, значит она фейковая.
            //методом инверсии легко догадаться что сайд будет противоположным от того куда мы ротейтили.

                if (fabsf(RightDistance) > Distance)
                    FreestandSide[idx] = 1;
                else if (fabsf(LeftDistance) > Distance)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
Внимание, ошибка в коде, через пару минут пофикшу.
P.s ошибка пофикшена.
можно было сделать покороче, но и так сойдёт
 
Keep Ev0lving, Stay Fatal
Эксперт
Статус
Оффлайн
Регистрация
6 Фев 2018
Сообщения
1,548
Реакции[?]
584
Поинты[?]
100K
Warning: этот код представлен исключительно в образовательных целях. Он требует дальнейшей доработки.
C++:
//Это демонстрационный код антифристенд ресольвера, работающего на довольно простых и базовых принципах.
         
           //получаем левую и правую позу игрока исходя из матриц
            auto leftPose = GetHitboxPos(player, left_matrixes, HITBOX_HEAD);
            auto rightPose = GetHitboxPos(player, right_matrixes, HITBOX_HEAD);

            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.
            float left_damage = g_AutoWall.Think(leftPose , player, HITGROUP_HEAD).m_damage;
            float right_damage = g_AutoWall.Think(rightPose , player, HITGROUP_HEAD).m_damage;
            //данные строчки нужны тогда, когда игрок за стенкой, и луч не может дойти до энеми. Смотри обьяснение ниже.

            CTraceFilter filter;

            trace_t tr;

            Ray_t RayToleft, RayToRight;

            Vector CurrentLocalPose;

            //получаем начальный угол глаз откуда будет выпускаться луч. В данном случае это eyeAngles локала.
            CurrentLocalPose = csgo->local->GetEyeAngles();

             /*есть моя недоработка, что использую макс десинк дельту, это не есть хорошо, т.к эта функция дает максимально возможную дельту игрока при заданных параметрах,
            а не ту, которая есть на самом деле.*/

            //Сетапим позицию плеера Для начала его правую сторону.
            Vector RightPose(player->GetEyeAngles().x, player->GetEyeAngles().y - player->GetDSYDelta(), player->GetEyeAngles().z);
            //опять сетапим позицию плеера, теперь уже его левую сторону.
            Vector LeftPose(player->GetEyeAngles().x, player->GetEyeAngles().y + player->GetDSYDelta(), player->GetEyeAngles().z);

            //Фильтр, чтоб игнорировать локал плеера и не трейсить самого себя.
            filter.pSkip = csgo->local;

            //Получаем дистанцию до игрока.
            float Distance = std::floor(csgo->local->GetAbsOrigin().DistTo(player->GetAbsOrigin()));

            float RightDistance, LeftDistance;
      
            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToRight.Init(CurrentLocalPose, RightPose);
            interfaces.trace->TraceRay(RayToRight, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в правую позу противника.
            RightDistance = (tr.endpos - tr.startpos).Length();

            //Инициализируем и выпускаем луч из локал позы, до позы энеми.
            RayToleft.Init(CurrentLocalPose, LeftPose);
            interfaces.trace->TraceRay(RayToleft, MASK_SHOT, &filter, &tr);
            //Получаем длинну луча, выпущенного в левую позу противника.
            LeftDistance = (tr.endpos - tr.startpos).Length();
      
            //Здесь мы делаем проверку, на то, что есть ли на челика аволл дамаг. Если есть, то энеми за стеной, вычисляем сайд путем простой логики.
            //Если аволл рассчитал что может нанести дамага в левую сторону больше чем в правую, то логично что у чела позитив сайд. И наоборот.
            //P.s почему бы не юзать просто трейсера?? А потому, что если энеми за непростреливаемой стенкой, то лучи просто уткнутся в стенку и вы не получите корректные данные.
            //Именно за этим и нужен автоволл метод.
            if (left_damage > 0.0f && right_damage > 0.0f) {

                if (left_damage > right_damage)
                    FreestandSide[idx] = 1;
                else if (left_damage < right_damage)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
            else {

            //how it works. В энеми выпускаются лучи. В лефт позу и райт позу. Если длинна луча больше чем дистанция до энеми, то он прошел сковзь модель, значит она фейковая.
            //методом инверсии легко догадаться что сайд будет противоположным от того куда мы ротейтили.

                if (fabsf(RightDistance) > Distance)
                    FreestandSide[idx] = 1;
                else if (fabsf(LeftDistance) > Distance)
                    FreestandSide[idx] = -1;
                else
                    FreestandSide[idx] = 0;
            }
Внимание, ошибка в коде, через пару минут пофикшу.
P.s ошибка пофикшена.
Попробовал на практике(Запастил под лв от шонакса по быстрому), результат +- неплохой. Мне понравилось :roflanPominki:
 
Сверху Снизу