Автор Тема: Расширение классов  (Прочитано 548 раз)

Оффлайн xanser

  • Главный Модератор
  • Постоялец
  • *****
  • Сообщений: 521
  • Репутация: +56/-0
  • Есть такая профессия - на работе сидеть
    • Просмотр профиля
Расширение классов
« : Январь 06, 2018, 05:10:43 pm »
В этом посте DK показывал пример, как расширить класс, "прикрепив" к нему дополнительные атрибуты. Насколько я понял, существующие пулы при этом не расширяются.
Код: C++
  1.     #include <plugin.h>
  2.      
  3.     using namespace plugin;
  4.      
  5.     class VehicleExtendedExample {
  6.     public:
  7.         class VehicleComponents { // Класс, который представляет наши данные (можно сказать, что эти данные "прикрепляются" к структуре транспорта)
  8.         public:
  9.             RwFrame *m_pDoorLF;
  10.             RwFrame *m_pDoorRF;
  11.             RwFrame *m_pDoorLR;
  12.             RwFrame *m_pDoorRR;
  13.      
  14.             VehicleComponents(CVehicle *) { // Конструктор этого класса будет вызван при вызове конструктора транспорта (CVehicle::CVehicle)
  15.                 m_pDoorLF = m_pDoorRF = m_pDoorLR = m_pDoorRR = nullptr; // устанавливаем все указатели в 0
  16.             }
  17.         };
  18.      
  19.         VehicleExtendedExample() {
  20.             static VehicleExtendedData<VehicleComponents> vehComps; // Создаем экземпляр нашего расширения. vehComps - это переменная, через которую мы будем
  21.                                                                     // обращаться к нашим данным (используя метод Get(CVehicle *транспорт) )
  22.      
  23.             Events::vehicleSetModelEvent += [](CVehicle *vehicle, int modelIndex) { // Выполняем нашу функцию, когда игра устанавливает модель транспорту
  24.                 if (vehicle->m_pRwClump) { // Если создан графический обьект модели (RpClump)
  25.                     vehComps.Get(vehicle).m_pDoorLF = CClumpModelInfo::GetFrameFromName(vehicle->m_pRwClump, "door_lf_dummy"); // Находим компоненты в иерархии
  26.                     vehComps.Get(vehicle).m_pDoorRF = CClumpModelInfo::GetFrameFromName(vehicle->m_pRwClump, "door_rf_dummy"); // и записываем их в наш класс
  27.                     vehComps.Get(vehicle).m_pDoorLR = CClumpModelInfo::GetFrameFromName(vehicle->m_pRwClump, "door_lr_dummy");
  28.                     vehComps.Get(vehicle).m_pDoorRR = CClumpModelInfo::GetFrameFromName(vehicle->m_pRwClump, "door_rr_dummy");
  29.                 }
  30.                 else // иначе устанавливаём всё в 0
  31.                     vehComps.Get(vehicle).m_pDoorLF = vehComps.Get(vehicle).m_pDoorRF = vehComps.Get(vehicle).m_pDoorLR = vehComps.Get(vehicle).m_pDoorRR = nullptr;
  32.             };
  33.      
  34.             Events::vehicleRenderEvent += [](CVehicle *vehicle) { // Выполняем нашу функцию, когда игра рендерит транспорт
  35.                 if (vehComps.Get(vehicle).m_pDoorLF)
  36.                     vehComps.Get(vehicle).m_pDoorLF->modelling.pos.z = 1.0f; // Сдвигаем компонент вверх
  37.                 if (vehComps.Get(vehicle).m_pDoorRF)
  38.                     vehComps.Get(vehicle).m_pDoorRF->modelling.pos.z = 1.0f;
  39.                 if (vehComps.Get(vehicle).m_pDoorLR)
  40.                     vehComps.Get(vehicle).m_pDoorLR->modelling.pos.z = 1.0f;
  41.                 if (vehComps.Get(vehicle).m_pDoorRR)
  42.                     vehComps.Get(vehicle).m_pDoorRR->modelling.pos.z = 1.0f;
  43.             };
  44.         }
  45.     } vehicleExtendedExample;

DK, можешь на простом примере показать общий принцип расширения классов через прикрепление новых атрибутов. К примеру, есть условный класс
Код: C++
  1. class CVector {
  2. public:
  3.     float x;
  4.     float y;
  5.     CVector();
  6. } vector2d[100];

И есть, например, пул таких координат по определенному адресу памяти, где идет по порядку vector2d[0].x, veсtor2d[0].y, vector2d[1].x, veсtor2d[1].y, vector2d[2].x, veсtor2d[2].y...
Как к этому классу "прикрепить" еще свою координату float z, чтобы обращаться уже к vector2d.x, vector2d.y, vector3d.Get(vector2d).z и не повредить существующий пул. Пример не связан с игрой.

