Advertisement
Guest User

SA-MP Spike Strips (fs) (update 2)

a guest
Jul 5th, 2013
526
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Pawn 20.11 KB | None | 0 0
  1. /*
  2.  * SA-MP Spike Strips
  3.  *
  4.  * Copyright (c) 2013, Stylock
  5.  * This file is provided as is with no warranties of any kind.
  6.  */
  7.  
  8. /*
  9.  * Changelog
  10.  *
  11.  *      5/7/2013:
  12.  *          ~ changed parameter order in OnSpikeStripPopTire callback
  13.  *          ~ fixed a bug where OnSpikeStripPopTire callback wasn't getting called
  14.  *          ~ fixed incorrect arguments being passed to SetTimerEx function
  15.  *          ~ added a function named SpikeStrip_DeleteAll that deletes all spike strips
  16.  *
  17.  *      4/7/2013:
  18.  *          ~ removed the auto-adjustment of the Z coordinate when creating a spike strip
  19.  *          ~ added a callback named OnSpikeStripPopTire that is called when a tire is popped
  20.  *          ~ added a function named SpikeStrip_IsValid that checks the validity of a spike strip
  21.  *          ~ added a function named SpikeStrip_SetGhost that toggles a player's ghost mode
  22.  *          ~ added a function named SpikeStrip_IsGhost that checks whether a player is in ghost mode
  23.  *
  24.  *      3/7/2013:
  25.  *          ~ initial release
  26.  */
  27.  
  28. #include <a_samp>
  29. #include <YSI\y_iterate>
  30. #include <spikestrip>
  31.  
  32. static stock
  33.     g_SpikeStrip[MAX_SPIKE_STRIPS],
  34.     Iterator:g_Spike<MAX_SPIKE_STRIPS>,
  35.     Float:g_Spike_x1[MAX_SPIKE_STRIPS],
  36.     Float:g_Spike_y1[MAX_SPIKE_STRIPS],
  37.     Float:g_Spike_x2[MAX_SPIKE_STRIPS],
  38.     Float:g_Spike_y2[MAX_SPIKE_STRIPS],
  39.     Float:g_Spike_x3[MAX_SPIKE_STRIPS],
  40.     Float:g_Spike_y3[MAX_SPIKE_STRIPS],
  41.     Float:g_Spike_x4[MAX_SPIKE_STRIPS],
  42.     Float:g_Spike_y4[MAX_SPIKE_STRIPS],
  43.     Float:g_Spike_zA[MAX_SPIKE_STRIPS],
  44.     Float:g_Tire1_x1[MAX_PLAYERS],
  45.     Float:g_Tire1_y1[MAX_PLAYERS],
  46.     Float:g_Tire1_z1[MAX_PLAYERS],
  47.     Float:g_Tire1_x2[MAX_PLAYERS],
  48.     Float:g_Tire1_y2[MAX_PLAYERS],
  49.     Float:g_Tire1_z2[MAX_PLAYERS],
  50.     Float:g_Tire1_x3[MAX_PLAYERS],
  51.     Float:g_Tire1_y3[MAX_PLAYERS],
  52.     Float:g_Tire1_z3[MAX_PLAYERS],
  53.     Float:g_Tire1_x4[MAX_PLAYERS],
  54.     Float:g_Tire1_y4[MAX_PLAYERS],
  55.     Float:g_Tire1_z4[MAX_PLAYERS],
  56.     Float:g_Tire2_x1[MAX_PLAYERS],
  57.     Float:g_Tire2_y1[MAX_PLAYERS],
  58.     Float:g_Tire2_x2[MAX_PLAYERS],
  59.     Float:g_Tire2_z1[MAX_PLAYERS],
  60.     Float:g_Tire2_y2[MAX_PLAYERS],
  61.     Float:g_Tire2_z2[MAX_PLAYERS],
  62.     g_GetGhostMode[MAX_PLAYERS char],
  63.     g_GetTireState[MAX_PLAYERS char],
  64.     g_GetTireCount[MAX_PLAYERS char],
  65.     g_GetVehicleID[MAX_PLAYERS],
  66.     g_GetTickCount[MAX_PLAYERS],
  67.     g_GetServerTC,
  68.     g_Timer;
  69.  
  70. enum (<<= 1)
  71. {
  72.     e_TIRE_RR = 0b0001,
  73.     e_TIRE_FR,
  74.     e_TIRE_RL,
  75.     e_TIRE_FL,
  76. }
  77.  
  78. #define Public%0\32;%0(%1) \
  79.     forward public %0(%1); \
  80.     public %0(%1)
  81.  
  82. Public SS_GetServerTC()
  83. {
  84.     // Store the tick count for fast access. Better than
  85.     // calling the function 20 times per second per player.
  86.     g_GetServerTC = GetTickCount();
  87.     return 1;
  88. }
  89.  
  90. public OnFilterScriptInit()
  91. {
  92.     g_Timer = SetTimer("SS_GetServerTC", 50, 1);
  93.     return 1;
  94. }
  95.  
  96. public OnFilterScriptExit()
  97. {
  98.     SpikeStrip_DeleteAll_MA();
  99.     KillTimer(g_Timer);
  100.     return 1;
  101. }
  102.  
  103. public OnPlayerConnect(playerid)
  104. {
  105.     g_GetGhostMode{playerid} = 0;
  106.     return 1;
  107. }
  108.  
  109. public OnPlayerUpdate(playerid)
  110. {
  111.     static
  112.         Float:matrix3x3[9],
  113.         Float:x1, Float:y1, Float:z1,
  114.         Float:x2, Float:y2, Float:z2,
  115.         Float:x3, Float:y3, Float:z3,
  116.         Float:x4, Float:y4, Float:z4;
  117.     if (g_GetTickCount[playerid] < g_GetServerTC)
  118.     {
  119.         if (GetPlayerState(playerid) == 2) // Driver
  120.         {
  121.             if (IsPlayerNPC(playerid))
  122.             {
  123.                 return 1;
  124.             }
  125.             if (!g_GetGhostMode{playerid})
  126.             {
  127.                 new
  128.                     vid = GetPlayerVehicleID(playerid);
  129.                 if (vid != g_GetVehicleID[playerid])
  130.                 {
  131.                     new
  132.                         mid = GetVehicleModel(vid);
  133.                     g_GetTireCount{playerid} = SS_GetTireCount(mid);
  134.                     g_GetTireState{playerid} = SS_GetTireState(vid);
  135.                     GetVehicleModelInfo(mid, 6, x1, y1, z1);
  136.                     SS_GetTireSize(mid, e_TIRE_RR, z2);
  137.                     // Save rear wheel offsets
  138.                     g_Tire2_x1[playerid] = x1,
  139.                     g_Tire2_y1[playerid] = y1,
  140.                     g_Tire2_z1[playerid] = z1 - z2 / 2;
  141.                     GetVehicleModelInfo(mid, 5, x1, y1, z1);
  142.                     SS_GetTireSize(mid, e_TIRE_FR, z2);
  143.                     // Save front wheel offsets
  144.                     g_Tire2_x2[playerid] = x1,
  145.                     g_Tire2_y2[playerid] = y1,
  146.                     g_Tire2_z2[playerid] = z1 - z2 / 2;
  147.                 }
  148.                 if (g_GetTireCount{playerid}) // Check if the player's vehicle has any tires
  149.                 {
  150.                     if (g_GetTireState{playerid} < 0b1111) // Check if atleast one tire is not flat (0b1111 = all tires are flat)
  151.                     {
  152.                         SS_GetVehicleRotationMatrix(vid, matrix3x3);
  153.                         // If the tire is not flat, then get its position
  154.                         !(g_GetTireState{playerid} & e_TIRE_RR) && SS_GetTirePos(vid, x1, y1, z1, g_Tire2_x1[playerid], g_Tire2_y1[playerid], g_Tire2_z1[playerid], matrix3x3), // RR
  155.                         !(g_GetTireState{playerid} & e_TIRE_FR) && SS_GetTirePos(vid, x2, y2, z2, g_Tire2_x2[playerid], g_Tire2_y2[playerid], g_Tire2_z2[playerid], matrix3x3); // FR
  156.                         if (g_GetTireCount{playerid} > 2)
  157.                         {
  158.                             !(g_GetTireState{playerid} & e_TIRE_RL) && SS_GetTirePos(vid, x3, y3, z3, -g_Tire2_x1[playerid], g_Tire2_y1[playerid], g_Tire2_z1[playerid], matrix3x3), // RL
  159.                             !(g_GetTireState{playerid} & e_TIRE_FL) && SS_GetTirePos(vid, x4, y4, z4, -g_Tire2_x2[playerid], g_Tire2_y2[playerid], g_Tire2_z2[playerid], matrix3x3); // FL
  160.                         }
  161.                         foreach (new i : g_Spike)
  162.                         {
  163.                             if (IsPlayerInRangeOfPoint(playerid, 60.0, g_Spike_x1[i], g_Spike_y1[i], g_Spike_zA[i]))
  164.                             {
  165.                                 // If the tire is not flat, then monitor it
  166.                                 !(g_GetTireState{playerid} & e_TIRE_RR) && SS_MonitorTire(vid, e_TIRE_RR, i, playerid, x1, y1, z1, g_Tire1_x1[playerid], g_Tire1_y1[playerid], g_Tire1_z1[playerid]), // RR
  167.                                 !(g_GetTireState{playerid} & e_TIRE_FR) && SS_MonitorTire(vid, e_TIRE_FR, i, playerid, x2, y2, z2, g_Tire1_x2[playerid], g_Tire1_y2[playerid], g_Tire1_z2[playerid]); // FR
  168.                                 if (g_GetTireCount{playerid} > 2)
  169.                                 {
  170.                                     !(g_GetTireState{playerid} & e_TIRE_RL) && SS_MonitorTire(vid, e_TIRE_RL, i, playerid, x3, y3, z3, g_Tire1_x3[playerid], g_Tire1_y3[playerid], g_Tire1_z3[playerid]), // RL
  171.                                     !(g_GetTireState{playerid} & e_TIRE_FL) && SS_MonitorTire(vid, e_TIRE_FL, i, playerid, x4, y4, z4, g_Tire1_x4[playerid], g_Tire1_y4[playerid], g_Tire1_z4[playerid]); // FL
  172.                                 }
  173.                             }
  174.                         }
  175.                         // If the tire is not flat, then save its position
  176.                         !(g_GetTireState{playerid} & e_TIRE_RR) && (g_Tire1_x1[playerid] = x1, g_Tire1_y1[playerid] = y1, g_Tire1_z1[playerid] = z1),
  177.                         !(g_GetTireState{playerid} & e_TIRE_FR) && (g_Tire1_x2[playerid] = x2, g_Tire1_y2[playerid] = y2, g_Tire1_z2[playerid] = z2);
  178.                         if (g_GetTireCount{playerid} > 2)
  179.                         {
  180.                             !(g_GetTireState{playerid} & e_TIRE_RL) && (g_Tire1_x3[playerid] = x3, g_Tire1_y3[playerid] = y3, g_Tire1_z3[playerid] = z3),
  181.                             !(g_GetTireState{playerid} & e_TIRE_FL) && (g_Tire1_x4[playerid] = x4, g_Tire1_y4[playerid] = y4, g_Tire1_z4[playerid] = z4);
  182.                         }
  183.                     }
  184.                 }
  185.                 g_GetVehicleID[playerid] = vid;
  186.             }
  187.         }
  188.         g_GetTickCount[playerid] = g_GetServerTC + SS_TIME_INTERVAL;
  189.     }
  190.     return 1;
  191. }
  192.  
  193. public OnVehicleDamageStatusUpdate(vehicleid, playerid)
  194. {
  195.     new
  196.         tire_state = SS_GetTireState(vehicleid);
  197.     if (tire_state != g_GetTireState{playerid})
  198.     {
  199.         if (g_GetTireState{playerid} > tire_state) // Check if atleast on tire is fixed
  200.         {
  201.             new
  202.                 Float:matrix3x3[9];
  203.             SS_GetVehicleRotationMatrix(vehicleid, matrix3x3);
  204.             if (e_TIRE_RR & (g_GetTireState{playerid} & ~tire_state)) // If a flat tire is fixed
  205.             {
  206.                 SS_GetTirePos(vehicleid, g_Tire1_x1[playerid], g_Tire1_y1[playerid], g_Tire1_z1[playerid], g_Tire2_x1[playerid], g_Tire2_y1[playerid], g_Tire2_z1[playerid], matrix3x3);
  207.             }
  208.             if (e_TIRE_FR & (g_GetTireState{playerid} & ~tire_state)) // If a flat tire is fixed
  209.             {
  210.                 SS_GetTirePos(vehicleid, g_Tire1_x2[playerid], g_Tire1_y2[playerid], g_Tire1_z2[playerid], g_Tire2_x2[playerid], g_Tire2_y2[playerid], g_Tire2_z2[playerid], matrix3x3);
  211.             }
  212.             if (e_TIRE_RL & (g_GetTireState{playerid} & ~tire_state)) // If a flat tire is fixed
  213.             {
  214.                 SS_GetTirePos(vehicleid, g_Tire1_x3[playerid], g_Tire1_y3[playerid], g_Tire1_z3[playerid], -g_Tire2_x1[playerid], g_Tire2_y1[playerid], g_Tire2_z1[playerid], matrix3x3);
  215.             }
  216.             if (e_TIRE_FL & (g_GetTireState{playerid} & ~tire_state)) // If a flat tire is fixed
  217.             {
  218.                 SS_GetTirePos(vehicleid, g_Tire1_x4[playerid], g_Tire1_y4[playerid], g_Tire1_z4[playerid], -g_Tire2_x2[playerid], g_Tire2_y2[playerid], g_Tire2_z2[playerid], matrix3x3);
  219.             }
  220.         }
  221.         g_GetTireState{playerid} = tire_state;
  222.     }
  223.     return 1;
  224. }
  225.  
  226. stock SS_MonitorTire(vid, tire, sid, pid, Float:x1, Float:y1, Float:z1, Float:x2, Float:y2, Float:z2)
  227. {
  228.     new
  229.         Float:distance = 1.0;
  230.     if (SS_SegmentsIntersect_2D(g_Spike_x1[sid], g_Spike_y1[sid], g_Spike_x2[sid], g_Spike_y2[sid], x1, y1, x2, y2))
  231.     {
  232.         SS_DistanceLineToLine_3D(g_Spike_x1[sid], g_Spike_y1[sid], g_Spike_zA[sid], g_Spike_x2[sid], g_Spike_y2[sid], g_Spike_zA[sid], x1, y1, z1, x2, y2, z2, distance);
  233.     }
  234.  
  235.     #if SS_LINE_SEGMENTS >= 2
  236.  
  237.     else if (SS_SegmentsIntersect_2D(g_Spike_x3[sid], g_Spike_y3[sid], g_Spike_x4[sid], g_Spike_y4[sid], x1, y1, x2, y2))
  238.     {
  239.         SS_DistanceLineToLine_3D(g_Spike_x3[sid], g_Spike_y3[sid], g_Spike_zA[sid], g_Spike_x4[sid], g_Spike_y4[sid], g_Spike_zA[sid], x1, y1, z1, x2, y2, z2, distance);
  240.     }
  241.  
  242.     #endif
  243.  
  244.     #if SS_LINE_SEGMENTS == 4
  245.  
  246.     else if (SS_SegmentsIntersect_2D(g_Spike_x1[sid], g_Spike_y1[sid], g_Spike_x3[sid], g_Spike_y3[sid], x1, y1, x2, y2))
  247.     {
  248.         SS_DistanceLineToLine_3D(g_Spike_x1[sid], g_Spike_y1[sid], g_Spike_zA[sid], g_Spike_x3[sid], g_Spike_y3[sid], g_Spike_zA[sid], x1, y1, z1, x2, y2, z2, distance);
  249.     }
  250.     else if (SS_SegmentsIntersect_2D(g_Spike_x2[sid], g_Spike_y2[sid], g_Spike_x4[sid], g_Spike_y4[sid], x1, y1, x2, y2))
  251.     {
  252.         SS_DistanceLineToLine_3D(g_Spike_x2[sid], g_Spike_y2[sid], g_Spike_zA[sid], g_Spike_x4[sid], g_Spike_y4[sid], g_Spike_zA[sid], x1, y1, z1, x2, y2, z2, distance);
  253.     }
  254.  
  255.     #endif
  256.  
  257.     if (distance < 0.24)
  258.     {
  259.         if (vid == g_GetVehicleID[pid]) // Make sure surprise tire pops don't occur
  260.         {
  261.             new
  262.                 data1,
  263.                 data2,
  264.                 data3,
  265.                 data4;
  266.             GetVehicleDamageStatus(vid, data1, data2, data3, data4);
  267.             UpdateVehicleDamageStatus(vid, data1, data2, data3, (data4 | tire)); // Pop
  268.             CallRemoteFunction("OnSpikeStripPopTire", "iiii", sid, vid, pid, tire);
  269.         }
  270.     }
  271.     return 1;
  272. }
  273.  
  274. stock SS_GetTireState(vid)
  275. {
  276.     new
  277.         data;
  278.     GetVehicleDamageStatus(vid, data, data, data, data);
  279.     return data;
  280. }
  281.  
  282. stock SS_GetTireCount(mid)
  283. {
  284.     static const
  285.         tire_data[] =
  286.     {
  287.         4, 4, 4, 6, 4, 4, 4, 4, 6, 4,
  288.         4, 4, 4, 4, 4, 4, 4, 0, 4, 4,
  289.         4, 4, 4, 4, 4, 0, 4, 4, 4, 4,
  290.         0, 6, 4, 6, 4, 4, 4, 6, 4, 4,
  291.         4, 0, 4, 6, 4, 4, 0, 0, 2, 0,
  292.         4, 4, 0, 0, 0, 6, 4, 4, 4, 4,
  293.         0, 2, 2, 2, 0, 0, 4, 4, 2, 0,
  294.         4, 4, 0, 0, 4, 4, 0, 4, 4, 4,
  295.         4, 0, 4, 4, 0, 4, 4, 0, 0, 4,
  296.         4, 4, 4, 0, 4, 4, 4, 0, 4, 4,
  297.         4, 0, 4, 4, 4, 4, 4, 4, 4, 0,
  298.         0, 0, 0, 0, 6, 6, 4, 4, 4, 0,
  299.         0, 2, 2, 2, 6, 4, 4, 4, 4, 4,
  300.         4, 4, 6, 4, 4, 4, 4, 0, 0, 0,
  301.         4, 4, 4, 4, 4, 4, 4, 4, 0, 4,
  302.         4, 4, 4, 0, 4, 4, 4, 4, 4, 4,
  303.         4, 4, 4, 0, 0, 4, 4, 4, 4, 0,
  304.         0, 4, 4, 4, 4, 4, 4, 0, 6, 4,
  305.         4, 2, 4, 4, 4, 4, 2, 4, 4, 4,
  306.         0, 4, 0, 0, 0, 0, 4, 4, 4, 4,
  307.         4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
  308.         4, 4
  309.     };
  310.     // Aircraft, boats, bicycles, trains
  311.     // and RC vehicles return zero tires
  312.     return tire_data[mid - 400];
  313. }
  314.  
  315. stock SS_GetTireSize(mid, tire, &Float:size)
  316. {
  317.     static const
  318.         Float:tire_size_R[] =
  319.     {
  320.         // Rear wheel size (from vehicles.ide)
  321.         0.7680, 0.7749, 0.6999, 1.1000, 0.6600, 0.6999, 2.2799, 1.0000, 1.0599, 0.7500,
  322.         0.8000, 0.6999, 0.6999, 0.7200, 0.7599, 0.6800, 0.8640, 0.0000, 0.6999, 0.6399,
  323.         0.7879, 0.6499, 0.6999, 0.6999, 0.9200, 0.0000, 0.6999, 0.9359, 0.9139, 0.6999,
  324.         0.0000, 1.0000, 1.2999, 1.2000, 0.8000, 1.1000, 0.6999, 1.0000, 0.6999, 0.6999,
  325.         0.6999, 0.0000, 0.6800, 1.0820, 1.5000, 0.6800, 0.0000, 0.0000, 0.4639, 0.0000,
  326.         1.1000, 0.7500, 0.0000, 0.0000, 0.0000, 1.2000, 0.8399, 0.5000, 0.7200, 0.6999,
  327.         0.0000, 0.6700, 0.4639, 0.5600, 0.0000, 0.0000, 0.6999, 0.6999, 0.6200, 0.0000,
  328.         0.8939, 0.6000, 0.0000, 0.0000, 0.6999, 0.6999, 0.0000, 0.7599, 0.6999, 0.6999,
  329.         0.6999, 0.0000, 0.6999, 0.6600, 0.0000, 0.6000, 1.5000, 0.0000, 0.0000, 0.8999,
  330.         0.9200, 0.6499, 0.6999, 0.0000, 0.8199, 0.9720, 0.6999, 0.0000, 0.7599, 0.8000,
  331.         0.8000, 0.0000, 0.8199, 0.8199, 0.6999, 0.8999, 0.7730, 0.6999, 0.8000, 0.0000,
  332.         0.0000, 0.0000, 0.0000, 0.0000, 1.1059, 1.1799, 0.7500, 0.7500, 0.6600, 0.0000,
  333.         0.0000, 0.6800, 0.6800, 0.6700, 1.0000, 0.9200, 0.6999, 0.6999, 0.8500, 0.6999,
  334.         0.4499, 1.2999, 1.0000, 0.6999, 0.6999, 0.7400, 0.6999, 0.0000, 0.0000, 0.0000,
  335.         0.6999, 1.0000, 0.7400, 0.6999, 1.0000, 0.6999, 0.6999, 0.6999, 0.0000, 0.6840,
  336.         0.7599, 0.7500, 0.8399, 0.0000, 0.8399, 0.6999, 1.5000, 1.5000, 0.7879, 0.6999,
  337.         0.8700, 0.6999, 0.6800, 0.0000, 0.0000, 0.6399, 0.6999, 0.6999, 0.6999, 0.0000,
  338.         0.0000, 0.2599, 0.5600, 1.1399, 0.5000, 0.6999, 0.6999, 0.0000, 1.0000, 0.8999,
  339.         0.7799, 0.6800, 0.7699, 0.7500, 1.1200, 0.7400, 0.6539, 0.6999, 0.8600, 0.7400,
  340.         0.0000, 1.1000, 0.0000, 0.0000, 0.0000, 0.0000, 0.6999, 0.6999, 0.6999, 0.9499,
  341.         0.6999, 1.3660, 0.6999, 0.6999, 0.6999, 0.6999, 0.6000, 0.6000, 0.6000, 0.7599,
  342.         0.3199, 0.6800
  343.        
  344.     };
  345.     if (tire & (e_TIRE_RR | e_TIRE_RL))
  346.     {
  347.         size = tire_size_R[mid - 400];
  348.         return 1;
  349.     }
  350.     static const
  351.         Float:tire_size_F[] =
  352.     {
  353.         // Front wheel size (from vehicles.ide)
  354.         0.7680, 0.7749, 0.6999, 1.1000, 0.6600, 0.6999, 2.2799, 1.0000, 1.0599, 0.7500,
  355.         0.8000, 0.6999, 0.6999, 0.7200, 0.7599, 0.6800, 0.8640, 0.0000, 0.6999, 0.6399,
  356.         0.7879, 0.6499, 0.6999, 0.6999, 0.8399, 0.0000, 0.6999, 0.9359, 0.9139, 0.6999,
  357.         0.0000, 1.0000, 1.2999, 1.2000, 0.7200, 1.1000, 0.6999, 1.0000, 0.6999, 0.6999,
  358.         0.6999, 0.0000, 0.6800, 1.0820, 1.5000, 0.6800, 0.0000, 0.0000, 0.4639, 0.0000,
  359.         1.1000, 0.6999, 0.0000, 0.0000, 0.0000, 1.2000, 0.8399, 0.5000, 0.7200, 0.6999,
  360.         0.0000, 0.6700, 0.4639, 0.7799, 0.0000, 0.0000, 0.6999, 0.6999, 0.6800, 0.0000,
  361.         0.8939, 0.6000, 0.0000, 0.0000, 0.6999, 0.6999, 0.0000, 0.7599, 0.6999, 0.6999,
  362.         0.6999, 0.0000, 0.6999, 0.6600, 0.0000, 0.6000, 1.5000, 0.0000, 0.0000, 0.8999,
  363.         0.9200, 0.6499, 0.6999, 0.0000, 0.8199, 0.9720, 0.6999, 0.0000, 0.7599, 0.8000,
  364.         0.8000, 0.0000, 0.8199, 0.8199, 0.6999, 0.8999, 0.7730, 0.6999, 0.8000, 0.0000,
  365.         0.0000, 0.0000, 0.0000, 0.0000, 1.1059, 1.1799, 0.7500, 0.7500, 0.6600, 0.0000,
  366.         0.0000, 0.6800, 0.6800, 0.6700, 1.1200, 0.9200, 0.6999, 0.6999, 0.8500, 0.6999,
  367.         0.4499, 0.6800, 0.5879, 0.6999, 0.6999, 0.7400, 0.6999, 0.0000, 0.0000, 0.0000,
  368.         0.6999, 1.0000, 0.7400, 0.6999, 1.0000, 0.6999, 0.6999, 0.6999, 0.0000, 0.6840,
  369.         0.7599, 0.7500, 0.8399, 0.0000, 0.8399, 0.6999, 1.5000, 1.5000, 0.7879, 0.6999,
  370.         0.8700, 0.6999, 0.6800, 0.0000, 0.0000, 0.6399, 0.6999, 0.6999, 0.5500, 0.0000,
  371.         0.0000, 0.2599, 0.4799, 1.1399, 0.5000, 0.6999, 0.6999, 0.0000, 1.0000, 0.8999,
  372.         0.7799, 0.6800, 0.7699, 0.6600, 1.1200, 0.7400, 0.6539, 0.6999, 0.8600, 0.7400,
  373.         0.0000, 1.1000, 0.0000, 0.0000, 0.0000, 0.0000, 0.6999, 0.6999, 0.6999, 0.9499,
  374.         0.6999, 1.3660, 0.6999, 0.6999, 0.6999, 0.6999, 0.6000, 0.6000, 0.6000, 0.7599,
  375.         0.3199, 0.6800
  376.     };
  377.     if (tire & (e_TIRE_FR | e_TIRE_FL))
  378.     {
  379.         size = tire_size_F[mid - 400];
  380.         return 1;
  381.     }
  382.     return 1;
  383. }
  384.  
  385. stock SS_GetTirePos(vid, &Float:px, &Float:py, &Float:pz, Float:ox, Float:oy, Float:oz, Float:matrix3x3[])
  386. {
  387.     GetVehiclePos(vid, px, py, pz);
  388.     px = px + ox * (1 - 2 * (matrix3x3[4] + matrix3x3[7])) + oy * (2 * (matrix3x3[1] + matrix3x3[8])) + oz * (2 * (matrix3x3[2] - matrix3x3[6])),
  389.     py = py + ox * (2 * (matrix3x3[1] - matrix3x3[8])) + oy * (1 - 2 * (matrix3x3[0] + matrix3x3[7])) + oz * (2 * (matrix3x3[5] + matrix3x3[3])),
  390.     pz = pz + ox * (2 * (matrix3x3[2] + matrix3x3[6])) + oy * (2 * (matrix3x3[5] - matrix3x3[3])) + oz * (1 - 2 * (matrix3x3[0] + matrix3x3[4]));
  391.     return 1;
  392. }
  393.  
  394. stock SS_GetVehicleRotationMatrix(vid, Float:matrix3x3[])
  395. {
  396.     new
  397.         Float:qw,
  398.         Float:qx,
  399.         Float:qy,
  400.         Float:qz;
  401.     GetVehicleRotationQuat(vid, qw, qx, qy, qz);
  402.     matrix3x3[0] = qx * qx, matrix3x3[1] = qx * qy, matrix3x3[2] = qx * qz,
  403.     matrix3x3[3] = qx * qw, matrix3x3[4] = qy * qy, matrix3x3[5] = qy * qz,
  404.     matrix3x3[6] = qy * qw, matrix3x3[7] = qz * qz, matrix3x3[8] = qz * qw;
  405.     return 1;
  406. }
  407.  
  408. /*
  409. This function checks if two line segments intersect (2D space)
  410. */
  411. stock SS_SegmentsIntersect_2D(Float:x1, Float:y1, Float:x2, Float:y2, Float:x3, Float:y3, Float:x4, Float:y4)
  412. {
  413.     new
  414.         Float:xA = x2 - x1,
  415.         Float:yA = y2 - y1,
  416.         Float:xB = x4 - x3,
  417.         Float:yB = y4 - y3,
  418.         Float:d  = xA * yB - yA * xB;
  419.     if (!d)
  420.     {
  421.         // Lines are parallel, or one or
  422.         // both segments are zero-length
  423.         return 0;
  424.     }
  425.     new
  426.         Float:xC = x3 - x1,
  427.         Float:yC = y3 - y1,
  428.         Float:pA = (xC * yB - yC * xB) / d,
  429.         Float:pB = (xC * yA - yC * xA) / d;
  430.     if (pA < 0 || pA > 1 || pB < 0 || pB > 1)
  431.     {
  432.         return 0;
  433.     }
  434.     // Compute the intersection point
  435.     // xi = x1 + pA * xA
  436.     // yi = y1 + pA * yA
  437.     return 1;
  438. }
  439.  
  440. /*
  441. This function computes the shortest distance between two lines (3D space)
  442. */
  443. stock SS_DistanceLineToLine_3D(Float:x1, Float:y1, Float:z1, Float:x2, Float:y2, Float:z2, Float:x3, Float:y3, Float:z3, Float:x4, Float:y4, Float:z4, &Float:distance)
  444. {
  445.     new
  446.         Float:ux = x2 - x1,
  447.         Float:uy = y2 - y1,
  448.         Float:uz = z2 - z1,
  449.         Float:vx = x4 - x3,
  450.         Float:vy = y4 - y3,
  451.         Float:vz = z4 - z3,
  452.         Float:wx = x1 - x3,
  453.         Float:wy = y1 - y3,
  454.         Float:wz = z1 - z3,
  455.         Float:uu = ux * ux + uy * uy + uz * uz,
  456.         Float:uv = ux * vx + uy * vy + uz * vz,
  457.         Float:uw = ux * wx + uy * wy + uz * wz,
  458.         Float:vv = vx * vx + vy * vy + vz * vz,
  459.         Float:vw = vx * wx + vy * wy + vz * wz,
  460.         Float:d  = uu * vv - uv * uv,
  461.         Float:pA = (uv * vw - vv * uw) / d,
  462.         Float:pB = (uu * vw - uv * uw) / d,
  463.         // The difference of the two closest points
  464.         Float:dx = wx + pA * ux - pB * vx,
  465.         Float:dy = wy + pA * uy - pB * vy,
  466.         Float:dz = wz + pA * uz - pB * vz;
  467.     distance = floatsqroot(dx * dx + dy * dy + dz * dz);
  468.     return 1;
  469. }
  470.  
  471. Public SpikeStrip_Create_MA(mid, Float:x, Float:y, Float:z, Float:a)
  472. {
  473.     new
  474.         idx = Iter_Free(g_Spike);
  475.     if (idx != -1)
  476.     {
  477.         new
  478.             Float:adjust,
  479.             Float:length;
  480.         switch (mid)
  481.         {
  482.             case 2892:
  483.             {
  484.                 length = 5.0;
  485.             }
  486.             case 2899:
  487.             {
  488.                 length = 2.5;
  489.                 adjust = 0.118;
  490.             }
  491.             default:
  492.             {
  493.                 return INVALID_OBJECT_ID;
  494.             }
  495.         }
  496.         new
  497.             id = CreateObject(mid, x, y, z + adjust, 0.0, 0.0, a - 90.0);
  498.         if (id != INVALID_OBJECT_ID) // Check if the object exists
  499.         {
  500.             a = -a;
  501.             Iter_Add(g_Spike, idx);
  502.             g_SpikeStrip[idx] = id;
  503.  
  504.             #if SS_LINE_SEGMENTS == 1
  505.                
  506.             g_Spike_x1[idx] = x + length * floatsin(a - 90.0, degrees);
  507.             g_Spike_y1[idx] = y + length * floatcos(a - 90.0, degrees);
  508.             g_Spike_x2[idx] = x - length * floatsin(a - 90.0, degrees);
  509.             g_Spike_y2[idx] = y - length * floatcos(a - 90.0, degrees);
  510.  
  511.             #endif
  512.            
  513.             #if SS_LINE_SEGMENTS >= 2
  514.            
  515.             new
  516.                 value;
  517.             mid != 2892 && (value = 10) || (value = 5);
  518.             g_Spike_x1[idx] = x + length * floatsin(a - (90.0 + value), degrees);
  519.             g_Spike_y1[idx] = y + length * floatcos(a - (90.0 + value), degrees);
  520.             g_Spike_x3[idx] = x + length * floatsin(a - (90.0 - value), degrees);
  521.             g_Spike_y3[idx] = y + length * floatcos(a - (90.0 - value), degrees);
  522.            
  523.             #if SS_LINE_SEGMENTS == 2
  524.            
  525.             g_Spike_x2[idx] = x - length * floatsin(a - (90.0 + value), degrees);
  526.             g_Spike_y2[idx] = y - length * floatcos(a - (90.0 + value), degrees);
  527.             g_Spike_x4[idx] = x - length * floatsin(a - (90.0 - value), degrees);
  528.             g_Spike_y4[idx] = y - length * floatcos(a - (90.0 - value), degrees);
  529.  
  530.             #endif
  531.  
  532.             #if SS_LINE_SEGMENTS == 4
  533.  
  534.             g_Spike_x2[idx] = x - length * floatsin(a - (90.0 - value), degrees);
  535.             g_Spike_y2[idx] = y - length * floatcos(a - (90.0 - value), degrees);
  536.             g_Spike_x4[idx] = x - length * floatsin(a - (90.0 + value), degrees);
  537.             g_Spike_y4[idx] = y - length * floatcos(a - (90.0 + value), degrees);
  538.  
  539.             #endif
  540.            
  541.             #endif
  542.  
  543.             g_Spike_zA[idx] = z;
  544.             return idx;
  545.         }
  546.     }
  547.     return INVALID_OBJECT_ID;
  548. }
  549.  
  550. Public SpikeStrip_Delete_MA(sid)
  551. {
  552.     if (Iter_Contains(g_Spike, sid))
  553.     {
  554.         Iter_Remove(g_Spike, sid);
  555.         DestroyObject(g_SpikeStrip[sid]);
  556.     }
  557.     return 1;
  558. }
  559.  
  560. Public SpikeStrip_DeleteAll_MA()
  561. {
  562.     foreach (new i : g_Spike)
  563.     {
  564.         DestroyObject(g_SpikeStrip[i]);
  565.         Iter_SafeRemove(g_Spike, i, i);
  566.     }
  567.     return 1;
  568. }
  569.  
  570. Public SpikeStrip_IsValid_MA(sid)
  571. {
  572.     return Iter_Contains(g_Spike, sid);
  573. }
  574.  
  575. Public SpikeStrip_SetGhost_MA(pid, bool:toggle)
  576. {
  577.     g_GetVehicleID[pid] = 0;
  578.     g_GetGhostMode{pid} = toggle;
  579.     return 1;
  580. }
  581.  
  582. Public SpikeStrip_IsGhost_MA(pid)
  583. {
  584.     return g_GetGhostMode{pid};
  585. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement