Прокол шины (1) и двоичные операции - Форум Cheat-Master.ru
  • Страница 1 из 1
  • 1
Модератор форума: Phoenixxx_Czar, Getbackthere, [CM]OlegEhtler  
Форум » Pawno программирование SAMP » Уроки | FAQ » Прокол шины (1) и двоичные операции
Прокол шины (1) и двоичные операции
BaH_Warn Дата: Понедельник, 25.05.2015, 07:10 | Сообщение # 1
Боец
Сообщений: 69
Статус: Offline
Приветствую! Сегодня я постараюсь вам рассказать, как можно сделать солидную системку при использовании не сложных, а самое главное понятных алгоритмов.
Система позволяет вам проколоть колесо машины и тем самым помочь отыграть РП ситуацию. Также можно произвести небольшие изменения в системе и заставить систему уже не ломать колёса, а чинить! Тем самым Вы прекрасно преобразите работу механика на своём проекте.

Небольшое вступление:

Разработчики сделали эту систему в виде двоичного числа: у нас 4 колеса и следовательно у нас 2^4 комбинаций, а из школьного курса информатики мы знаем, что в комбинациях от 0b0000 до 0b1111 ровно 16 комбинаций. Как вы уже должны догадываться, что 4 числа у нас не просто так.
Каждое число соответствует своему колесу. Например, если мы запишем в переменную с колёсами число 0b0001, то это будет обозначать, что проколото заднее правое колесо (от водителя):
Код
o-o  
  | |  
  o-x  

Пояснение: тут "х" - проколотое колесо

И следовательно алгоритм действий очень прост: нам нужно разложить число на "0" и "1" и просто проверить. Если "0", то проколоть, иначе - сказать об неверном действии игроку (пользвателю). Реализация алгоритма представлена ниже
Код команды:
Код
CMD:useneedle(playerid, params[])  
{  
     if(IsPlayerInAnyVehicle(playerid)) return SendClientMessage(playerid, COLOR_GREY, "Вы не можете сделать это из машины");  
     new vehicleid = GetVehicleByPlayer(playerid);  
     if(vehicleid == -1) return SendClientMessage(playerid, COLOR_GREY, "Вы не рядом с машиной");  
     new tire = GetTireByPlayer(playerid, vehicleid);  
     if(tire == -1) return SendClientMessage(playerid, COLOR_GREY, "Вы не у колеса");  
         new Panel, Door, Light, Tires;  
         if(Tires != 0) return SendClientMessage(playerid, COLOR_GREY, "У этой машины уже проколото колесо");  
       
         GetVehicleDamageStatus(vehicleid, Panel, Door, Light, Tires); //Получаем информацию о состоянии деталей машины  
     new bool:tirestatus[4]; // Создаём переменные со статусом  
     new Tires_temp = Tires; //Нужна переменная для перевода её в двоичную систему  
     for(new i = 0; i < 4; i++) // цикл для перевода в двоичную систему смотреть [I]пометку 1[/I] ниже  
     {  
         if(Tires_temp % 2 == 1) tirestatus[i] = true;  
         Tires_temp = Tires_temp / 2;  
     }  
     switch (tire) //Смотри пометку 2 ниже  
     {  
         case 4:  
         {  
             if(tirestatus[0]) return SendClientMessage(playerid, COLOR_GREY, "Колесо уже проколото");  
             Tires += 0b1000;   
         }  
         case 3:  
         {  
             if(tirestatus[1]) return SendClientMessage(playerid, COLOR_GREY, "Колесо уже проколото");  
             Tires += 0b0100;  
         }  
         case 2:  
         {  
             if(tirestatus[2]) return SendClientMessage(playerid, COLOR_GREY, "Колесо уже проколото");  
             Tires += 0b0010;  
         }  
         case 1:  
         {  
             if(tirestatus[3]) return SendClientMessage(playerid, COLOR_GREY, "Колесо уже проколото");  
             Tires += 0b0001;  
         }  
     }  
     UpdateVehicleDamageStatus(vehicleid, Panel, Door, Light, Tires); // Сохраняем статус авто  
     return 1;  
}  

Коды функций:
Код
//Нам нужна машина ближайшая к игроку  
stock GetVehicleByPlayer(playerid) //вернёт ид авто в радиусе 2.5, если авто нет, то вернёт -1   
{  
     new vehicleid = -1;  
     new Float:carX, Float:carY, Float:carZ;  
     for(new i = 0; i < MAX_VEHICLES; i++)  
     {  
         GetVehiclePos(i, carX, carY, carZ);  
         if(IsPlayerInRangeOfPoint(playerid, 2.4, carX, carY,carZ)) {  
             vehicleid = i;  
             break;  
         }  
     }  
     return vehicleid;  
}  

Помимо машины, нам нужно и колесо.
Высчитывал на среднем значении нескольких, разных по размеру машин.
Код
stock GetTireByPlayer(playerid, vehicleid)  
{  
     new Float:x, Float:y, Float:z, Float:carX, Float:carY, Float:carZ;  
     GetPlayerPos(playerid, x, y, z);  
     GetVehiclePos(vehicleid, carX, carY, carZ);  
       
     new totalX;  
     totalX = floatround(x - carX, floatround_floor);  
     new totalY;  
     totalY = floatround(y- carY, floatround_floor);  
       
     //более точный вариант  
       
     /*if ((1.45 <= totalX <= 1.5) && (-2.0 <= totalY <= -1.95)) return 1;    // 1  
     else if ((1.52 <= totalX <= 1.57) && (1.56 <= totalY <= 1.61)) return 2;    //2  
     else if ((-1.56 <= totalX <= -1.51) && (-173 <= totalY <= -1.68)) return 3;    //3  
     else if ((-1.46 <= totalX <= -1.41) && (1.87 <= totalY <= 1.92)) return 4;    //4  
     else return -1;*/  
       

         //логически ужасный вариант, но работает. Его надо просто принять таким.  
     if ((totalX >= 1) && (totalY <= -1)) return 1;    // 1  
     else if ((totalX >= 1) && (totalY >= 1)) return 2;    //2  
     else if ((totalX <= -1) && (totalY <= -1)) return 3;    //3  
     else if ((totalX <= -1) && (totalY >= 1)) return 4;    //4  
     else return -1;  
}  

Пометка [1]:

Делим число на основание системы счисления и записываем остатки - вот так переводится число из десятичной в любую.
Тут мы делим число на 2 и проверяем на остатки. Так как в 2ой системе есть 0 и 1, а т.е. либо делится нацело (без остатка), либо остаток 1, который будет обозначать, что оно занято.

Пометка [2]:

Тут мы уже знаем колесо, с которым работает игрок и просто прибавляем число в двоичной системе!
Т.е. 0b0101 + 0b1010 = 1111
проще говоря "производим наложение"
Кстати. Проверка перед сложением позволяет избежать наложения 1 на 1, что в результате будет давать 0.
Подведём итоги:

Если что-то не понятно, то приношу свои искренние извинения, так как старался объяснить всё примитивно и понятно.
Для спецов: Коллеги, прошу не обращать внимания на чересчур примитивный код. Данный код подстраивался под начинающего кодера и несёт в себе исключительно типизированные конструкции.
[CM]Enrique Дата: Четверг, 28.05.2015, 12:29 | Сообщение # 2
Любитель
Сообщений: 42
Статус: Offline
Спасибо)
Форум » Pawno программирование SAMP » Уроки | FAQ » Прокол шины (1) и двоичные операции
  • Страница 1 из 1
  • 1
Поиск:
Статистика Форума
Лучшие пользователи
Admin [39113]

GеNius [7209]

[CM]Russel [5557]

kenlo763 [4952]

[CM]AGRESSOR [4639]

Snake_Firm [4452]

Сэс [4416]

Artem_Buero [4223]

[CM]Durman [3204]

[CM]Рафаэль [3080]

iMaddy [2855]

sky_Woker [2854]

getrekt [2745]

Новые пользователи
pokotiloroman91 [18:24]

stephensh5 [12:00]

calliesv7 [06:11]

louqm16 [22:14]

artushak [16:32]

Kingpolker [15:42]

leeyv11 [15:12]

Trappa17 [01:00]

Djamalchik [16:40]

ajeense [14:24]

654470559 [08:55]

Newtone [03:01]

godspeed [21:31]