tpw 2315 Posted November 13, 2010 (edited) Hi all A while ago AZcoder gave me the heads up on a nice little "invincibility script" which worked thusly: In each unit's init I added an eventhandler addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] unitnearlykilled.sqf: // Units don't die, thanks to AZCoder for the tips private ["_targ","_dmg","_totalDmg"]; _targ = _this select 0; _dmg = _this select 2; // calculate damage _totalDmg = (damage _targ) + _dmg; if (_totalDmg > 0.5) then { _totalDmg = 0.5; }; _targ setDamage _totalDmg; This combination worked very well right up until I installed CO patch 1.55 (75445). Now it does absolutely nothing. The eventhandler is handling the event, but the script it calls is not working as previously. I've even simplified it to the following for total invulnerability. _targ = _this select 0; _targ setDamage 0; but it still refuses to work. Does anyone know what might have changed to cause this behaviour, or if there are any workarounds? Edited November 14, 2010 by Dwarden resolved problem Share this post Link to post Share on other sites
snkman 351 Posted November 13, 2010 addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] It should be: this addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] Also wouldn't it be easyer to use: this allowDamage False; ;) Share this post Link to post Share on other sites
tpw 2315 Posted November 13, 2010 addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] It should be: this addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] Also wouldn't it be easyer to use: this allowDamage False; ;) Thanks SNKMAN I actually do use this addEventHandler ["HandleDamage", {_this execVM "scripts\unitnearlykilled.sqf"}] , just forgot to put the "this" in my post. The eventhandler is working. this allowDamage False is not as useful because with the functioning script, players can still take damage, or it can be refined further so that they are knocked out etc. Share this post Link to post Share on other sites
tpw 2315 Posted November 14, 2010 After a bit of research it turns out that ACE 1.6 is causing the issue, since it sets up its own HandleDamage eventhandler ( in ace_sys_wounds), which overrides anything I put in mine. Share this post Link to post Share on other sites
sickboy 13 Posted November 14, 2010 (edited) Only if you have the optional wounds system enabled. Same should occur if you have BIS wounding enabled I guess. Also check the coding notes of the wounding system for additional information and options to override ACE wounds; http://ace.dev-heaven.net/wagn/Wounding_System Specifically ace_w_allow_dam and ace_w_eh object variables, and the addDamage function. Additionally, it's recommended not to use execVM, not just for performance reasons (http://community.bistudio.com/wiki/6thSense.eu:EG#Scripting_Tips) but because handleDamage eventhandler expects a return value (number), based on the return value it applies damage. execVM returns a script-handle. Call (compile preProcessFile or a global variable with the function), will return whatever you tell it to return at the exit of the function. http://community.bistudio.com/wiki/ArmA_2:_Event_Handlers#HandleDamage Edited November 14, 2010 by Sickboy Share this post Link to post Share on other sites
tpw 2315 Posted November 14, 2010 Only if you have the optional wounds system enabled. Same should occur if you have BIS wounding enabled I guess.Also check the coding notes of the wounding system for additional information and options to override ACE wounds; http://ace.dev-heaven.net/wagn/Wounding_System Specifically ace_w_allow_dam and ace_w_eh object variables, and the addDamage function. Additionally, it's recommended not to use execVM, not just for performance reasons (http://community.bistudio.com/wiki/6thSense.eu:EG#Scripting_Tips) but because handleDamage eventhandler expects a return value (number), based on the return value it applies damage. execVM returns a script-handle. Call (compile preProcessFile or a global variable with the function), will return whatever you tell it to return at the exit of the function. http://community.bistudio.com/wiki/ArmA_2:_Event_Handlers#HandleDamage Huge thanks for all the info Sickboy. That's given me plenty of light reading to do... FWIW I'll gladly ditch my script in favour of all the other excellent stuff ACE brings to the game. ---------- Post added at 23:10 ---------- Previous post was at 22:52 ---------- Might this do the trick? [unit, <damage value between 0 and 1>] call ace_sys_wounds_fnc_addDamage; If I set value of 0.5 does it add that much damage or set the total damage to 0.5? Is there such a command: ace_sys_wounds_fnc_setDamage; Share this post Link to post Share on other sites
sickboy 13 Posted November 14, 2010 addDamage adds it. old function prdamcheck sets it iirc. I think you could best override the wounds behaviour by setting "the ace_w_eh" object variable on the unit(s) as described in the wounds notes. And then use your own handleDamage eventhandler. Share this post Link to post Share on other sites
xeno 234 Posted November 14, 2010 You can disable ACE handleDamage and handleHeal completely. To disable handleDamage (means, no handleDamage EH is added to units) use the following in init.sqf: if (isServer) then { ace_w_no_handledamage = true; publicVariable "ace_w_no_handledamage"; }; To remove handleHeal (no handleHeal EH is added to units): if (isServer) then { ace_w_no_handleheal = true; publicVariable "ace_w_no_handleheal"; }; (or put those variables in an object init line: ace_w_no_handledamage = true; ace_w_no_handleheal = true; ) Xeno Share this post Link to post Share on other sites
tpw 2315 Posted November 14, 2010 Thanks so much gentlemen, I shall give these a try ASAP. Basically, I really like the way ACE handles damage and wounds, I just want it so that the units cannot be killed, but knocked out instead. It blows my mind how well this game and its mods are supported! Share this post Link to post Share on other sites
AZCoder 921 Posted November 14, 2010 tpw: If you are interested, I have a more complete version of the function that I use in the campaign I am building. I have tested it with the current 1.6 ACE with wounding, and it works fine. I did not do anything special to make it work, although this version is a little different. I wrote this solely with single player in mind, so if you are doing MP it may need publicVariable calls and such. I have no experience with MP scripting. In your init.sqf, define the function like this: AZC_fnc_invincible = compile preprocessFile "fnc_invincible.sqf"; You can change the AZC name, I'm just using my OFPEC tag :) For the test I did, I placed a soldier named Cpl Boom. After the code above, put this: [boom,120] call AZC_fnc_invincible; The 120 is the max number of seconds that Boom will be incapacitated. So change that as you wish. Here is the code for fnc_invincible.sqf /* ---------------------------------------------------------------------------- Function: AZC_fnc_invincible Author: AZCoder Version: 1.0 Created: 10/18/2010 Modified: 11/14/2010 Description: Makes given unit invincible to death. Its purpose is to simulate severe injuries without allowing a key AI to die during a mission. Parameters: _unit - unit to keep alive; if it's human then it will simulate injury _recovery - recovery time from severe injury in seconds Returns: nothing. Examples: [Escobar,60] call AZC_fnc_invincible; --> unit Escobar will remain incapcitated for 60 seconds if mortally wounded. ---------------------------------------------------------------------------- */ private ["_unit","_recovery","_unitRecovery"]; _unit = _this select 0; _recovery = _this select 1; if (_recovery < 1) then { _recovery = 1; }; // store variable with unique name in mission namespace _unitRecovery = format["AZC_recover%1",_unit]; missionNamespace setVariable[_unitRecovery, _recovery]; _unit addEventHandler ["HandleDamage", { private ["_targ","_dmg","_totalDmg"]; _targ = _this select 0; _dmg = _this select 2; // calculate damage _totalDmg = (damage _targ) + _dmg; if (_totalDmg > 0.88) then { // must set damage because this event handler prevents it _targ setDamage 0.88; if (_targ isKindOf "Man") then { if (!alive(_targ)) exitWith {}; // if alive then run wounded animation for length of _recovery _targ playMove "AinjPpneMstpSnonWrflDnon"; [_targ] spawn { private ["_injured","_reco","_limit"]; _injured = _this select 0; _unitRecovery = format["AZC_recover%1",_injured]; _reco = missionNamespace getVariable _unitRecovery; _limit = time + _reco; // if unit gets healed during _recovery time, exit this loop while { damage _injured > 0.8 } do { // sleep won't work here, the intention is to allow a medic to heal the injuree if (time > _limit) exitWith { _injured setDamage 0.8; }; }; // set to normal "ready" animation _injured playMoveNow "AmovPercMstpSlowWrflDnon"; if (damage _injured > 0.8) then { _injured setDamage 0.8; }; }; }; } else { // if total damage less than .88, set damage to total of existing damage plus handled damage _targ setDamage _totalDmg; }; }]; If a medic heals the injured guy before the time limit passes, then the script will abort. Bear in mind, when the soldier is on the ground incapacitated, the animation really just places him on his back and he looks almost dead, but his head will move if you approach him. Share this post Link to post Share on other sites
tpw 2315 Posted November 15, 2010 You are a bloody legend AZC! I tried it and it works exactly as advertised! Actually this adds a huge amount to the gameplay, if I set it for me and everyone in my squad. If you get hit you go down and stay down for a few minutes, and even if you manage to get patched up, you can still pass out at some time in the future. So it seems like much less of a magic wand approach to healing. Thanks again AZC. Share this post Link to post Share on other sites
HateDread 13 Posted December 14, 2010 Thanks AZC for this. Just wondering, guys, is there a way to make it so that if all units specified go down at once, the mission fails (Like L4D's system), as nobody can patch anybody else up? I.e. if it spits out a variable that can be checked, one could just run a trigger with condition Unit1 --Incapacitated variable here-- && Unit2 --Incapacitated variable here- etc, etc. Any ideas? :) Share this post Link to post Share on other sites
sowens 71 Posted December 15, 2010 Thanks AZC for this.Just wondering, guys, is there a way to make it so that if all units specified go down at once, the mission fails (Like L4D's system), as nobody can patch anybody else up? I.e. if it spits out a variable that can be checked, one could just run a trigger with condition Unit1 --Incapacitated variable here-- && Unit2 --Incapacitated variable here- etc, etc. Any ideas? :) Could you put a counter in there to add +1 when incapped and -1 if healed. Add a define for the number of players on the map. Add a loop to see if the number of incapped = define and end the message when that happens? Share this post Link to post Share on other sites
katipo66 94 Posted December 21, 2010 @AZCoder... this script is awesome, a great SP revive option.. thanks. I am applying this script to me [player] as well as the AI in my group, what i find is enemy AI do not stop firing at you when unconcious, so i added setcaptive true and false like this if (!alive(_targ)) exitWith {}; // if alive then run wounded animation for length of _recovery _targ setUnconscious true; _targ setCaptive true; _targ playMove "AinjPpneMstpSnonWrflDnon"; [_targ] spawn { private ["_injured","_reco","_limit"]; _injured = _this select 0; _unitRecovery = format["AZC_recover%1",_injured]; _reco = missionNamespace getVariable _unitRecovery; _limit = time + _reco; // if unit gets healed during _recovery time, exit this loop while { damage _injured > 0.8 } do { // sleep won't work here, the intention is to allow a medic to heal the injuree if (time > _limit) exitWith { _injured setDamage 0.8; }; }; // set to normal "ready" animation _injured playMoveNow "AmovPercMstpSlowWrflDnon"; _injured setCaptive false; if (damage _injured > 0.8) then { _injured setDamage 0.8; }; Which works ok, i havent tested it a lot, but when unconscious enemy ignores you, and then engage again when revived.. but i seem to lose all my actions like the ability to reload and addactions etc. Is it possible to fast forward time [speed game up] while in an unconscious state, so that enemy AI move away from your position.. or thinking about it that may not work either if AI are set to defend/guard a position, What i had been doing before i saw this was using Norrins revive, and had the respawn marker follow the player at a certain distance (100/200 metres) and that works great but its not perfect.. Share this post Link to post Share on other sites