Константы по таблице GMod и устранены невидимые стены из плоскостей граней
Четыре жалобы из игры, все закрыты измерением. Константы движения (gmodwiki.com/ConVars_In_Garrysmod, не source-sdk-2013): sv_friction 4 -> 8 торможение 250 -> 10 за 0,40 с, путь 26 юнитов sv_stopspeed 100 -> 10 sv_gravity 800 -> 600 прыжок 45,6 -> 60,8 юнита, как в GMod sv_airaccelerate 12 -> 10 sv_maxvelocity 350 -> 3500 падение 585/589/590 -> 600/1200/1800/2400/3000 «В воздухе управление слабее»: в AirAccelerate кап sv_air_max_wishspeed ограничивает ЦЕЛЬ, а прибавка считается по некапленной wishspeed. Мы ограничивали и то и другое — прибавка была в 8,3 раза слабее. Замер после правки: рывок вбок даёт ровно 30,0 юнитов/с, как в Source. Поворот при полёте вперёд по-прежнему заблокирован (проекция 177 >> капа 30) — это верное поведение оригинала. «Высота шага терялась единица»: подъём ровно на sv_stepsime ставит низ габарита точно на грань ступени, грань считается касанием, и подшаг блокирует сам себя. Замерено: брались уступы до 17 и застревали на 18. В оригинале подъём на flStepSize + DIST_EPSILON. После правки — все до 18 включительно, 19 нет. «Невидимые стены, рампа как параллелипипед»: грань кирпича ограничивает плоскость, а не кирпич, и останавливает шаг где угодно на её уровне. Замерено: игрок останавливался за 3,4 юнита до настоящей преграды, блокировала верхняя грань соседнего кирпича. Правка: при t около нуля проверяется, что точка касания лежит на самом кирпиче. Замер после правки: преград «из воздуха» 0 (было 2), упоров за 30 с ходьбы 0. Проверено и отброшено измерением: кисти не работают как ящик (аудит 2126 кирпичей, 0 расхождений из 129684 точек); displacement не выпадает из сетки (11776 треугольников, выпало 0); скорость вдоль склона 239-263 против 250. Пара sv_falldistance/fall_speed НЕ введена осознанно: в таблице cvar'ов GMod её нет, а формула HL2 при отрицательной velocity[2] даёт замедление падения, а не разгон. Ставить непроверенные константы значило бы гадать. 228 тестов зелёные, clippy -D warnings чист.
This commit is contained in:
parent
f34c456034
commit
d6c49fd67a
2 changed files with 1004 additions and 28 deletions
File diff suppressed because it is too large
Load diff
118
docs/PARITY.md
118
docs/PARITY.md
|
|
@ -1179,3 +1179,121 @@ for (i=0; i < 3; i++) {
|
|||
с обнулением оси на 0).
|
||||
|
||||
Тесты: `speed_is_capped_at_max_velocity`, `non_finite_velocity_is_zeroed`.
|
||||
|
||||
## Часть B8. Свары GMod: константы и «невидимые стены» (сделано)
|
||||
|
||||
Четыре жалобы, все — из игры, все закрыты измерением.
|
||||
|
||||
### B8.1. «В воздухе управление слабее, чем в оригинальном GMod»
|
||||
|
||||
Таблица cvar'ов GMod (gmodwiki.com/ConVars_In_Garrysmod) и код
|
||||
`AirAccelerate` из CS:GO-версии `gamemovement.cpp` дают разные вещи:
|
||||
|
||||
```cpp
|
||||
wishspd = wishspeed;
|
||||
if (wishspd > 30) wishspd = 30; // цель ограничена
|
||||
addspeed = wishspd - currentspeed;
|
||||
accelspeed = accel * wishspeed * frametime; // а прибавка — по полной
|
||||
```
|
||||
|
||||
Кап `sv_air_max_wishspeed` = 30 ограничивает **цель**, но не величину прибавки.
|
||||
Мы ограничивали и то и другое, из-за чего прибавка была в 250/30 ≈ 8,3 раза
|
||||
слабее — это и есть ощущение «вялого управления в воздухе».
|
||||
|
||||
Замер после правки на gm_construct: рывок вбок в полёте даёт ровно **30,0**
|
||||
юнитов/с (кап достигается за один кадр, как в Source). Поворот при полёте
|
||||
вперёд по-прежнему заблокирован: проекция скорости на желаемое направление 177
|
||||
>> капа 30, прибавки нет — **это верное поведение оригинала**, а не дефект.
|
||||
|
||||
Заодно: `currentspeed` считается по **полной трёхмерной** скорости, а не по
|
||||
горизонтальной. В `AirMove` вертикаль не обнуляется, поэтому в падении управление
|
||||
слабее, чем в горизонтальном полёте, — ровно как в Source.
|
||||
|
||||
### B8.2. «Трение слабое, останавливаюсь долго»
|
||||
|
||||
Константы брались из SDK 2013, а у GMod они переопределены:
|
||||
|
||||
| cvar | SDK 2013 | **GMod** | было у нас |
|
||||
|---|---|---|---|
|
||||
| `sv_friction` | 4 | **8** | 4 |
|
||||
| `sv_stopspeed` | 100 | **10** | 100 |
|
||||
| `sv_gravity` | 800 | **600** | 800 |
|
||||
| `sv_airaccelerate` | 12 | **10** | 12 |
|
||||
| `sv_accelerate` | 10 | 10 | 10 |
|
||||
| `sv_maxvelocity` | 350 | **3500** | 350 |
|
||||
| `sv_stepsize` | 18 | 18 | 18 |
|
||||
| `sv_walkable_normal` | 0,7 | 0,7 | 0,7 |
|
||||
|
||||
Замер после правки: с 250 юнитов/с до 10 — за **0,40 с**, путь **26 юнитов**.
|
||||
|
||||
`sv_maxvelocity` = 3500, а не 350, — отдельная история: это потолок *по осям*, и
|
||||
при значении 350 вертикальная скорость падения упиралась в него сразу. Отсюда
|
||||
жалоба «падаю как мешок, без ускорения».
|
||||
|
||||
### B8.3. Прыжок и падение
|
||||
|
||||
`sv_gravity` = 600 и прыжок 270 дают 270²/1200 = **60,8** юнита высоты — как в
|
||||
GMod (замерено 60,8). В Source с гравитацией 800 было 45,6.
|
||||
|
||||
Падение в пустоте по секундам: **600, 1200, 1800, 2400, 3000** юнитов/с —
|
||||
равномерный разгон по `g·t` до потолка `sv_maxvelocity`. Прежде было
|
||||
585, 589, 590 — то есть упиралось в потолок 350 и стояло на месте.
|
||||
|
||||
### B8.4. О `sv_falldistance` / `fall_speed`: гипотеза, отброшенная измерением
|
||||
|
||||
Поначалу показалось, что «ускорение падения» — это пара cvar'ов HL2
|
||||
`sv_falldistance` + `fall_speed`. Проверка: в таблице cvar'ов GMod их **нет**, а
|
||||
формула `velocity[2] -= velocity[2] * fall_speed * frametime` при отрицательной
|
||||
`velocity[2]` даёт **замедление** падения, а не разгон. Ставить непроверенные
|
||||
константы значило бы гадать, поэтому пара не вводится: ускорение падения в GMod
|
||||
даёт постоянная гравитация плюс высокий `sv_maxvelocity`.
|
||||
|
||||
### B8.5. «Высота шага терялась единица»
|
||||
|
||||
Подшаг поднимает тело ровно на `sv_stepsize` = 18, и тогда низ габарита
|
||||
становится **точно на грань** ступени. Грань в этот момент считается касанием,
|
||||
отсечение обнуляет шаг, и подшаг блокирует сам себя.
|
||||
|
||||
Замер до правки: игрок перебирал уступы до **17** и застревал на **18**. В
|
||||
оригинале подъём идёт на `flStepSize + DIST_EPSILON` — не округление, а
|
||||
необходимость.
|
||||
|
||||
После введения `STEP_EPSILON` = 0,1: перебираются все уступы до **18** включительно,
|
||||
19 — нет. Ровно `sv_stepsize`.
|
||||
|
||||
### B8.6. «Невидимые стены, рамка превращается в параллелепипед»
|
||||
|
||||
Грань кирпича ограничивает **плоскость**, а не сам кирпич. Стоит телу оказаться
|
||||
на уровне этой плоскости где угодно — грань останавливает шаг, даже если
|
||||
кирпича там нет.
|
||||
|
||||
Замер на gm_construct: игрок, идущий по полу на `z = -144`, останавливался за
|
||||
**3,4 юнита** до настоящей преграды — блокировала верхняя грань соседнего
|
||||
кирпича, до которого было далеко. Такие грани встречаются на каждом стыке
|
||||
участков, а на наклонных поверхностях образуют блоки, сравнимые с габаритом
|
||||
целого кирпича, — «рампа превращается в параллелепипед».
|
||||
|
||||
Правка: при `t` около нуля (шаг обнуляется полностью) проверяется, что точка
|
||||
касания лежит на самом кирпиче, а не на продолжении его грани.
|
||||
|
||||
Проверка узкая и только для `t < 0,001` намеренно: проверять точку касания для
|
||||
всех `t` нельзя — при спуске с подшага тело опускается вертикально и в момент
|
||||
касания ещё находится в стороне от грани по горизонтали. На широкой проверке
|
||||
игрок переставал перебирать уступы уже высотой 4 юнита (замерено).
|
||||
|
||||
Замер после правки: преград «из воздуха» на 1800 шагов ходьбы по gm_construct —
|
||||
**0** (было 2), и упоров в бордюры за 30 с ходьбы — **0** кадров.
|
||||
|
||||
### B8.7. Проверенные гипотезы, оказавшиеся невиновными
|
||||
|
||||
Каждая проверялась замером, а не рассуждением, и все оказались в порядке:
|
||||
|
||||
- **Кисти кирпичей как ящик.** Синтетическая наклонная грань сходится с
|
||||
полутночными пространствами точно (`slanted_brush_is_not_treated_as_a_box`).
|
||||
- **Объём кирпичей на карте.** Аудит всех 2126 кирпичей gm_construct по сетке
|
||||
4×4×4 точек: **0 расхождений** (129684 проверок).
|
||||
- **Displacement выпадает из сетки.** `add_displacement_tris` молча выбрасывает
|
||||
треугольник, размазанный больше чем по 2048 юнитам. На карте: 11776
|
||||
треугольников, **выпало 0**.
|
||||
- **Скорость вдоль склона.** Рампа — не ящик: 239–263 юнита/с против 250 на
|
||||
ровном, при подъёме застреваний 0.
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue