DayZ 1.29
DayZ Explorer by KGB
 
Загрузка...
Поиск...
Не найдено

◆ AddLightSourceItem()

void SpawnItemOnLocation::AddLightSourceItem ( ItemBase lightsource)
protected

Adds a light source child.

См. определение в файле ItemBase.c строка 9640

9645{
9646 override bool CanPutAsAttachment(EntityAI parent)
9647 {
9648 return true;
9649 }
9650};
9651
9653{
9654
9655};
9656
9657//const bool QUANTITY_DEBUG_REMOVE_ME = false;
9658
9659class ItemBase extends InventoryItem
9660{
9664
9666
9667 static int m_DebugActionsMask;
9669 // ============================================
9670 // Variable Manipulation System
9671 // ============================================
9672 // Quantity
9673
9674 float m_VarQuantity;
9675 float m_VarQuantityPrev;//for client to know quantity changed during synchronization
9677 int m_VarQuantityMin;
9678 int m_VarQuantityMax;
9679 int m_Count;
9680 float m_VarStackMax;
9681 float m_StoreLoadedQuantity = float.LOWEST;
9682 // Wet
9683 float m_VarWet;
9684 float m_VarWetPrev;//for client to know wetness changed during synchronization
9685 float m_VarWetInit;
9686 float m_VarWetMin;
9687 float m_VarWetMax;
9688 // Cleanness
9689 int m_Cleanness;
9690 int m_CleannessInit;
9691 int m_CleannessMin;
9692 int m_CleannessMax;
9693 // impact sounds
9695 bool m_CanPlayImpactSound = true;
9696 float m_ImpactSpeed;
9698 //
9699 float m_HeatIsolation;
9700 float m_ItemModelLength;
9701 float m_ItemAttachOffset; // Offset length for when the item is attached e.g. to weapon
9703 int m_VarLiquidType;
9704 int m_ItemBehaviour; // -1 = not specified; 0 = heavy item; 1= onehanded item; 2 = twohanded item
9705 int m_QuickBarBonus;
9706 bool m_IsBeingPlaced;
9707 bool m_IsHologram;
9708 bool m_IsTakeable;
9709 bool m_ThrowItemOnDrop;
9712 bool m_FixDamageSystemInit = false; //can be changed on storage version check
9713 bool can_this_be_combined; //Check if item can be combined
9714 bool m_CanThisBeSplit; //Check if item can be split
9715 bool m_IsStoreLoad = false;
9716 bool m_CanShowQuantity;
9717 bool m_HasQuantityBar;
9718 protected bool m_CanBeDigged;
9719 protected bool m_IsResultOfSplit
9720
9721 string m_SoundAttType;
9722 // items color variables
9727 //-------------------------------------------------------
9728
9729 // light source managing
9731
9735
9736 //==============================================
9737 // agent system
9738 private int m_AttachedAgents;
9739
9741 void TransferModifiers(PlayerBase reciever);
9742
9743
9744 // Weapons & suppressors particle effects
9748 ref static map<string, int> m_WeaponTypeToID;
9749 static int m_LastRegisteredWeaponID = 0;
9750
9751 // Overheating effects
9753 float m_OverheatingShots;
9754 ref Timer m_CheckOverheating;
9755 int m_ShotsToStartOverheating = 0; // After these many shots, the overheating effect begins
9756 int m_MaxOverheatingValue = 0; // Limits the number of shots that will be tracked
9757 float m_OverheatingDecayInterval = 1; // Timer's interval for decrementing overheat effect's lifespan
9758 ref array <ref OverheatingParticle> m_OverheatingParticles;
9759
9761 protected bool m_HideSelectionsBySlot;
9762
9763 // Admin Log
9764 PluginAdminLog m_AdminLog;
9765
9766 // misc
9767 ref Timer m_PhysDropTimer;
9768
9769 // Attachment Locking variables
9770 ref array<int> m_CompatibleLocks;
9771 protected int m_LockType;
9772 protected ref EffectSound m_LockingSound;
9773 protected string m_LockSoundSet;
9774
9775 // ItemSoundHandler variables
9776 protected const int ITEM_SOUNDS_MAX = 63; // optimize network synch
9777 protected int m_SoundSyncPlay; // id for sound to play
9778 protected int m_SoundSyncStop; // id for sound to stop
9779 protected int m_SoundSyncSlotID = InventorySlots.INVALID; // slot id for attach/detach sound based on slot
9780
9782
9783 //temperature
9784 private float m_TemperaturePerQuantityWeight;
9785
9786 // -------------------------------------------------------------------------
9787 void ItemBase()
9788 {
9789 SetEventMask(EntityEvent.INIT); // Enable EOnInit event
9793
9794 if (!g_Game.IsDedicatedServer())
9795 {
9796 if (HasMuzzle())
9797 {
9799
9801 {
9803 }
9804 }
9805
9807 m_ActionsInitialize = false;
9808 }
9809
9810 m_OldLocation = null;
9811
9812 if (g_Game.IsServer())
9813 {
9814 m_AdminLog = PluginAdminLog.Cast(GetPlugin(PluginAdminLog));
9815 }
9816
9817 if (ConfigIsExisting("headSelectionsToHide"))
9818 {
9820 ConfigGetTextArray("headSelectionsToHide",m_HeadHidingSelections);
9821 }
9822
9823 m_HideSelectionsBySlot = false;
9824 if (ConfigIsExisting("hideSelectionsByinventorySlot"))
9825 {
9826 m_HideSelectionsBySlot = ConfigGetBool("hideSelectionsByinventorySlot");
9827 }
9828
9829 m_QuickBarBonus = Math.Max(0, ConfigGetInt("quickBarBonus"));
9830
9831 m_IsResultOfSplit = false;
9832
9834 }
9835
9836 override void InitItemVariables()
9837 {
9838 super.InitItemVariables();
9839
9840 m_VarQuantityInit = ConfigGetInt("varQuantityInit");
9841 m_VarQuantity = m_VarQuantityInit;//should be by the CE, this is just a precaution
9842 m_VarQuantityMin = ConfigGetInt("varQuantityMin");
9843 m_VarQuantityMax = ConfigGetInt("varQuantityMax");
9844 m_VarStackMax = ConfigGetFloat("varStackMax");
9845 m_Count = ConfigGetInt("count");
9846
9847 m_CanShowQuantity = ConfigGetBool("quantityShow");
9848 m_HasQuantityBar = ConfigGetBool("quantityBar");
9849
9850 m_CleannessInit = ConfigGetInt("varCleannessInit");
9852 m_CleannessMin = ConfigGetInt("varCleannessMin");
9853 m_CleannessMax = ConfigGetInt("varCleannessMax");
9854
9855 m_WantPlayImpactSound = false;
9856 m_ImpactSpeed = 0.0;
9857
9858 m_VarWetInit = ConfigGetFloat("varWetInit");
9860 m_VarWetMin = ConfigGetFloat("varWetMin");
9861 m_VarWetMax = ConfigGetFloat("varWetMax");
9862
9863 m_LiquidContainerMask = ConfigGetInt("liquidContainerType");
9864 if (IsLiquidContainer() && GetQuantity() != 0)
9866 m_IsBeingPlaced = false;
9867 m_IsHologram = false;
9868 m_IsTakeable = true;
9869 m_CanBeMovedOverride = false;
9873 m_CanBeDigged = ConfigGetBool("canBeDigged");
9874
9875 m_CompatibleLocks = new array<int>();
9876 ConfigGetIntArray("compatibleLocks", m_CompatibleLocks);
9877 m_LockType = ConfigGetInt("lockType");
9878
9879 //Define if item can be split and set ability to be combined accordingly
9880 m_CanThisBeSplit = false;
9881 can_this_be_combined = false;
9882 if (ConfigIsExisting("canBeSplit"))
9883 {
9884 can_this_be_combined = ConfigGetBool("canBeSplit");
9886 }
9887
9888 m_ItemBehaviour = -1;
9889 if (ConfigIsExisting("itemBehaviour"))
9890 m_ItemBehaviour = ConfigGetInt("itemBehaviour");
9891
9892 //RegisterNetSyncVariableInt("m_VariablesMask");
9893 if (HasQuantity()) RegisterNetSyncVariableFloat("m_VarQuantity", GetQuantityMin(), m_VarQuantityMax);
9894 RegisterNetSyncVariableFloat("m_VarWet", GetWetMin(), GetWetMax(), 2);
9895 RegisterNetSyncVariableInt("m_VarLiquidType");
9896 RegisterNetSyncVariableInt("m_Cleanness",0,1);
9897
9898 RegisterNetSyncVariableBoolSignal("m_WantPlayImpactSound");
9899 RegisterNetSyncVariableFloat("m_ImpactSpeed");
9900 RegisterNetSyncVariableInt("m_ImpactSoundSurfaceHash");
9901
9902 RegisterNetSyncVariableInt("m_ColorComponentR", 0, 255);
9903 RegisterNetSyncVariableInt("m_ColorComponentG", 0, 255);
9904 RegisterNetSyncVariableInt("m_ColorComponentB", 0, 255);
9905 RegisterNetSyncVariableInt("m_ColorComponentA", 0, 255);
9906
9907 RegisterNetSyncVariableBool("m_IsBeingPlaced");
9908 RegisterNetSyncVariableBool("m_IsTakeable");
9909 RegisterNetSyncVariableBool("m_IsHologram");
9910
9913 {
9914 RegisterNetSyncVariableInt("m_SoundSyncPlay", 0, ITEM_SOUNDS_MAX);
9915 RegisterNetSyncVariableInt("m_SoundSyncStop", 0, ITEM_SOUNDS_MAX);
9916 RegisterNetSyncVariableInt("m_SoundSyncSlotID", int.MIN, int.MAX);
9917 }
9918
9919 m_LockSoundSet = ConfigGetString("lockSoundSet");
9920
9922 if (ConfigIsExisting("temperaturePerQuantityWeight"))
9923 m_TemperaturePerQuantityWeight = ConfigGetFloat("temperaturePerQuantityWeight");
9924
9925 m_SoundSyncSlotID = -1;
9926 }
9927
9928 override int GetQuickBarBonus()
9929 {
9930 return m_QuickBarBonus;
9931 }
9932
9933 void InitializeActions()
9934 {
9936 if (!m_InputActionMap)
9937 {
9939 m_InputActionMap = iam;
9940 SetActions();
9942 }
9943 }
9944
9945 override void GetActions(typename action_input_type, out array<ActionBase_Basic> actions)
9946 {
9948 {
9949 m_ActionsInitialize = true;
9951 }
9952
9953 actions = m_InputActionMap.Get(action_input_type);
9954 }
9955
9956 void SetActions()
9957 {
9958 AddAction(ActionTakeItem);
9959 AddAction(ActionTakeItemToHands);
9960 AddAction(ActionWorldCraft);
9962 AddAction(ActionAttachWithSwitch);
9963 }
9964
9965 void SetActionAnimOverrides(); // Override action animation for specific item
9966
9967 void AddAction(typename actionName)
9968 {
9969 ActionBase action = ActionManagerBase.GetAction(actionName);
9970
9971 if (!action)
9972 {
9973 Debug.LogError("Action " + actionName + " dosn't exist!");
9974 return;
9975 }
9976
9977 typename ai = action.GetInputType();
9978 if (!ai)
9979 {
9980 m_ActionsInitialize = false;
9981 return;
9982 }
9983
9984 array<ActionBase_Basic> action_array = m_InputActionMap.Get(ai);
9985 if (!action_array)
9986 {
9987 action_array = new array<ActionBase_Basic>;
9988 m_InputActionMap.Insert(ai, action_array);
9989 }
9990 if (LogManager.IsActionLogEnable())
9991 {
9992 Debug.ActionLog(action.ToString() + " -> " + ai, this.ToString() , "n/a", "Add action");
9993 }
9994
9995 if (action_array.Find(action) != -1)
9996 {
9997 Debug.Log("Action " + action.Type() + " already added to " + this + ", skipping!");
9998 }
9999 else
10000 {
10001 action_array.Insert(action);
10002 }
10003 }
10004
10005 void RemoveAction(typename actionName)
10006 {
10007 PlayerBase player = PlayerBase.Cast(g_Game.GetPlayer());
10008 ActionBase action = player.GetActionManager().GetAction(actionName);
10009 typename ai = action.GetInputType();
10010 array<ActionBase_Basic> action_array = m_InputActionMap.Get(ai);
10011
10012 if (action_array)
10013 {
10014 action_array.RemoveItem(action);
10015 }
10016 }
10017
10018 // Allows override of default action command per item, defined in the SetActionAnimOverrides() of the item's class
10019 // Set -1 for params which should stay in default state
10020 void OverrideActionAnimation(typename action, int commandUID, int stanceMask = -1, int commandUIDProne = -1)
10021 {
10022 ActionOverrideData overrideData = new ActionOverrideData();
10023 overrideData.m_CommandUID = commandUID;
10024 overrideData.m_CommandUIDProne = commandUIDProne;
10025 overrideData.m_StanceMask = stanceMask;
10026
10027 TActionAnimOverrideMap actionMap = m_ItemActionOverrides.Get(action);
10028 if (!actionMap) // create new map of action > overidables map
10029 {
10030 actionMap = new TActionAnimOverrideMap();
10031 m_ItemActionOverrides.Insert(action, actionMap);
10032 }
10033
10034 actionMap.Insert(this.Type(), overrideData); // insert item -> overrides
10035
10036 }
10037
10038 void OnItemInHandsPlayerSwimStart(PlayerBase player);
10039
10040 ScriptedLightBase GetLight();
10041
10042 // Loads muzzle flash particle configuration from config and saves it to a map for faster access
10043 void LoadParticleConfigOnFire(int id)
10044 {
10045 if (!m_OnFireEffect)
10047
10050
10051 string config_to_search = "CfgVehicles";
10052 string muzzle_owner_config;
10053
10054 if (!m_OnFireEffect.Contains(id))
10055 {
10056 if (IsInherited(Weapon))
10057 config_to_search = "CfgWeapons";
10058
10059 muzzle_owner_config = config_to_search + " " + GetType() + " ";
10060
10061 string config_OnFire_class = muzzle_owner_config + "Particles " + "OnFire ";
10062
10063 int config_OnFire_subclass_count = g_Game.ConfigGetChildrenCount(config_OnFire_class);
10064
10065 if (config_OnFire_subclass_count > 0)
10066 {
10067 array<ref WeaponParticlesOnFire> WPOF_array = new array<ref WeaponParticlesOnFire>;
10068
10069 for (int i = 0; i < config_OnFire_subclass_count; i++)
10070 {
10071 string particle_class = "";
10072 g_Game.ConfigGetChildName(config_OnFire_class, i, particle_class);
10073 string config_OnFire_entry = config_OnFire_class + particle_class;
10074 WeaponParticlesOnFire WPOF = new WeaponParticlesOnFire(this, config_OnFire_entry);
10075 WPOF_array.Insert(WPOF);
10076 }
10077
10078
10079 m_OnFireEffect.Insert(id, WPOF_array);
10080 }
10081 }
10082
10083 if (!m_OnBulletCasingEjectEffect.Contains(id))
10084 {
10085 config_to_search = "CfgWeapons"; // Bullet Eject efect is supported on weapons only.
10086 muzzle_owner_config = config_to_search + " " + GetType() + " ";
10087
10088 string config_OnBulletCasingEject_class = muzzle_owner_config + "Particles " + "OnBulletCasingEject ";
10089
10090 int config_OnBulletCasingEject_count = g_Game.ConfigGetChildrenCount(config_OnBulletCasingEject_class);
10091
10092 if (config_OnBulletCasingEject_count > 0 && IsInherited(Weapon))
10093 {
10094 array<ref WeaponParticlesOnBulletCasingEject> WPOBE_array = new array<ref WeaponParticlesOnBulletCasingEject>;
10095
10096 for (i = 0; i < config_OnBulletCasingEject_count; i++)
10097 {
10098 string particle_class2 = "";
10099 g_Game.ConfigGetChildName(config_OnBulletCasingEject_class, i, particle_class2);
10100 string config_OnBulletCasingEject_entry = config_OnBulletCasingEject_class + particle_class2;
10101 WeaponParticlesOnBulletCasingEject WPOBE = new WeaponParticlesOnBulletCasingEject(this, config_OnBulletCasingEject_entry);
10102 WPOBE_array.Insert(WPOBE);
10103 }
10104
10105
10106 m_OnBulletCasingEjectEffect.Insert(id, WPOBE_array);
10107 }
10108 }
10109 }
10110
10111 // Loads muzzle flash particle configuration from config and saves it to a map for faster access
10113 {
10116
10117 if (!m_OnOverheatingEffect.Contains(id))
10118 {
10119 string config_to_search = "CfgVehicles";
10120
10121 if (IsInherited(Weapon))
10122 config_to_search = "CfgWeapons";
10123
10124 string muzzle_owner_config = config_to_search + " " + GetType() + " ";
10125 string config_OnOverheating_class = muzzle_owner_config + "Particles " + "OnOverheating ";
10126
10127 if (g_Game.ConfigIsExisting(config_OnOverheating_class))
10128 {
10129
10130 m_ShotsToStartOverheating = g_Game.ConfigGetFloat(config_OnOverheating_class + "shotsToStartOverheating");
10131
10133 {
10134 m_ShotsToStartOverheating = -1; // This prevents futher readings from config for future creations of this item
10135 string error = "Error reading config " + GetType() + ">Particles>OnOverheating - Parameter shotsToStartOverheating is configured wrong or is missing! Its value must be 1 or higher!";
10136 Error(error);
10137 return;
10138 }
10139
10140 m_OverheatingDecayInterval = g_Game.ConfigGetFloat(config_OnOverheating_class + "overheatingDecayInterval");
10141 m_MaxOverheatingValue = g_Game.ConfigGetFloat(config_OnOverheating_class + "maxOverheatingValue");
10142
10143
10144
10145 int config_OnOverheating_subclass_count = g_Game.ConfigGetChildrenCount(config_OnOverheating_class);
10146 array<ref WeaponParticlesOnOverheating> WPOOH_array = new array<ref WeaponParticlesOnOverheating>;
10147
10148 for (int i = 0; i < config_OnOverheating_subclass_count; i++)
10149 {
10150 string particle_class = "";
10151 g_Game.ConfigGetChildName(config_OnOverheating_class, i, particle_class);
10152 string config_OnOverheating_entry = config_OnOverheating_class + particle_class;
10153 int entry_type = g_Game.ConfigGetType(config_OnOverheating_entry);
10154
10155 if (entry_type == CT_CLASS)
10156 {
10157 WeaponParticlesOnOverheating WPOF = new WeaponParticlesOnOverheating(this, config_OnOverheating_entry);
10158 WPOOH_array.Insert(WPOF);
10159 }
10160 }
10161
10162
10163 m_OnOverheatingEffect.Insert(id, WPOOH_array);
10164 }
10165 }
10166 }
10167
10168 float GetOverheatingValue()
10169 {
10170 return m_OverheatingShots;
10171 }
10172
10173 void IncreaseOverheating(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
10174 {
10175 if (m_MaxOverheatingValue > 0)
10176 {
10178
10179 if (!m_CheckOverheating)
10181
10183 m_CheckOverheating.Run(m_OverheatingDecayInterval, this, "OnOverheatingDecay");
10184
10185 CheckOverheating(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
10186 }
10187 }
10188
10189 void CheckOverheating(ItemBase weapon = null, string ammoType = "", ItemBase muzzle_owner = null, ItemBase suppressor = null, string config_to_search = "")
10190 {
10192 UpdateOverheating(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
10193
10195 StartOverheating(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
10196
10198 StopOverheating(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
10199
10201 {
10203 }
10204 }
10205
10207 {
10209 }
10210
10211 void OnOverheatingDecay()
10212 {
10213 if (m_MaxOverheatingValue > 0)
10214 m_OverheatingShots -= 1 + m_OverheatingShots / m_MaxOverheatingValue; // The hotter a barrel is, the faster it needs to cool down.
10215 else
10217
10218 if (m_OverheatingShots <= 0)
10219 {
10222 }
10223 else
10224 {
10225 if (!m_CheckOverheating)
10227
10229 m_CheckOverheating.Run(m_OverheatingDecayInterval, this, "OnOverheatingDecay");
10230 }
10231
10232 CheckOverheating(this, "", this);
10233 }
10234
10235 void StartOverheating(ItemBase weapon = null, string ammoType = "", ItemBase muzzle_owner = null, ItemBase suppressor = null, string config_to_search = "")
10236 {
10238 ItemBase.PlayOverheatingParticles(this, ammoType, this, suppressor, "CfgWeapons");
10239 }
10240
10241 void UpdateOverheating(ItemBase weapon = null, string ammoType = "", ItemBase muzzle_owner = null, ItemBase suppressor = null, string config_to_search = "")
10242 {
10244 ItemBase.UpdateOverheatingParticles(this, ammoType, this, suppressor, "CfgWeapons");
10246 }
10247
10248 void StopOverheating(ItemBase weapon = null, string ammoType = "", ItemBase muzzle_owner = null, ItemBase suppressor = null, string config_to_search = "")
10249 {
10251 ItemBase.StopOverheatingParticles(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
10252 }
10253
10254 void RegisterOverheatingParticle(Particle p, float min_heat_coef, float max_heat_coef, int particle_id, Object parent, vector local_pos, vector local_ori)
10255 {
10257 m_OverheatingParticles = new array<ref OverheatingParticle>;
10258
10259 OverheatingParticle OP = new OverheatingParticle();
10260 OP.RegisterParticle(p);
10261 OP.SetOverheatingLimitMin(min_heat_coef);
10262 OP.SetOverheatingLimitMax(max_heat_coef);
10263 OP.SetParticleParams(particle_id, parent, local_pos, local_ori);
10264
10265 m_OverheatingParticles.Insert(OP);
10266 }
10267
10268 float GetOverheatingCoef()
10269 {
10270 if (m_MaxOverheatingValue > 0)
10272
10273 return -1;
10274 }
10275
10277 {
10279 {
10280 float overheat_coef = GetOverheatingCoef();
10281 int count = m_OverheatingParticles.Count();
10282
10283 for (int i = count; i > 0; --i)
10284 {
10285 int id = i - 1;
10286 OverheatingParticle OP = m_OverheatingParticles.Get(id);
10287 Particle p = OP.GetParticle();
10288
10289 float overheat_min = OP.GetOverheatingLimitMin();
10290 float overheat_max = OP.GetOverheatingLimitMax();
10291
10292 if (overheat_coef < overheat_min && overheat_coef >= overheat_max)
10293 {
10294 if (p)
10295 {
10296 p.Stop();
10297 OP.RegisterParticle(null);
10298 }
10299 }
10300 }
10301 }
10302 }
10303
10305 {
10307 {
10308 for (int i = m_OverheatingParticles.Count(); i > 0; i--)
10309 {
10310 int id = i - 1;
10311 OverheatingParticle OP = m_OverheatingParticles.Get(id);
10312
10313 if (OP)
10314 {
10315 Particle p = OP.GetParticle();
10316
10317 if (p)
10318 {
10319 p.Stop();
10320 }
10321
10322 delete OP;
10323 }
10324 }
10325
10326 m_OverheatingParticles.Clear();
10328 }
10329 }
10330
10332 float GetInfectionChance(int system = 0, Param param = null)
10333 {
10334 return 0.0;
10335 }
10336
10337
10338 float GetDisinfectQuantity(int system = 0, Param param1 = null)
10339 {
10340 return 250;//default value
10341 }
10342
10343 float GetFilterDamageRatio()
10344 {
10345 return 0;
10346 }
10347
10349 bool HasMuzzle()
10350 {
10351 if (IsInherited(Weapon) || IsInherited(SuppressorBase))
10352 return true;
10353
10354 return false;
10355 }
10356
10358 int GetMuzzleID()
10359 {
10360 if (!m_WeaponTypeToID)
10361 m_WeaponTypeToID = new map<string, int>;
10362
10363 if (m_WeaponTypeToID.Contains(GetType()))
10364 {
10365 return m_WeaponTypeToID.Get(GetType());
10366 }
10367 else
10368 {
10369 // Register new weapon ID
10371 }
10372
10374 }
10375
10382 {
10383 return -1;
10384 }
10385
10386
10387
10388 // -------------------------------------------------------------------------
10389 void ~ItemBase()
10390 {
10391 if (g_Game && g_Game.GetPlayer() && (!g_Game.IsDedicatedServer()))
10392 {
10393 PlayerBase player = PlayerBase.Cast(g_Game.GetPlayer());
10394 int r_index = player.GetHumanInventory().FindUserReservedLocationIndex(this);
10395
10396 if (r_index >= 0)
10397 {
10398 InventoryLocation r_il = new InventoryLocation;
10399 player.GetHumanInventory().GetUserReservedLocation(r_index,r_il);
10400
10401 player.GetHumanInventory().ClearUserReservedLocationAtIndex(r_index);
10402 int r_type = r_il.GetType();
10403 if (r_type == InventoryLocationType.CARGO || r_type == InventoryLocationType.PROXYCARGO)
10404 {
10405 r_il.GetParent().GetOnReleaseLock().Invoke(this);
10406 }
10407 else if (r_type == InventoryLocationType.ATTACHMENT)
10408 {
10409 r_il.GetParent().GetOnAttachmentReleaseLock().Invoke(this, r_il.GetSlot());
10410 }
10411
10412 }
10413
10414 player.GetHumanInventory().ClearUserReservedLocation(this);
10415 }
10416
10417 if (m_LockingSound)
10418 SEffectManager.DestroyEffect(m_LockingSound);
10419 }
10420
10421
10422
10423 // -------------------------------------------------------------------------
10424 static int GetDebugActionsMask()
10425 {
10426 return ItemBase.m_DebugActionsMask;
10427 }
10428
10429 static bool HasDebugActionsMask(int mask)
10430 {
10431 return ItemBase.m_DebugActionsMask & mask;
10432 }
10433
10434 static void SetDebugActionsMask(int mask)
10435 {
10436 ItemBase.m_DebugActionsMask = mask;
10437 }
10438
10439 static void AddDebugActionsMask(int mask)
10440 {
10441 ItemBase.m_DebugActionsMask |= mask;
10442 }
10443
10444 static void RemoveDebugActionsMask(int mask)
10445 {
10446 ItemBase.m_DebugActionsMask &= ~mask;
10447 }
10448
10449 static void ToggleDebugActionsMask(int mask)
10450 {
10451 if (HasDebugActionsMask(mask))
10452 {
10454 }
10455 else
10456 {
10457 AddDebugActionsMask(mask);
10458 }
10459 }
10460
10461 // -------------------------------------------------------------------------
10462 void SetCEBasedQuantity()
10463 {
10464 if (GetEconomyProfile())
10465 {
10466 float q_max = GetEconomyProfile().GetQuantityMax();
10467 if (q_max > 0)
10468 {
10469 float q_min = GetEconomyProfile().GetQuantityMin();
10470 float quantity_randomized = Math.RandomFloatInclusive(q_min, q_max);
10471
10472 if (HasComponent(COMP_TYPE_ENERGY_MANAGER))//more direct access for speed
10473 {
10474 ComponentEnergyManager comp = GetCompEM();
10475 if (comp && (comp.GetEnergyMaxPristine() || comp.GetEnergyAtSpawn()))//checking for a potential for energy, we need to check both values, as both are optional, only when both are set to 0, we know the item can't have energy
10476 {
10477 comp.SetEnergy0To1(quantity_randomized);
10478 }
10479 }
10480 else if (HasQuantity())
10481 {
10482 SetQuantityNormalized(quantity_randomized, false);
10483 //PrintString("<==> Normalized quantity for item: "+ GetType()+", qmin:"+q_min.ToString()+"; qmax:"+q_max.ToString()+";quantity:" +quantity_randomized.ToString());
10484 }
10485
10486 }
10487 }
10488 }
10489
10491 void LockToParent()
10492 {
10493 EntityAI parent = GetHierarchyParent();
10494
10495 if (parent)
10496 {
10497 InventoryLocation inventory_location_to_lock = new InventoryLocation;
10498 GetInventory().GetCurrentInventoryLocation(inventory_location_to_lock);
10499 parent.GetInventory().SetSlotLock(inventory_location_to_lock.GetSlot(), true);
10500 }
10501 }
10502
10504 void UnlockFromParent()
10505 {
10506 EntityAI parent = GetHierarchyParent();
10507
10508 if (parent)
10509 {
10510 InventoryLocation inventory_location_to_unlock = new InventoryLocation;
10511 GetInventory().GetCurrentInventoryLocation(inventory_location_to_unlock);
10512 parent.GetInventory().SetSlotLock(inventory_location_to_unlock.GetSlot(), false);
10513 }
10514 }
10515
10516 override void CombineItemsClient(EntityAI entity2, bool use_stack_max = true)
10517 {
10518 /*
10519 ref Param1<EntityAI> item = new Param1<EntityAI>(entity2);
10520 RPCSingleParam(ERPCs.RPC_ITEM_COMBINE, item, g_Game.GetPlayer());
10521 */
10522 ItemBase item2 = ItemBase.Cast(entity2);
10523
10524 if (g_Game.IsClient())
10525 {
10526 if (ScriptInputUserData.CanStoreInputUserData())
10527 {
10528 ScriptInputUserData ctx = new ScriptInputUserData;
10530 ctx.Write(-1);
10531 ItemBase i1 = this; // @NOTE: workaround for correct serialization
10532 ctx.Write(i1);
10533 ctx.Write(item2);
10534 ctx.Write(use_stack_max);
10535 ctx.Write(-1);
10536 ctx.Send();
10537
10538 if (IsCombineAll(item2, use_stack_max))
10539 {
10540 g_Game.GetPlayer().GetInventory().AddInventoryReservationEx(item2,null,GameInventory.c_InventoryReservationTimeoutShortMS);
10541 }
10542 }
10543 }
10544 else if (!g_Game.IsMultiplayer())
10545 {
10546 CombineItems(item2, use_stack_max);
10547 }
10548 }
10549
10550 bool IsLiquidPresent()
10551 {
10552 return (GetLiquidType() != 0 && HasQuantity());
10553 }
10554
10555 bool IsLiquidContainer()
10556 {
10557 return m_LiquidContainerMask != 0;
10558 }
10559
10561 {
10562 return m_LiquidContainerMask;
10563 }
10564
10565 bool IsBloodContainer()
10566 {
10567 //m_LiquidContainerMask & GROUP_LIQUID_BLOOD ???
10568 return false;
10569 }
10570
10571 bool IsNVG()
10572 {
10573 return false;
10574 }
10575
10578 bool IsExplosive()
10579 {
10580 return false;
10581 }
10582
10584 {
10585 return "";
10586 }
10587
10589
10590 bool IsLightSource()
10591 {
10592 return false;
10593 }
10594
10596 {
10597 return true;
10598 }
10599
10600 //--- ACTION CONDITIONS
10601 //direction
10602 bool IsFacingPlayer(PlayerBase player, string selection)
10603 {
10604 return true;
10605 }
10606
10607 bool IsPlayerInside(PlayerBase player, string selection)
10608 {
10609 return true;
10610 }
10611
10612 override bool CanObstruct()
10613 {
10614 PlayerBase player = PlayerBase.Cast(g_Game.GetPlayer());
10615 return !player || !IsPlayerInside(player, "");
10616 }
10617
10618 override bool IsBeingPlaced()
10619 {
10620 return m_IsBeingPlaced;
10621 }
10622
10623 void SetIsBeingPlaced(bool is_being_placed)
10624 {
10625 m_IsBeingPlaced = is_being_placed;
10626 if (!is_being_placed)
10628 SetSynchDirty();
10629 }
10630
10631 //server-side
10632 void OnEndPlacement() {}
10633
10634 override bool IsHologram()
10635 {
10636 return m_IsHologram;
10637 }
10638
10639 bool CanBeDigged()
10640 {
10641 return m_CanBeDigged;
10642 }
10643
10645 {
10646 return 1;
10647 }
10648
10649 bool CanMakeGardenplot()
10650 {
10651 return false;
10652 }
10653
10654 void SetIsHologram(bool is_hologram)
10655 {
10656 m_IsHologram = is_hologram;
10657 SetSynchDirty();
10658 }
10659 /*
10660 protected float GetNutritionalEnergy()
10661 {
10662 Edible_Base edible = Edible_Base.Cast(this);
10663 return edible.GetFoodEnergy();
10664 }
10665
10666 protected float GetNutritionalWaterContent()
10667 {
10668 Edible_Base edible = Edible_Base.Cast(this);
10669 return edible.GetFoodWater();
10670 }
10671
10672 protected float GetNutritionalIndex()
10673 {
10674 Edible_Base edible = Edible_Base.Cast(this);
10675 return edible.GetFoodNutritionalIndex();
10676 }
10677
10678 protected float GetNutritionalFullnessIndex()
10679 {
10680 Edible_Base edible = Edible_Base.Cast(this);
10681 return edible.GetFoodTotalVolume();
10682 }
10683
10684 protected float GetNutritionalToxicity()
10685 {
10686 Edible_Base edible = Edible_Base.Cast(this);
10687 return edible.GetFoodToxicity();
10688
10689 }
10690 */
10691
10692
10693 // -------------------------------------------------------------------------
10694 override void OnMovedInsideCargo(EntityAI container)
10695 {
10696 super.OnMovedInsideCargo(container);
10697
10698 MiscGameplayFunctions.RemoveAllAttachedChildrenByTypename(this, {Bolt_Base});
10699 }
10700
10701 override void EEItemLocationChanged(notnull InventoryLocation oldLoc, notnull InventoryLocation newLoc)
10702 {
10703 super.EEItemLocationChanged(oldLoc, newLoc);
10704
10705 PlayerBase newPlayer = null;
10706 PlayerBase oldPlayer = null;
10707
10708 if (newLoc.GetParent())
10709 newPlayer = PlayerBase.Cast(newLoc.GetParent().GetHierarchyRootPlayer());
10710
10711 if (oldLoc.GetParent())
10712 oldPlayer = PlayerBase.Cast(oldLoc.GetParent().GetHierarchyRootPlayer());
10713
10714 if (oldPlayer && oldLoc.GetType() == InventoryLocationType.HANDS)
10715 {
10716 int rIndex = oldPlayer.GetHumanInventory().FindUserReservedLocationIndex(this);
10717
10718 if (rIndex >= 0)
10719 {
10720 InventoryLocation rIl = new InventoryLocation;
10721 oldPlayer.GetHumanInventory().GetUserReservedLocation(rIndex, rIl);
10722
10723 oldPlayer.GetHumanInventory().ClearUserReservedLocationAtIndex(rIndex);
10724 int rType = rIl.GetType();
10725 if (rType == InventoryLocationType.CARGO || rType == InventoryLocationType.PROXYCARGO)
10726 {
10727 rIl.GetParent().GetOnReleaseLock().Invoke(this);
10728 }
10729 else if (rType == InventoryLocationType.ATTACHMENT)
10730 {
10731 rIl.GetParent().GetOnAttachmentReleaseLock().Invoke(this, rIl.GetSlot());
10732 }
10733
10734 }
10735 }
10736
10737 if (newLoc.GetType() == InventoryLocationType.HANDS && oldLoc.GetType() != InventoryLocationType.TEMP)
10738 {
10739 if (newPlayer)
10740 newPlayer.ForceStandUpForHeavyItems(newLoc.GetItem());
10741
10742 if (newPlayer == oldPlayer)
10743 {
10744 if (oldLoc.GetParent() && newPlayer.GetHumanInventory().LocationGetEntity(oldLoc) == NULL)
10745 {
10746 if (oldLoc.GetType() == InventoryLocationType.CARGO)
10747 {
10748 if (oldLoc.GetParent().GetInventory().TestAddEntityInCargoExLoc(oldLoc, false, false, false, true, false, false))
10749 {
10750 newPlayer.GetHumanInventory().SetUserReservedLocation(this,oldLoc);
10751 }
10752 }
10753 else
10754 {
10755 newPlayer.GetHumanInventory().SetUserReservedLocation(this,oldLoc);
10756 }
10757 }
10758
10759 if (newPlayer.GetHumanInventory().FindUserReservedLocationIndex(this) >= 0)
10760 {
10761 int type = oldLoc.GetType();
10762 if (type == InventoryLocationType.CARGO || type == InventoryLocationType.PROXYCARGO)
10763 {
10764 oldLoc.GetParent().GetOnSetLock().Invoke(this);
10765 }
10766 else if (type == InventoryLocationType.ATTACHMENT)
10767 {
10768 oldLoc.GetParent().GetOnAttachmentSetLock().Invoke(this, oldLoc.GetSlot());
10769 }
10770 }
10771 if (!m_OldLocation)
10772 {
10773 m_OldLocation = new InventoryLocation;
10774 }
10775 m_OldLocation.Copy(oldLoc);
10776 }
10777 else
10778 {
10779 if (m_OldLocation)
10780 {
10781 m_OldLocation.Reset();
10782 }
10783 }
10784
10785 g_Game.GetAnalyticsClient().OnItemAttachedAtPlayer(this,"Hands");
10786 }
10787 else
10788 {
10789 if (newPlayer)
10790 {
10791 int resIndex = newPlayer.GetHumanInventory().FindCollidingUserReservedLocationIndex(this, newLoc);
10792 if (resIndex >= 0)
10793 {
10794 InventoryLocation il = new InventoryLocation;
10795 newPlayer.GetHumanInventory().GetUserReservedLocation(resIndex, il);
10796 ItemBase it = ItemBase.Cast(il.GetItem());
10797 newPlayer.GetHumanInventory().ClearUserReservedLocationAtIndex(resIndex);
10798 int rel_type = il.GetType();
10799 if (rel_type == InventoryLocationType.CARGO || rel_type == InventoryLocationType.PROXYCARGO)
10800 {
10801 il.GetParent().GetOnReleaseLock().Invoke(it);
10802 }
10803 else if (rel_type == InventoryLocationType.ATTACHMENT)
10804 {
10805 il.GetParent().GetOnAttachmentReleaseLock().Invoke(it, il.GetSlot());
10806 }
10807 //it.GetOnReleaseLock().Invoke(it);
10808 }
10809 }
10810 else if (oldPlayer && newLoc.GetType() == InventoryLocationType.GROUND && m_ThrowItemOnDrop)
10811 {
10812 //ThrowPhysically(oldPlayer, vector.Zero);
10813 m_ThrowItemOnDrop = false;
10814 }
10815
10816 if (m_OldLocation)
10817 {
10818 m_OldLocation.Reset();
10819 }
10820 }
10821
10822 if (oldLoc.GetType() == InventoryLocationType.TEMP)
10823 {
10824 PluginInventoryRepair.Cast(GetPlugin(PluginInventoryRepair)).Remove(oldLoc.GetItem());
10825 }
10826
10827 if (newLoc.GetType() == InventoryLocationType.TEMP)
10828 {
10829 PluginInventoryRepair.Cast(GetPlugin(PluginInventoryRepair)).Add(oldLoc.GetItem());
10830 }
10831 }
10832
10833 override void EOnContact(IEntity other, Contact extra)
10834 {
10836 {
10837 int liquidType = -1;
10838 float impactSpeed = ProcessImpactSoundEx(other, extra, m_ConfigWeight, m_ImpactSoundSurfaceHash, liquidType);
10839 if (impactSpeed > 0.0)
10840 {
10841 m_ImpactSpeed = impactSpeed;
10842 #ifndef SERVER
10843 PlayImpactSound(m_ConfigWeight, m_ImpactSpeed, m_ImpactSoundSurfaceHash);
10844 #else
10845 m_WantPlayImpactSound = true;
10846 SetSynchDirty();
10847 #endif
10848 m_CanPlayImpactSound = (liquidType == -1);// prevents further playing of the sound when the surface is a liquid type
10849 }
10850 }
10851
10852 #ifdef SERVER
10853 if (GetCompEM() && GetCompEM().IsPlugged())
10854 {
10855 if (GetCompEM().GetCordLength() < vector.Distance(GetPosition(), GetCompEM().GetEnergySource().GetPosition()))
10856 GetCompEM().UnplugThis();
10857 }
10858 #endif
10859 }
10860
10861 void RefreshPhysics();
10862
10863 override void OnCreatePhysics()
10864 {
10866 }
10867
10868 override void OnItemAttachmentSlotChanged(notnull InventoryLocation oldLoc, notnull InventoryLocation newLoc)
10869 {
10870
10871 }
10872 // -------------------------------------------------------------------------
10873 override void OnItemLocationChanged(EntityAI old_owner, EntityAI new_owner)
10874 {
10875 super.OnItemLocationChanged(old_owner, new_owner);
10876
10877 PlayerBase relatedPlayer = PlayerBase.Cast(old_owner);
10878 PlayerBase playerNew = PlayerBase.Cast(new_owner);
10879
10880 if (!relatedPlayer && playerNew)
10881 relatedPlayer = playerNew;
10882
10883 if (relatedPlayer && relatedPlayer.GetPerformedActionID() != -1)
10884 {
10885 ActionManagerBase actionMgr = relatedPlayer.GetActionManager();
10886 if (actionMgr)
10887 {
10888 ActionBase currentAction = actionMgr.GetRunningAction();
10889 if (currentAction)
10890 currentAction.OnItemLocationChanged(this);
10891 }
10892 }
10893
10894 Man ownerPlayerOld = null;
10895 Man ownerPlayerNew = null;
10896
10897 if (old_owner)
10898 {
10899 if (old_owner.IsMan())
10900 {
10901 ownerPlayerOld = Man.Cast(old_owner);
10902 }
10903 else
10904 {
10905 ownerPlayerOld = Man.Cast(old_owner.GetHierarchyRootPlayer());
10906 }
10907 }
10908 else
10909 {
10910 if (new_owner && IsElectricAppliance() && GetCompEM() && GetCompEM().IsPlugged())
10911 {
10912 ActionBase action = ActionManagerBase.GetAction(ActionRepositionPluggedItem);
10913
10914 if (!action || !playerNew || playerNew.GetPerformedActionID() != action.GetID())
10915 {
10916 GetCompEM().UnplugThis();
10917 }
10918 }
10919 }
10920
10921 if (new_owner)
10922 {
10923 if (new_owner.IsMan())
10924 {
10925 ownerPlayerNew = Man.Cast(new_owner);
10926 }
10927 else
10928 {
10929 ownerPlayerNew = Man.Cast(new_owner.GetHierarchyRootPlayer());
10930 }
10931 }
10932
10933 if (ownerPlayerOld != ownerPlayerNew)
10934 {
10935 if (ownerPlayerOld)
10936 {
10937 array<EntityAI> subItemsExit = new array<EntityAI>;
10938 GetInventory().EnumerateInventory(InventoryTraversalType.PREORDER,subItemsExit);
10939 for (int i = 0; i < subItemsExit.Count(); i++)
10940 {
10941 ItemBase itemExit = ItemBase.Cast(subItemsExit.Get(i));
10942 itemExit.OnInventoryExit(ownerPlayerOld);
10943 }
10944 }
10945
10946 if (ownerPlayerNew)
10947 {
10948 array<EntityAI> subItemsEnter = new array<EntityAI>;
10949 GetInventory().EnumerateInventory(InventoryTraversalType.PREORDER,subItemsEnter);
10950 for (int j = 0; j < subItemsEnter.Count(); j++)
10951 {
10952 ItemBase itemEnter = ItemBase.Cast(subItemsEnter.Get(j));
10953 itemEnter.OnInventoryEnter(ownerPlayerNew);
10954 }
10955 }
10956 }
10957 else if (ownerPlayerNew != null)
10958 {
10959 PlayerBase nplayer;
10960 if (PlayerBase.CastTo(nplayer, ownerPlayerNew))
10961 {
10962 array<EntityAI> subItemsUpdate = new array<EntityAI>;
10963 GetInventory().EnumerateInventory(InventoryTraversalType.PREORDER,subItemsUpdate);
10964 for (int k = 0; k < subItemsUpdate.Count(); k++)
10965 {
10966 ItemBase itemUpdate = ItemBase.Cast(subItemsUpdate.Get(k));
10967 itemUpdate.UpdateQuickbarShortcutVisibility(nplayer);
10968 }
10969 }
10970 }
10971
10972 if (old_owner)
10973 old_owner.OnChildItemRemoved(this);
10974 if (new_owner)
10975 new_owner.OnChildItemReceived(this);
10976 }
10977
10978 // -------------------------------------------------------------------------------
10979 override void EEDelete(EntityAI parent)
10980 {
10981 super.EEDelete(parent);
10982 PlayerBase player = PlayerBase.Cast(GetHierarchyRootPlayer());
10983 if (player)
10984 {
10985 OnInventoryExit(player);
10986
10987 if (player.IsAlive())
10988 {
10989 int r_index = player.GetHumanInventory().FindUserReservedLocationIndex(this);
10990 if (r_index >= 0)
10991 {
10992 InventoryLocation r_il = new InventoryLocation;
10993 player.GetHumanInventory().GetUserReservedLocation(r_index,r_il);
10994
10995 player.GetHumanInventory().ClearUserReservedLocationAtIndex(r_index);
10996 int r_type = r_il.GetType();
10997 if (r_type == InventoryLocationType.CARGO || r_type == InventoryLocationType.PROXYCARGO)
10998 {
10999 r_il.GetParent().GetOnReleaseLock().Invoke(this);
11000 }
11001 else if (r_type == InventoryLocationType.ATTACHMENT)
11002 {
11003 r_il.GetParent().GetOnAttachmentReleaseLock().Invoke(this, r_il.GetSlot());
11004 }
11005
11006 }
11007
11008 player.RemoveQuickBarEntityShortcut(this);
11009 }
11010 }
11011 }
11012 // -------------------------------------------------------------------------------
11013 override void EEKilled(Object killer)
11014 {
11015 super.EEKilled(killer);
11016
11018 if (killer && killer.IsFireplace() && CanExplodeInFire())
11019 {
11020 if (GetTemperature() >= GameConstants.ITEM_TEMPERATURE_TO_EXPLODE_MIN)
11021 {
11022 if (IsMagazine())
11023 {
11024 if (Magazine.Cast(this).GetAmmoCount() > 0)
11025 {
11026 ExplodeAmmo();
11027 }
11028 }
11029 else
11030 {
11031 Explode(DamageType.EXPLOSION);
11032 }
11033 }
11034 }
11035 }
11036
11037 override void OnWasAttached(EntityAI parent, int slot_id)
11038 {
11039 MiscGameplayFunctions.RemoveAllAttachedChildrenByTypename(this, {Bolt_Base});
11040
11041 super.OnWasAttached(parent, slot_id);
11042
11043 if (HasQuantity())
11044 UpdateNetSyncVariableFloat("m_VarQuantity", GetQuantityMin(), m_VarQuantityMax);
11045
11046 if (g_Game.IsServer() || !g_Game.IsMultiplayer()) // single player or server side multiplayer
11047 StartItemSoundServer(SoundConstants.ITEM_ATTACH, slot_id);
11048 }
11049
11050 override void OnWasDetached(EntityAI parent, int slot_id)
11051 {
11052 super.OnWasDetached(parent, slot_id);
11053
11054 if (HasQuantity())
11055 UpdateNetSyncVariableFloat("m_VarQuantity", GetQuantityMin(), m_VarQuantityMax);
11056
11057 if (g_Game.IsServer() || !g_Game.IsMultiplayer()) // single player or server side multiplayer
11058 StartItemSoundServer(SoundConstants.ITEM_DETACH, slot_id);
11059 }
11060
11061 override string ChangeIntoOnAttach(string slot)
11062 {
11063 int idx;
11064 TStringArray inventory_slots = new TStringArray;
11065 TStringArray attach_types = new TStringArray;
11066
11067 ConfigGetTextArray("ChangeInventorySlot",inventory_slots);
11068 if (inventory_slots.Count() < 1) //is string
11069 {
11070 inventory_slots.Insert(ConfigGetString("ChangeInventorySlot"));
11071 attach_types.Insert(ConfigGetString("ChangeIntoOnAttach"));
11072 }
11073 else //is array
11074 {
11075 ConfigGetTextArray("ChangeIntoOnAttach",attach_types);
11076 }
11077
11078 idx = inventory_slots.Find(slot);
11079 if (idx < 0)
11080 return "";
11081
11082 return attach_types.Get(idx);
11083 }
11084
11085 override string ChangeIntoOnDetach()
11086 {
11087 int idx = -1;
11088 string slot;
11089
11090 TStringArray inventory_slots = new TStringArray;
11091 TStringArray detach_types = new TStringArray;
11092
11093 this.ConfigGetTextArray("ChangeInventorySlot",inventory_slots);
11094 if (inventory_slots.Count() < 1) //is string
11095 {
11096 inventory_slots.Insert(this.ConfigGetString("ChangeInventorySlot"));
11097 detach_types.Insert(this.ConfigGetString("ChangeIntoOnDetach"));
11098 }
11099 else //is array
11100 {
11101 this.ConfigGetTextArray("ChangeIntoOnDetach",detach_types);
11102 if (detach_types.Count() < 1)
11103 detach_types.Insert(this.ConfigGetString("ChangeIntoOnDetach"));
11104 }
11105
11106 for (int i = 0; i < inventory_slots.Count(); i++)
11107 {
11108 slot = inventory_slots.Get(i);
11109 }
11110
11111 if (slot != "")
11112 {
11113 if (detach_types.Count() == 1)
11114 idx = 0;
11115 else
11116 idx = inventory_slots.Find(slot);
11117 }
11118 if (idx < 0)
11119 return "";
11120
11121 return detach_types.Get(idx);
11122 }
11123
11124 void ExplodeAmmo()
11125 {
11126 //timer
11127 ref Timer explode_timer = new Timer(CALL_CATEGORY_SYSTEM);
11128
11129 //min/max time
11130 float min_time = 1;
11131 float max_time = 3;
11132 float delay = Math.RandomFloat(min_time, max_time);
11133
11134 explode_timer.Run(delay, this, "DoAmmoExplosion");
11135 }
11136
11137 void DoAmmoExplosion()
11138 {
11139 Magazine magazine = Magazine.Cast(this);
11140 int pop_sounds_count = 6;
11141 string pop_sounds[ 6 ] = { "ammopops_1","ammopops_2","ammopops_3","ammopops_4","ammopops_5","ammopops_6" };
11142
11143 //play sound
11144 int sound_idx = Math.RandomInt(0, pop_sounds_count - 1);
11145 string sound_name = pop_sounds[ sound_idx ];
11146 g_Game.CreateSoundOnObject(this, sound_name, 20, false);
11147
11148 //remove ammo count
11149 magazine.ServerAddAmmoCount(-1);
11150
11151 //if condition then repeat -> ExplodeAmmo
11152 float min_temp_to_explode = 100; //min temperature for item to explode
11153
11154 if (magazine.GetAmmoCount() > 0 && GetTemperature() >= min_temp_to_explode) //TODO ? add check for parent -> fireplace
11155 {
11156 ExplodeAmmo();
11157 }
11158 }
11159
11160 // -------------------------------------------------------------------------------
11161 override void EEHitBy(TotalDamageResult damageResult, int damageType, EntityAI source, int component, string dmgZone, string ammo, vector modelPos, float speedCoef)
11162 {
11163 super.EEHitBy(damageResult, damageType, source, component, dmgZone, ammo, modelPos, speedCoef);
11164
11165 const int CHANCE_DAMAGE_CARGO = 4;
11166 const int CHANCE_DAMAGE_ATTACHMENT = 1;
11167 const int CHANCE_DAMAGE_NOTHING = 2;
11168
11169 if (IsClothing() || IsContainer() || IsItemTent())
11170 {
11171 float dmg = damageResult.GetDamage("","Health") * -0.5;
11172 int chances;
11173 int rnd;
11174
11175 if (GetInventory().GetCargo())
11176 {
11177 chances = CHANCE_DAMAGE_CARGO + CHANCE_DAMAGE_ATTACHMENT + CHANCE_DAMAGE_NOTHING;
11178 rnd = Math.RandomInt(0,chances);
11179
11180 if (rnd < CHANCE_DAMAGE_CARGO)
11181 {
11182 DamageItemInCargo(dmg);
11183 }
11184 else if (rnd < (chances - CHANCE_DAMAGE_NOTHING))
11185 {
11187 }
11188 }
11189 else
11190 {
11191 chances = CHANCE_DAMAGE_ATTACHMENT + CHANCE_DAMAGE_NOTHING;
11192 rnd = Math.RandomInt(0,chances);
11193
11194 if (rnd < CHANCE_DAMAGE_ATTACHMENT)
11195 {
11197 }
11198 }
11199 }
11200 }
11201
11202 bool DamageItemInCargo(float damage)
11203 {
11204 CargoBase cargo = GetInventory().GetCargo();
11205 if (cargo)
11206 {
11207 int item_count = cargo.GetItemCount();
11208 if (item_count > 0)
11209 {
11210 int random_pick = Math.RandomInt(0, item_count);
11211 ItemBase item = ItemBase.Cast(cargo.GetItem(random_pick));
11212 if (!item.IsExplosive())
11213 {
11214 item.AddHealth("","",damage);
11215 return true;
11216 }
11217 }
11218 }
11219 return false;
11220 }
11221
11222 bool DamageItemAttachments(float damage)
11223 {
11224 GameInventory inventory = GetInventory();
11225 int attachment_count = inventory.AttachmentCount();
11226 if (attachment_count > 0)
11227 {
11228 int random_pick = Math.RandomInt(0, attachment_count);
11229 ItemBase attachment = ItemBase.Cast(inventory.GetAttachmentFromIndex(random_pick));
11230 if (!attachment.IsExplosive())
11231 {
11232 attachment.AddHealth("","",damage);
11233 return true;
11234 }
11235 }
11236 return false;
11237 }
11238
11239 override bool IsSplitable()
11240 {
11241 return m_CanThisBeSplit;
11242 }
11243 //----------------
11244 override bool CanBeSplit()
11245 {
11246 if (IsSplitable() && (GetQuantity() > 1))
11247 return GetInventory().CanRemoveEntity();
11248
11249 return false;
11250 }
11251
11252 protected bool ShouldSplitQuantity(float quantity)
11253 {
11254 // don't call 'CanBeSplit' here, too strict and will introduce a freeze-crash when dismantling fence with a fireplace nearby
11255 if (!IsSplitable())
11256 return false;
11257
11258 // nothing to split?
11259 if (GetQuantity() <= 1)
11260 return false;
11261
11262 // check if we should re-use the item instead of creating a new copy?
11263 // implicit cast to int, if 'IsSplitable' returns true, these values are assumed ints
11264 int delta = GetQuantity() - quantity;
11265 if (delta == 0)
11266 return false;
11267
11268 // valid to split
11269 return true;
11270 }
11271
11272 override void SplitIntoStackMaxClient(EntityAI destination_entity, int slot_id )
11273 {
11274 if (g_Game.IsClient())
11275 {
11276 if (ScriptInputUserData.CanStoreInputUserData())
11277 {
11278 ScriptInputUserData ctx = new ScriptInputUserData;
11280 ctx.Write(1);
11281 ItemBase i1 = this; // @NOTE: workaround for correct serialization
11282 ctx.Write(i1);
11283 ctx.Write(destination_entity);
11284 ctx.Write(true);
11285 ctx.Write(slot_id);
11286 ctx.Send();
11287 }
11288 }
11289 else if (!g_Game.IsMultiplayer())
11290 {
11291 SplitIntoStackMax(destination_entity, slot_id, PlayerBase.Cast(g_Game.GetPlayer()));
11292 }
11293 }
11294
11295 void SplitIntoStackMax(EntityAI destination_entity, int slot_id, PlayerBase player)
11296 {
11297 float split_quantity_new;
11298 ItemBase new_item;
11299 float quantity = GetQuantity();
11300 float stack_max = GetTargetQuantityMax(slot_id);
11301 InventoryLocation loc = new InventoryLocation;
11302
11303 if (destination_entity && slot_id != -1 && InventorySlots.IsSlotIdValid(slot_id))
11304 {
11305 if (stack_max <= GetQuantity())
11306 split_quantity_new = stack_max;
11307 else
11308 split_quantity_new = GetQuantity();
11309
11310 if (ShouldSplitQuantity(split_quantity_new))
11311 {
11312 new_item = ItemBase.Cast(destination_entity.GetInventory().CreateAttachmentEx(this.GetType(), slot_id));
11313 if (new_item)
11314 {
11315 new_item.SetResultOfSplit(true);
11316 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11317 AddQuantity(-split_quantity_new, false, true);
11318 new_item.SetQuantity(split_quantity_new, false, true);
11319 }
11320 }
11321 }
11322 else if (destination_entity && slot_id == -1)
11323 {
11324 if (quantity > stack_max)
11325 split_quantity_new = stack_max;
11326 else
11327 split_quantity_new = quantity;
11328
11329 if (ShouldSplitQuantity(split_quantity_new))
11330 {
11331 GameInventory destinationInventory = destination_entity.GetInventory();
11332 if (destinationInventory.FindFreeLocationFor(this, FindInventoryLocationType.ANY, loc))
11333 {
11334 Object o = destinationInventory.LocationCreateEntity(loc, GetType(), ECE_IN_INVENTORY, RF_DEFAULT);
11335 new_item = ItemBase.Cast(o);
11336 }
11337
11338 if (new_item)
11339 {
11340 new_item.SetResultOfSplit(true);
11341 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11342 AddQuantity(-split_quantity_new, false, true);
11343 new_item.SetQuantity(split_quantity_new, false, true);
11344 }
11345 }
11346 }
11347 else
11348 {
11349 if (stack_max != 0)
11350 {
11351 if (stack_max < GetQuantity())
11352 {
11353 split_quantity_new = GetQuantity() - stack_max;
11354 }
11355
11356 if (split_quantity_new == 0)
11357 {
11358 if (!g_Game.IsMultiplayer())
11359 player.PhysicalPredictiveDropItem(this);
11360 else
11361 player.ServerDropEntity(this);
11362 return;
11363 }
11364
11365 if (ShouldSplitQuantity(split_quantity_new))
11366 {
11367 new_item = ItemBase.Cast(g_Game.CreateObjectEx(GetType(), player.GetWorldPosition(), ECE_PLACE_ON_SURFACE));
11368
11369 if (new_item)
11370 {
11371 new_item.SetResultOfSplit(true);
11372 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11373 SetQuantity(split_quantity_new, false, true);
11374 new_item.SetQuantity(stack_max, false, true);
11375 new_item.PlaceOnSurface();
11376 }
11377 }
11378 }
11379 }
11380 }
11381
11382 override void SplitIntoStackMaxEx(EntityAI destination_entity, int slot_id)
11383 {
11384 float split_quantity_new;
11385 ItemBase new_item;
11386 float quantity = GetQuantity();
11387 float stack_max = GetTargetQuantityMax(slot_id);
11388 InventoryLocation loc = new InventoryLocation;
11389
11390 if (destination_entity && slot_id != -1 && InventorySlots.IsSlotIdValid(slot_id))
11391 {
11392 if (stack_max <= GetQuantity())
11393 split_quantity_new = stack_max;
11394 else
11395 split_quantity_new = GetQuantity();
11396
11397 if (ShouldSplitQuantity(split_quantity_new))
11398 {
11399 new_item = ItemBase.Cast(destination_entity.GetInventory().CreateAttachmentEx(this.GetType(), slot_id));
11400 if (new_item)
11401 {
11402 new_item.SetResultOfSplit(true);
11403 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11404 AddQuantity(-split_quantity_new, false, true);
11405 new_item.SetQuantity(split_quantity_new, false, true);
11406 }
11407 }
11408 }
11409 else if (destination_entity && slot_id == -1)
11410 {
11411 if (quantity > stack_max)
11412 split_quantity_new = stack_max;
11413 else
11414 split_quantity_new = quantity;
11415
11416 if (ShouldSplitQuantity(split_quantity_new))
11417 {
11418 GameInventory destinationInventory = destination_entity.GetInventory();
11419 if (destinationInventory.FindFreeLocationFor(this, FindInventoryLocationType.ANY, loc))
11420 {
11421 Object o = destinationInventory.LocationCreateEntity(loc, GetType(), ECE_IN_INVENTORY, RF_DEFAULT);
11422 new_item = ItemBase.Cast(o);
11423 }
11424
11425 if (new_item)
11426 {
11427 new_item.SetResultOfSplit(true);
11428 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11429 AddQuantity(-split_quantity_new, false, true);
11430 new_item.SetQuantity(split_quantity_new, false, true);
11431 }
11432 }
11433 }
11434 else
11435 {
11436 if (stack_max != 0)
11437 {
11438 if (stack_max < GetQuantity())
11439 {
11440 split_quantity_new = GetQuantity() - stack_max;
11441 }
11442
11443 if (ShouldSplitQuantity(split_quantity_new))
11444 {
11445 new_item = ItemBase.Cast(g_Game.CreateObjectEx(GetType(),GetWorldPosition(), ECE_PLACE_ON_SURFACE));
11446
11447 if (new_item)
11448 {
11449 new_item.SetResultOfSplit(true);
11450 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11451 SetQuantity(split_quantity_new, false, true);
11452 new_item.SetQuantity(stack_max, false, true);
11453 new_item.PlaceOnSurface();
11454 }
11455 }
11456 }
11457 }
11458 }
11459
11460 void SplitIntoStackMaxToInventoryLocationClient(notnull InventoryLocation dst)
11461 {
11462 if (g_Game.IsClient())
11463 {
11464 if (ScriptInputUserData.CanStoreInputUserData())
11465 {
11466 ScriptInputUserData ctx = new ScriptInputUserData;
11468 ctx.Write(4);
11469 ItemBase thiz = this; // @NOTE: workaround for correct serialization
11470 ctx.Write(thiz);
11471 dst.WriteToContext(ctx);
11472 ctx.Send();
11473 }
11474 }
11475 else if (!g_Game.IsMultiplayer())
11476 {
11478 }
11479 }
11480
11481 void SplitIntoStackMaxCargoClient(EntityAI destination_entity, int idx, int row, int col)
11482 {
11483 if (g_Game.IsClient())
11484 {
11485 if (ScriptInputUserData.CanStoreInputUserData())
11486 {
11487 ScriptInputUserData ctx = new ScriptInputUserData;
11489 ctx.Write(2);
11490 ItemBase dummy = this; // @NOTE: workaround for correct serialization
11491 ctx.Write(dummy);
11492 ctx.Write(destination_entity);
11493 ctx.Write(true);
11494 ctx.Write(idx);
11495 ctx.Write(row);
11496 ctx.Write(col);
11497 ctx.Send();
11498 }
11499 }
11500 else if (!g_Game.IsMultiplayer())
11501 {
11502 SplitIntoStackMaxCargo(destination_entity, idx, row, col);
11503 }
11504 }
11505
11506 void SplitIntoStackMaxToInventoryLocation(notnull InventoryLocation dst)
11507 {
11509 }
11510
11511 ItemBase SplitIntoStackMaxToInventoryLocationEx(notnull InventoryLocation dst)
11512 {
11513 float quantity = GetQuantity();
11514 float split_quantity_new;
11515 ItemBase new_item;
11516 if (dst.IsValid())
11517 {
11518 int slot_id = dst.GetSlot();
11519 float stack_max = GetTargetQuantityMax(slot_id);
11520
11521 if (quantity > stack_max)
11522 split_quantity_new = stack_max;
11523 else
11524 split_quantity_new = quantity;
11525
11526 if (ShouldSplitQuantity(split_quantity_new))
11527 {
11528 new_item = ItemBase.Cast(GameInventory.LocationCreateEntity(dst, this.GetType(), ECE_IN_INVENTORY, RF_DEFAULT));
11529
11530 if (new_item)
11531 {
11532 new_item.SetResultOfSplit(true);
11533 MiscGameplayFunctions.TransferItemProperties(this,new_item);
11534 AddQuantity(-split_quantity_new, false, true);
11535 new_item.SetQuantity(split_quantity_new, false, true);
11536 }
11537
11538 return new_item;
11539 }
11540 }
11541
11542 return null;
11543 }
11544
11545 void SplitIntoStackMaxCargo(EntityAI destination_entity, int idx, int row, int col)
11546 {
11547 float quantity = GetQuantity();
11548 float split_quantity_new;
11549 ItemBase new_item;
11550 if (destination_entity)
11551 {
11552 float stackable = GetTargetQuantityMax();
11553 if (quantity > stackable)
11554 split_quantity_new = stackable;
11555 else
11556 split_quantity_new = quantity;
11557
11558 if (ShouldSplitQuantity(split_quantity_new))
11559 {
11560 new_item = ItemBase.Cast(destination_entity.GetInventory().CreateEntityInCargoEx(this.GetType(), idx, row, col, false));
11561 if (new_item)
11562 {
11563 new_item.SetResultOfSplit(true);
11564 MiscGameplayFunctions.TransferItemProperties(this,new_item);
11565 AddQuantity(-split_quantity_new, false, true);
11566 new_item.SetQuantity(split_quantity_new, false, true);
11567 }
11568 }
11569 }
11570 }
11571
11572 void SplitIntoStackMaxHandsClient(PlayerBase player)
11573 {
11574 if (g_Game.IsClient())
11575 {
11576 if (ScriptInputUserData.CanStoreInputUserData())
11577 {
11578 ScriptInputUserData ctx = new ScriptInputUserData;
11580 ctx.Write(3);
11581 ItemBase i1 = this; // @NOTE: workaround for correct serialization
11582 ctx.Write(i1);
11583 ItemBase destination_entity = this;
11584 ctx.Write(destination_entity);
11585 ctx.Write(true);
11586 ctx.Write(0);
11587 ctx.Send();
11588 }
11589 }
11590 else if (!g_Game.IsMultiplayer())
11591 {
11592 SplitIntoStackMaxHands(player);
11593 }
11594 }
11595
11596 void SplitIntoStackMaxHands(PlayerBase player)
11597 {
11598 float quantity = GetQuantity();
11599 float split_quantity_new;
11600 ref ItemBase new_item;
11601 if (player)
11602 {
11603 float stackable = GetTargetQuantityMax();
11604 if (quantity > stackable)
11605 split_quantity_new = stackable;
11606 else
11607 split_quantity_new = quantity;
11608
11609 if (ShouldSplitQuantity(split_quantity_new))
11610 {
11611 EntityAI in_hands = player.GetHumanInventory().CreateInHands(this.GetType());
11612 new_item = ItemBase.Cast(in_hands);
11613 if (new_item)
11614 {
11615 new_item.SetResultOfSplit(true);
11616 MiscGameplayFunctions.TransferItemProperties(this,new_item);
11617 AddQuantity(-split_quantity_new, false, true);
11618 new_item.SetQuantity(split_quantity_new, false, true);
11619 }
11620 }
11621 }
11622 }
11623
11624 void SplitItemToInventoryLocation(notnull InventoryLocation dst)
11625 {
11626 float quantity = GetQuantity();
11627 float split_quantity_new = Math.Floor(quantity * 0.5);
11628
11629 if (!ShouldSplitQuantity(split_quantity_new))
11630 return;
11631
11632 ItemBase new_item = ItemBase.Cast(GameInventory.LocationCreateEntity(dst, GetType(), ECE_IN_INVENTORY, RF_DEFAULT));
11633
11634 if (new_item)
11635 {
11636 if (new_item.GetQuantityMax() < split_quantity_new)
11637 {
11638 split_quantity_new = new_item.GetQuantityMax();
11639 }
11640
11641 new_item.SetResultOfSplit(true);
11642 MiscGameplayFunctions.TransferItemProperties(this, new_item);
11643
11644 if (dst.IsValid() && dst.GetType() == InventoryLocationType.ATTACHMENT && split_quantity_new > 1)
11645 {
11646 AddQuantity(-1, false, true);
11647 new_item.SetQuantity(1, false, true);
11648 }
11649 else
11650 {
11651 AddQuantity(-split_quantity_new, false, true);
11652 new_item.SetQuantity(split_quantity_new, false, true);
11653 }
11654 }
11655 }
11656
11657 void SplitItem(PlayerBase player)
11658 {
11659 float quantity = GetQuantity();
11660 float split_quantity_new = Math.Floor(quantity / 2);
11661
11662 if (!ShouldSplitQuantity(split_quantity_new))
11663 return;
11664
11665 InventoryLocation invloc = new InventoryLocation;
11666 bool found = player.GetInventory().FindFirstFreeLocationForNewEntity(GetType(), FindInventoryLocationType.ATTACHMENT, invloc);
11667
11668 ItemBase new_item;
11669 new_item = player.CreateCopyOfItemInInventoryOrGroundEx(this, true);
11670
11671 if (new_item)
11672 {
11673 if (new_item.GetQuantityMax() < split_quantity_new)
11674 {
11675 split_quantity_new = new_item.GetQuantityMax();
11676 }
11677 if (found && invloc.IsValid() && invloc.GetType() == InventoryLocationType.ATTACHMENT && split_quantity_new > 1)
11678 {
11679 AddQuantity(-1, false, true);
11680 new_item.SetQuantity(1, false, true);
11681 }
11682 else if (split_quantity_new > 1)
11683 {
11684 AddQuantity(-split_quantity_new, false, true);
11685 new_item.SetQuantity(split_quantity_new, false, true);
11686 }
11687 }
11688 }
11689
11691 void OnQuantityChanged(float delta)
11692 {
11693 SetWeightDirty();
11694 ItemBase parent = ItemBase.Cast(GetHierarchyParent());
11695
11696 if (parent)
11697 parent.OnAttachmentQuantityChangedEx(this, delta);
11698
11699 if (IsLiquidContainer())
11700 {
11701 if (GetQuantityNormalized() <= 0.0)
11702 {
11704 }
11705 else if (GetLiquidType() == LIQUID_NONE)
11706 {
11707 ErrorEx("Undefined liquid type quantity changed, please define liquid type first! Using init value.",ErrorExSeverity.INFO);
11709 }
11710 }
11711 }
11712
11715 {
11716 // insert code here
11717 }
11718
11720 void OnAttachmentQuantityChangedEx(ItemBase item , float delta)
11721 {
11723 }
11724
11725 override void EEHealthLevelChanged(int oldLevel, int newLevel, string zone)
11726 {
11727 super.EEHealthLevelChanged(oldLevel,newLevel,zone);
11728
11729 if (g_Game.IsServer())
11730 {
11731 if (newLevel == GameConstants.STATE_RUINED)
11732 {
11734 EntityAI parent = GetHierarchyParent();
11735 if (parent && parent.IsFireplace())
11736 {
11737 CargoBase cargo = GetInventory().GetCargo();
11738 if (cargo)
11739 {
11740 for (int i = 0; i < cargo.GetItemCount(); ++i)
11741 {
11742 parent.GetInventory().TakeEntityToInventory(InventoryMode.SERVER, FindInventoryLocationType.CARGO, cargo.GetItem(i));
11743 }
11744 }
11745 }
11746 }
11747
11748 if (IsResultOfSplit())
11749 {
11750 // reset the splitting result flag, return to normal item behavior
11751 SetResultOfSplit(false);
11752 return;
11753 }
11754
11755 if (m_Cleanness != 0 && oldLevel < newLevel && newLevel != 0)
11756 {
11757 SetCleanness(0);//unclean the item upon damage dealt
11758 }
11759 }
11760 }
11761
11762 // just the split? TODO: verify
11763 override void OnRightClick()
11764 {
11765 super.OnRightClick();
11766
11767 if (CanBeSplit() && !GetDayZGame().IsLeftCtrlDown() && !g_Game.GetPlayer().GetInventory().HasInventoryReservation(this,null))
11768 {
11769 if (g_Game.IsClient())
11770 {
11771 if (ScriptInputUserData.CanStoreInputUserData())
11772 {
11773 EntityAI root = GetHierarchyRoot();
11774 Man playerOwner = GetHierarchyRootPlayer();
11775 InventoryLocation dst = new InventoryLocation;
11776
11777 // If we have no hierarchy root player and the root is the same as this item the source item is in the vicinity so we want to create the new split item there also
11778 if (!playerOwner && root && root == this)
11779 {
11781 }
11782 else
11783 {
11784 // Check if we can place the new split item in the same parent where the source item is placed in or otherwise drop it in vicinity
11785 GetInventory().GetCurrentInventoryLocation(dst);
11786 if (!dst.GetParent() || dst.GetParent() && !dst.GetParent().GetInventory().FindFreeLocationFor(this, FindInventoryLocationType.CARGO, dst))
11787 {
11788 PlayerBase player = PlayerBase.Cast(g_Game.GetPlayer());
11789 if (!player.GetInventory().FindFreeLocationFor(this, FindInventoryLocationType.CARGO, dst) || !playerOwner)
11790 {
11792 }
11793 else
11794 {
11795 dst.SetCargo(dst.GetParent(), this, dst.GetIdx(), dst.GetRow(), dst.GetCol(), dst.GetFlip());
11796 /* hacky solution to check reservation of "this" item instead of null since the gamecode is checking null against null and returning reservation=true incorrectly
11797 this shouldnt cause issues within this scope*/
11798 if (g_Game.GetPlayer().GetInventory().HasInventoryReservation(this, dst))
11799 {
11801 }
11802 else
11803 {
11804 g_Game.GetPlayer().GetInventory().AddInventoryReservationEx(null, dst, GameInventory.c_InventoryReservationTimeoutShortMS);
11805 }
11806 }
11807 }
11808 }
11809
11810 ScriptInputUserData ctx = new ScriptInputUserData;
11812 ctx.Write(4);
11813 ItemBase thiz = this; // @NOTE: workaround for correct serialization
11814 ctx.Write(thiz);
11815 dst.WriteToContext(ctx);
11816 ctx.Write(true); // dummy
11817 ctx.Send();
11818 }
11819 }
11820 else if (!g_Game.IsMultiplayer())
11821 {
11822 SplitItem(PlayerBase.Cast(g_Game.GetPlayer()));
11823 }
11824 }
11825 }
11826
11827 protected void SetInventoryLocationToVicinityOrCurrent(EntityAI root, inout InventoryLocation dst)
11828 {
11829 if (root)
11830 {
11831 vector m4[4];
11832 root.GetTransform(m4);
11833 dst.SetGround(this, m4);
11834 }
11835 else
11836 {
11837 GetInventory().GetCurrentInventoryLocation(dst);
11838 }
11839 }
11840
11841 override bool CanBeCombined(EntityAI other_item, bool reservation_check = true, bool stack_max_limit = false)
11842 {
11843 //TODO: delete check zero quantity check after fix double posts hands fsm events
11844 if (!other_item || GetType() != other_item.GetType() || (IsFullQuantity() && other_item.GetQuantity() > 0) || other_item == this)
11845 return false;
11846
11847 if (GetHealthLevel() == GameConstants.STATE_RUINED || other_item.GetHealthLevel() == GameConstants.STATE_RUINED)
11848 return false;
11849
11850 //can_this_be_combined = ConfigGetBool("canBeSplit");
11852 return false;
11853
11854
11855 Magazine mag = Magazine.Cast(this);
11856 if (mag)
11857 {
11858 if (mag.GetAmmoCount() >= mag.GetAmmoMax())
11859 return false;
11860
11861 if (stack_max_limit)
11862 {
11863 Magazine other_mag = Magazine.Cast(other_item);
11864 if (other_item)
11865 {
11866 if (mag.GetAmmoCount() + other_mag.GetAmmoCount() > mag.GetAmmoMax())
11867 return false;
11868 }
11869
11870 }
11871 }
11872 else
11873 {
11874 //TODO: delete check zero quantity check after fix double posts hands fsm events
11875 if (GetQuantity() >= GetQuantityMax() && other_item.GetQuantity() > 0 )
11876 return false;
11877
11878 if (stack_max_limit && (GetQuantity() + other_item.GetQuantity() > GetQuantityMax()))
11879 return false;
11880 }
11881
11882 PlayerBase player = null;
11883 if (CastTo(player, GetHierarchyRootPlayer())) //false when attached to player's attachment slot
11884 {
11885 if (player.GetInventory().HasAttachment(this))
11886 return false;
11887
11888 if (player.IsItemsToDelete())
11889 return false;
11890 }
11891
11892 if (reservation_check && (GetInventory().HasInventoryReservation(this, null) || other_item.GetInventory().HasInventoryReservation(other_item, null)))
11893 return false;
11894
11895 int slotID;
11896 string slotName;
11897 if (GetInventory().GetCurrentAttachmentSlotInfo(slotID,slotName) && GetHierarchyParent().GetInventory().GetSlotLock(slotID))
11898 return false;
11899
11900 return true;
11901 }
11902
11903 bool IsCombineAll(ItemBase other_item, bool use_stack_max = false)
11904 {
11905 return ComputeQuantityUsed(other_item, use_stack_max) == other_item.GetQuantity();
11906 }
11907
11908 bool IsResultOfSplit()
11909 {
11910 return m_IsResultOfSplit;
11911 }
11912
11913 void SetResultOfSplit(bool value)
11914 {
11915 m_IsResultOfSplit = value;
11916 }
11917
11918 int ComputeQuantityUsed(ItemBase other_item, bool use_stack_max = true)
11919 {
11920 return ComputeQuantityUsedEx(other_item, use_stack_max);
11921 }
11922
11923 float ComputeQuantityUsedEx(ItemBase other_item, bool use_stack_max = true)
11924 {
11925 float other_item_quantity = other_item.GetQuantity();
11926 float this_free_space;
11927
11928 float stack_max = GetQuantityMax();
11929
11930 this_free_space = stack_max - GetQuantity();
11931
11932 if (other_item_quantity > this_free_space)
11933 {
11934 return this_free_space;
11935 }
11936 else
11937 {
11938 return other_item_quantity;
11939 }
11940 }
11941
11942 override void CombineItemsEx(EntityAI entity2, bool use_stack_max = true)
11943 {
11944 CombineItems(ItemBase.Cast(entity2),use_stack_max);
11945 }
11946
11947 void CombineItems(ItemBase other_item, bool use_stack_max = true)
11948 {
11949 if (!CanBeCombined(other_item, false))
11950 return;
11951
11952 if (!IsMagazine() && other_item)
11953 {
11954 float quantity_used = ComputeQuantityUsedEx(other_item,use_stack_max);
11955 if (quantity_used != 0)
11956 {
11957 float hp1 = GetHealth01("","");
11958 float hp2 = other_item.GetHealth01("","");
11959 float hpResult = ((hp1*GetQuantity()) + (hp2*quantity_used));
11960 hpResult = hpResult / (GetQuantity() + quantity_used);
11961
11962 hpResult *= GetMaxHealth();
11963 Math.Round(hpResult);
11964 SetHealth("", "Health", hpResult);
11965
11966 AddQuantity(quantity_used);
11967 other_item.AddQuantity(-quantity_used);
11968 }
11969 }
11970 OnCombine(other_item);
11971 }
11972
11973 void OnCombine(ItemBase other_item)
11974 {
11975 #ifdef SERVER
11976 if (!GetHierarchyRootPlayer() && GetHierarchyParent())
11977 GetHierarchyParent().IncreaseLifetimeUp();
11978 #endif
11979 };
11980
11981 void GetRecipesActions(Man player, out TSelectableActionInfoArray outputList)
11982 {
11983 PlayerBase p = PlayerBase.Cast(player);
11984
11985 array<int> recipesIds = p.m_Recipes;
11986 PluginRecipesManager moduleRecipesManager = PluginRecipesManager.Cast(GetPlugin(PluginRecipesManager));
11987 if (moduleRecipesManager)
11988 {
11989 EntityAI itemInHands = player.GetEntityInHands();
11990 moduleRecipesManager.GetValidRecipes(ItemBase.Cast(this), ItemBase.Cast(itemInHands), recipesIds, p);
11991 }
11992
11993 for (int i = 0;i < recipesIds.Count(); i++)
11994 {
11995 int key = recipesIds.Get(i);
11996 string recipeName = moduleRecipesManager.GetRecipeName(key);
11997 outputList.Insert(new TSelectableActionInfo(SAT_CRAFTING, key, recipeName));
11998 }
11999 }
12000
12001 // -------------------------------------------------------------------------
12002 override void GetDebugActions(out TSelectableActionInfoArrayEx outputList)
12003 {
12004 super.GetDebugActions(outputList);
12005
12006 //quantity
12007 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.ADD_QUANTITY, "Quantity +20%", FadeColors.LIGHT_GREY));
12008 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.REMOVE_QUANTITY, "Quantity -20%", FadeColors.LIGHT_GREY));
12009 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SET_QUANTITY_0, "Set Quantity 0", FadeColors.LIGHT_GREY));
12010 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SET_MAX_QUANTITY, "Set Quantity Max", FadeColors.LIGHT_GREY));
12011 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12012
12013 //health
12014 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.ADD_HEALTH, "Health +20%", FadeColors.LIGHT_GREY));
12015 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.REMOVE_HEALTH, "Health -20%", FadeColors.LIGHT_GREY));
12016 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.DESTROY_HEALTH, "Health 0", FadeColors.LIGHT_GREY));
12017 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12018 //temperature
12019 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.ADD_TEMPERATURE, "Temperature +20", FadeColors.LIGHT_GREY));
12020 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.REMOVE_TEMPERATURE, "Temperature -20", FadeColors.LIGHT_GREY));
12021 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.FLIP_FROZEN, "Toggle Frozen", FadeColors.LIGHT_GREY));
12022 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12023
12024 //wet
12025 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.ADD_WETNESS, "Wetness +20", FadeColors.LIGHT_GREY));
12026 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.REMOVE_WETNESS, "Wetness -20", FadeColors.LIGHT_GREY));
12027 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12028
12029 //liquidtype
12030 if (IsLiquidContainer())
12031 {
12032 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.LIQUIDTYPE_UP, "LiquidType Next", FadeColors.LIGHT_GREY));
12033 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.LIQUIDTYPE_DOWN, "LiquidType Previous", FadeColors.LIGHT_GREY));
12034 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12035 }
12036
12037 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.MAKE_SPECIAL, "Make Special", FadeColors.LIGHT_GREY));
12038 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12039
12040 // watch
12041 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.WATCH_ITEM, "Watch (CTRL-Z)", FadeColors.LIGHT_GREY));
12042 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.WATCH_PLAYER, "Watch Player", FadeColors.LIGHT_GREY));
12043 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12044
12045 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.DELETE, "Delete", FadeColors.RED));
12046
12047 InventoryLocation loc = new InventoryLocation();
12048 GetInventory().GetCurrentInventoryLocation(loc);
12049 if (!loc || loc.GetType() == InventoryLocationType.GROUND)
12050 {
12051 if (Gizmo_IsSupported())
12052 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.GIZMO_OBJECT, "Gizmo Object", FadeColors.LIGHT_GREY));
12053 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.GIZMO_PHYSICS, "Gizmo Physics (SP Only)", FadeColors.LIGHT_GREY)); // intentionally allowed for testing physics desync
12054 }
12055
12056 outputList.Insert(new TSelectableActionInfoWithColor(SAT_DEBUG_ACTION, EActions.SEPARATOR, "___________________________", FadeColors.RED));
12057 }
12058
12059 // -------------------------------------------------------------------------
12060 // -------------------------------------------------------------------------
12061 // -------------------------------------------------------------------------
12062 override bool OnAction(int action_id, Man player, ParamsReadContext ctx)
12063 {
12064 super.OnAction(action_id, player, ctx);
12065
12066 if (g_Game.IsClient() || !g_Game.IsMultiplayer())
12067 {
12068 switch (action_id)
12069 {
12070 case EActions.GIZMO_OBJECT:
12071 if (GetGizmoApi())
12072 GetGizmoApi().SelectObject(this);
12073 return true;
12074 case EActions.GIZMO_PHYSICS:
12075 if (GetGizmoApi())
12076 GetGizmoApi().SelectPhysics(GetPhysics());
12077 return true;
12078 }
12079 }
12080
12081 if (g_Game.IsServer())
12082 {
12083 switch (action_id)
12084 {
12085 case EActions.DELETE:
12086 Delete();
12087 return true;
12088 }
12089 }
12090
12091 if (action_id >= EActions.RECIPES_RANGE_START && action_id < EActions.RECIPES_RANGE_END)
12092 {
12093 PluginRecipesManager plugin_recipes_manager = PluginRecipesManager.Cast(GetPlugin(PluginRecipesManager));
12094 int idWithoutOffset = action_id - EActions.RECIPES_RANGE_START;
12095 PlayerBase p = PlayerBase.Cast(player);
12096 if (EActions.RECIPES_RANGE_START < 1000)
12097 {
12098 float anim_length = plugin_recipes_manager.GetRecipeLengthInSecs(idWithoutOffset);
12099 float specialty_weight = plugin_recipes_manager.GetRecipeSpecialty(idWithoutOffset);
12100 }
12101 }
12102 #ifndef SERVER
12103 else if (action_id == EActions.WATCH_PLAYER)
12104 {
12105 PluginDeveloper.SetDeveloperItemClientEx(player);
12106 }
12107 #endif
12108 if (g_Game.IsServer())
12109 {
12110 if (action_id >= EActions.DEBUG_ITEM_WATCH_BUTTON_RANGE_START && action_id < EActions.DEBUG_ITEM_WATCH_BUTTON_RANGE_END)
12111 {
12112 int id = action_id - EActions.DEBUG_ITEM_WATCH_BUTTON_RANGE_START;
12113 OnDebugButtonPressServer(id + 1);
12114 }
12115
12116 else if (action_id >= EActions.DEBUG_AGENTS_RANGE_INJECT_START && action_id < EActions.DEBUG_AGENTS_RANGE_INJECT_END)
12117 {
12118 int agent_id = action_id - EActions.DEBUG_AGENTS_RANGE_INJECT_START;
12119 InsertAgent(agent_id,100);
12120 }
12121
12122 else if (action_id >= EActions.DEBUG_AGENTS_RANGE_REMOVE_START && action_id < EActions.DEBUG_AGENTS_RANGE_REMOVE_END)
12123 {
12124 int agent_id2 = action_id - EActions.DEBUG_AGENTS_RANGE_REMOVE_START;
12125 RemoveAgent(agent_id2);
12126 }
12127
12128 else if (action_id == EActions.ADD_QUANTITY)
12129 {
12130 if (IsMagazine())
12131 {
12132 Magazine mag = Magazine.Cast(this);
12133 mag.ServerSetAmmoCount(mag.GetAmmoCount() + mag.GetAmmoMax() * 0.2);
12134 }
12135 else
12136 {
12137 AddQuantity(GetQuantityMax() * 0.2);
12138 }
12139
12140 if (m_EM)
12141 {
12142 m_EM.AddEnergy(m_EM.GetEnergyMax() * 0.2);
12143 }
12144 //PrintVariables();
12145 }
12146
12147 else if (action_id == EActions.REMOVE_QUANTITY) //Quantity -20%
12148 {
12149 if (IsMagazine())
12150 {
12151 Magazine mag2 = Magazine.Cast(this);
12152 mag2.ServerSetAmmoCount(mag2.GetAmmoCount() - mag2.GetAmmoMax() * 0.2);
12153 }
12154 else
12155 {
12156 AddQuantity(- GetQuantityMax() * 0.2);
12157 }
12158 if (m_EM)
12159 {
12160 m_EM.AddEnergy(- m_EM.GetEnergyMax() * 0.2);
12161 }
12162 //PrintVariables();
12163 }
12164
12165 else if (action_id == EActions.SET_QUANTITY_0) //SetMaxQuantity
12166 {
12167 SetQuantity(0);
12168
12169 if (m_EM)
12170 {
12171 m_EM.SetEnergy(0);
12172 }
12173 }
12174
12175 else if (action_id == EActions.SET_MAX_QUANTITY) //SetMaxQuantity
12176 {
12178
12179 if (m_EM)
12180 {
12181 m_EM.SetEnergy(m_EM.GetEnergyMax());
12182 }
12183 }
12184
12185 else if (action_id == EActions.ADD_HEALTH)
12186 {
12187 AddHealth("","",GetMaxHealth("","Health")/5);
12188 }
12189 else if (action_id == EActions.REMOVE_HEALTH)
12190 {
12191 AddHealth("","",-GetMaxHealth("","Health")/5);
12192 }
12193 else if (action_id == EActions.DESTROY_HEALTH)
12194 {
12195 SetHealth01("","",0);
12196 }
12197 else if (action_id == EActions.WATCH_ITEM)
12198 {
12200 mid.RegisterDebugItem(ItemBase.Cast(this), PlayerBase.Cast(player));
12201 #ifdef DEVELOPER
12202 SetDebugDeveloper_item(this);
12203 #endif
12204 }
12205
12206 else if (action_id == EActions.ADD_TEMPERATURE)
12207 {
12208 AddTemperature(20);
12209 //PrintVariables();
12210 }
12211
12212 else if (action_id == EActions.REMOVE_TEMPERATURE)
12213 {
12214 AddTemperature(-20);
12215 //PrintVariables();
12216 }
12217
12218 else if (action_id == EActions.FLIP_FROZEN)
12219 {
12220 SetFrozen(!GetIsFrozen());
12221 //PrintVariables();
12222 }
12223
12224 else if (action_id == EActions.ADD_WETNESS)
12225 {
12226 AddWet(GetWetMax()/5);
12227 //PrintVariables();
12228 }
12229
12230 else if (action_id == EActions.REMOVE_WETNESS)
12231 {
12232 AddWet(-GetWetMax()/5);
12233 //PrintVariables();
12234 }
12235
12236 else if (action_id == EActions.LIQUIDTYPE_UP)
12237 {
12238 int curr_type = GetLiquidType();
12239 SetLiquidType(curr_type * 2);
12240 //AddWet(1);
12241 //PrintVariables();
12242 }
12243
12244 else if (action_id == EActions.LIQUIDTYPE_DOWN)
12245 {
12246 int curr_type2 = GetLiquidType();
12247 SetLiquidType(curr_type2 / 2);
12248 }
12249
12250 else if (action_id == EActions.MAKE_SPECIAL)
12251 {
12252 auto debugParams = DebugSpawnParams.WithPlayer(player);
12253 OnDebugSpawnEx(debugParams);
12254 }
12255
12256 }
12257
12258
12259 return false;
12260 }
12261
12262 // -------------------------------------------------------------------------
12263
12264
12267 void OnActivatedByTripWire();
12268
12270 void OnActivatedByItem(notnull ItemBase item);
12271
12272 //----------------------------------------------------------------
12273 //returns true if item is able to explode when put in fire
12274 bool CanExplodeInFire()
12275 {
12276 return false;
12277 }
12278
12279 //----------------------------------------------------------------
12280 bool CanEat()
12281 {
12282 return true;
12283 }
12284
12285 //----------------------------------------------------------------
12286 override bool IsIgnoredByConstruction()
12287 {
12288 return true;
12289 }
12290
12291 //----------------------------------------------------------------
12292 //has FoodStages in config?
12293 bool HasFoodStage()
12294 {
12295 string config_path = string.Format("CfgVehicles %1 Food FoodStages", GetType());
12296 return g_Game.ConfigIsExisting(config_path);
12297 }
12298
12300 FoodStage GetFoodStage()
12301 {
12302 return null;
12303 }
12304
12305 bool CanBeCooked()
12306 {
12307 return false;
12308 }
12309
12310 bool CanBeCookedOnStick()
12311 {
12312 return false;
12313 }
12314
12316 void RefreshAudioVisualsOnClient( CookingMethodType cooking_method, bool is_done, bool is_empty, bool is_burned );
12318
12319 //----------------------------------------------------------------
12320 bool CanRepair(ItemBase item_repair_kit)
12321 {
12322 PluginRepairing module_repairing = PluginRepairing.Cast(GetPlugin(PluginRepairing));
12323 return module_repairing.CanRepair(this, item_repair_kit);
12324 }
12325
12326 //----------------------------------------------------------------
12327 bool Repair(PlayerBase player, ItemBase item_repair_kit, float specialty_weight)
12328 {
12329 PluginRepairing module_repairing = PluginRepairing.Cast(GetPlugin(PluginRepairing));
12330 return module_repairing.Repair(player, this, item_repair_kit, specialty_weight);
12331 }
12332
12333 //----------------------------------------------------------------
12334 int GetItemSize()
12335 {
12336 /*
12337 vector v_size = this.ConfigGetVector("itemSize");
12338 int v_size_x = v_size[0];
12339 int v_size_y = v_size[1];
12340 int size = v_size_x * v_size_y;
12341 return size;
12342 */
12343
12344 return 1;
12345 }
12346
12347 //----------------------------------------------------------------
12348 //Override for allowing seemingly unallowed moves when two clients send a conflicting message simultaneously
12349 bool CanBeMovedOverride()
12350 {
12351 return m_CanBeMovedOverride;
12352 }
12353
12354 //----------------------------------------------------------------
12355 //Override for allowing seemingly unallowed moves when two clients send a conflicting message simultaneously
12356 void SetCanBeMovedOverride(bool setting)
12357 {
12358 m_CanBeMovedOverride = setting;
12359 }
12360
12361 //----------------------------------------------------------------
12369 void MessageToOwnerStatus(string text)
12370 {
12371 PlayerBase player = PlayerBase.Cast(this.GetHierarchyRootPlayer());
12372
12373 if (player)
12374 {
12375 player.MessageStatus(text);
12376 }
12377 }
12378
12379 //----------------------------------------------------------------
12387 void MessageToOwnerAction(string text)
12388 {
12389 PlayerBase player = PlayerBase.Cast(this.GetHierarchyRootPlayer());
12390
12391 if (player)
12392 {
12393 player.MessageAction(text);
12394 }
12395 }
12396
12397 //----------------------------------------------------------------
12405 void MessageToOwnerFriendly(string text)
12406 {
12407 PlayerBase player = PlayerBase.Cast(this.GetHierarchyRootPlayer());
12408
12409 if (player)
12410 {
12411 player.MessageFriendly(text);
12412 }
12413 }
12414
12415 //----------------------------------------------------------------
12423 void MessageToOwnerImportant(string text)
12424 {
12425 PlayerBase player = PlayerBase.Cast(this.GetHierarchyRootPlayer());
12426
12427 if (player)
12428 {
12429 player.MessageImportant(text);
12430 }
12431 }
12432
12433 override bool IsItemBase()
12434 {
12435 return true;
12436 }
12437
12438 // Checks if item is of questioned kind
12439 override bool KindOf(string tag)
12440 {
12441 bool found = false;
12442 string item_name = this.GetType();
12443 ref TStringArray item_tag_array = new TStringArray;
12444 g_Game.ConfigGetTextArray("cfgVehicles " + item_name + " itemInfo", item_tag_array);
12445
12446 int array_size = item_tag_array.Count();
12447 for (int i = 0; i < array_size; i++)
12448 {
12449 if (item_tag_array.Get(i) == tag)
12450 {
12451 found = true;
12452 break;
12453 }
12454 }
12455 return found;
12456 }
12457
12458
12459 override void OnRPC(PlayerIdentity sender, int rpc_type,ParamsReadContext ctx)
12460 {
12461 //Debug.Log("OnRPC called");
12462 super.OnRPC(sender, rpc_type,ctx);
12463
12464 //Play soundset for attachment locking (ActionLockAttachment.c)
12465 switch (rpc_type)
12466 {
12467 #ifndef SERVER
12468 case ERPCs.RPC_SOUND_LOCK_ATTACH:
12469 Param2<bool, string> p = new Param2<bool, string>(false, "");
12470
12471 if (!ctx.Read(p))
12472 return;
12473
12474 bool play = p.param1;
12475 string soundSet = p.param2;
12476
12477 if (play)
12478 {
12479 if (m_LockingSound)
12480 {
12482 {
12483 m_LockingSound = SEffectManager.PlaySound(soundSet, GetPosition(), 0, 0, true);
12484 }
12485 }
12486 else
12487 {
12488 m_LockingSound = SEffectManager.PlaySound(soundSet, GetPosition(), 0, 0, true);
12489 }
12490 }
12491 else
12492 {
12493 SEffectManager.DestroyEffect(m_LockingSound);
12494 }
12495
12496 break;
12497 #endif
12498
12499 }
12500
12501 if (GetWrittenNoteData())
12502 {
12503 GetWrittenNoteData().OnRPC(sender, rpc_type,ctx);
12504 }
12505 }
12506
12507 //-----------------------------
12508 // VARIABLE MANIPULATION SYSTEM
12509 //-----------------------------
12510 int NameToID(string name)
12511 {
12512 PluginVariables plugin = PluginVariables.Cast(GetPlugin(PluginVariables));
12513 return plugin.GetID(name);
12514 }
12515
12516 string IDToName(int id)
12517 {
12518 PluginVariables plugin = PluginVariables.Cast(GetPlugin(PluginVariables));
12519 return plugin.GetName(id);
12520 }
12521
12523 void OnSyncVariables(ParamsReadContext ctx)//with ID optimization
12524 {
12525 //Debug.Log("OnSyncVariables called for item: "+ ToString(this.GetType()),"varSync");
12526 //read the flags
12527 int varFlags;
12528 if (!ctx.Read(varFlags))
12529 return;
12530
12531 if (varFlags & ItemVariableFlags.FLOAT)
12532 {
12533 ReadVarsFromCTX(ctx);
12534 }
12535 }
12536
12537 override void SerializeNumericalVars(array<float> floats_out)
12538 {
12539 //some variables handled on EntityAI level already!
12540 super.SerializeNumericalVars(floats_out);
12541
12542 // the order of serialization must be the same as the order of de-serialization
12543 //--------------------------------------------
12544 if (IsVariableSet(VARIABLE_QUANTITY))
12545 {
12546 floats_out.Insert(m_VarQuantity);
12547 }
12548 //--------------------------------------------
12549 if (IsVariableSet(VARIABLE_WET))
12550 {
12551 floats_out.Insert(m_VarWet);
12552 }
12553 //--------------------------------------------
12554 if (IsVariableSet(VARIABLE_LIQUIDTYPE))
12555 {
12556 floats_out.Insert(m_VarLiquidType);
12557 }
12558 //--------------------------------------------
12559 if (IsVariableSet(VARIABLE_COLOR))
12560 {
12561 floats_out.Insert(m_ColorComponentR);
12562 floats_out.Insert(m_ColorComponentG);
12563 floats_out.Insert(m_ColorComponentB);
12564 floats_out.Insert(m_ColorComponentA);
12565 }
12566 //--------------------------------------------
12567 if (IsVariableSet(VARIABLE_CLEANNESS))
12568 {
12569 floats_out.Insert(m_Cleanness);
12570 }
12571 }
12572
12573 override void DeSerializeNumericalVars(array<float> floats)
12574 {
12575 //some variables handled on EntityAI level already!
12576 super.DeSerializeNumericalVars(floats);
12577
12578 // the order of serialization must be the same as the order of de-serialization
12579 int index = 0;
12580 int mask = Math.Round(floats.Get(index));
12581
12582 index++;
12583 //--------------------------------------------
12584 if (mask & VARIABLE_QUANTITY)
12585 {
12586 if (m_IsStoreLoad)
12587 {
12588 SetStoreLoadedQuantity(floats.Get(index));
12589 }
12590 else
12591 {
12592 float quantity = floats.Get(index);
12593 SetQuantity(quantity, true, false, false, false);
12594 }
12595 index++;
12596 }
12597 //--------------------------------------------
12598 if (mask & VARIABLE_WET)
12599 {
12600 float wet = floats.Get(index);
12601 SetWet(wet);
12602 index++;
12603 }
12604 //--------------------------------------------
12605 if (mask & VARIABLE_LIQUIDTYPE)
12606 {
12607 int liquidtype = Math.Round(floats.Get(index));
12608 SetLiquidType(liquidtype);
12609 index++;
12610 }
12611 //--------------------------------------------
12612 if (mask & VARIABLE_COLOR)
12613 {
12614 m_ColorComponentR = Math.Round(floats.Get(index));
12615 index++;
12616 m_ColorComponentG = Math.Round(floats.Get(index));
12617 index++;
12618 m_ColorComponentB = Math.Round(floats.Get(index));
12619 index++;
12620 m_ColorComponentA = Math.Round(floats.Get(index));
12621 index++;
12622 }
12623 //--------------------------------------------
12624 if (mask & VARIABLE_CLEANNESS)
12625 {
12626 int cleanness = Math.Round(floats.Get(index));
12627 SetCleanness(cleanness);
12628 index++;
12629 }
12630 }
12631
12632 override void WriteVarsToCTX(ParamsWriteContext ctx)
12633 {
12634 super.WriteVarsToCTX(ctx);
12635
12636 //--------------------------------------------
12637 if (IsVariableSet(VARIABLE_QUANTITY))
12638 {
12639 ctx.Write(GetQuantity());
12640 }
12641 //--------------------------------------------
12642 if (IsVariableSet(VARIABLE_WET))
12643 {
12644 ctx.Write(GetWet());
12645 }
12646 //--------------------------------------------
12647 if (IsVariableSet(VARIABLE_LIQUIDTYPE))
12648 {
12649 ctx.Write(GetLiquidType());
12650 }
12651 //--------------------------------------------
12652 if (IsVariableSet(VARIABLE_COLOR))
12653 {
12654 int r,g,b,a;
12655 GetColor(r,g,b,a);
12656 ctx.Write(r);
12657 ctx.Write(g);
12658 ctx.Write(b);
12659 ctx.Write(a);
12660 }
12661 //--------------------------------------------
12662 if (IsVariableSet(VARIABLE_CLEANNESS))
12663 {
12664 ctx.Write(GetCleanness());
12665 }
12666 }
12667
12668 override bool ReadVarsFromCTX(ParamsReadContext ctx, int version = -1)//with ID optimization
12669 {
12670 if (!super.ReadVarsFromCTX(ctx,version))
12671 return false;
12672
12673 int intValue;
12674 float value;
12675
12676 if (version < 140)
12677 {
12678 if (!ctx.Read(intValue))
12679 return false;
12680
12681 m_VariablesMask = intValue;
12682 }
12683
12684 if (m_VariablesMask & VARIABLE_QUANTITY)
12685 {
12686 if (!ctx.Read(value))
12687 return false;
12688
12689 if (IsStoreLoad())
12690 {
12692 }
12693 else
12694 {
12695 SetQuantity(value, true, false, false, false);
12696 }
12697 }
12698 //--------------------------------------------
12699 if (version < 140)
12700 {
12701 if (m_VariablesMask & VARIABLE_TEMPERATURE)
12702 {
12703 if (!ctx.Read(value))
12704 return false;
12705 SetTemperatureDirect(value);
12706 }
12707 }
12708 //--------------------------------------------
12709 if (m_VariablesMask & VARIABLE_WET)
12710 {
12711 if (!ctx.Read(value))
12712 return false;
12713 SetWet(value);
12714 }
12715 //--------------------------------------------
12716 if (m_VariablesMask & VARIABLE_LIQUIDTYPE)
12717 {
12718 if (!ctx.Read(intValue))
12719 return false;
12720 SetLiquidType(intValue);
12721 }
12722 //--------------------------------------------
12723 if (m_VariablesMask & VARIABLE_COLOR)
12724 {
12725 int r,g,b,a;
12726 if (!ctx.Read(r))
12727 return false;
12728 if (!ctx.Read(g))
12729 return false;
12730 if (!ctx.Read(b))
12731 return false;
12732 if (!ctx.Read(a))
12733 return false;
12734
12735 SetColor(r,g,b,a);
12736 }
12737 //--------------------------------------------
12738 if (m_VariablesMask & VARIABLE_CLEANNESS)
12739 {
12740 if (!ctx.Read(intValue))
12741 return false;
12742 SetCleanness(intValue);
12743 }
12744 //--------------------------------------------
12745 if (version >= 138 && version < 140)
12746 {
12747 if (m_VariablesMask & VARIABLE_TEMPERATURE)
12748 {
12749 if (!ctx.Read(intValue))
12750 return false;
12751 SetFrozen(intValue);
12752 }
12753 }
12754
12755 return true;
12756 }
12757
12758 //----------------------------------------------------------------
12759 override bool OnStoreLoad(ParamsReadContext ctx, int version)
12760 {
12761 m_IsStoreLoad = true;
12763 {
12764 m_FixDamageSystemInit = true;
12765 }
12766
12767 if (!super.OnStoreLoad(ctx, version))
12768 {
12769 m_IsStoreLoad = false;
12770 return false;
12771 }
12772
12773 if (version >= 114)
12774 {
12775 bool hasQuickBarIndexSaved;
12776
12777 if (!ctx.Read(hasQuickBarIndexSaved))
12778 {
12779 m_IsStoreLoad = false;
12780 return false;
12781 }
12782
12783 if (hasQuickBarIndexSaved)
12784 {
12785 int itmQBIndex;
12786
12787 //Load quickbar item bind
12788 if (!ctx.Read(itmQBIndex))
12789 {
12790 m_IsStoreLoad = false;
12791 return false;
12792 }
12793
12794 PlayerBase parentPlayer = PlayerBase.Cast(GetHierarchyRootPlayer());
12795 if (itmQBIndex != -1 && parentPlayer)
12796 parentPlayer.SetLoadedQuickBarItemBind(this, itmQBIndex);
12797 }
12798 }
12799 else
12800 {
12801 // Backup of how it used to be
12802 PlayerBase player;
12803 int itemQBIndex;
12804 if (version == int.MAX)
12805 {
12806 if (!ctx.Read(itemQBIndex))
12807 {
12808 m_IsStoreLoad = false;
12809 return false;
12810 }
12811 }
12812 else if (Class.CastTo(player, GetHierarchyRootPlayer()))
12813 {
12814 //Load quickbar item bind
12815 if (!ctx.Read(itemQBIndex))
12816 {
12817 m_IsStoreLoad = false;
12818 return false;
12819 }
12820 if (itemQBIndex != -1 && player)
12821 player.SetLoadedQuickBarItemBind(this,itemQBIndex);
12822 }
12823 }
12824
12825 if (version < 140)
12826 {
12827 // variable management system
12828 if (!LoadVariables(ctx, version))
12829 {
12830 m_IsStoreLoad = false;
12831 return false;
12832 }
12833 }
12834
12835 //agent trasmission system
12836 if (!LoadAgents(ctx, version))
12837 {
12838 m_IsStoreLoad = false;
12839 return false;
12840 }
12841 if (version >= 132)
12842 {
12843 RemotelyActivatedItemBehaviour raib = GetRemotelyActivatedItemBehaviour();
12844 if (raib)
12845 {
12846 if (!raib.OnStoreLoad(ctx,version))
12847 {
12848 m_IsStoreLoad = false;
12849 return false;
12850 }
12851 }
12852 }
12853
12854 m_IsStoreLoad = false;
12855 return true;
12856 }
12857
12858 //----------------------------------------------------------------
12859
12860 override void OnStoreSave(ParamsWriteContext ctx)
12861 {
12862 super.OnStoreSave(ctx);
12863
12864 PlayerBase player;
12865 if (PlayerBase.CastTo(player,GetHierarchyRootPlayer()))
12866 {
12867 ctx.Write(true); // Keep track of if we should actually read this in or not
12868 //Save quickbar item bind
12869 int itemQBIndex = -1;
12870 itemQBIndex = player.FindQuickBarEntityIndex(this);
12871 ctx.Write(itemQBIndex);
12872 }
12873 else
12874 {
12875 ctx.Write(false); // Keep track of if we should actually read this in or not
12876 }
12877
12878 SaveAgents(ctx);//agent trasmission system
12879
12880 RemotelyActivatedItemBehaviour raib = GetRemotelyActivatedItemBehaviour();
12881 if (raib)
12882 {
12883 raib.OnStoreSave(ctx);
12884 }
12885 }
12886 //----------------------------------------------------------------
12887
12888 override void AfterStoreLoad()
12889 {
12890 super.AfterStoreLoad();
12891
12893 {
12895 }
12896
12897 if (GetStoreLoadedQuantity() != float.LOWEST)
12898 {
12900 SetStoreLoadedQuantity(float.LOWEST);//IMPORTANT to do this !! we use 'm_StoreLoadedQuantity' inside SetQuantity to distinguish between initial quantity setting and the consequent(normal gameplay) calls
12901 }
12902 }
12903
12904 override void EEOnAfterLoad()
12905 {
12906 super.EEOnAfterLoad();
12907
12909 {
12910 m_FixDamageSystemInit = false;
12911 }
12912
12915 }
12916
12917 bool CanBeDisinfected()
12918 {
12919 return false;
12920 }
12921
12922
12923 //----------------------------------------------------------------
12924 override void OnVariablesSynchronized()
12925 {
12926 if (m_Initialized)
12927 {
12928 #ifdef PLATFORM_CONSOLE
12929 //bruteforce it is
12930 if (IsSplitable())
12931 {
12932 UIScriptedMenu menu = g_Game.GetUIManager().FindMenu(MENU_INVENTORY);
12933 if (menu)
12934 {
12935 menu.Refresh();
12936 }
12937 }
12938 #endif
12939 }
12940
12942 {
12943 PlayImpactSound(m_ConfigWeight, m_ImpactSpeed, m_ImpactSoundSurfaceHash);
12944 m_WantPlayImpactSound = false;
12945 }
12946
12948 {
12949 SetWeightDirty();
12951 }
12952 if (m_VarWet != m_VarWetPrev)
12953 {
12956 }
12957
12958 if (m_SoundSyncPlay != 0)
12959 {
12962
12963 m_SoundSyncPlay = 0;
12964 m_SoundSyncSlotID = -1;
12965 }
12966 if (m_SoundSyncStop != 0)
12967 {
12969 m_ItemSoundHandler.StopItemSoundClient(m_SoundSyncStop);
12970 m_SoundSyncStop = 0;
12971 }
12972
12973 super.OnVariablesSynchronized();
12974 }
12975
12976 //------------------------- Quantity
12977 //----------------------------------------------------------------
12979 override bool SetQuantity(float value, bool destroy_config = true, bool destroy_forced = false, bool allow_client = false, bool clamp_to_stack_max = true)
12980 {
12981 if (!IsServerCheck(allow_client))
12982 return false;
12983
12984 if (!HasQuantity())
12985 return false;
12986
12987 float min = GetQuantityMin();
12988 float max = GetQuantityMax();
12989
12990 if (value <= (min + 0.001))
12991 value = min;
12992
12993 if (value == min)
12994 {
12995 if (destroy_config)
12996 {
12997 bool dstr = ConfigGetBool("varQuantityDestroyOnMin");
12998 if (dstr)
12999 {
13000 m_VarQuantity = Math.Clamp(value, min, max);
13001 this.Delete();
13002 return true;
13003 }
13004 }
13005 else if (destroy_forced)
13006 {
13007 m_VarQuantity = Math.Clamp(value, min, max);
13008 this.Delete();
13009 return true;
13010 }
13011 // we get here if destroy_config IS true AND dstr(config destroy param) IS false;
13012 RemoveAllAgents();//we remove all agents when we got to the min value, but the item is not getting deleted
13013 }
13014
13015 float delta = m_VarQuantity;
13016 m_VarQuantity = Math.Clamp(value, min, max);
13017
13018 if (g_Game.IsServer() || !g_Game.IsMultiplayer()) // single player or server side multiplayer
13019 {
13020 EntityAI parent = GetHierarchyRoot();
13021 InventoryLocation iLoc = new InventoryLocation();
13022 GetInventory().GetCurrentInventoryLocation(iLoc);
13023 if (iLoc && iLoc.IsValid() && delta != m_VarQuantity)
13024 {
13025 int iLocSlot = iLoc.GetSlot();
13026 if (delta < m_VarQuantity && iLoc.GetType() != InventoryLocationType.GROUND)
13027 {
13028 StartItemSoundServer(SoundConstants.ITEM_ATTACH, iLocSlot);
13029 }
13030 if (delta > m_VarQuantity && m_VarQuantity != 0 && !IsPrepareToDelete() && iLoc.GetType() == InventoryLocationType.ATTACHMENT)
13031 {
13032 StartItemSoundServer(SoundConstants.ITEM_DETACH, iLocSlot);
13033 }
13034 }
13035 }
13036
13037 if (GetStoreLoadedQuantity() == float.LOWEST)//any other value means we are setting quantity from storage
13038 {
13039 delta = m_VarQuantity - delta;
13040
13041 if (delta)
13042 OnQuantityChanged(delta);
13043 }
13044
13045 SetVariableMask(VARIABLE_QUANTITY);
13046
13047 return false;
13048 }
13049
13050 //----------------------------------------------------------------
13052 bool AddQuantity(float value, bool destroy_config = true, bool destroy_forced = false)
13053 {
13054 return SetQuantity(GetQuantity() + value, destroy_config, destroy_forced);
13055 }
13056 //----------------------------------------------------------------
13057 void SetQuantityMax()
13058 {
13059 float max = GetQuantityMax();
13060 SetQuantity(max);
13061 }
13062
13063 override void SetQuantityToMinimum()
13064 {
13065 float min = GetQuantityMin();
13066 SetQuantity(min);
13067 }
13068 //----------------------------------------------------------------
13070 override void SetQuantityNormalized(float value, bool destroy_config = true, bool destroy_forced = false)
13071 {
13072 float value_clamped = Math.Clamp(value, 0, 1);//just to make sure
13073 int result = Math.Round(Math.Lerp(GetQuantityMin(), GetQuantityMax(), value_clamped));
13074 SetQuantity(result, destroy_config, destroy_forced);
13075 }
13076
13077 //----------------------------------------------------------------
13079 override float GetQuantityNormalized()
13080 {
13081 return Math.InverseLerp(GetQuantityMin(), GetQuantityMax(),m_VarQuantity);
13082 }
13083
13085 {
13086 return GetQuantityNormalized();
13087 }
13088
13089 /*void SetAmmoNormalized(float value)
13090 {
13091 float value_clamped = Math.Clamp(value, 0, 1);
13092 Magazine this_mag = Magazine.Cast(this);
13093 int max_rounds = this_mag.GetAmmoMax();
13094 int result = value * max_rounds;//can the rounded if higher precision is required
13095 this_mag.SetAmmoCount(result);
13096 }*/
13097 //----------------------------------------------------------------
13098 override int GetQuantityMax()
13099 {
13100 int slot = -1;
13101 GameInventory inventory = GetInventory();
13102 if (inventory)
13103 {
13104 InventoryLocation il = new InventoryLocation;
13105 inventory.GetCurrentInventoryLocation(il);
13106 slot = il.GetSlot();
13107 }
13108
13109 return GetTargetQuantityMax(slot);
13110 }
13111
13112 override int GetTargetQuantityMax(int attSlotID = -1)
13113 {
13114 float quantity_max = 0;
13115
13116 if (IsSplitable()) //only stackable/splitable items can check for stack size
13117 {
13118 if (attSlotID != -1)
13119 quantity_max = InventorySlots.GetStackMaxForSlotId(attSlotID);
13120
13121 if (quantity_max <= 0)
13122 quantity_max = m_VarStackMax;
13123 }
13124
13125 if (quantity_max <= 0)
13126 quantity_max = m_VarQuantityMax;
13127
13128 return quantity_max;
13129 }
13130 //----------------------------------------------------------------
13131 override int GetQuantityMin()
13132 {
13133 return m_VarQuantityMin;
13134 }
13135 //----------------------------------------------------------------
13136 int GetQuantityInit()
13137 {
13138 return m_VarQuantityInit;
13139 }
13140
13141 //----------------------------------------------------------------
13142 override bool HasQuantity()
13143 {
13144 return !(GetQuantityMax() - GetQuantityMin() == 0);
13145 }
13146
13147 override float GetQuantity()
13148 {
13149 return m_VarQuantity;
13150 }
13151
13152 bool IsFullQuantity()
13153 {
13154 return GetQuantity() >= GetQuantityMax();
13155 }
13156
13157 //Calculates weight of single item without attachments and cargo
13158 override float GetSingleInventoryItemWeightEx()
13159 {
13160 //this needs to be first stored inside local variables, when returned directly during inside return call, the result is completely different due to enforce script bug
13161 float weightEx = GetWeightEx();//overall weight of the item
13162 float special = GetInventoryAndCargoWeight();//cargo and attachment weight
13163 return weightEx - special;
13164 }
13165
13166 // Obsolete, use GetSingleInventoryItemWeightEx() instead
13168 {
13170 }
13171
13172 override protected float GetWeightSpecialized(bool forceRecalc = false)
13173 {
13174 if (IsSplitable()) //quantity determines size of the stack
13175 {
13176 #ifdef DEVELOPER
13177 if (WeightDebug.m_VerbosityFlags & WeightDebugType.RECALC_FORCED)
13178 {
13179 WeightDebugData data1 = WeightDebug.GetWeightDebug(this);
13180 data1.SetCalcDetails("TIB1: " + GetConfigWeightModifiedDebugText() +" * " + GetQuantity()+"(quantity)");
13181 }
13182 #endif
13183
13184 return GetQuantity() * GetConfigWeightModified();
13185 }
13186 else if (HasEnergyManager())// items with energy manager
13187 {
13188 #ifdef DEVELOPER
13189 if (WeightDebug.m_VerbosityFlags & WeightDebugType.RECALC_FORCED)
13190 {
13191 WeightDebugData data2 = WeightDebug.GetWeightDebug(this);
13192 data2.SetCalcDetails("TIB2: "+super.GetWeightSpecialized(forceRecalc)+"(contents weight) + " + GetConfigWeightModifiedDebugText() +" + " + GetCompEM().GetEnergy()+"(energy) * " + ConfigGetFloat("weightPerQuantityUnit") +"(weightPerQuantityUnit)");
13193 }
13194 #endif
13195 return super.GetWeightSpecialized(forceRecalc) + (GetCompEM().GetEnergy() * ConfigGetFloat("weightPerQuantityUnit")) + GetConfigWeightModified();
13196 }
13197 else//everything else
13198 {
13199 #ifdef DEVELOPER
13200 if (WeightDebug.m_VerbosityFlags & WeightDebugType.RECALC_FORCED)
13201 {
13202 WeightDebugData data3 = WeightDebug.GetWeightDebug(this);
13203 data3.SetCalcDetails("TIB3: "+super.GetWeightSpecialized(forceRecalc)+"(contents weight) + " + GetConfigWeightModifiedDebugText() +" + " + GetQuantity()+"(quantity) * " + ConfigGetFloat("weightPerQuantityUnit") +"(weightPerQuantityUnit))");
13204 }
13205 #endif
13206 return super.GetWeightSpecialized(forceRecalc) + (GetQuantity() * ConfigGetFloat("weightPerQuantityUnit")) + GetConfigWeightModified();
13207 }
13208 }
13209
13211 int GetNumberOfItems()
13212 {
13213 int item_count = 0;
13214 ItemBase item;
13215
13216 GameInventory inventory = GetInventory();
13217 CargoBase cargo = inventory.GetCargo();
13218 if (cargo != NULL)
13219 {
13220 item_count = cargo.GetItemCount();
13221 }
13222
13223 int nAttachments = inventory.AttachmentCount();
13224 for (int i = 0; i < nAttachments; ++i)
13225 {
13226 Class.CastTo(item, inventory.GetAttachmentFromIndex(i));
13227 if (item)
13228 item_count += item.GetNumberOfItems();
13229 }
13230 return item_count;
13231 }
13232
13234 float GetUnitWeight(bool include_wetness = true)
13235 {
13236 float weight = 0;
13237 float wetness = 1;
13238 if (include_wetness)
13239 wetness += GetWet();
13240 if (IsSplitable()) //quantity determines size of the stack
13241 {
13242 weight = wetness * m_ConfigWeight;
13243 }
13244 else if (IsLiquidContainer()) //is a liquid container, default liquid weight is set to 1. May revisit later?
13245 {
13246 weight = 1;
13247 }
13248 return weight;
13249 }
13250
13251 //-----------------------------------------------------------------
13252
13253 override void ClearInventory()
13254 {
13255 GameInventory inventory = GetInventory();
13256 if ((g_Game.IsServer() || !g_Game.IsMultiplayer()) && inventory)
13257 {
13258 array<EntityAI> items = new array<EntityAI>;
13259 inventory.EnumerateInventory(InventoryTraversalType.INORDER, items);
13260 for (int i = 0; i < items.Count(); ++i)
13261 {
13262 ItemBase item = ItemBase.Cast(items.Get(i));
13263 if (item)
13264 {
13265 g_Game.ObjectDelete(item);
13266 }
13267 }
13268 }
13269 }
13270
13271 //------------------------- Energy
13272
13273 //----------------------------------------------------------------
13274 float GetEnergy()
13275 {
13276 float energy = 0;
13277 if (HasEnergyManager())
13278 {
13279 energy = GetCompEM().GetEnergy();
13280 }
13281 return energy;
13282 }
13283
13284
13285 override void OnEnergyConsumed()
13286 {
13287 super.OnEnergyConsumed();
13288
13290 }
13291
13292 override void OnEnergyAdded()
13293 {
13294 super.OnEnergyAdded();
13295
13297 }
13298
13299 // Converts energy (from Energy Manager) to quantity, if enabled.
13301 {
13302 if (g_Game.IsServer() && HasEnergyManager() && GetCompEM().HasConversionOfEnergyToQuantity())
13303 {
13304 if (HasQuantity())
13305 {
13306 float energy_0to1 = GetCompEM().GetEnergy0To1();
13307 SetQuantityNormalized(energy_0to1);
13308 }
13309 }
13310 }
13311
13312 //----------------------------------------------------------------
13313 float GetHeatIsolationInit()
13314 {
13315 return ConfigGetFloat("heatIsolation");
13316 }
13317
13318 float GetHeatIsolation()
13319 {
13320 return m_HeatIsolation;
13321 }
13322
13323 float GetDryingIncrement(string pIncrementName)
13324 {
13325 string paramPath = string.Format("CfgVehicles %1 EnvironmentWetnessIncrements Drying %2", GetType(), pIncrementName);
13326 if (g_Game.ConfigIsExisting(paramPath))
13327 return g_Game.ConfigGetFloat(paramPath);
13328
13329 return 0.0;
13330 }
13331
13332 float GetSoakingIncrement(string pIncrementName)
13333 {
13334 string paramPath = string.Format("CfgVehicles %1 EnvironmentWetnessIncrements Soaking %2", GetType(), pIncrementName);
13335 if (g_Game.ConfigIsExisting(paramPath))
13336 return g_Game.ConfigGetFloat(paramPath);
13337
13338 return 0.0;
13339 }
13340 //----------------------------------------------------------------
13341 override void SetWet(float value, bool allow_client = false)
13342 {
13343 if (!IsServerCheck(allow_client))
13344 return;
13345
13346 float min = GetWetMin();
13347 float max = GetWetMax();
13348
13349 float previousValue = m_VarWet;
13350
13351 m_VarWet = Math.Clamp(value, min, max);
13352
13353 if (previousValue != m_VarWet)
13354 {
13355 SetVariableMask(VARIABLE_WET);
13356 OnWetChanged(m_VarWet, previousValue);
13357 }
13358 }
13359 //----------------------------------------------------------------
13360 override void AddWet(float value)
13361 {
13362 SetWet(GetWet() + value);
13363 }
13364 //----------------------------------------------------------------
13365 override void SetWetMax()
13366 {
13368 }
13369 //----------------------------------------------------------------
13370 override float GetWet()
13371 {
13372 return m_VarWet;
13373 }
13374 //----------------------------------------------------------------
13375 override float GetWetMax()
13376 {
13377 return m_VarWetMax;
13378 }
13379 //----------------------------------------------------------------
13380 override float GetWetMin()
13381 {
13382 return m_VarWetMin;
13383 }
13384 //----------------------------------------------------------------
13385 override float GetWetInit()
13386 {
13387 return m_VarWetInit;
13388 }
13389 //----------------------------------------------------------------
13390 override void OnWetChanged(float newVal, float oldVal)
13391 {
13392 EWetnessLevel newLevel = GetWetLevelInternal(newVal);
13393 EWetnessLevel oldLevel = GetWetLevelInternal(oldVal);
13394 if (newLevel != oldLevel)
13395 {
13396 OnWetLevelChanged(newLevel,oldLevel);
13397 }
13398 }
13399
13400 override void OnWetLevelChanged(EWetnessLevel newLevel, EWetnessLevel oldLevel)
13401 {
13402 SetWeightDirty();
13403 }
13404
13405 override EWetnessLevel GetWetLevel()
13406 {
13407 return GetWetLevelInternal(m_VarWet);
13408 }
13409
13410 //----------------------------------------------------------------
13411
13412 override void SetStoreLoad(bool value)
13413 {
13414 m_IsStoreLoad = value;
13415 }
13416
13417 override bool IsStoreLoad()
13418 {
13419 return m_IsStoreLoad;
13420 }
13421
13422 override void SetStoreLoadedQuantity(float value)
13423 {
13424 m_StoreLoadedQuantity = value;
13425 }
13426
13427 override float GetStoreLoadedQuantity()
13428 {
13429 return m_StoreLoadedQuantity;
13430 }
13431
13432 //----------------------------------------------------------------
13433
13434 float GetItemModelLength()
13435 {
13436 if (ConfigIsExisting("itemModelLength"))
13437 {
13438 return ConfigGetFloat("itemModelLength");
13439 }
13440 return 0;
13441 }
13442
13443 float GetItemAttachOffset()
13444 {
13445 if (ConfigIsExisting("itemAttachOffset"))
13446 {
13447 return ConfigGetFloat("itemAttachOffset");
13448 }
13449 return 0;
13450 }
13451
13452 override void SetCleanness(int value, bool allow_client = false)
13453 {
13454 if (!IsServerCheck(allow_client))
13455 return;
13456
13457 int previousValue = m_Cleanness;
13458
13459 m_Cleanness = Math.Clamp(value, m_CleannessMin, m_CleannessMax);
13460
13461 if (previousValue != m_Cleanness)
13462 SetVariableMask(VARIABLE_CLEANNESS);
13463 }
13464
13465 override int GetCleanness()
13466 {
13467 return m_Cleanness;
13468 }
13469
13471 {
13472 return true;
13473 }
13474
13475 //----------------------------------------------------------------
13476 // ATTACHMENT LOCKING
13477 // Getters relevant to generic ActionLockAttachment
13478 int GetLockType()
13479 {
13480 return m_LockType;
13481 }
13482
13483 string GetLockSoundSet()
13484 {
13485 return m_LockSoundSet;
13486 }
13487
13488 //----------------------------------------------------------------
13489 //------------------------- Color
13490 // sets items color variable given color components
13491 override void SetColor(int r, int g, int b, int a)
13492 {
13497 SetVariableMask(VARIABLE_COLOR);
13498 }
13500 override void GetColor(out int r,out int g,out int b,out int a)
13501 {
13506 }
13507
13508 bool IsColorSet()
13509 {
13510 return IsVariableSet(VARIABLE_COLOR);
13511 }
13512
13514 string GetColorString()
13515 {
13516 int r,g,b,a;
13517 GetColor(r,g,b,a);
13518 r = r/255;
13519 g = g/255;
13520 b = b/255;
13521 a = a/255;
13522 return MiscGameplayFunctions.GetColorString(r, g, b, a);
13523 }
13524 //----------------------------------------------------------------
13525 //------------------------- LiquidType
13526
13527 override void SetLiquidType(int value, bool allow_client = false)
13528 {
13529 if (!IsServerCheck(allow_client))
13530 return;
13531
13532 int old = m_VarLiquidType;
13533 m_VarLiquidType = value;
13534 OnLiquidTypeChanged(old,value);
13535 SetVariableMask(VARIABLE_LIQUIDTYPE);
13536 }
13537
13538 int GetLiquidTypeInit()
13539 {
13540 return ConfigGetInt("varLiquidTypeInit");
13541 }
13542
13543 override int GetLiquidType()
13544 {
13545 return m_VarLiquidType;
13546 }
13547
13548 protected void OnLiquidTypeChanged(int oldType, int newType)
13549 {
13550 if (newType == LIQUID_NONE && GetIsFrozen())
13551 SetFrozen(false);
13552 }
13553
13555 void UpdateQuickbarShortcutVisibility(PlayerBase player)
13556 {
13557 player.SetEnableQuickBarEntityShortcut(this,!GetHierarchyParent() || GetHierarchyParent().GetInventory().AreChildrenAccessible());
13558 }
13559
13560 // -------------------------------------------------------------------------
13562 void OnInventoryEnter(Man player)
13563 {
13564 PlayerBase nplayer;
13565 if (PlayerBase.CastTo(nplayer, player))
13566 {
13567 m_CanPlayImpactSound = true;
13568 nplayer.SetEnableQuickBarEntityShortcut(this,!GetHierarchyParent() || GetHierarchyParent().GetInventory().AreChildrenAccessible());
13569 }
13570 }
13571
13572 // -------------------------------------------------------------------------
13574 void OnInventoryExit(Man player)
13575 {
13576 PlayerBase nplayer;
13577 if (PlayerBase.CastTo(nplayer,player))
13578 {
13579 nplayer.SetEnableQuickBarEntityShortcut(this, false);
13580 }
13581
13582 player.GetHumanInventory().ClearUserReservedLocationForContainer(this);
13583
13584 if (HasEnergyManager())
13585 {
13586 GetCompEM().UpdatePlugState(); // Unplug the el. device if it's necesarry.
13587 }
13588 }
13589
13590 // ADVANCED PLACEMENT EVENTS
13591 override void OnPlacementStarted(Man player)
13592 {
13593 super.OnPlacementStarted(player);
13594
13595 SetTakeable(false);
13596 }
13597
13598 override void OnPlacementComplete(Man player, vector position = "0 0 0", vector orientation = "0 0 0")
13599 {
13600 if (m_AdminLog)
13601 {
13602 m_AdminLog.OnPlacementComplete(player, this);
13603 }
13604
13605 super.OnPlacementComplete(player, position, orientation);
13606 }
13607
13608 //-----------------------------
13609 // AGENT SYSTEM
13610 //-----------------------------
13611 //--------------------------------------------------------------------------
13612 bool ContainsAgent(int agent_id)
13613 {
13614 if (agent_id & m_AttachedAgents)
13615 {
13616 return true;
13617 }
13618 else
13619 {
13620 return false;
13621 }
13622 }
13623
13624 //--------------------------------------------------------------------------
13625 override void RemoveAgent(int agent_id)
13626 {
13627 if (ContainsAgent(agent_id))
13628 {
13629 m_AttachedAgents = ~agent_id & m_AttachedAgents;
13630 }
13631 }
13632
13633 //--------------------------------------------------------------------------
13634 override void RemoveAllAgents()
13635 {
13636 m_AttachedAgents = 0;
13637 }
13638 //--------------------------------------------------------------------------
13639 override void RemoveAllAgentsExcept(int agent_to_keep)
13640 {
13641 m_AttachedAgents = m_AttachedAgents & agent_to_keep;
13642 }
13643 // -------------------------------------------------------------------------
13644 override void InsertAgent(int agent, float count = 1)
13645 {
13646 if (count < 1)
13647 return;
13648 //Debug.Log("Inserting Agent on item: " + agent.ToString() +" count: " + count.ToString());
13650 }
13651
13653 void TransferAgents(int agents)
13654 {
13656 }
13657
13658 // -------------------------------------------------------------------------
13659 override int GetAgents()
13660 {
13661 return m_AttachedAgents;
13662 }
13663 //----------------------------------------------------------------------
13664
13665 /*int GetContaminationType()
13666 {
13667 int contamination_type;
13668
13669 const int CONTAMINATED_MASK = eAgents.CHOLERA | eAgents.INFLUENZA | eAgents.SALMONELLA | eAgents.BRAIN;
13670 const int POISONED_MASK = eAgents.FOOD_POISON | eAgents.CHEMICAL_POISON;
13671 const int NERVE_GAS_MASK = eAgents.CHEMICAL_POISON;
13672 const int DIRTY_MASK = eAgents.WOUND_AGENT;
13673
13674 Edible_Base edible = Edible_Base.Cast(this);
13675 int agents = GetAgents();
13676 if (edible)
13677 {
13678 NutritionalProfile profile = Edible_Base.GetNutritionalProfile(edible);
13679 if (profile)
13680 {
13681 agents = agents | profile.GetAgents();//merge item's agents with nutritional agents
13682 }
13683 }
13684 if (agents & CONTAMINATED_MASK)
13685 {
13686 contamination_type = contamination_type | EContaminationTypes.ITEM_BADGE_CONTAMINATED;
13687 }
13688 if (agents & POISONED_MASK)
13689 {
13690 contamination_type = contamination_type | EContaminationTypes.ITEM_BADGE_POISONED;
13691 }
13692 if (agents & NERVE_GAS_MASK)
13693 {
13694 contamination_type = contamination_type | EContaminationTypes.ITEM_BADGE_NERVE_GAS;
13695 }
13696 if (agents & DIRTY_MASK)
13697 {
13698 contamination_type = contamination_type | EContaminationTypes.ITEM_BADGE_DIRTY;
13699 }
13700
13701 return agents;
13702 }*/
13703
13704 // -------------------------------------------------------------------------
13705 bool LoadAgents(ParamsReadContext ctx, int version)
13706 {
13707 if (!ctx.Read(m_AttachedAgents))
13708 return false;
13709 return true;
13710 }
13711 // -------------------------------------------------------------------------
13713 {
13714
13716 }
13717 // -------------------------------------------------------------------------
13718
13720 override void CheckForRoofLimited(float timeTresholdMS = 3000)
13721 {
13722 super.CheckForRoofLimited(timeTresholdMS);
13723
13724 float time = g_Game.GetTime();
13725 if ((time - m_PreviousRoofTestTime) >= timeTresholdMS)
13726 {
13727 m_PreviousRoofTestTime = time;
13728 SetRoofAbove(MiscGameplayFunctions.IsUnderRoof(this));
13729 }
13730 }
13731
13732 // returns item's protection level against enviromental hazard, for masks with filters, returns the filters protection for valid filter, otherwise 0
13733 float GetProtectionLevel(int type, bool consider_filter = false, int system = 0)
13734 {
13735 if (IsDamageDestroyed() || (HasQuantity() && GetQuantity() <= 0))
13736 {
13737 return 0;
13738 }
13739
13740 if (GetInventory().GetAttachmentSlotsCount() != 0)//is it an item with attachable filter ?
13741 {
13742 ItemBase filter = ItemBase.Cast(FindAttachmentBySlotName("GasMaskFilter"));
13743 if (filter)
13744 return filter.GetProtectionLevel(type, false, system);//it's a valid filter, return the protection
13745 else
13746 return 0;//otherwise return 0 when no filter attached
13747 }
13748
13749 string subclassPath, entryName;
13750
13751 switch (type)
13752 {
13753 case DEF_BIOLOGICAL:
13754 entryName = "biological";
13755 break;
13756 case DEF_CHEMICAL:
13757 entryName = "chemical";
13758 break;
13759 default:
13760 entryName = "biological";
13761 break;
13762 }
13763
13764 subclassPath = "CfgVehicles " + this.GetType() + " Protection ";
13765
13766 return g_Game.ConfigGetFloat(subclassPath + entryName);
13767 }
13768
13769
13770
13772 override void EEOnCECreate()
13773 {
13774 if (!IsMagazine())
13776
13778 }
13779
13780
13781 //-------------------------
13782 // OPEN/CLOSE USER ACTIONS
13783 //-------------------------
13785 void Open();
13786 void Close();
13787 bool IsOpen()
13788 {
13789 return true;
13790 }
13791
13792 override bool CanDisplayCargo()
13793 {
13794 return IsOpen();
13795 }
13796
13797
13798 // ------------------------------------------------------------
13799 // CONDITIONS
13800 // ------------------------------------------------------------
13801 override bool CanPutInCargo(EntityAI parent)
13802 {
13803 if (parent)
13804 {
13805 if (parent.IsInherited(DayZInfected))
13806 return true;
13807
13808 if (!parent.IsRuined())
13809 return true;
13810 }
13811
13812 return true;
13813 }
13814
13815 override bool CanPutAsAttachment(EntityAI parent)
13816 {
13817 if (!super.CanPutAsAttachment(parent))
13818 {
13819 return false;
13820 }
13821
13822 if (!IsRuined() && !parent.IsRuined())
13823 {
13824 return true;
13825 }
13826
13827 return false;
13828 }
13829
13830 override bool CanReceiveItemIntoCargo(EntityAI item)
13831 {
13832 //removed 15.06. coz of loading from storage -> after load items in cargo was lost -> waiting for proper solution
13833 //if (GetHealthLevel() == GameConstants.STATE_RUINED)
13834 // return false;
13835
13836 return super.CanReceiveItemIntoCargo(item);
13837 }
13838
13839 override bool CanReceiveAttachment(EntityAI attachment, int slotId)
13840 {
13841 //removed 15.06. coz of loading from storage -> after load items in cargo was lost -> waiting for proper solution
13842 //if (GetHealthLevel() == GameConstants.STATE_RUINED)
13843 // return false;
13844
13845 GameInventory attachmentInv = attachment.GetInventory();
13846 if (attachmentInv && attachmentInv.GetCargo() && attachmentInv.GetCargo().GetItemCount() > 0)
13847 {
13848 if (GetHierarchyParent() && !GetHierarchyParent().IsInherited(PlayerBase))
13849 return false;
13850 }
13851
13852 InventoryLocation loc = new InventoryLocation();
13853 attachment.GetInventory().GetCurrentInventoryLocation(loc);
13854 if (loc && loc.IsValid() && !GetInventory().AreChildrenAccessible())
13855 return false;
13856
13857 return super.CanReceiveAttachment(attachment, slotId);
13858 }
13859
13860 override bool CanReleaseAttachment(EntityAI attachment)
13861 {
13862 if (!super.CanReleaseAttachment(attachment))
13863 return false;
13864
13865 return GetInventory().AreChildrenAccessible();
13866 }
13867
13868 /*override bool CanLoadAttachment(EntityAI attachment)
13869 {
13870 //removed 15.06. coz of loading from storage -> after load items in cargo was lost -> waiting for proper solution
13871 //if (GetHealthLevel() == GameConstants.STATE_RUINED)
13872 // return false;
13873
13874 GameInventory attachmentInv = attachment.GetInventory();
13875 if (attachmentInv && attachmentInv.GetCargo() && attachmentInv.GetCargo().GetItemCount() > 0)
13876 {
13877 bool boo = (GetHierarchyParent() && !GetHierarchyParent().IsInherited(PlayerBase));
13878 ErrorEx("CanLoadAttachment | this: " + this + " | attachment: " + attachment + " | boo: " + boo,ErrorExSeverity.INFO);
13879
13880 if (GetHierarchyParent() && !GetHierarchyParent().IsInherited(PlayerBase))
13881 return false;
13882 }
13883
13884 return super.CanLoadAttachment(attachment);
13885 }*/
13886
13887 // Plays muzzle flash particle effects
13888 static void PlayFireParticles(ItemBase weapon, int muzzle_index, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
13889 {
13890 int id = muzzle_owner.GetMuzzleID();
13891 array<ref WeaponParticlesOnFire> WPOF_array = m_OnFireEffect.Get(id);
13892
13893 if (WPOF_array)
13894 {
13895 for (int i = 0; i < WPOF_array.Count(); i++)
13896 {
13897 WeaponParticlesOnFire WPOF = WPOF_array.Get(i);
13898
13899 if (WPOF)
13900 {
13901 WPOF.OnActivate(weapon, muzzle_index, ammoType, muzzle_owner, suppressor, config_to_search);
13902 }
13903 }
13904 }
13905 }
13906
13907 // Plays bullet eject particle effects (usually just smoke, the bullet itself is a 3D model and is not part of this function)
13908 static void PlayBulletCasingEjectParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
13909 {
13910 int id = muzzle_owner.GetMuzzleID();
13911 array<ref WeaponParticlesOnBulletCasingEject> WPOBE_array = m_OnBulletCasingEjectEffect.Get(id);
13912
13913 if (WPOBE_array)
13914 {
13915 for (int i = 0; i < WPOBE_array.Count(); i++)
13916 {
13917 WeaponParticlesOnBulletCasingEject WPOBE = WPOBE_array.Get(i);
13918
13919 if (WPOBE)
13920 {
13921 WPOBE.OnActivate(weapon, 0, ammoType, muzzle_owner, suppressor, config_to_search);
13922 }
13923 }
13924 }
13925 }
13926
13927 // Plays all weapon overheating particles
13928 static void PlayOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
13929 {
13930 int id = muzzle_owner.GetMuzzleID();
13931 array<ref WeaponParticlesOnOverheating> WPOOH_array = weapon.m_OnOverheatingEffect.Get(id);
13932
13933 if (WPOOH_array)
13934 {
13935 for (int i = 0; i < WPOOH_array.Count(); i++)
13936 {
13937 WeaponParticlesOnOverheating WPOOH = WPOOH_array.Get(i);
13938
13939 if (WPOOH)
13940 {
13941 WPOOH.OnActivate(weapon, 0, ammoType, muzzle_owner, suppressor, config_to_search);
13942 }
13943 }
13944 }
13945 }
13946
13947 // Updates all weapon overheating particles
13948 static void UpdateOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
13949 {
13950 int id = muzzle_owner.GetMuzzleID();
13951 array<ref WeaponParticlesOnOverheating> WPOOH_array = weapon.m_OnOverheatingEffect.Get(id);
13952
13953 if (WPOOH_array)
13954 {
13955 for (int i = 0; i < WPOOH_array.Count(); i++)
13956 {
13957 WeaponParticlesOnOverheating WPOOH = WPOOH_array.Get(i);
13958
13959 if (WPOOH)
13960 {
13961 WPOOH.OnUpdate(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
13962 }
13963 }
13964 }
13965 }
13966
13967 // Stops overheating particles
13968 static void StopOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
13969 {
13970 int id = muzzle_owner.GetMuzzleID();
13971 array<ref WeaponParticlesOnOverheating> WPOOH_array = weapon.m_OnOverheatingEffect.Get(id);
13972
13973 if (WPOOH_array)
13974 {
13975 for (int i = 0; i < WPOOH_array.Count(); i++)
13976 {
13977 WeaponParticlesOnOverheating WPOOH = WPOOH_array.Get(i);
13978
13979 if (WPOOH)
13980 {
13981 WPOOH.OnDeactivate(weapon, ammoType, muzzle_owner, suppressor, config_to_search);
13982 }
13983 }
13984 }
13985 }
13986
13987 //----------------------------------------------------------------
13988 //Item Behaviour - unified approach
13989 override bool IsHeavyBehaviour()
13990 {
13991 if (m_ItemBehaviour == 0)
13992 {
13993 return true;
13994 }
13995
13996 return false;
13997 }
13998
13999 override bool IsOneHandedBehaviour()
14000 {
14001 if (m_ItemBehaviour == 1)
14002 {
14003 return true;
14004 }
14005
14006 return false;
14007 }
14008
14009 override bool IsTwoHandedBehaviour()
14010 {
14011 if (m_ItemBehaviour == 2)
14012 {
14013 return true;
14014 }
14015
14016 return false;
14017 }
14018
14019 bool IsDeployable()
14020 {
14021 return false;
14022 }
14023
14025 float GetDeployTime()
14026 {
14027 return UATimeSpent.DEFAULT_DEPLOY;
14028 }
14029
14030
14031 //----------------------------------------------------------------
14032 // Item Targeting (User Actions)
14033 override void SetTakeable(bool pState)
14034 {
14035 m_IsTakeable = pState;
14036 SetSynchDirty();
14037 }
14038
14039 override bool IsTakeable()
14040 {
14041 return m_IsTakeable;
14042 }
14043
14044 // For cases where we want to show object widget which cant be taken to hands
14046 {
14047 return false;
14048 }
14049
14051 protected void PreLoadSoundAttachmentType()
14052 {
14053 string att_type = "None";
14054
14055 if (ConfigIsExisting("soundAttType"))
14056 {
14057 att_type = ConfigGetString("soundAttType");
14058 }
14059
14060 m_SoundAttType = att_type;
14061 }
14062
14063 override string GetAttachmentSoundType()
14064 {
14065 return m_SoundAttType;
14066 }
14067
14068 //----------------------------------------------------------------
14069 //SOUNDS - ItemSoundHandler
14070 //----------------------------------------------------------------
14071
14072 string GetPlaceSoundset(); // played when deploy starts
14073 string GetLoopDeploySoundset(); // played when deploy starts and stopped when it finishes
14074 string GetDeploySoundset(); // played when deploy sucessfully finishes
14075 string GetLoopFoldSoundset(); // played when fold starts and stopped when it finishes
14076 string GetFoldSoundset(); // played when fold sucessfully finishes
14077
14079 {
14080 if (!m_ItemSoundHandler)
14082
14083 return m_ItemSoundHandler;
14084 }
14085
14086 // override to initialize sounds
14087 protected void InitItemSounds()
14088 {
14089 if (GetPlaceSoundset() == string.Empty && GetDeploySoundset() == string.Empty && GetLoopDeploySoundset() == string.Empty && !GetInventoryItemType().SetDetachSoundEvent() && !GetInventoryItemType().SetAttachSoundEvent())
14090 return;
14091
14093
14094 if (GetPlaceSoundset() != string.Empty)
14095 handler.AddSound(SoundConstants.ITEM_PLACE, GetPlaceSoundset());
14096
14097 if (GetDeploySoundset() != string.Empty)
14098 handler.AddSound(SoundConstants.ITEM_DEPLOY, GetDeploySoundset());
14099
14100 SoundParameters params = new SoundParameters();
14101 params.m_Loop = true;
14102 if (GetLoopDeploySoundset() != string.Empty)
14103 handler.AddSound(SoundConstants.ITEM_DEPLOY_LOOP, GetLoopDeploySoundset(), params);
14104 }
14105
14106 // Start sound using ItemSoundHandler
14107 void StartItemSoundServer(int id, int slotId)
14108 {
14109 if (g_Game.IsServer() || !g_Game.IsMultiplayer()) // single player or server side multiplayer
14110 {
14111 m_SoundSyncSlotID = slotId;
14112 m_SoundSyncPlay = id;
14113
14114 SetSynchDirty();
14115
14116 g_Game.GetCallQueue(CALL_CATEGORY_SYSTEM).Remove(ClearStartItemSoundServer); // in case one is queued already
14117 g_Game.GetCallQueue(CALL_CATEGORY_SYSTEM).CallLater(ClearStartItemSoundServer, 100);
14118 }
14119 }
14120
14121 void StartItemSoundServer(int id)
14122 {
14123 StartItemSoundServer(id, InventorySlots.INVALID);
14124 }
14125
14126 // Stop sound using ItemSoundHandler
14127 void StopItemSoundServer(int id)
14128 {
14129 if (!g_Game.IsServer())
14130 return;
14131
14132 m_SoundSyncStop = id;
14133 SetSynchDirty();
14134
14135 g_Game.GetCallQueue(CALL_CATEGORY_SYSTEM).Remove(ClearStopItemSoundServer); // in case one is queued already
14136 g_Game.GetCallQueue(CALL_CATEGORY_SYSTEM).CallLater(ClearStopItemSoundServer, 100);
14137 }
14138
14139 protected void ClearStartItemSoundServer()
14140 {
14141 m_SoundSyncPlay = 0;
14142 m_SoundSyncSlotID = InventorySlots.INVALID;
14143 }
14144
14145 protected void ClearStopItemSoundServer()
14146 {
14147 m_SoundSyncStop = 0;
14148 }
14149
14150 void OnApply(PlayerBase player);
14151
14153 {
14154 return 1.0;
14155 };
14156 //returns applicable selection
14157 array<string> GetHeadHidingSelection()
14158 {
14160 }
14161
14163 {
14165 }
14166
14167 WrittenNoteData GetWrittenNoteData() {};
14168
14170 {
14171 SetDynamicPhysicsLifeTime(0.01);
14172 m_ItemBeingDroppedPhys = false;
14173 }
14174
14176 {
14177 array<string> zone_names = new array<string>;
14178 GetDamageZones(zone_names);
14179 for (int i = 0; i < zone_names.Count(); i++)
14180 {
14181 SetHealthMax(zone_names.Get(i),"Health");
14182 }
14183 SetHealthMax("","Health");
14184 }
14185
14187 void SetZoneDamageCEInit()
14188 {
14189 float global_health = GetHealth01("","Health");
14190 array<string> zones = new array<string>;
14191 GetDamageZones(zones);
14192 //set damage of all zones to match global health level
14193 for (int i = 0; i < zones.Count(); i++)
14194 {
14195 SetHealth01(zones.Get(i),"Health",global_health);
14196 }
14197 }
14198
14200 bool IsCoverFaceForShave(string slot_name)
14201 {
14202 return IsExclusionFlagPresent(PlayerBase.GetFaceCoverageShaveValues());
14203 }
14204
14205 void ProcessItemWetness(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
14206 {
14207 if (!hasRootAsPlayer)
14208 {
14209 if (refParentIB)
14210 {
14211 // parent is wet
14212 if ((refParentIB.GetWet() >= GameConstants.STATE_SOAKING_WET) && (m_VarWet < m_VarWetMax))
14213 AddWet(delta * GameConstants.WETNESS_RATE_WETTING_INSIDE);
14214 // parent has liquid inside
14215 else if ((refParentIB.GetLiquidType() != 0) && (refParentIB.GetQuantity() > 0) && (m_VarWet < m_VarWetMax))
14216 AddWet(delta * GameConstants.WETNESS_RATE_WETTING_LIQUID);
14217 // drying
14218 else if (m_VarWet > m_VarWetMin)
14219 AddWet(-1 * delta * GetDryingIncrement("ground") * 2);
14220 }
14221 else
14222 {
14223 // drying on ground or inside non-itembase (car, ...)
14224 if (m_VarWet > m_VarWetMin)
14225 AddWet(-1 * delta * GetDryingIncrement("ground"));
14226 }
14227 }
14228 }
14229
14230 void ProcessItemTemperature(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
14231 {
14233 {
14234 float target = g_Game.GetMission().GetWorldData().GetBaseEnvTemperatureAtObject(this);
14235 if (GetTemperature() != target || !IsFreezeThawProgressFinished())
14236 {
14237 float heatPermCoef = 1.0;
14238 EntityAI ent = this;
14239 while (ent)
14240 {
14241 heatPermCoef *= ent.GetHeatPermeabilityCoef();
14242 ent = ent.GetHierarchyParent();
14243 }
14244
14245 SetTemperatureEx(new TemperatureDataInterpolated(target,ETemperatureAccessTypes.ACCESS_WORLD,delta,GameConstants.TEMP_COEF_WORLD,heatPermCoef));
14246 }
14247 }
14248 }
14249
14250 void HierarchyCheck(out bool hasParent, out bool hasRootAsPlayer, out ItemBase refParentIB)
14251 {
14252 // hierarchy check for an item to decide whether it has some parent and it is in some player inventory
14253 EntityAI parent = GetHierarchyParent();
14254 if (!parent)
14255 {
14256 hasParent = false;
14257 hasRootAsPlayer = false;
14258 }
14259 else
14260 {
14261 hasParent = true;
14262 hasRootAsPlayer = (GetHierarchyRootPlayer() != null);
14263 refParentIB = ItemBase.Cast(parent);
14264 }
14265 }
14266
14267 protected void ProcessDecay(float delta, bool hasRootAsPlayer)
14268 {
14269 // this is stub, implemented on Edible_Base
14270 }
14271
14272 bool CanDecay()
14273 {
14274 // return true used on selected food clases so they can decay
14275 return false;
14276 }
14277
14278 protected bool CanProcessDecay()
14279 {
14280 // this is stub, implemented on Edible_Base class
14281 // used to determine whether it is still necessary for the food to decay
14282 return false;
14283 }
14284
14285 protected bool CanHaveWetness()
14286 {
14287 // return true used on selected items that have a wetness effect
14288 return false;
14289 }
14290
14292 bool CanBeConsumed(ConsumeConditionData data = null)
14293 {
14294 return !GetIsFrozen() && IsOpen();
14295 }
14296
14297 override void ProcessVariables()
14298 {
14299 bool hasParent = false, hasRootAsPlayer = false;
14300 ItemBase refParentIB;
14301
14302 bool wwtu = g_Game.IsWorldWetTempUpdateEnabled();
14303 bool foodDecay = g_Game.IsFoodDecayEnabled();
14304
14305 if (wwtu || foodDecay)
14306 {
14307 bool processWetness = wwtu && CanHaveWetness();
14308 bool processTemperature = wwtu && CanHaveTemperature();
14309 bool processDecay = foodDecay && CanDecay() && CanProcessDecay();
14310
14311 if (processWetness || processTemperature || processDecay)
14312 {
14313 HierarchyCheck(hasParent, hasRootAsPlayer, refParentIB);
14314
14315 if (processWetness)
14316 ProcessItemWetness(m_ElapsedSinceLastUpdate, hasParent, hasRootAsPlayer, refParentIB);
14317
14318 if (processTemperature)
14319 ProcessItemTemperature(m_ElapsedSinceLastUpdate, hasParent, hasRootAsPlayer, refParentIB);
14320
14321 if (processDecay)
14322 ProcessDecay(m_ElapsedSinceLastUpdate, hasRootAsPlayer);
14323 }
14324 }
14325 }
14326
14329 {
14330 return m_TemperaturePerQuantityWeight * GameConstants.ITEM_TEMPERATURE_QUANTITY_WEIGHT_MULTIPLIER;
14331 }
14332
14333 override float GetTemperatureFreezeThreshold()
14334 {
14336 return Liquid.GetFreezeThreshold(GetLiquidType());
14337
14338 return super.GetTemperatureFreezeThreshold();
14339 }
14340
14341 override float GetTemperatureThawThreshold()
14342 {
14344 return Liquid.GetThawThreshold(GetLiquidType());
14345
14346 return super.GetTemperatureThawThreshold();
14347 }
14348
14349 override float GetItemOverheatThreshold()
14350 {
14352 return Liquid.GetBoilThreshold(GetLiquidType());
14353
14354 return super.GetItemOverheatThreshold();
14355 }
14356
14357 override float GetTemperatureFreezeTime()
14358 {
14359 if (HasQuantity())
14360 return Math.Lerp(GameConstants.TEMPERATURE_TIME_FREEZE_MIN,Math.Max(GameConstants.TEMPERATURE_TIME_FREEZE_MIN,super.GetTemperatureFreezeTime()),GetQuantityNormalized());
14361
14362 return super.GetTemperatureFreezeTime();
14363 }
14364
14365 override float GetTemperatureThawTime()
14366 {
14367 if (HasQuantity())
14368 return Math.Lerp(GameConstants.TEMPERATURE_TIME_THAW_MIN,Math.Max(GameConstants.TEMPERATURE_TIME_FREEZE_MIN,super.GetTemperatureThawTime()),GetQuantityNormalized());
14369
14370 return super.GetTemperatureThawTime();
14371 }
14372
14374 void AffectLiquidContainerOnFill(int liquid_type, float amount);
14376 void AffectLiquidContainerOnTransfer(int liquidType, float amount, float sourceLiquidTemperature);
14377
14378 bool IsCargoException4x3(EntityAI item)
14379 {
14380 return (item.IsKindOf("Cauldron") || item.IsKindOf("Pot") || item.IsKindOf("FryingPan") || item.IsKindOf("SmallProtectorCase") || (item.IsKindOf("PortableGasStove") && item.FindAttachmentBySlotName("CookingEquipment")));
14381 }
14382
14384 {
14385 MiscGameplayFunctions.TransferItemProperties(oldItem, this);
14386 }
14387
14389 void AddLightSourceItem(ItemBase lightsource)
14390 {
14391 m_LightSourceItem = lightsource;
14392 }
14393
14395 {
14396 m_LightSourceItem = null;
14397 }
14398
14400 {
14401 return m_LightSourceItem;
14402 }
14403
14405 array<int> GetValidFinishers()
14406 {
14407 return null;
14408 }
14409
14411 bool GetActionWidgetOverride(out typename name)
14412 {
14413 return false;
14414 }
14415
14416 bool PairWithDevice(notnull ItemBase otherDevice)
14417 {
14418 if (g_Game.IsServer())
14419 {
14420 ItemBase explosive = otherDevice;
14422 if (!trg)
14423 {
14424 trg = RemoteDetonatorTrigger.Cast(otherDevice);
14425 explosive = this;
14426 }
14427
14428 explosive.PairRemote(trg);
14429 trg.SetControlledDevice(explosive);
14430
14431 int persistentID = RemotelyActivatedItemBehaviour.GeneratePersistentID();
14432 trg.SetPersistentPairID(persistentID);
14433 explosive.SetPersistentPairID(persistentID);
14434
14435 return true;
14436 }
14437 return false;
14438 }
14439
14441 float GetBaitEffectivity()
14442 {
14443 float ret = 1.0;
14444 if (HasQuantity())
14445 ret *= GetQuantityNormalized();
14446 ret *= GetHealth01();
14447
14448 return ret;
14449 }
14450
14451 #ifdef DEVELOPER
14452 override void SetDebugItem()
14453 {
14454 super.SetDebugItem();
14455 _itemBase = this;
14456 }
14457
14458 override string GetDebugText()
14459 {
14460 string text = super.GetDebugText();
14461
14462 text += string.Format("Heat isolation(raw): %1\n", GetHeatIsolation());
14463 text += string.Format("Heat isolation(modified): %1\n", MiscGameplayFunctions.GetCurrentItemHeatIsolation(this));
14464
14465 return text;
14466 }
14467 #endif
14468
14469 bool CanBeUsedForSuicide()
14470 {
14471 return true;
14472 }
14473
14475 //DEPRECATED BELOW
14477 // Backwards compatibility
14478 void ProcessItemWetnessAndTemperature(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
14479 {
14480 ProcessItemWetness(delta, hasParent, hasRootAsPlayer, refParentIB);
14481 ProcessItemTemperature(delta, hasParent, hasRootAsPlayer, refParentIB);
14482 }
14483
14484 // replaced by ItemSoundHandler
14485 protected EffectSound m_SoundDeployFinish;
14486 protected EffectSound m_SoundPlace;
14487 protected EffectSound m_DeployLoopSoundEx;
14488 protected EffectSound m_SoundDeploy;
14489 bool m_IsPlaceSound;
14490 bool m_IsDeploySound;
14492
14493 string GetDeployFinishSoundset();
14494 void PlayDeploySound();
14495 void PlayDeployFinishSound();
14496 void PlayPlaceSound();
14497 void PlayDeployLoopSoundEx();
14498 void StopDeployLoopSoundEx();
14499 void SoundSynchRemoteReset();
14500 void SoundSynchRemote();
14501 bool UsesGlobalDeploy(){return false;}
14502 bool CanPlayDeployLoopSound(){return false;}
14504 bool IsPlaceSound(){return m_IsPlaceSound;}
14505 bool IsDeploySound(){return m_IsDeploySound;}
14506 void SetIsPlaceSound(bool is_place_sound);
14507 void SetIsDeploySound(bool is_deploy_sound);
14508
14509 [Obsolete("Use ItemSoundHandler instead")]
14511 void PlayAttachSound(string slot_type)
14512 {
14513 if (!g_Game.IsDedicatedServer())
14514 {
14515 if (ConfigIsExisting("attachSoundSet"))
14516 {
14517 string cfg_path = "";
14518 string soundset = "";
14519 string type_name = GetType();
14520
14521 TStringArray cfg_soundset_array = new TStringArray;
14522 TStringArray cfg_slot_array = new TStringArray;
14523 ConfigGetTextArray("attachSoundSet",cfg_soundset_array);
14524 ConfigGetTextArray("attachSoundSlot",cfg_slot_array);
14525
14526 if (cfg_soundset_array.Count() > 0 && cfg_soundset_array.Count() == cfg_slot_array.Count())
14527 {
14528 for (int i = 0; i < cfg_soundset_array.Count(); i++)
14529 {
14530 if (cfg_slot_array[i] == slot_type)
14531 {
14532 soundset = cfg_soundset_array[i];
14533 break;
14534 }
14535 }
14536 }
14537
14538 if (soundset != "")
14539 {
14540 EffectSound sound = SEffectManager.PlaySound(soundset, GetPosition());
14541 sound.SetAutodestroy(true);
14542 }
14543 }
14544 }
14545 }
14546
14547 void PlayDetachSound(string slot_type) {}
14548}
14549
14550EntityAI SpawnItemOnLocation(string object_name, notnull InventoryLocation loc, bool full_quantity)
14551{
14552 EntityAI entity = SpawnEntity(object_name, loc, ECE_IN_INVENTORY, RF_DEFAULT);
14553 if (entity)
14554 {
14555 bool is_item = entity.IsInherited(ItemBase);
14556 if (is_item && full_quantity)
14557 {
14558 ItemBase item = ItemBase.Cast(entity);
14559 item.SetQuantity(item.GetQuantityInit());
14560 }
14561 }
14562 else
14563 {
14564 ErrorEx("Cannot spawn entity: " + object_name,ErrorExSeverity.INFO);
14565 return NULL;
14566 }
14567 return entity;
14568}
14569
14570void SetupSpawnedItem(ItemBase item, float health, float quantity)
14571{
14572 if (item)
14573 {
14574 if (health > 0)
14575 item.SetHealth("", "", health);
14576
14577 if (item.CanHaveTemperature())
14578 {
14579 item.SetTemperatureDirect(GameConstants.ITEM_TEMPERATURE_NEUTRAL_ZONE_MIDDLE);
14580 if (item.CanFreeze())
14581 item.SetFrozen(false);
14582 }
14583
14584 if (item.HasEnergyManager())
14585 {
14586 if (quantity >= 0)
14587 {
14588 item.GetCompEM().SetEnergy0To1(quantity);
14589 }
14590 else
14591 {
14592 item.GetCompEM().SetEnergy(Math.AbsFloat(quantity));
14593 }
14594 }
14595 else if (item.IsMagazine())
14596 {
14597 Magazine mag = Magazine.Cast(item);
14598 if (quantity >= 0)
14599 {
14600 mag.ServerSetAmmoCount(mag.GetAmmoMax() * quantity);
14601 }
14602 else
14603 {
14604 mag.ServerSetAmmoCount(Math.AbsFloat(quantity));
14605 }
14606
14607 }
14608 else
14609 {
14610 if (quantity >= 0)
14611 {
14612 item.SetQuantityNormalized(quantity, false);
14613 }
14614 else
14615 {
14616 item.SetQuantity(Math.AbsFloat(quantity));
14617 }
14618
14619 }
14620 }
14621}
14622
14623#ifdef DEVELOPER
14624ItemBase _itemBase;//watched item goes here(LCTRL+RMB->Watch)
14625#endif
Param4< int, int, string, int > TSelectableActionInfoWithColor
Param3 TSelectableActionInfo
EWetnessLevel
Определения 3_Game/DayZ/Entities/EntityAI.c:2
bool SetAttachSoundEvent()
void InventoryItemType()
bool SetDetachSoundEvent()
InventoryMode
NOTE: PREDICTIVE is not to be used at all in multiplayer.
const int INPUT_UDT_ITEM_MANIPULATION
class LogManager EntityAI
eBleedingSourceType GetType()
ItemSuppressor SuppressorBase
void ActionDropItem()
Определения ActionDropItem.c:34
void ActionManagerBase(PlayerBase player)
Определения ActionManagerBase.c:63
map< typename, ref array< ActionBase_Basic > > TInputActionMap
Определения ActionManagerClient.c:1
void AddAction(typename actionName)
Определения AdvancedCommunication.c:220
void RemoveAction(typename actionName)
Определения AdvancedCommunication.c:252
TInputActionMap m_InputActionMap
Определения AdvancedCommunication.c:137
bool m_ActionsInitialize
Определения AdvancedCommunication.c:138
override void GetActions(typename action_input_type, out array< ActionBase_Basic > actions)
Определения AdvancedCommunication.c:202
void InitializeActions()
Определения AdvancedCommunication.c:190
string Debug()
Определения CachedEquipmentStorageBase.c:29
const int ECE_PLACE_ON_SURFACE
Определения CentralEconomy.c:37
proto native void SpawnEntity(string sClassName, vector vPos, float fRange, int iCount)
Spawn an entity through CE.
const int ECE_IN_INVENTORY
Определения CentralEconomy.c:36
const int RF_DEFAULT
Определения CentralEconomy.c:65
PlayerSpawnPresetDiscreteItemSetSlotData name
one set for cargo
PlayerSpawnPreset slotName
Open
Implementations only.
override void EEOnCECreate()
Определения ContaminatedArea_Dynamic.c:42
map
Определения ControlsXboxNew.c:4
CookingMethodType
Определения Cooking.c:2
DamageType
exposed from C++ (do not change)
Определения DamageSystem.c:11
DayZGame g_Game
Определения DayZGame.c:3942
DayZGame GetDayZGame()
Определения DayZGame.c:3944
EActions
Определения EActions.c:2
ERPCs
Определения ERPCs.c:2
PluginAdminLog m_AdminLog
Определения EmoteManager.c:159
const int MIN
Определения EnConvert.c:28
const int MAX
Определения EnConvert.c:27
float GetTemperature()
Определения Environment.c:500
override bool IsExplosive()
Определения ExplosivesBase.c:59
override bool IsPrepareToDelete()
Определения FireplaceBase.c:643
override bool CanHaveTemperature()
Определения FireplaceBase.c:561
class GP5GasMask extends MaskBase ItemBase
proto GizmoApi GetGizmoApi()
Empty
Определения Hand_States.c:14
FindInventoryLocationType
flags for searching locations in inventory
Определения InventoryLocation.c:18
InventoryLocationType
types of Inventory Location
Определения InventoryLocation.c:4
class BoxCollidingParams component
ComponentInfo for BoxCollidingResult.
bool DamageItemInCargo(float damage)
Определения ItemBase.c:6453
static bool HasDebugActionsMask(int mask)
Определения ItemBase.c:5680
bool HidesSelectionBySlot()
Определения ItemBase.c:9413
float m_VarWetMin
Определения ItemBase.c:4937
void SplitItem(PlayerBase player)
Определения ItemBase.c:6908
void CopyScriptPropertiesFrom(EntityAI oldItem)
Определения ItemBase.c:9634
override void InsertAgent(int agent, float count=1)
Определения ItemBase.c:8895
override float GetQuantityNormalized()
Gets quantity in normalized 0..1 form between the item's Min a Max values as defined by item's config...
Определения ItemBase.c:8330
static void SetDebugActionsMask(int mask)
Определения ItemBase.c:5685
void SetIsDeploySound(bool is_deploy_sound)
bool IsOpen()
Определения ItemBase.c:9038
void SplitItemToInventoryLocation(notnull InventoryLocation dst)
Определения ItemBase.c:6875
override bool IsHeavyBehaviour()
Определения ItemBase.c:9240
override void SetWetMax()
Определения ItemBase.c:8616
bool IsCoverFaceForShave(string slot_name)
DEPRECATED in use, but returns correct values nontheless. Check performed elsewhere.
Определения ItemBase.c:9451
void ClearStartItemSoundServer()
Определения ItemBase.c:9390
float m_VarWet
Определения ItemBase.c:4934
void ProcessItemTemperature(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
Определения ItemBase.c:9481
map< typename, ref ActionOverrideData > TActionAnimOverrideMap
Определения ItemBase.c:3
override void RemoveAllAgentsExcept(int agent_to_keep)
Определения ItemBase.c:8890
static ref map< int, ref array< ref WeaponParticlesOnBulletCasingEject > > m_OnBulletCasingEjectEffect
Определения ItemBase.c:4997
bool CanBeMovedOverride()
Определения ItemBase.c:7600
override void SetWet(float value, bool allow_client=false)
Определения ItemBase.c:8592
ref TIntArray m_SingleUseActions
Определения ItemBase.c:4983
void StartItemSoundServer(int id, int slotId)
Определения ItemBase.c:9358
override void ProcessVariables()
Определения ItemBase.c:9548
ref TStringArray m_HeadHidingSelections
Определения ItemBase.c:5011
float GetWeightSpecialized(bool forceRecalc=false)
Определения ItemBase.c:8423
bool LoadAgents(ParamsReadContext ctx, int version)
Определения ItemBase.c:8956
void UpdateQuickbarShortcutVisibility(PlayerBase player)
To be called on moving item within character's inventory; 'player' should never be null.
Определения ItemBase.c:8806
void OverrideActionAnimation(typename action, int commandUID, int stanceMask=-1, int commandUIDProne=-1)
Определения ItemBase.c:5271
ref array< ref OverheatingParticle > m_OverheatingParticles
Определения ItemBase.c:5009
override float GetTemperatureFreezeThreshold()
Определения ItemBase.c:9584
bool m_IsSoundSynchRemote
Определения ItemBase.c:9742
float m_OverheatingShots
Определения ItemBase.c:5004
void StopItemSoundServer(int id)
Определения ItemBase.c:9378
static void ToggleDebugActionsMask(int mask)
Определения ItemBase.c:5700
void IncreaseOverheating(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:5424
override float GetTemperatureFreezeTime()
Определения ItemBase.c:9608
ref array< int > m_CompatibleLocks
Определения ItemBase.c:5021
bool CanBeCooked()
Определения ItemBase.c:7556
override void CombineItemsClient(EntityAI entity2, bool use_stack_max=true)
Определения ItemBase.c:5767
float m_TemperaturePerQuantityWeight
Определения ItemBase.c:5035
bool m_RecipesInitialized
Определения ItemBase.c:4919
void SplitIntoStackMax(EntityAI destination_entity, int slot_id, PlayerBase player)
Определения ItemBase.c:6546
override float GetTemperatureThawThreshold()
Определения ItemBase.c:9592
override void OnEnergyConsumed()
Определения ItemBase.c:8536
void RefreshAudioVisualsOnClient(CookingMethodType cooking_method, bool is_done, bool is_empty, bool is_burned)
cooking-related effect methods
Определения Bottle_Base.c:158
int GetNumberOfItems()
Returns the number of items in cargo, otherwise returns 0(non-cargo objects). Recursive.
Определения ItemBase.c:8462
override EWetnessLevel GetWetLevel()
Определения ItemBase.c:8656
float GetSingleInventoryItemWeight()
Определения ItemBase.c:8418
ref TIntArray m_InteractActions
Определения ItemBase.c:4985
void MessageToOwnerStatus(string text)
Send message to owner player in grey color.
Определения ItemBase.c:7620
float m_VarQuantity
Определения ItemBase.c:4925
bool CanPlayDeployLoopSound()
Определения ItemBase.c:9753
override float GetWetMax()
Определения ItemBase.c:8626
bool CanBeUsedForSuicide()
Определения ItemBase.c:9720
override void CombineItemsEx(EntityAI entity2, bool use_stack_max=true)
Определения ItemBase.c:7193
void OnItemInHandsPlayerSwimStart(PlayerBase player)
void SetIsHologram(bool is_hologram)
Определения ItemBase.c:5905
void OnSyncVariables(ParamsReadContext ctx)
DEPRECATED (most likely)
Определения ItemBase.c:7774
void DoAmmoExplosion()
Определения ItemBase.c:6388
static ref map< int, ref array< ref WeaponParticlesOnFire > > m_OnFireEffect
Определения ItemBase.c:4996
void SplitIntoStackMaxCargoClient(EntityAI destination_entity, int idx, int row, int col)
Определения ItemBase.c:6732
int GetItemSize()
Определения ItemBase.c:7585
bool m_CanBeMovedOverride
Определения ItemBase.c:4962
override string ChangeIntoOnAttach(string slot)
Определения ItemBase.c:6312
void UpdateOverheating(ItemBase weapon=null, string ammoType="", ItemBase muzzle_owner=null, ItemBase suppressor=null, string config_to_search="")
Определения ItemBase.c:5492
bool CanDecay()
Определения ItemBase.c:9523
ScriptedLightBase GetLight()
string GetPlaceSoundset()
bool AddQuantity(float value, bool destroy_config=true, bool destroy_forced=false)
add item quantity[related to varQuantity... config entry], destroy_config = true > if the quantity re...
Определения ItemBase.c:8303
void SetQuantityMax()
Определения ItemBase.c:8308
override float GetQuantity()
Определения ItemBase.c:8398
int m_ColorComponentR
Определения ItemBase.c:4974
int m_ShotsToStartOverheating
Определения ItemBase.c:5006
override void OnWetChanged(float newVal, float oldVal)
Определения ItemBase.c:8641
void StopOverheating(ItemBase weapon=null, string ammoType="", ItemBase muzzle_owner=null, ItemBase suppressor=null, string config_to_search="")
Определения ItemBase.c:5499
static void PlayFireParticles(ItemBase weapon, int muzzle_index, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:9139
void OnOverheatingDecay()
Определения ItemBase.c:5462
float GetDryingIncrement(string pIncrementName)
Определения ItemBase.c:8574
void SoundSynchRemoteReset()
int m_Cleanness
Определения ItemBase.c:4940
bool HasMuzzle()
Returns true if this item has a muzzle (weapons, suppressors)
Определения ItemBase.c:5600
bool UsesGlobalDeploy()
Определения ItemBase.c:9752
int m_ItemBehaviour
Определения ItemBase.c:4955
override bool CanReleaseAttachment(EntityAI attachment)
Определения ItemBase.c:9111
float m_HeatIsolation
Определения ItemBase.c:4950
float m_VarWetInit
Определения ItemBase.c:4936
override void OnMovedInsideCargo(EntityAI container)
Определения ItemBase.c:5945
void SetCEBasedQuantity()
Определения ItemBase.c:5713
bool m_CanPlayImpactSound
Определения ItemBase.c:4946
override string GetAttachmentSoundType()
Определения ItemBase.c:9314
float GetOverheatingCoef()
Определения ItemBase.c:5519
array< string > GetHeadHidingSelection()
Определения ItemBase.c:9408
void PlayAttachSound(string slot_type)
Plays sound on item attach. Be advised, the config structure may slightly change in 1....
Определения ItemBase.c:9762
override bool IsStoreLoad()
Определения ItemBase.c:8668
int ComputeQuantityUsed(ItemBase other_item, bool use_stack_max=true)
Определения ItemBase.c:7169
bool IsLightSource()
Определения ItemBase.c:5841
bool m_HasQuantityBar
Определения ItemBase.c:4968
void SetResultOfSplit(bool value)
Определения ItemBase.c:7164
void SplitIntoStackMaxCargo(EntityAI destination_entity, int idx, int row, int col)
Определения ItemBase.c:6796
void OnAttachmentQuantityChanged(ItemBase item)
Called on server side when some attachment's quantity is changed. Call super.OnAttachmentQuantityChan...
Определения ItemBase.c:6965
void UpdateAllOverheatingParticles()
Определения ItemBase.c:5527
float GetSoakingIncrement(string pIncrementName)
Определения ItemBase.c:8583
static void StopOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:9219
override float GetStoreLoadedQuantity()
Определения ItemBase.c:8678
int m_LockType
Определения ItemBase.c:5022
const int ITEM_SOUNDS_MAX
Определения ItemBase.c:5027
bool m_CanBeDigged
Определения ItemBase.c:4969
float m_ItemAttachOffset
Определения ItemBase.c:4952
float GetItemModelLength()
Определения ItemBase.c:8685
bool m_ThrowItemOnDrop
Определения ItemBase.c:4960
override bool ReadVarsFromCTX(ParamsReadContext ctx, int version=-1)
Определения ItemBase.c:7919
override void CheckForRoofLimited(float timeTresholdMS=3000)
Roof check for entity, limited by time (anti-spam solution)
Определения ItemBase.c:8971
void Close()
float GetHeatIsolation()
Определения ItemBase.c:8569
void CombineItems(ItemBase other_item, bool use_stack_max=true)
Определения ItemBase.c:7198
void TransferModifiers(PlayerBase reciever)
appears to be deprecated, legacy code
float GetTemperaturePerQuantityWeight()
Used in heat comfort calculations only!
Определения ItemBase.c:9579
bool CanHaveWetness()
Определения ItemBase.c:9536
int m_CleannessMin
Определения ItemBase.c:4942
void TransferAgents(int agents)
transfer agents from another item
Определения ItemBase.c:8904
string IDToName(int id)
Определения ItemBase.c:7767
bool CanBeConsumed(ConsumeConditionData data=null)
Items cannot be consumed if frozen by default. Override for exceptions.
Определения ItemBase.c:9543
float GetHeatIsolationInit()
Определения ItemBase.c:8564
void PlayPlaceSound()
void SetCanBeMovedOverride(bool setting)
Определения ItemBase.c:7607
override bool HasQuantity()
Определения ItemBase.c:8393
float m_VarWetPrev
Определения ItemBase.c:4935
int m_SoundSyncStop
Определения ItemBase.c:5029
bool IsCargoException4x3(EntityAI item)
Определения ItemBase.c:9629
ref TIntArray m_ContinuousActions
Определения ItemBase.c:4984
int GetMuzzleID()
Returns global muzzle ID. If not found, then it gets automatically registered.
Определения ItemBase.c:5609
void LoadParticleConfigOnFire(int id)
Определения ItemBase.c:5294
int m_VarLiquidType
Определения ItemBase.c:4954
int m_QuickBarBonus
Определения ItemBase.c:4956
void PreLoadSoundAttachmentType()
Attachment Sound Type getting from config file.
Определения ItemBase.c:9302
override float GetWetInit()
Определения ItemBase.c:8636
int m_ImpactSoundSurfaceHash
Определения ItemBase.c:4948
int m_SoundSyncPlay
Определения ItemBase.c:5028
int m_MaxOverheatingValue
Определения ItemBase.c:5007
void SetupSpawnedItem(ItemBase item, float health, float quantity)
Определения ItemBase.c:4931
bool m_IsTakeable
Определения ItemBase.c:4959
bool ShouldSplitQuantity(float quantity)
Определения ItemBase.c:6503
static ref map< string, int > m_WeaponTypeToID
Определения ItemBase.c:4999
string GetLockSoundSet()
Определения ItemBase.c:8734
string GetColorString()
Returns item's PROCEDURAL color as formated string, i.e. "#(argb,8,8,3)color(0.15,...
Определения ItemBase.c:8765
array< int > GetValidFinishers()
returns an array of possible finishers
Определения ItemBase.c:9656
void OnAttachmentQuantityChangedEx(ItemBase item, float delta)
Called on server side when some attachment's quantity is changed. Call super.OnAttachmentQuantityChan...
Определения ItemBase.c:6971
class ItemBase extends InventoryItem SpawnItemOnLocation(string object_name, notnull InventoryLocation loc, bool full_quantity)
Определения ItemBase.c:4911
ItemSoundHandler GetItemSoundHandler()
Определения ItemBase.c:9329
override int GetQuantityMin()
Определения ItemBase.c:8382
void SplitIntoStackMaxToInventoryLocationClient(notnull InventoryLocation dst)
Определения ItemBase.c:6711
override int GetQuickBarBonus()
Определения ItemBase.c:5179
override void SetTakeable(bool pState)
Определения ItemBase.c:9284
float m_OverheatingDecayInterval
Определения ItemBase.c:5008
void SetIsPlaceSound(bool is_place_sound)
override void SplitIntoStackMaxClient(EntityAI destination_entity, int slot_id)
Определения ItemBase.c:6523
void HierarchyCheck(out bool hasParent, out bool hasRootAsPlayer, out ItemBase refParentIB)
Определения ItemBase.c:9501
bool CanProcessDecay()
Определения ItemBase.c:9529
void RemoveAudioVisualsOnClient()
Определения Bottle_Base.c:151
void SoundSynchRemote()
static void AddDebugActionsMask(int mask)
Определения ItemBase.c:5690
void PlayDeployLoopSoundEx()
void RemoveLightSourceItem()
Определения ItemBase.c:9645
bool CanRepair(ItemBase item_repair_kit)
Определения ItemBase.c:7571
bool can_this_be_combined
Определения ItemBase.c:4964
EffectSound m_SoundDeploy
Определения ItemBase.c:9739
int m_SoundSyncSlotID
Определения ItemBase.c:5030
int m_Count
Определения ItemBase.c:4930
float GetBaitEffectivity()
generic effectivity as a bait for animal catching
Определения ItemBase.c:9692
float GetDeployTime()
how long it takes to deploy this item in seconds
Определения ItemBase.c:9276
override bool IsSplitable()
Определения ItemBase.c:6490
bool DamageItemAttachments(float damage)
Определения ItemBase.c:6473
override void WriteVarsToCTX(ParamsWriteContext ctx)
Определения ItemBase.c:7883
void ConvertEnergyToQuantity()
Определения ItemBase.c:8551
override void RemoveAllAgents()
Определения ItemBase.c:8885
override void SetQuantityToMinimum()
Определения ItemBase.c:8314
bool m_WantPlayImpactSound
Определения ItemBase.c:4945
override float GetTemperatureThawTime()
Определения ItemBase.c:9616
ref map< int, ref array< ref WeaponParticlesOnOverheating > > m_OnOverheatingEffect
Определения ItemBase.c:4998
int m_ColorComponentG
Определения ItemBase.c:4975
float m_StoreLoadedQuantity
Определения ItemBase.c:4932
void MessageToOwnerAction(string text)
Send message to owner player in yellow color.
Определения ItemBase.c:7638
int m_ColorComponentA
Определения ItemBase.c:4977
int m_VarQuantityInit
Определения ItemBase.c:4927
float GetFilterDamageRatio()
Определения ItemBase.c:5594
override void SetLiquidType(int value, bool allow_client=false)
Определения ItemBase.c:8778
void OnQuantityChanged(float delta)
Called on server side when this item's quantity is changed. Call super.OnQuantityChanged(); first whe...
Определения ItemBase.c:6942
void OnApply(PlayerBase player)
override void SetQuantityNormalized(float value, bool destroy_config=true, bool destroy_forced=false)
Sets quantity in normalized 0..1 form between the item's Min a Max values as defined by item's config...
Определения ItemBase.c:8321
bool m_HideSelectionsBySlot
Определения ItemBase.c:5012
bool IsOverheatingEffectActive()
Определения ItemBase.c:5457
void SetIsBeingPlaced(bool is_being_placed)
Определения ItemBase.c:5874
int GetLiquidContainerMask()
Определения ItemBase.c:5811
void SetInventoryLocationToVicinityOrCurrent(EntityAI root, inout InventoryLocation dst)
Определения ItemBase.c:7078
ref Timer m_CheckOverheating
Определения ItemBase.c:5005
void RegisterOverheatingParticle(Particle p, float min_heat_coef, float max_heat_coef, int particle_id, Object parent, vector local_pos, vector local_ori)
Определения ItemBase.c:5505
float GetEnergy()
Определения ItemBase.c:8525
bool CanBeDigged()
Определения ItemBase.c:5890
bool GetActionWidgetOverride(out typename name)
If we need a different (handheld)item action widget displayed, the logic goes in here.
Определения ItemBase.c:9662
bool IsNVG()
Определения ItemBase.c:5822
float GetUnitWeight(bool include_wetness=true)
Obsolete, use GetWeightEx instead.
Определения ItemBase.c:8485
void SetZoneDamageCEInit()
Sets zone damages to match randomized global health set by CE (CE spawn only)
Определения ItemBase.c:9438
bool m_IsDeploySound
Определения ItemBase.c:9741
bool CanEat()
Определения ItemBase.c:7531
static void PlayOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:9179
override bool IsOneHandedBehaviour()
Определения ItemBase.c:9250
void AddLightSourceItem(ItemBase lightsource)
Adds a light source child.
Определения ItemBase.c:9640
bool IsLiquidContainer()
Определения ItemBase.c:5806
FoodStage GetFoodStage()
overridden on Edible_Base; so we don't have to parse configs all the time
Определения ItemBase.c:7551
override float GetSingleInventoryItemWeightEx()
Определения ItemBase.c:8409
void SaveAgents(ParamsWriteContext ctx)
Определения ItemBase.c:8963
override int GetTargetQuantityMax(int attSlotID=-1)
Определения ItemBase.c:8363
int m_CleannessInit
Определения ItemBase.c:4941
float GetDisinfectQuantity(int system=0, Param param1=null)
Определения ItemBase.c:5589
override int GetAgents()
Определения ItemBase.c:8910
int m_VarQuantityMax
Определения ItemBase.c:4929
override bool IsHologram()
Определения ItemBase.c:5885
float GetItemAttachOffset()
Определения ItemBase.c:8694
bool IsPlaceSound()
Определения ItemBase.c:9755
static int GetDebugActionsMask()
Определения ItemBase.c:5675
override int GetLiquidType()
Определения ItemBase.c:8794
void ProcessDecay(float delta, bool hasRootAsPlayer)
Определения ItemBase.c:9518
override bool IsItemBase()
Определения ItemBase.c:7684
void PlayDeploySound()
override bool IsTwoHandedBehaviour()
Определения ItemBase.c:9260
void ExplodeAmmo()
Определения ItemBase.c:6375
bool IsCombineAll(ItemBase other_item, bool use_stack_max=false)
Определения ItemBase.c:7154
float GetProtectionLevel(int type, bool consider_filter=false, int system=0)
Определения ItemBase.c:8984
static void PlayBulletCasingEjectParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:9159
override void OnEnergyAdded()
Определения ItemBase.c:8543
void AffectLiquidContainerOnFill(int liquid_type, float amount)
from enviro source
void AffectLiquidContainerOnTransfer(int liquidType, float amount, float sourceLiquidTemperature)
from other liquid container source
string GetExplosiveTriggerSlotName()
Определения ItemBase.c:5834
EffectSound m_DeployLoopSoundEx
Определения ItemBase.c:9738
override void DeSerializeNumericalVars(array< float > floats)
Определения ItemBase.c:7824
void StopItemDynamicPhysics()
Определения ItemBase.c:9420
bool HasFoodStage()
Определения ItemBase.c:7544
override void SetStoreLoad(bool value)
Определения ItemBase.c:8663
float GetOverheatingValue()
Определения ItemBase.c:5419
bool ContainsAgent(int agent_id)
Определения ItemBase.c:8863
override void AddWet(float value)
Определения ItemBase.c:8611
bool IsLiquidPresent()
Определения ItemBase.c:5801
bool IsFullQuantity()
Определения ItemBase.c:8403
override void EOnContact(IEntity other, Contact extra)
Определения ItemBase.c:6084
void SplitIntoStackMaxHands(PlayerBase player)
Определения ItemBase.c:6847
void SplitIntoStackMaxHandsClient(PlayerBase player)
Определения ItemBase.c:6823
int m_CleannessMax
Определения ItemBase.c:4943
float m_VarStackMax
Определения ItemBase.c:4931
ref Timer m_PhysDropTimer
Определения ItemBase.c:5018
void MessageToOwnerFriendly(string text)
Send message to owner player in green color.
Определения ItemBase.c:7656
override void SetStoreLoadedQuantity(float value)
Определения ItemBase.c:8673
bool m_IsResultOfSplit string m_SoundAttType
distinguish if item has been created as new or it came from splitting (server only flag)
Определения ItemBase.c:4972
void CheckOverheating(ItemBase weapon=null, string ammoType="", ItemBase muzzle_owner=null, ItemBase suppressor=null, string config_to_search="")
Определения ItemBase.c:5440
void UnlockFromParent()
Unlocks this item from its attachment slot of its parent.
Определения ItemBase.c:5755
bool Repair(PlayerBase player, ItemBase item_repair_kit, float specialty_weight)
Определения ItemBase.c:7578
void OnLiquidTypeChanged(int oldType, int newType)
Определения ItemBase.c:8799
void StartOverheating(ItemBase weapon=null, string ammoType="", ItemBase muzzle_owner=null, ItemBase suppressor=null, string config_to_search="")
Определения ItemBase.c:5486
void PlayDeployFinishSound()
bool AllowFoodConsumption()
Определения ItemBase.c:8721
bool m_IsOverheatingEffectActive
Определения ItemBase.c:5003
int m_LiquidContainerMask
Определения ItemBase.c:4953
void ProcessItemWetness(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
Определения ItemBase.c:9456
override int GetCleanness()
Определения ItemBase.c:8716
bool PairWithDevice(notnull ItemBase otherDevice)
Определения ItemBase.c:9667
bool IsDeploySound()
Определения ItemBase.c:9756
static void RemoveDebugActionsMask(int mask)
Определения ItemBase.c:5695
static void UpdateOverheatingParticles(ItemBase weapon, string ammoType, ItemBase muzzle_owner, ItemBase suppressor, string config_to_search)
Определения ItemBase.c:9199
int m_VarQuantityMin
Определения ItemBase.c:4928
void PerformDamageSystemReinit()
Определения ItemBase.c:9426
override void ClearInventory()
Определения ItemBase.c:8504
static int m_LastRegisteredWeaponID
Определения ItemBase.c:5000
ItemBase GetLightSourceItem()
Определения ItemBase.c:9650
void MessageToOwnerImportant(string text)
Send message to owner player in red color.
Определения ItemBase.c:7674
override float GetItemOverheatThreshold()
Определения ItemBase.c:9600
void StopDeployLoopSoundEx()
bool m_CanThisBeSplit
Определения ItemBase.c:4965
override void SerializeNumericalVars(array< float > floats_out)
Определения ItemBase.c:7788
ItemBase SplitIntoStackMaxToInventoryLocationEx(notnull InventoryLocation dst)
Определения ItemBase.c:6762
float m_ItemModelLength
Определения ItemBase.c:4951
bool m_IsHologram
Определения ItemBase.c:4958
static int m_DebugActionsMask
Определения ItemBase.c:4918
void KillAllOverheatingParticles()
Определения ItemBase.c:5555
bool CanBeCookedOnStick()
Определения ItemBase.c:7561
override int GetQuantityMax()
Определения ItemBase.c:8349
void GetRecipesActions(Man player, out TSelectableActionInfoArray outputList)
Определения ItemBase.c:7232
void OnActivatedByTripWire()
bool IsColorSet()
Определения ItemBase.c:8759
override void RemoveAgent(int agent_id)
Определения ItemBase.c:8876
bool m_ItemBeingDroppedPhys
Определения ItemBase.c:4961
override bool CanPutAsAttachment(EntityAI parent)
Определения ItemBase.c:9066
void PlayDetachSound(string slot_type)
Определения ItemBase.c:9798
static ref map< typename, ref TInputActionMap > m_ItemTypeActionsMap
Определения ItemBase.c:4912
void ProcessItemWetnessAndTemperature(float delta, bool hasParent, bool hasRootAsPlayer, ItemBase refParentIB)
Определения ItemBase.c:9729
override bool IsBeingPlaced()
Определения ItemBase.c:5869
int GetQuantityInit()
Определения ItemBase.c:8387
float ComputeQuantityUsedEx(ItemBase other_item, bool use_stack_max=true)
Определения ItemBase.c:7174
bool IsResultOfSplit()
Определения ItemBase.c:7159
bool m_FixDamageSystemInit
Определения ItemBase.c:4963
float m_ImpactSpeed
Определения ItemBase.c:4947
bool m_IsStoreLoad
Определения ItemBase.c:4966
int GetLiquidTypeInit()
Определения ItemBase.c:8789
string GetDeployFinishSoundset()
ItemBase m_LightSourceItem
Определения ItemBase.c:4981
void LockToParent()
Locks this item in it's current attachment slot of its parent. This makes the "locked" icon visible i...
Определения ItemBase.c:5742
override void SplitIntoStackMaxEx(EntityAI destination_entity, int slot_id)
Определения ItemBase.c:6633
int m_AttachedAgents
Определения ItemBase.c:4989
string m_LockSoundSet
Определения ItemBase.c:5024
void LoadParticleConfigOnOverheating(int id)
Определения ItemBase.c:5363
float m_VarQuantityPrev
Определения ItemBase.c:4926
bool IsSoundSynchRemote()
Определения ItemBase.c:9754
bool m_CanShowQuantity
Определения ItemBase.c:4967
override void OnRightClick()
Определения ItemBase.c:7014
int m_ColorComponentB
Определения ItemBase.c:4976
static ref map< typename, ref TActionAnimOverrideMap > m_ItemActionOverrides
Определения ItemBase.c:4914
bool IsActionTargetVisible()
Определения ItemBase.c:9296
override void OnItemAttachmentSlotChanged(notnull InventoryLocation oldLoc, notnull InventoryLocation newLoc)
Определения ItemBase.c:6119
override void EEHitBy(TotalDamageResult damageResult, int damageType, EntityAI source, int component, string dmgZone, string ammo, vector modelPos, float speedCoef)
Определения ItemBase.c:6412
bool m_IsBeingPlaced
Определения ItemBase.c:4957
int NameToID(string name)
Определения ItemBase.c:7761
void ~ItemBase()
Определения ItemBase.c:5640
override void OnWetLevelChanged(EWetnessLevel newLevel, EWetnessLevel oldLevel)
Определения ItemBase.c:8651
void ClearStopItemSoundServer()
Определения ItemBase.c:9396
override string ChangeIntoOnDetach()
Определения ItemBase.c:6336
float m_VarWetMax
Определения ItemBase.c:4938
void SplitIntoStackMaxToInventoryLocation(notnull InventoryLocation dst)
Определения ItemBase.c:6757
int GetLockType()
Определения ItemBase.c:8729
EffectSound m_SoundDeployFinish
Определения ItemBase.c:9736
override float GetWet()
Определения ItemBase.c:8621
EffectSound m_SoundPlace
Определения ItemBase.c:9737
float GetQuantityNormalizedScripted()
Определения ItemBase.c:8335
override void SetCleanness(int value, bool allow_client=false)
Определения ItemBase.c:8703
bool m_IsPlaceSound
Определения ItemBase.c:9740
override float GetWetMin()
Определения ItemBase.c:8631
ref ItemSoundHandler m_ItemSoundHandler
Определения ItemBase.c:5032
override bool KindOf(string tag)
Определения ItemBase.c:7690
void ItemSoundHandler(ItemBase parent)
Определения ItemSoundHandler.c:31
string Type
Определения JsonDataContaminatedArea.c:11
EffectSound m_LockingSound
Определения Land_Underground_Entrance.c:336
string GetDebugText()
Определения ModifierBase.c:71
@ LOWEST
Определения PPEConstants.c:54
void PluginItemDiagnostic()
Определения PluginItemDiagnostic.c:74
PluginBase GetPlugin(typename plugin_type)
Определения PluginManager.c:325
override RemotelyActivatedItemBehaviour GetRemotelyActivatedItemBehaviour()
Определения RemoteDetonator.c:272
void RemoteDetonatorTrigger()
Определения RemoteDetonator.c:233
override void OnActivatedByItem(notnull ItemBase item)
Called when this item is activated by other.
Определения RemoteDetonator.c:305
int particle_id
Определения SmokeSimulation.c:28
ETemperatureAccessTypes
Определения TemperatureAccessConstants.c:2
override void Explode(int damageType, string ammoType="")
Определения Trap_LandMine.c:220
bool m_Initialized
Определения UiHintPanel.c:317
int GetID()
Определения ActionBase.c:1335
void OnItemLocationChanged(ItemBase item)
Определения ActionBase.c:974
GetInputType()
Определения ActionBase.c:221
int m_StanceMask
Определения ActionBase.c:25
int m_CommandUIDProne
Определения ActionBase.c:24
int m_CommandUID
Определения ActionBase.c:23
proto native int GetItemCount()
proto native EntityAI GetItem(int index)
float GetEnergyAtSpawn()
Определения ComponentEnergyManager.c:1325
void SetEnergy0To1(float energy01)
Energy manager: Sets stored energy for this device between 0 and MAX based on relative input value be...
Определения ComponentEnergyManager.c:550
float GetEnergyMaxPristine()
Energy manager: Returns the maximum amount of energy this device can store. It's damage is NOT taken ...
Определения ComponentEnergyManager.c:1320
override void SetAutodestroy(bool auto_destroy)
Sets whether Effect automatically cleans up when it stops.
Определения EffectSound.c:603
bool IsSoundPlaying()
Get whether EffectSound is currently playing.
Определения EffectSound.c:274
override bool IsMan()
Определения 3_Game/DayZ/Entities/Man.c:48
proto native EntityAI GetAttachmentFromIndex(int index)
proto native bool GetCurrentInventoryLocation(out notnull InventoryLocation loc)
returns information about current item location
proto native bool EnumerateInventory(InventoryTraversalType tt, out array< EntityAI > items)
enumerate inventory using traversal type and filling items array
proto native CargoBase GetCargo()
cargo
static proto native EntityAI LocationCreateEntity(notnull InventoryLocation inv_loc, string type, int iSetupFlags, int iRotation)
creates new item directly at location
proto native int AttachmentCount()
Returns count of attachments attached to this item.
proto native bool FindFreeLocationFor(notnull EntityAI item, FindInventoryLocationType flags, out notnull InventoryLocation loc)
FindFreeLocationFor.
proto void SelectObject(Object object)
proto void SelectPhysics(Physics physics)
Определения ItemBase.c:21
proto native bool IsValid()
verify current set inventory location
proto native EntityAI GetParent()
returns parent of current inventory location
proto native int GetSlot()
returns slot id if current type is Attachment
proto native int GetCol()
returns column of cargo if current type is Cargo / ProxyCargo
proto native int GetRow()
returns row of cargo if current type is Cargo / ProxyCargo
bool WriteToContext(ParamsWriteContext ctx)
Определения InventoryLocation.c:507
proto native int GetType()
returns type of InventoryLocation
proto native int GetIdx()
returns index of cargo if current type is Cargo / ProxyCargo
proto native void SetCargo(notnull EntityAI parent, EntityAI e, int idx, int row, int col, bool flip)
sets current inventory location type to Cargo with coordinates (idx, row, col)
proto native bool GetFlip()
returns flip status of cargo
proto native EntityAI GetItem()
returns item of current inventory location
InventoryLocation.
Определения InventoryLocation.c:30
override bool CanDisplayCargo()
Определения TentBase.c:91
override void OnInventoryEnter(Man player)
Определения BarbedWire.c:203
override string GetFoldSoundset()
Определения BaseBuildingBase.c:108
override bool CanPutAsAttachment(EntityAI parent)
Определения ItemBase.c:7
override bool CanReceiveItemIntoCargo(EntityAI item)
Определения TentBase.c:934
override bool OnStoreLoad(ParamsReadContext ctx, int version)
Определения GardenBase.c:199
override void OnWasDetached(EntityAI parent, int slot_id)
override void EEOnAfterLoad()
Определения GardenBase.c:242
override void EEDelete(EntityAI parent)
Определения BaseBuildingBase.c:68
override bool CanBeRepairedByCrafting()
Определения TentBase.c:86
override void OnPlacementStarted(Man player)
Определения BatteryCharger.c:376
override void OnItemLocationChanged(EntityAI old_owner, EntityAI new_owner)
Определения BarbedWire.c:357
override bool IsElectricAppliance()
Определения BatteryCharger.c:43
override bool IsItemTent()
Определения TentBase.c:81
override string GetLoopFoldSoundset()
Определения BaseBuildingBase.c:113
override bool CanMakeGardenplot()
Определения FieldShovel.c:3
override void GetDebugActions(out TSelectableActionInfoArrayEx outputList)
Определения PowerGenerator.c:397
override void EEItemLocationChanged(notnull InventoryLocation oldLoc, notnull InventoryLocation newLoc)
Определения HandcuffsLocked.c:12
override WrittenNoteData GetWrittenNoteData()
Определения Paper.c:30
override int GetDamageSystemVersionChange()
Определения BaseBuildingBase.c:1238
override bool SetQuantity(float value, bool destroy_config=true, bool destroy_forced=false, bool allow_client=false, bool clamp_to_stack_max=true)
Определения PileOfWoodenPlanks.c:88
override void InitItemVariables()
Определения Matchbox.c:3
override void SetActionAnimOverrides()
Определения PickAxe.c:28
override void OnCreatePhysics()
Определения BaseBuildingBase.c:489
override string GetDeploySoundset()
Определения BarbedWire.c:392
override float GetBandagingEffectivity()
Определения BandageDressing.c:49
override bool OnAction(int action_id, Man player, ParamsReadContext ctx)
Определения PowerGenerator.c:409
override void EEHealthLevelChanged(int oldLevel, int newLevel, string zone)
Определения BaseBuildingBase.c:496
override void OnStoreSave(ParamsWriteContext ctx)
Определения GardenBase.c:266
override void AfterStoreLoad()
Определения BarbedWire.c:155
override int GetOnDigWormsAmount()
Определения FieldShovel.c:27
override bool IsSelfAdjustingTemperature()
Определения PortableGasStove.c:287
override bool IsPlayerInside(PlayerBase player, string selection)
Определения BaseBuildingBase.c:1037
override void OnVariablesSynchronized()
Определения GardenBase.c:97
override void RefreshPhysics()
Определения BatteryCharger.c:359
override bool CanObstruct()
Определения BaseBuildingBase.c:84
override void OnWasAttached(EntityAI parent, int slot_id)
override bool CanReceiveAttachment(EntityAI attachment, int slotId)
Определения BaseBuildingBase.c:982
override bool CanPutInCargo(EntityAI parent)
Определения GardenBase.c:331
override string GetLoopDeploySoundset()
Определения BarbedWire.c:397
override void OnPlacementComplete(Man player, vector position="0 0 0", vector orientation="0 0 0")
Определения BarbedWire.c:372
override void OnInventoryExit(Man player)
Определения BatteryCharger.c:341
override bool IsTakeable()
Определения BaseBuildingBase.c:1008
override bool IsIgnoredByConstruction()
Определения BaseBuildingBase.c:1170
override void InitItemSounds()
Определения BaseBuildingBase.c:94
override void EEKilled(Object killer)
Определения HandcuffsLocked.c:70
override void OnCombine(ItemBase other_item)
Определения BandageDressing.c:71
override bool CanExplodeInFire()
Определения LargeGasCannister.c:3
override bool IsFacingPlayer(PlayerBase player, string selection)
Определения BaseBuildingBase.c:1032
override bool CanBeCombined(EntityAI other_item, bool reservation_check=true, bool stack_max_limit=false)
Определения Rag.c:61
override bool IsBloodContainer()
Определения BloodContainerBase.c:10
override bool CanBeSplit()
Определения Rag.c:34
override bool IsDeployable()
Определения BaseBuildingBase.c:365
override void OnRPC(PlayerIdentity sender, int rpc_type, ParamsReadContext ctx)
Определения ToolBase.c:24
override bool CanBeDisinfected()
Определения BandageDressing.c:54
override float GetInfectionChance(int system=0, Param param=null)
Определения BandageDressing.c:59
override void OnEndPlacement()
Определения KitBase.c:65
Определения ItemBase.c:14
Определения EnMath.c:7
float GetOverheatingLimitMax()
Определения WeaponParticles.c:417
void SetOverheatingLimitMax(float max)
Определения WeaponParticles.c:407
void SetParticleParams(int particle_id, Object parent, vector local_pos, vector local_ori)
Определения WeaponParticles.c:422
float GetOverheatingLimitMin()
Определения WeaponParticles.c:412
Particle GetParticle()
Определения WeaponParticles.c:397
void SetOverheatingLimitMin(float min)
Определения WeaponParticles.c:402
void RegisterParticle(Particle p)
Определения WeaponParticles.c:392
void Stop()
Legacy function for backwards compatibility with 1.14 and below.
Определения Particle.c:266
void SetControlledDevice(EntityAI pDevice)
Определения RemoteDetonator.c:140
bool OnStoreLoad(ParamsReadContext ctx, int version)
void OnStoreSave(ParamsWriteContext ctx)
proto native void Send()
proto bool Write(void value_out)
proto bool Read(void value_in)
bool m_Loop
Определения ItemSoundHandler.c:5
override void Stop()
Определения DayZPlayerImplement.c:40
proto native float GetDamage(string zoneName, string healthType)
override void Refresh()
Определения ChatInputMenu.c:70
void SetCalcDetails(string details)
Определения 3_Game/DayZ/tools/Debug.c:916
void OnRPC(PlayerIdentity sender, int rpc_type, ParamsReadContext ctx)
Определения WrittenNoteData.c:13
const float LOWEST
Определения EnConvert.c:113
Serializer ParamsReadContext
Определения gameplay.c:15
class LOD Object
InventoryTraversalType
tree traversal type, for more see http://en.wikipedia.org/wiki/Tree_traversal
Определения gameplay.c:6
Serializer ParamsWriteContext
Определения gameplay.c:16
const int DEF_BIOLOGICAL
Определения 3_Game/DayZ/constants.c:515
const int DEF_CHEMICAL
Определения 3_Game/DayZ/constants.c:516
const int COMP_TYPE_ENERGY_MANAGER
Определения Component.c:9
ErrorExSeverity
Определения EnDebug.c:62
void Error(string err)
Messagebox with error message.
Определения EnDebug.c:90
enum ShapeType ErrorEx
proto native void SetColor(int color)
array< string > TStringArray
Определения EnScript.c:712
array< int > TIntArray
Определения EnScript.c:714
void Obsolete(string msg="")
Определения EnScript.c:371
EntityEvent
Entity events for event-mask, or throwing event from code.
Определения EnEntity.c:45
static const float ITEM_TEMPERATURE_NEUTRAL_ZONE_MIDDLE
Определения 3_Game/DayZ/constants.c:811
const int VARIABLE_LIQUIDTYPE
Определения 3_Game/DayZ/constants.c:635
const int VARIABLE_CLEANNESS
Определения 3_Game/DayZ/constants.c:638
const int VARIABLE_COLOR
Определения 3_Game/DayZ/constants.c:637
const int VARIABLE_TEMPERATURE
Определения 3_Game/DayZ/constants.c:633
const int VARIABLE_QUANTITY
Определения 3_Game/DayZ/constants.c:631
const int VARIABLE_WET
Определения 3_Game/DayZ/constants.c:634
const int LIQUID_NONE
Определения 3_Game/DayZ/constants.c:532
static proto float AbsFloat(float f)
Returns absolute value.
const int MENU_INVENTORY
Определения 3_Game/DayZ/constants.c:180
proto native bool dBodyIsDynamic(notnull IEntity ent)
const int SAT_CRAFTING
Определения 3_Game/DayZ/constants.c:456
const int SAT_DEBUG_ACTION
Определения 3_Game/DayZ/constants.c:457
vector GetPosition()
Get the world position of the Effect.
Определения Effect.c:473
static proto string Format(string fmt, void param1=NULL, void param2=NULL, void param3=NULL, void param4=NULL, void param5=NULL, void param6=NULL, void param7=NULL, void param8=NULL, void param9=NULL)
Gets n-th character from string.
const int CALL_CATEGORY_GAMEPLAY
Определения 3_Game/DayZ/tools/tools.c:10
const int CALL_CATEGORY_SYSTEM
Определения 3_Game/DayZ/tools/tools.c:8
proto native int GetColor()