PDA

Просмотр полной версии : [Function] processLineOfSight



Seregamil
12.06.2014, 07:56
Функция, рисующая луч в игровом мире от одной точки до другой и возвращающая позицию, в которой луч столкнулся с объектом/машиной/игроком.
Недопрототип функции в МТА: https://wiki.multitheftauto.com/wiki/ProcessLineOfSight , но этот недопрототип полезен и в САМПе.

Аргументы:


processLineOfSight(
//координаты старта
Float: start_x,
Float: start_y,
Float: start_z,

//координаты конца, в них же записываются координаты последней доступной точки
&Float: end_x,
&Float: end_y,
&Float: end_z,

//параметры проверки
bool: check_vehicles, //true - проверять машины, false - пропускать машины
bool: check_players ) //true - проверять игроков, false - пропускать игроков


Функция:


#define radiusCollision 3.0

processLineOfSight( Float: start_x, Float: start_y, Float: start_z, &Float: end_x, &Float: end_y, &Float: end_z, bool: check_vehicles, bool: check_players ){//by Seregamil
new distance_between_points = floatround( VectorSize( end_x - start_x, end_y - start_y, end_z - start_z ) );
if( distance_between_points == 0 )
return ;

new Float: pack_pos_x = floatdiv( end_x - start_x, float( distance_between_points ) ),
Float: pack_pos_y = floatdiv( end_y - start_y, float( distance_between_points ) ),
Float: pack_pos_z = floatdiv( end_z - start_z, float( distance_between_points ) ),
Float: map_z = 0.0,
j = -1, Float: pos_x, Float: pos_y, Float: pos_z , i = 1;

do{
start_x += pack_pos_x;
start_y += pack_pos_y;
start_z += pack_pos_z;

if( check_vehicles ){
for( ; i != MAX_VEHICLES; i++ ){
if( !IsValidVehicle( i ) ) continue;
GetVehiclePos( i, pos_x, pos_y, pos_z );
if( VectorSize( pos_x - start_x, pos_y - start_y, pos_z - start_z ) > radiusCollision ) continue;

end_x = start_x;
end_y = start_y;
end_z = start_z;

return ;
}
}

if( check_players ){
for( i = GetMaxPlayers() - 1; i != -1; i-- ){
if( IsPlayerNPC( i ) || !IsPlayerConnected( i ) ) continue;
GetPlayerPos( i, pos_x, pos_y, pos_z );
if( !IsPlayerInRangeOfPoint( i , radiusCollision, pos_x, pos_y, pos_z ) ) continue;

end_x = start_x;
end_y = start_y;
end_z = start_z;

return ;
}
}

MapAndreas_FindZ_For2DCoord( start_x, start_y, map_z );

if( map_z < start_z )
continue;

end_x = start_x;
end_y = start_y;
end_z = start_z;
break;
}
while( ++j < distance_between_points );
}


Дополнительные функции, используемые в системе:
native IsValidVehicle(vehicleid);
Плагин MapAndreas: http://forum.sa-mp.com/showthread.php?t=275492

http://breedpmnr.ru/i/C613679

Пример использования:

new Float:x = 0.0, Float:y = 0.0, Float:z = 0.0, Object = CreateObject( 2000, -10.4548,55.2839,12.1676, 0.0, 0.0, 0.0 );
processLineOfSight( -10.4548,55.2839,12.1676, x,y,z, false, true );
MoveObject(Object, x,y,z,3.0);

Автор: Seregamil

Daniel_Cortez
12.06.2014, 16:20
for( i = 0; i != MAX_VEHICLES; i++ )
Fail.
Страдает стиль задания имён в идентификаторах (processLineOfSight - другие скриптеры могут путаться при использовании этой функции).
IsValidVehicle можно было объявить ещё перед началом функции (пример (http://pro-pawn.ru/showthread.php?8347)). Не то, чтобы обязательно, но не помешало бы.
Для чего функции присвоен атрибут "public"? Возвращение функцией значений через SetTimer/SetTimerEx/CallLocalFunction невозможно (да и зачем оно вообще?)
Часть табуляции сделана табами, ещё часть - пробелами, из-за чего местами табуляция неправильная. Сделай уже выбор между пробелами и табами.

^_^
12.06.2014, 17:34
Хорошая задумка - молодец, правда насчёт оформления кода я соглашусь с постом выше... Собственно, недостатки которые заметил я: (не воспринимай слишком критично, но мы же идеалисты : 3)

1) Использование ненужной функции IsValidVehicle. Лично я использую уже задекларированую - GetVehicleModel. Она также возвращает нуль если машина не создана.

2) Отсутствии в функции параметра точности (можно по дефолту сделать 3.0)
VectorSize( pos_x - start_x, pos_y - start_y, pos_z - start_z ) > 3.0
!IsPlayerInRangeOfPoint( i , 3.0, pos_x, pos_y, pos_z )
Мне лично кажется, что 3.0 не очень хороший радиус, особенно по оси Z, тебе виднее...

Seregamil
12.06.2014, 19:50
Код:

