Пропуск роликов

Материал из GTAModding.ru
Версия от 11:08, 2 января 2010; Lego (обсуждение | вклад)

(разн.) ← Предыдущая | Текущая версия (разн.) | Следующая → (разн.)
Перейти к: навигация, поиск

В стандартных миссиях Rockstar North большинство роликов можно пропустить, нажав клавишу Shift. В скриптах со времён San Andreas это реализуется не проверкой на нажатие Shift, а встроенными в игру опкодами/функциями.

Пропуск роликов в San Andreas

В SA пропуск роликов реализуется всего лишь парой опкодов:

0707: start_scene_skip_to @End_Scene
0701: end_scene_skip

Первый включает режим пропуска ролика и назначает метку, на которую прыгает игра при нажатии клавиши. Второй его выключает. Пример:

  1. 0707: start_scene_skip_to @End_Scene
  2. {Ролик...}
  3. :End_Scene
  4. 0701: end_scene_skip

При этом нужно учитывать, что игра при нажатии клавиши прыгнет на эту метку, пропуская все опкоды (как jump) и после ролика (после опкода end_scene_skip) нужно поставить (PutAt и Angle) актёров и машины так, как если бы они стояли после ролика, также если внутри ролика машины взрываются, то после ролика их нужно взорвать опкодом 08CB, и т. д. . Более того, нельзя создавать внутри ролика чего бы то нибыло, что будет использоваться вне ролика. То есть если вы создали актёра внутри ролика, а после ролика дали ему команду зайти в машину, а игрок пропустил ролик, то актёр не создатся и скрипт даст команду несуществующему актёру зайти в машину. Итог: игра зависла. Решение: создать актёра до начала ролика (вне пространства между опкодами start_scene_skip_to и end_scene_skip). И ещё: обычно ролики начинаются и заканчиваются фейдами (опкод fade).

Возможные ошибки

Пример ошибки и её решения

Неправильно:

  1. 0707: start_scene_skip_to @End_Scene
  2. {актёр создаётся нутри ролика}
  3. 1@ = Actor.Create(Special, #SPECIAL02, -2044.6775, 159.0651, 28.8359)
  4. {Ролик...}
  5. :End_Scene
  6. 0701: end_scene_skip
  7. 0631: put_actor 1@ in_group $PLAYER_GROUP {<< Ира заиснет тут}

Правильно:

  1. {актёр создаётся не ролика}
  2. 1@ = Actor.Create(Special, #SPECIAL02, -2044.6775, 159.0651, 28.8359)
  3.  
  4. 0707: start_scene_skip_to @End_Scene
  5. {Ролик...}
  6. :End_Scene
  7. 0701: end_scene_skip
  8. 0631: put_actor 1@ in_group $PLAYER_GROUP

Пример мини-ролика

  1. thread 'rolik'
  2.  
  3. {$CLEO}
  4.  
  5. var
  6.   $Player_Char: Player
  7.   $Player_Actor: Actor
  8. end
  9.  
  10. while true
  11.   if and
  12.     $Player_Char.Defined
  13.     $ONMISSION == false
  14.     00FE: actor $PLAYER_ACTOR sphere 1 in_sphere 2476.9993 -1679.3445 13.3376 radius 2.0 2.0 3.0 
  15.   then
  16.     fade 0 500
  17.     while fading
  18.       wait 0
  19.     end
  20.     $Player_Char.CanMove = false
  21.  
  22.     #MAVERICK.Load
  23.     #MRWHOOP.Load
  24.     #WMOICE.Load
  25.  
  26.  
  27.     :load
  28.     wait 0
  29.     if and
  30.       #MAVERICK.Available
  31.       #MRWHOOP.Available
  32.       #WMOICE.Available
  33.     jf @load
  34.  
  35.     042B: clear_peds_from_cube_cornerA 2500.511 -1663.5464 11.0 cornerB 2420.6042 -1653.6869 15.0
  36.     03BA: clear_cars_from_cube_cornerA 2500.511 -1663.5464 11.0 cornerB 2420.6042 -1653.6869 15.0
  37.  
  38.     1@ = Car.Create(#MRWHOOP, 2412.1978, -1655.386, 12.6141)
  39.     Car.Angle(1@) = 270.0
  40.     Car.SetSpeedInstantly(1@, 20.0)
  41.     Car.SetMaxSpeed(1@, 30.0)
  42.     0423: set_car 1@ improved_handling_to 2.0 // (float)
  43.     0397: enable_car 1@ siren 1 
  44.     0129: 2@ = create_actor_pedtype 23 model #WMOICE in_car 1@ driverseat
  45.     01C8: 3@ = create_actor_pedtype 23 model #WMOICE in_car 1@ passenger_seat 0
  46.     4@ = Actor.Create(23, #WMOICE, 0.0, 0.0, 0.0)
  47.     0464: put_actor 4@ into_turret_on_car 1@ at_car_offset 0.7 -0.4 0.23 position 3 shooting_angle_limit 0.0 with_weapon 0 
  48.     #MAVERICK.Destroy
  49.     #MRWHOOP.Destroy
  50.     #WMOICE.Destroy    
  51.     0707: start_scene_skip_to @end_scene1
  52.     0704: car 1@ drive_to 2490.0583 -1656.3477 13.5915
  53.     Camera.SetPosition(2473.269, -1672.4255, 17.2742, 0.0,0.0,0.0)
  54.     Camera.OnVehicle(1@, 15, 2)
  55.     0A48: enable_menu_access_in_widescreen_mode 1 
  56.     02A3: enable_widescreen 1 
  57.     fade 1 1000
  58.  
  59.     while 81AF: not car 1@ sphere 1 in_sphere 2490.0583 -1656.3477 13.5915 radius 4.0 4.0 1.5
  60.       wait 0
  61.     end
  62.  
  63.     wait 1000
  64.  
  65.     :end_scene1
  66.     0701: end_scene_skip
  67.     fade 0 500 ms
  68.     while fading
  69.       wait 0
  70.     end
  71.     0397: enable_car 1@ siren 0     
  72.     02A3: enable_widescreen 0
  73.     Car.PutAt(1@, 2490.0583, -1656.3477, 13.5915)// Что-бы при пропуске
  74.     Car.Angle(1@) = 270.0                        // машина стояла где надо
  75.     Camera.Restore_WithJumpCut   
  76.     // Можно заменить на RemoveReferences
  77.     0AB1: call_scm_func @CarChangeRef 2 params handle 1@ ref 1 {random}
  78.     0AB1: call_scm_func @ActorChangeRef 2 params handle 2@ ref 1 {random}
  79.     0AB1: call_scm_func @ActorChangeRef 2 params handle 3@ ref 1 {random}
  80.     0AB1: call_scm_func @ActorChangeRef 2 params handle 4@ ref 1 {random}
  81.     $Player_Char.CanMove = true
  82.     fade 1 500
  83.  
  84.     while 00FE: actor $PLAYER_ACTOR sphere 0 in_sphere 2476.9993 -1679.3445 13.3376 radius 2.0 2.0 3.0 
  85.       wait 0
  86.     end
  87.   end
  88.   wait 0
  89. end
  90.  
  91. // Это понимать необязательно, к ролику не относится.
  92. // Это аналогично RemoveReferences и AddReferences.
  93.  
  94. :ActorChangeRef
  95. 0A96: 2@ = actor 0@ struct
  96. 2@+=0x484
  97. 0A8C: write_memory 2@ size 1 value 1@ virtual_protect 0
  98. 0AB2: ret 0
  99.  
  100. :CarChangeRef
  101. 0A97: 2@ = car 0@ struct
  102. 2@+=0x4A4
  103. 0A8C: write_memory 2@ size 1 value 1@ virtual_protect 0
  104. 0AB2: ret 0