/// <summary> /// 复制(深拷贝) /// </summary> protected override void toCopy(BaseData data) { if (!(data is DamageOneData)) { return; } DamageOneData mData = (DamageOneData)data; this.instanceID = mData.instanceID; this.isHit = mData.isHit; this.isCrit = mData.isCrit; if (mData.damages != null) { if (this.damages != null) { this.damages.clear(); this.damages.ensureCapacity(mData.damages.size()); } else { this.damages = new SList <DIntData>(); } SList <DIntData> damagesT = this.damages; if (!mData.damages.isEmpty()) { DIntData[] damagesVValues = mData.damages.getValues(); for (int damagesVI = 0, damagesVLen = mData.damages.length(); damagesVI < damagesVLen; ++damagesVI) { DIntData damagesV = damagesVValues[damagesVI]; DIntData damagesU; if (damagesV != null) { damagesU = (DIntData)BytesControl.createData(DIntData.dataID); damagesU.copy(damagesV); } else { damagesU = null; nullObjError("damagesU"); } damagesT.add(damagesU); } } } else { this.damages = null; nullObjError("damages"); } this.isKilled = mData.isKilled; this.arg = mData.arg; }
protected override void doAttackMoment(int moment, Unit from, Unit attacker, Unit target, AttackData lastData, DamageOneData damageOneData) { if (!_g14) { _m14 = instance.Type.GetMethod("doAttackMoment", 6); _g14 = true; } if (_m14 != null && !_b14) { _b14 = true; _p6[0] = moment; _p6[1] = from; _p6[2] = attacker; _p6[3] = target; _p6[4] = lastData; _p6[5] = damageOneData; appdomain.Invoke(_m14, instance, _p6); _p6[0] = null; _p6[1] = null; _p6[2] = null; _p6[3] = null; _p6[4] = null; _p6[5] = null; _b14 = false; } else { base.doAttackMoment(moment, from, attacker, target, lastData, damageOneData); } }
public override void onUnitDamage(Unit unit, Unit from, AttackConfig config, DamageOneData data) { if (!_g13) { _m13 = instance.Type.GetMethod("onUnitDamage", 4); _g13 = true; } if (_m13 != null && !_b13) { _b13 = true; _p4[0] = unit; _p4[1] = from; _p4[2] = config; _p4[3] = data; appdomain.Invoke(_m13, instance, _p4); _p4[0] = null; _p4[1] = null; _p4[2] = null; _p4[3] = null; _b13 = false; } else { base.onUnitDamage(unit, from, config, data); } }
public override void onDamage(Unit from, AttackConfig config, DamageOneData data) { if (!_g25) { _m25 = instance.Type.GetMethod("onDamage", 3); _g25 = true; } if (_m25 != null && !_b25) { _b25 = true; _p3[0] = from; _p3[1] = config; _p3[2] = data; appdomain.Invoke(_m25, instance, _p3); _p3[0] = null; _p3[1] = null; _p3[2] = null; _b25 = false; } else { base.onDamage(from, config, data); } }
public virtual void onDamage(Unit from, AttackConfig config, DamageOneData data) { if (config.hitEffect > 0) { _unit.show.playEffect(config.hitEffect); } _scene.show.onUnitDamage(_unit, from, config, data); }
/** 单位受伤 */ public virtual void onUnitDamage(Unit unit, Unit from, AttackConfig config, DamageOneData data) { //需要显示 if (unit.isSelfControl() || from.isSelfControl()) { foreach (DIntData v in data.damages) { Ctrl.print("受击伤害", v.value); showOneDamage(unit, v.key, v.value); } } }
/// <summary> /// 复制(潜拷贝) /// </summary> protected override void toShadowCopy(BaseData data) { if (!(data is DamageOneData)) { return; } DamageOneData mData = (DamageOneData)data; this.instanceID = mData.instanceID; this.isHit = mData.isHit; this.isCrit = mData.isCrit; this.damages = mData.damages; this.isKilled = mData.isKilled; this.arg = mData.arg; }
/** 执行攻击数据 */ private void toExecuteAttack(AttackData data) { Unit from = _scene.getFightUnit(data.fromInstanceID); if (from == null) { return; } Unit attacker = from.fight.getAttackerUnit(); if (attacker == null) { return; } int attackerInstanceID = attacker.instanceID; SkillTargetData tData = data.targetData; AttackConfig config = data.config; AttackLevelConfig levelConfig = data.levelConfig; //主目标 Unit mTarget = _scene.getFightUnit(tData.targetInstanceID); SList <Unit> tempTargets = new SList <Unit>(); //构造目标组 toMakeTargets(tempTargets, from, attacker, mTarget, tData, config, levelConfig); Unit target; //TODO:攻击前动作组 //如果跳过伤害阶段 if (config.passDamage) { for (int i = 0, len = tempTargets.size(); i < len; ++i) { target = tempTargets[i]; //不可被攻击 if (target.fight.getStatusLogic().cantBeAttackTarget()) { continue; } //添加buff if (levelConfig.addBuffProbID > 0) { if (attacker.fight.randomProb(levelConfig.addBuffProbID)) { int adderInstanceID = attackerInstanceID == target.instanceID ? -1 :attackerInstanceID; foreach (DIntData v in levelConfig.addBuffs) { target.fight.getBuffLogic().addBuff(v.key, v.value, adderInstanceID); } } } //有子弹 if (levelConfig.bullet.key > 0) { from.fight.createAndExecuteBullet(levelConfig.bullet.key, levelConfig.bullet.value, tData); } } } else { doAttackMoment(AttackMomentType.AttackBeforeHit, @from, attacker, null, data, null); if (!tempTargets.isEmpty()) { SList <Unit> tempKilledUnits = null; SList <DamageOneData> damageDataList = new SList <DamageOneData>(); StatusDataLogic attackerStatus = attacker.fight.getStatusLogic(); AttributeDataLogic attackerAttribute = attacker.fight.getAttributeLogic(); BuffDataLogic attackerBuffLogic = attacker.fight.getBuffLogic(); StatusDataLogic targetStatus; AttributeDataLogic targetAttribute; bool momentHitted = false; for (int i = 0, len = tempTargets.size(); i < len; ++i) { target = tempTargets[i]; targetStatus = target.fight.getStatusLogic(); targetAttribute = target.fight.getAttributeLogic(); //不可被攻击 if (targetStatus.cantBeAttackTarget()) { continue; } //上次血量 int lastHp = targetAttribute.getHp(); DamageOneData damageOneData = new DamageOneData(); damageOneData.instanceID = target.instanceID; damageDataList.add(damageOneData); SList <DIntData> damageList = new SList <DIntData>(); damageOneData.damages = damageList; damageOneData.isHit = toCountIsHit(data, attacker, target); doAttackMoment(AttackMomentType.BeAttackBeforeHit, target, target, attacker, data, damageOneData); int realDamage = 0; if (damageOneData.isHit) { if (!momentHitted) { momentHitted = true; doAttackMoment(AttackMomentType.AttackOnHitAnyTarget, @from, attacker, target, data, damageOneData); } if (target == mTarget) { doAttackMoment(AttackMomentType.AttackBeforeDamageMainTarget, @from, attacker, target, data, damageOneData); } doAttackMoment(AttackMomentType.AttackBeforeDamageEachTarget, @from, attacker, target, data, damageOneData); doAttackMoment(AttackMomentType.BeAttackBeforeDamage, target, target, attacker, data, damageOneData); //添加buff if (levelConfig.addBuffProbID > 0) { if (attacker.fight.randomProb(levelConfig.addBuffProbID)) { int adderInstanceID = attackerInstanceID == target.instanceID ? -1 :attackerInstanceID; foreach (DIntData v in levelConfig.addBuffs) { target.fight.getBuffLogic().addBuff(v.key, v.value, adderInstanceID); } } } //有子弹 DIntData levelConfigBullet; if ((levelConfigBullet = levelConfig.bullet).key > 0) { from.fight.createAndExecuteBullet(levelConfigBullet.key, levelConfigBullet.value, tData); } bool isCrit = damageOneData.isCrit = toCountIsCrit(data, attacker, target); SkillVarConfig varConfig; int[] damages; int damageType; int damageValue; int attackValue; int damageVarIndex = 0; //伤害组 for (int j = 0, jLen = levelConfig.damages.Length; j < jLen; ++j) { varConfig = levelConfig.varConfigT[j]; damages = levelConfig.damages[j]; damageType = damages[0]; if (data.isRecorded) { attackValue = BaseGameUtils.calculateSkillVarValueForSelf(varConfig, data.selfAttackValues, damageVarIndex, target.fight.getDataLogic()); damageVarIndex += varConfig.args.Length; } else { attackValue = BaseGameUtils.calculateSkillVarValueFull(varConfig, attacker.fight.getDataLogic(), target.fight.getDataLogic()); } damageValue = toCalculateDamage(data, damageType, damages, attackValue, isCrit, attackerAttribute, targetAttribute, attacker, target); if (damageValue > 0) { if (needDamageHurt(damageType)) { int rd = 0; if (!targetStatus.isDamageImmun()) { rd = takeDamage(damageType, damageValue, targetAttribute, target); } if (Global.damageValueUseRealDamage) { damageValue = rd; } realDamage += rd; } //TODO:反伤类 damageList.add(DIntData.create(damageType, damageValue)); } } if (realDamage > 0) { _scene.method.onUnitTakeDamage(target, realDamage, attacker); } if (target == mTarget) { doAttackMoment(AttackMomentType.AttackAfterDamageMainTarget, @from, attacker, target, data, damageOneData); } doAttackMoment(AttackMomentType.AttackAfterDamageEachTarget, @from, attacker, target, data, damageOneData); doAttackMoment(AttackMomentType.BeAttackAfterDamage, target, target, attacker, data, damageOneData); //扣除buff次数 attackerBuffLogic.subBuffNumArr(BuffSubNumType.UseAttackFromGroup, config.groups); attackerBuffLogic.subBuffNumArr(BuffSubNumType.MakeDamage, levelConfig.damageTypesT); target.fight.getBuffLogic().subBuffNumArr(BuffSubNumType.BeDamage, levelConfig.damageTypesT); //血减到0 if (lastHp > 0 && targetAttribute.getAttribute(AttributeType.Hp) <= 0 && targetStatus.isAlive()) { if (tempKilledUnits == null) { tempKilledUnits = new SList <Unit>(); } tempKilledUnits.add(target); } } //受伤(客户端受伤即使realDamage为0也需要) target.fight.onDamage(from, attacker, config, damageOneData); } onAttackDamage(from, config, tData); //处理击杀 if (tempKilledUnits != null) { for (int i = 0, len = tempKilledUnits.size(); i < len; ++i) { //活着 if ((target = tempKilledUnits[i]).fight.isAlive()) { //被击杀时刻 doAttackMoment(AttackMomentType.BeforeBeKill, target, target, attacker, data, null); //可被伤害击杀 if (!target.fight.getStatusLogic().cantBeKillByDamage()) { target.fight.doDead(attacker, config.killType); } //击杀时刻 doAttackMoment(AttackMomentType.AfterKill, from, attacker, target, data, null); } } } } doAttackMoment(AttackMomentType.AttackAfterHit, from, attacker, null, data, null); } }
/** 攻击伤害来自服务器 */ public void onAttackDamageFromServer(int fromInstanceID, int attackID, int attackLevel, SkillTargetData targetData, DamageOneData damage) { Unit from = _scene.getFightUnit(fromInstanceID); if (from == null) { return; } AttackConfig config = AttackConfig.get(attackID); onAttackDamage(from, config, targetData); Unit attaker = from.fight.getAttackerUnit(); Unit target = _scene.getFightUnit(damage.instanceID); if (target != null) { target.fight.onDamage(from, attaker, config, damage); } }
protected virtual void doAttackMoment(int moment, Unit from, Unit attacker, Unit target, AttackData lastData, DamageOneData damageOneData) { int[][] intArr; if ((intArr = lastData.levelConfig.momentActionsT[moment]) != null) { foreach (int[] args in intArr) { if (args[0] == moment) { if (attacker.fight.randomProb(args[1])) { doOneAttackAction(args, 2, from, attacker, target, lastData); } } } } IntObjectMap <int[]> momentDic = attacker.fight.getBuffLogic().getAttackProbActionDic(moment); if (momentDic != null && momentDic.size() > 0) { int[][] momentValues = momentDic.getValues(); int[] momentV; for (int j = momentValues.Length - 1; j >= 0; --j) { if ((momentV = momentValues[j]) != null) { if (momentV[2] <= 0 || lastData.config.hasGroup(momentV[2])) { if (attacker.fight.randomProb(momentV[3])) { doOneAttackAction(momentV, 4, from, attacker, target, lastData); } } } } } }
/// <summary> /// 读取字节流(完整版) /// </summary> protected override void toReadBytesFull(BytesReadStream stream) { base.toReadBytesFull(stream); stream.startReadObj(); this.fromInstanceID = stream.readInt(); BaseData targetT = stream.readDataFullNotNull(); if (targetT != null) { if (targetT is SkillTargetData) { this.target = (SkillTargetData)targetT; } else { this.target = new SkillTargetData(); if (!(targetT.GetType().IsAssignableFrom(typeof(SkillTargetData)))) { stream.throwTypeReadError(typeof(SkillTargetData), targetT.GetType()); } this.target.shadowCopy(targetT); } } else { this.target = null; } this.id = stream.readInt(); this.level = stream.readInt(); if (stream.readBoolean()) { int damageDatasLen = stream.readLen(); if (this.damageDatas != null) { this.damageDatas.clear(); this.damageDatas.ensureCapacity(damageDatasLen); } else { this.damageDatas = new SList <DamageOneData>(); } SList <DamageOneData> damageDatasT = this.damageDatas; for (int damageDatasI = damageDatasLen - 1; damageDatasI >= 0; --damageDatasI) { DamageOneData damageDatasV; if (stream.readBoolean()) { BaseData damageDatasVT = stream.readDataFullNotNull(); if (damageDatasVT != null) { if (damageDatasVT is DamageOneData) { damageDatasV = (DamageOneData)damageDatasVT; } else { damageDatasV = new DamageOneData(); if (!(damageDatasVT.GetType().IsAssignableFrom(typeof(DamageOneData)))) { stream.throwTypeReadError(typeof(DamageOneData), damageDatasVT.GetType()); } damageDatasV.shadowCopy(damageDatasVT); } } else { damageDatasV = null; } } else { damageDatasV = null; } damageDatasT.add(damageDatasV); } } else { this.damageDatas = null; } stream.endReadObj(); }
/// <summary> /// 转文本输出 /// </summary> protected override void toWriteDataString(DataWriter writer) { base.toWriteDataString(writer); writer.writeTabs(); writer.sb.Append("fromInstanceID"); writer.sb.Append(':'); writer.sb.Append(this.fromInstanceID); writer.writeEnter(); writer.writeTabs(); writer.sb.Append("target"); writer.sb.Append(':'); if (this.target != null) { this.target.writeDataString(writer); } else { writer.sb.Append("SkillTargetData=null"); } writer.writeEnter(); writer.writeTabs(); writer.sb.Append("id"); writer.sb.Append(':'); writer.sb.Append(this.id); writer.writeEnter(); writer.writeTabs(); writer.sb.Append("level"); writer.sb.Append(':'); writer.sb.Append(this.level); writer.writeEnter(); writer.writeTabs(); writer.sb.Append("damageDatas"); writer.sb.Append(':'); writer.sb.Append("List<DamageOneData>"); if (this.damageDatas != null) { SList <DamageOneData> damageDatasT = this.damageDatas; int damageDatasLen = damageDatasT.size(); writer.sb.Append('('); writer.sb.Append(damageDatasLen); writer.sb.Append(')'); writer.writeEnter(); writer.writeLeftBrace(); for (int damageDatasI = 0; damageDatasI < damageDatasLen; ++damageDatasI) { DamageOneData damageDatasV = damageDatasT.get(damageDatasI); writer.writeTabs(); writer.sb.Append(damageDatasI); writer.sb.Append(':'); if (damageDatasV != null) { damageDatasV.writeDataString(writer); } else { writer.sb.Append("DamageOneData=null"); } writer.writeEnter(); } writer.writeRightBrace(); } else { writer.sb.Append("=null"); } writer.writeEnter(); }
/// <summary> /// 是否数据一致 /// </summary> protected override bool toDataEquals(BaseData data) { DamageOneData mData = (DamageOneData)data; if (this.instanceID != mData.instanceID) { return(false); } if (this.isHit != mData.isHit) { return(false); } if (this.isCrit != mData.isCrit) { return(false); } if (mData.damages != null) { if (this.damages == null) { return(false); } if (this.damages.size() != mData.damages.size()) { return(false); } SList <DIntData> damagesT = this.damages; SList <DIntData> damagesR = mData.damages; int damagesLen = damagesT.size(); for (int damagesI = 0; damagesI < damagesLen; ++damagesI) { DIntData damagesU = damagesT.get(damagesI); DIntData damagesV = damagesR.get(damagesI); if (damagesV != null) { if (damagesU == null) { return(false); } if (!damagesU.dataEquals(damagesV)) { return(false); } } else { if (damagesU != null) { return(false); } } } } else { if (this.damages != null) { return(false); } } if (this.isKilled != mData.isKilled) { return(false); } if (this.arg != mData.arg) { return(false); } return(true); }