for( i = 0; i != MAX_VEHICLES; i++ )

Fail.
Чего тебе тут ненравится?

Страдает стиль задания имён в идентификаторах (processLineOfSight - другие скриптеры могут путаться при использовании этой функции).
всмысле - путаться?

Для чего функции присвоен атрибут "public"? Возвращение функцией значений через SetTimer/SetTimerEx/CallLocalFunction невозможно (да и зачем оно вообще?)
первоначальный прототип функции предназначался немного для другого.

Часть табуляции сделана табами, ещё часть - пробелами, из-за чего местами табуляция неправильная. Сделай уже выбор между пробелами и табами.
А вот это уже косяк сайта, весь мой код сделан табами.

1) Использование ненужной функции IsValidVehicle. Лично я использую уже задекларированую - GetVehicleModel. Она также возвращает нуль если машина не создана.
код для меня - логически понятнее.

2) Отсутствии в функции параметра точности (можно по дефолту сделать 3.0)
VectorSize( pos_x - start_x, pos_y - start_y, pos_z - start_z ) > 3.0
!IsPlayerInRangeOfPoint( i , 3.0, pos_x, pos_y, pos_z )
Мне лично кажется, что 3.0 не очень хороший радиус, особенно по оси Z, тебе виднее...
а вот тут пожалуй добавлю макрос, сами ставьте нужный вам радиус.

DeimoS
12.06.2014, 19:59
Чего тебе тут ненравится?

ID авто в SA-MP начинаются с единицы. Нулевой ID - невалидный

Seregamil
12.06.2014, 20:05
Обновил

Salvacore
13.06.2014, 01:46
Если ты код написал для себя, зачем выкладывать -_- ?

KShaddix
13.06.2014, 03:05
Если ты код написал для себя, зачем выкладывать -_- ?

Не хватайся за куски фраз. Он не имел в виду, что писал лично для себя. По сути дела, он правильней сделал для восприятия аудитории, смотрящей со стороны, потому что IsValidVehicle использовал по назначению.

Salvacore
13.06.2014, 03:16
Не хватайся за куски фраз. Он не имел в виду, что писал лично для себя. По сути дела, он правильней сделал для восприятия аудитории, смотрящей со стороны, потому что IsValidVehicle использовал по назначению.
Простите пожалуйста.
Но факт остаётся фактом.

Seregamil
13.06.2014, 05:48
Если ты код написал для себя, зачем выкладывать -_- ?

Что для людей логически понятней?


if( !IsValidVehicle( vehicleid ) )



if( !GetVehicleModel( vehicleid ) )

DeimoS
13.06.2014, 10:02
Простите пожалуйста.
Но факт остаётся фактом.

То есть, теперь надо использовать функции так, как нравится другим, а не по назначению, иначе лучше не выкладывать код? Сам то понял к чему придрался?
IsValidVehicle (http://wiki.sa-mp.com/wiki/IsValidVehicle) - Check if a vehicle is created.
GetPlayerVehicleID (http://wiki.sa-mp.com/wiki/GetPlayerVehicleID) - This function gets the ID of the vehicle the player is currently in.
Использование какой функции поможет понять смысл кода человеку, который не читал описание системы, а лишь просто попал на код? Вы и

public ...;
public ...
Тоже так же используете, заставляя бедные умы новичков путаться. Используя функции не по назначению вы так же убиваете читаемость кода, как если бы писали название функций/переменных транслитом или же не использовали табуляцию. Только вот первый случай вы встречаете адекватно, а за остальные случаи сразу называете код дерьмом и человека нубом. Как-то это неправильно

Salvacore
13.06.2014, 15:39
То есть, теперь надо использовать функции так, как нравится другим, а не по назначению, иначе лучше не выкладывать код? Сам то понял к чему придрался?
1)Надо писать функции так что бы было понятно людям.(Есстессна как хотите, моя точка зрения)[И не надо говорить типа я что то не понятно пишу, я за это получаю люли :3 ]
2)Выкладывать плюшки всегда хорошо :3
3)Мне просто не понравилось [ playerid ](Если это не выпендрёж то ладно)
4)Закроем тему

Seregamil
13.06.2014, 19:18
1)Надо писать функции так что бы было понятно людям.(Есстессна как хотите, моя точка зрения)[И не надо говорить типа я что то не понятно пишу, я за это получаю люли :3 ]
2)Выкладывать плюшки всегда хорошо :3
3)Мне просто не понравилось [ playerid ](Если это не выпендрёж то ладно)
4)Закроем тему

Если приебаться не можешь к коду, то лучше промолчал бы вообще.

Salvacore
13.06.2014, 19:21
Если приебаться не можешь к коду, то лучше промолчал бы вообще.
Прикопался к коду я в скайпе другому человеку.

Seregamil
13.06.2014, 19:44
Прикопался к коду я в скайпе другому человеку.

А чего ты к автору кода то не прикапываешься

Salvacore
13.06.2014, 20:01
А чего ты к автору кода то не прикапываешься
Да-к всё уже написали.