Статистика ( общая по моделям ), шт.
Подбираемый фонарик v 2.5
Подбираемый фонарик v 2.5
Подбираемый фонарик v 2.5
Автор / ы урока : Дядя Миша Просмотров : 2180 ( +2 ) Прислал / (а) : Streit Дата создания : 07.04.2011 21:00:34 Источник : http://www.half-life.ru/forum Рейтинг : ( 5 ) Поделиться :
Имеются следующие переводы : |
русский |
Ниже представлен код подбираемого фонарика, код разработан BUzer, дополнения и поправки - мои (G-Cont).
Для начала сделаем саму подбираемую ентитю. Для этого откроем items.cpp и внесем туда код нового предмета - item_flashlight
(можно в конец файла).
class CItemFlashlight : public CItem
{
void Spawn( void )
{
Precache( );
SET_MODEL(ENT(pev), "models/w_flashlight.mdl");
CItem::Spawn( );
}
void Precache( void )
{
PRECACHE_MODEL ("models/w_flashlight.mdl");
PRECACHE_SOUND( "items/gunpickup2.wav" );
}
BOOL MyTouch( CBasePlayer *pPlayer )
{
if ( pPlayer->pev->weapons & (1<<WEAPON_FLASHLIGHT) )
return FALSE;
pPlayer->pev->weapons |= (1<<WEAPON_FLASHLIGHT);
MESSAGE_BEGIN( MSG_ONE, gmsgItemPickup, NULL, pPlayer->pev );
WRITE_STRING( STRING(pev->classname) );
MESSAGE_END();
EMIT_SOUND_SUIT( pPlayer->edict(), "items/gunpickup2.wav" );
return TRUE;
}
};
LINK_ENTITY_TO_CLASS(item_flashlight, CItemFlashlight);
Теперь нам нужно задекларировать переменную weapon_flashlight в системе
Для этого откройте weapons.h и cdll_dll.h и добавьте в каждый следующую строку
#define WEAPON_FLASHLIGHT 30
добавлять переменную в cdll_dll.h нужно для того, что бы она была
задекларирована и в client.dll - что нужно для отключения прорисовки фонарика.
Добавлять строку нужно (в обоих файлах) перед строкой
Эта строка встречается в каждом файле по одному разу.
Теперь нам нужно прекэшировать фонарик, как предмет, если мы например захотим получить его
из консоли, набрав команду give item_flashlight
Если этого не сделать - игра вывалиться с ошибкой прекэшинга.
Итак откроем weapons.cpp и найдем функцию W_Precache
добавим туда строку
UTIL_PrecacheOther( "item_flashlight" );
Добавлять строку нужно после строки
UTIL_PrecacheOther( "item_longjump" );
Ну и давайте тогда уж сделаем, чтобы фонарик можно было получить по стандартной "читерской"
команде impulse 101
Для этого откройте player.cpp и найдите в нем строку
GiveNamedItem( "item_flashlight" );
GiveNamedItem( "item_suit" );
Итак, фонарик как предмет у нас уже есть и мы даже можем его подбирать
Однако толку от него пока мало, так если вы скомпилируете вышеприведенный код, то с удивлением
обнаружите, что, хотя фонарик и можно подбирать, но от него ничего не зависит и функция прорисовки
фонарика и его отключение по прежнему зависят от наличия костюма, но не фонарика
Давайте исправим данный баг.
Откройте снова player.cpp, а если вы его не закрывали, то это еще лучше
и найдите там строку FlashlightTurnOn
немного ниже вы найдете строку
if ( (pev->weapons & (1<<WEAPON_SUIT)) )
замените в ней WEAPON_SUIT на WEAPON_FLASHLIGHT
Теперь фонарик будет невозможно включить если у вас его нету
Однако его спрайт в правом верхнем углу экрана все равно будет рисоваться как при наличии фонарика
так и при отсутствии оного, что не есть хорошо, будем фиксить и этот баг.
Откройте папку cl_dll и найдите там файл flashlight.cpp.
откройте этот файл и найдите в нем строку
затем найдите, чуть ниже строку
if (!(gHUD.m_iWeaponBits & (1<<(WEAPON_SUIT)) ))
if (!(gHUD.m_iWeaponBits & (1<<(WEAPON_SUIT)) && (gHUD.m_iWeaponBits & (1<<(WEAPON_FLASHLIGHT)) )))
Теперь спрайт фонарика будет отрисовываться при соблюдении двух условий - при наличии собственно
фонарика и при наличии костюма.
Чтобы фонарик отрисовывался при его поднятии нужно нарисовать его картинку и запихнуть в спрайт
с названием 640hud2. Фонарик для разрешения 320 рисовать необязательно, поскольку при таком
разрешении практически никто не играет. Однако если вы всеже надумаете это сделать, то его удобно
будет запихнуть в спрайт 320hud2. В hud.txt нам будет нужно добавить две строки - для разрешения
320 х 200 и 640 х 480 соответственно.
item_flashlight 320 320hud2 68 72 20 20
item_flashlight 640 640hud2 176 144 44 44
куда их дописывать - я думаю сообразите
в начале файла hud.txt будет прописано некое число, после добавления двух вышеприведенных
строк это число нужно будет увеличить на 2, т.е. если было прописано 125 вам нужно будет
прописать 127.
Для самых ленивых моделька и спрайты выложены в архиве внизу.
Что бы добавить фонарик на карту создайте точечную ентитю item_flashlight.
Можно сделать так, чтобы фонарик автоматически появлялся у игрока при старте карты для этого
допишем следующий код:
в cbase.h добавим булевскую переменную
extern BOOL g_startFlashlight;
откроем файл gamerules.cpp, найдем строку GetPlayerSpawnSpot
и перед строкой
if (pentSpawnSpot->v.spawnflags & 2) //Спаунфлаг равен 2 для совместимости со спиритом
{
g_startFlashlight = TRUE;//если вы подобные извращения производите в нем
}
Теперь откроем файл singleplay_gamerules.cpp и найдем в нем строку PlayerSpawn
и после строки
CBaseEntity *pWeaponEntity = NULL;
добавим код, который присваивает переменной WEAPON_FLASHLIGHT значение TRUE по умолчанию.
if (g_startFlashlight)
pPlayer->pev->weapons |= (1<<WEAPON_FLASHLIGHT);
в world.cpp перед функциями worldspawn (там где перечислены спаунфлаги) нужно будет
добавить
Ну вот собственно и все, проставьте у info_player_start параметр spawnflags 2
и вы увидите, что фонарик появляется у вас при загрузке карты (даже если костюма на вас нету).
Фонарик заряжаемый от батарей. Согласитесь, что самозаряжающийся фонарик - это несколько неестественно
Давайте сделаем так, чтобы фонарик зраяжался от батарей, подобно костюму, (тут возможны два варианта:
либо фонарик заряжается от основных батарей, либо от своих, особых батарей, я подробно рассмотрю оба варианта).
Для начала давайте сделаем, чтобы фонарик не самоподзаряжался.
Для этого откройте Player.CPP, найдите UpdateClientData и в этой функции найдите
Code:
удалите (или просто закомментируйте)
вот эту часть кода
if (m_iFlashBattery < 100)
{
m_flFlashLightTime = FLASH_CHARGE_TIME + gpGlobals->time;
ALERT( at_console, "battery is charged\n" );
m_iFlashBattery++;
}
else
Теперь давайте сделаем, чтобы фонарик невозможно было включить, если он полностью разряжен
(вы будете удивлены, но если отключить подзарядку, то фонарик продолжает преспокойно гореть,
даже когда весь заряд вышел).
Для этого найдем функцию (выше UpdateClientData)
void CBasePlayer :: FlashlightTurnOn
и добавим в ней, в самом верху следующий код
if (m_iFlashBattery == 0)//g-cont
{
EMIT_SOUND_DYN( ENT(pev), CHAN_WEAPON, SOUND_FLASHLIGHT_ON, 1.0, ATTN_NORM, 0, PITCH_NORM );//Clik, clik, a tolky = 0
return;
}
строка EMIT_SOUND_DYN( ENT(pev), CHAN_WEAPON…
нужна для большей реалистичности - так как кликать можно и разряженным фонариком.
Теперь мы увеличим время разрядки фонарика (в стандартном режиме он разряжается за 3 минуты),
согласитесь, было бы нечестно, если бы фонарик, без подзарядки разряжался за те же три минуты
в жизни, а впереди - километры вентиляций со злобными хедкрабами
Сделать это очень легко - переходим в самый верх player.cpp и ищем строку
#define FLASH_DRAIN_TIME 1.2
и замените в ней 1.2 на большее значение, например на 15 - это даст примерно полчаса
работы фонаря без подзарядки, что довольно реалистично, и заставляет игрока экономить
ставший драгоценным теперь свет .
Теперь создадим собсно, саму батарейку, для чего откроем items.cpp
в самом верху файла, рядом с
extern int gmsgItemPickup;
extern int gmsgFlashBattery;
это нам нужно, для обновления иконки заряда фонарика (для передачи данных в клиент).
Теперь у нас - два пути - либо сделать так, чтобы обычная батарейка заряжала фонарь
совместно с костюмом, либо сделать отдельную батарейку для фонаря, первый способ проще,
но в игровом плане дает меньше гибкости, хотя тогда его можно применять и в обычном ХЛ.
Итак способ 1 - общая батарейка.
Найдите комментарий
// Suit reports new power level
и перед ним добавьте следующий код.
if (pPlayer->m_iFlashBattery < 100)
{
pPlayer->m_iFlashBattery = pPlayer->m_iFlashBattery + 20;
// ALERT( at_console, "flashlight is charged\n");
if (pPlayer->m_iFlashBattery > 100)
{
pPlayer->m_iFlashBattery = 100;
}
}
MESSAGE_BEGIN( MSG_ONE, gmsgFlashBattery, NULL, pPlayer->pev );
WRITE_BYTE(pPlayer->m_iFlashBattery);
MESSAGE_END();
Все, теперь обычная батарейка будет подзаряжать и заодно и фонарик.
Способ 2 - отдельная батарейка для фонаря (разумеется оба способа можно использовать вместе).
Опустимся в конец файла items.cpp и добавим следующий код.
//========================================================
// Battery for charger flashlight
// Copyright 2004 Shambler Team
// All Rights Reserved
//========================================================
class CItemFlashBattery : public CItem
{
void Spawn( void )
{
Precache( );
SET_MODEL(ENT(pev), "models/w_battery.mdl");
CItem::Spawn( );
}
void Precache( void )
{
PRECACHE_MODEL ("models/w_battery.mdl");
PRECACHE_SOUND( "items/gunpickup2.wav" );
}
BOOL MyTouch( CBasePlayer *pPlayer )
{
if ( pPlayer->pev->deadflag != DEAD_NO )
{
return FALSE;
}
if (pPlayer->m_iFlashBattery >= 99)
{
return FALSE;
}
if ( ( pPlayer->pev->weapons & (1<<WEAPON_FLASHLIGHT) ) )
{
if (pPlayer->m_iFlashBattery < 100)
{
pPlayer->m_iFlashBattery = pPlayer->m_iFlashBattery + 20;
// ALERT( at_console, "battery is charged\n");
}
else
return FALSE;
MESSAGE_BEGIN( MSG_ONE, gmsgFlashBattery, NULL, pPlayer->pev );
WRITE_BYTE(pPlayer->m_iFlashBattery);
MESSAGE_END();
EMIT_SOUND( pPlayer->edict(), CHAN_ITEM, "items/gunpickup2.wav", 1, ATTN_NORM );
MESSAGE_BEGIN( MSG_ONE, gmsgItemPickup, NULL, pPlayer->pev );
WRITE_STRING( STRING(pev->classname) );
MESSAGE_END();
return TRUE;
}
return FALSE;
}
};
LINK_ENTITY_TO_CLASS( item_flashlight_battery, CItemFlashBattery );
Модель - обычная батарейка, но разумеется можно заюзать свою, изменив
к ней путь.
Если вы вдруг решили заюзать второе дополнение, без вставления кода
самого подбираемого фонаря (а это также возможно), то замените
WEAPON_FLASHLIGHT на WEAPON_SUIT в выше приведенном коде.
Данную батарейку невозможно взять, если у вас нету фонарика,
или если его заряд полон.
Почти что все, теперь нам нужно сделать, чтобы батарейку для фонаря
мы могли получить по стандартной читерской команде, по give и
могли проставить ее в спаун разбиваемого ящика.
Откроем многострадальный Player.cpp и найдем строку case 101
и добавьте куда-нибудь к остальным строкам
GiveNamedItem( "item_flashlight_battery" );
Теперь займемся прекэшингом - откроем weapons.cpp и найдем функцию W_Precache
добавим туда строку
UTIL_PrecacheOther( "item_flashlight_battery" );
Остался последний штрих - добавить фонарик с батарейкой в func_pushable и func_breakable
Откройте func_break.cpp
и в самом верху, где идет перечисление предметов
const char *CBreakable::pSpawnObjects[] =
{
NULL, // 0
"item_battery", // 1
"item_healthkit", // 2
"weapon_9mmhandgun",// 3
"ammo_9mmclip", // 4
"weapon_9mmAR", // 5
"ammo_9mmAR", // 6
"ammo_ARgrenades", // 7
"weapon_shotgun", // 8
"ammo_buckshot", // 9
"weapon_crossbow", // 10
и так далее, в самом низу добавьте
"item_flashlight" //22
"item_flashlight_battery" //23
Соответственно, вызвать предметы можно будет поставив в поле spawnobject
22 - для фонаря, 23 - для его батарейки.
На этом все, код fgd, для вашего любимого хаммера напишете сами, ибо кварк умеет такие вещи делать автоматически
Похожие 1. Динамическое освещение - этой статье будет описан способ добавления динамических вспышек света, которые можно использовать для еффекта молнии 2. Мазлфлэш на брашах - Мазлфлэш на брашах 3. Как сделать старый 640 худ из 2560/1280 нового худа - сидел, думал как вернуть старые времена, додумал
Вы не можете комментировать, т.к. вы не зарегистрированы.