Оффлайн DK

  • Новичек
  • **
  • Сообщений: 229
  • Репутация: +319/-0
    • dk22pac
    • Просмотр профиля
Re: Расширение классов
« Ответ #1 : Январь 09, 2018, 10:41:26 pm »
xanser, В C++ нет расширения классов в "рантайме", по крайней мере, встроенного в язык (стандарт).
То, что есть в plugin-sdk - это вещь конкретно заточенная под пулы в GTA.
Тут реализация зависит от того, где это надо применить. Если покажешь конкретно - возможно, смогу помочь.

PS vector2d[100] - это не пул, а массив. См. Объектный пул
« Последнее редактирование: Январь 09, 2018, 10:55:12 pm от DK »
Plugin-SDK https://github.com/DK22Pac/plugin-sdk

Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv

Оффлайн xanser

  • Главный Модератор
  • Постоялец
  • *****
  • Сообщений: 521
  • Репутация: +56/-0
  • Есть такая профессия - на работе сидеть
    • Просмотр профиля
Re: Расширение классов
« Ответ #2 : Январь 10, 2018, 04:22:39 am »
Мне интересен сам используемый прием. Поэтому хотелось пошагово на простом примере сначала понять суть, за счет чего происходит "прикрепление", и какой синтаксис должен быть от начала до конца. Если смотреть пример по CVehicle, там код не полностью приведен в сообщении, для меня остались пробелы в таких местах:
Код: C++
  1. VehicleComponents(CVehicle *) { // Конструктор этого класса будет вызван при вызове конструктора транспорта (CVehicle::CVehicle)
Не очень понятно, почему происходит вызов нового конструктора при вызове стандартного CVehicle::CVehicle
Код: C++
  1. static VehicleExtendedData<VehicleComponents> vehComps;
Не описано, что такое VehicleExtendedData
Код: C++
  1. vehComps.Get(vehicle).m_pDoorLF
Как выглядит функция Get() ?
Видимо ответы в самом sdk, но так тяжело изучать что-то, копая чужой код. Вот и хотелось на отвлеченном примере понять сам принцип, а потом уже идти от простого к сложному.
« Последнее редактирование: Январь 10, 2018, 04:36:15 am от xanser »

Оффлайн DK

  • Новичек
  • **
  • Сообщений: 229
  • Репутация: +319/-0
    • dk22pac
    • Просмотр профиля
Re: Расширение классов
« Ответ #3 : Январь 12, 2018, 11:06:19 am »
Я тебя не совсем понимаю. Если тебе надо это для GTA - почему не использовать готовое решение?
Plugin-SDK https://github.com/DK22Pac/plugin-sdk

Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv

Оффлайн xanser

  • Главный Модератор
  • Постоялец
  • *****
  • Сообщений: 521
  • Репутация: +56/-0
  • Есть такая профессия - на работе сидеть
    • Просмотр профиля
Re: Расширение классов
« Ответ #4 : Январь 12, 2018, 11:42:35 am »
Может захочется еще что-то расширить кроме машин, например CPed, допустим добавить "голод". Да и просто понимать, как сделано, может где еще пригодится. Форум-то для того и нужен, чтобы научиться, а не только брать чужое. Если будет желание, опиши хотя бы последовательность действий, хотя и за твой пример уже спасибо.

Оффлайн DK

  • Новичек
  • **
  • Сообщений: 229
  • Репутация: +319/-0
    • dk22pac
    • Просмотр профиля
Re: Расширение классов
« Ответ #5 : Январь 12, 2018, 02:18:18 pm »
xanser, сейчас в sdk работают расширения для CPed, CVehicle и CObject.
Пример для обьектов (см. спойлер)
« Последнее редактирование: Январь 12, 2018, 02:20:57 pm от DK »
Plugin-SDK https://github.com/DK22Pac/plugin-sdk

Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv

Оффлайн xanser

  • Главный Модератор
  • Постоялец
  • *****
  • Сообщений: 521
  • Репутация: +56/-0
  • Есть такая профессия - на работе сидеть
    • Просмотр профиля
Re: Расширение классов
« Ответ #6 : Январь 16, 2018, 04:24:02 am »
Последний вопрос - функция Get() получает объект перебором всех существующих, пока не найдет совпадение, или сразу выхватывает нужного?

Оффлайн DK

  • Новичек
  • **
  • Сообщений: 229
  • Репутация: +319/-0
    • dk22pac
    • Просмотр профиля
Re: Расширение классов
« Ответ #7 : Январь 16, 2018, 07:54:31 am »
Цитировать
сразу выхватывает нужного
Plugin-SDK https://github.com/DK22Pac/plugin-sdk

Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv