public static int getDamage(float inputAtk, float def, float inputMagicAtk = 0.0f, float magicDef = 0.0f, float damagePer = 1.0f, float minimumDamagePer = 1.0f, float damagePer2 = 1.0f, float inputTempDiscountDamageValue = 1.0f) // damagePer2는 공격동작중 한번에 여러번 타격판정이 들어가는 경우에 사용한다. { //#if UNITY_EDITOR // Log.log("atk:",atk,"def:",def,"magicAtk:",magicAtk,"magicDef:",magicDef,"damagePer:",damagePer,"minimumDamagePer:",minimumDamagePer,"damagePer2:",damagePer2); //#endif IFloat atk = inputAtk; IFloat magicAtk = inputMagicAtk; IFloat tempDiscountDamageValue = inputTempDiscountDamageValue; damagePer = (Mathf.Round(damagePer * 100.0f)) / 100.0f; //데미지 = 물리공격력 * (1/SQRT(물리방어력)) * A + 마법공격력 * (1/SQRT(마법방어력)) * B //* SQRT : 제곱근, A : 데미지보정계수 (5), B : 데미지보정계수 (5) if (Xfloat.lessEqualThan(def, 0)) { def = 1; } if (Xfloat.lessEqualThan(magicDef, 0)) { magicDef = 1; } atk = (atk * (1.0f / Mathf.Sqrt(def))) * 5.0f + (magicAtk * (1.0f / Mathf.Sqrt(magicDef)) * 5.0f); // damagePer // 기본 데미지의 몇 %. // minimumDamagePer // 데미지의 최소 비율. if (Xfloat.lessThan(damagePer, 1.0f)) { atk = atk * minimumDamagePer + ((atk - (atk * minimumDamagePer)) * damagePer); } // 얘는 한공격 동작에 데미지가 여러번 들어가는 경우 그 횟수로 나누어줘서 밸런스를 맞춰주기 위함이다. atk *= damagePer2; // 이런 코드를 만들고 싶지 않았으나... 공격타입 5번과 15번은 단계마다 특정비율로 데미지를 깍는다. // 거치는 곳이 많기 때문에 어쩔 수 없이 예외를 만들어 데미지를 깍아준다. atk *= tempDiscountDamageValue; int gValue = Mathf.RoundToInt(atk * 100.0f); if (GameManager.inGameRandom.Range(0, 100) < gValue % 100) { return(gValue / 100 + 1); } else { return(gValue / 100); } }
// pvp 캐릭터 후진. public bool moveBackward() { _v = cTransformPosition; _v2 = _v; _v2.x += (isPlayerSide)?-1000.0f:1000.0f; _v2.z = 0.0f; _q = Util.getLookRotationQuaternion(_v2 - cTransformPosition); _v2 = _q.eulerAngles; _v2.y += 180.0f; _q.eulerAngles = _v2; if (Xfloat.greaterThan(Quaternion.Angle(_q, tf.rotation), 5)) { tf.rotation = Util.getFixedQuaternionSlerp(tf.rotation, _q, CharacterAction.rotationSpeed * GameManager.globalDeltaTime); } _v -= (IVector3)(tf.forward) * stat.speed * GameManager.globalDeltaTime; _v.y = 0; if (isPlayerSide) { if (Xfloat.greaterThan(_v.x, StageManager.mapStartPosX.Get()) && cm.checkPlayerMonsterBlockLine(this)) { setPosition(_v); } else { state = NORMAL; return(false); } } else { if (Xfloat.lessThan(_v.x, StageManager.mapEndPosX.Get()) && cm.checkMonsterBlockLine(this)) { setPosition(_v); } else { state = NORMAL; return(false); } } //if(_state != WALK) state = BWALK; return(true); }
public bool canMonsterHeroTargetingType1(Monster attacker, int targetIndex = -1) { // 타겟팅 1,2번 _target = null; //<1 : 히어로 전방 A거리(cm), B지름> // - 바닥에 뭔가가 떨어지거나 생성되는 스킬에 적용 // - 타게팅(차징)중 히어로 전방 A거리에 B지름 형태의 (원형 마법진모양의) 타게팅 데칼을 표시함 // - 설정된 지름의 크기에 따라서 원형태의 마법진 이미지의 크기를 변경해서 표시함 // - B지름이 400을 넘어가면 타원으로 (일단;) 늘려서 표시 _fixedLineLeft = -(float)targetAttr[0] - ((float)targetAttr[1]) * 0.5f; _fixedLineRight = -(float)targetAttr[0] + ((float)targetAttr[1]) * 0.5f; if (targetType == Skill.TargetType.ENEMY) { // 플레이어 몬스터에서 고른다. (적의 적군) _target = GameManager.me.characterManager.getCloseEnemyTargetByIndexForHeroMonster(attacker.isPlayerSide, targetIndex); } else { // 적 몬스터에서 고른다. (적의 아군) _target = GameManager.me.characterManager.getCloseTeamTarget(attacker.isPlayerSide, attacker); } if (_target == null) { return(false); } _v = attacker.cTransformPosition; if (Xfloat.greaterThan(_target.cTransformPosition.x, GameManager.me.characterManager.targetZonePlayerLine + _fixedLineLeft) && Xfloat.lessThan(_target.cTransformPosition.x, StageManager.mapEndPosX.Get() + _fixedLineRight)) { attacker.setSkillTarget(_target); attacker.skillTargetChecker = ctFixed; attacker.skillMove = ctMoveFixed; _target = null; return(true); } _target = null; return(false); }
public void startChangePlayer(bool isPlayerSide) { if (DebugManager.instance.useTagMatchMode == false) { return; } CharacterManager cm = GameManager.me.characterManager; List <Monster> myMonList; List <Monster> enemyMonList; if (isPlayerSide) { if (waitingForPlayerChange) { return; } waitingForPlayerChange = true; GameManager.me.player.setChange(false); myMonList = cm.playerMonster; enemyMonList = cm.monsters; GameManager.me.uiManager.uiPlay.playerChangeControlPanelEffect.gameObject.SetActive(true); StartCoroutine(hidePlayerChangeControllPanelEffect()); // playerChangeDelay.Set(0.5f); } else { if (waitingForPVPChange) { return; } waitingForPVPChange = true; GameManager.me.pvpPlayer.setChange(false); myMonList = cm.monsters; enemyMonList = cm.playerMonster; // pvpChangeDelay.Set(0.5f); } foreach (Monster mon in myMonList) { if (mon.isPlayer == false && mon.isEnabled) { mon.dead(); } } // 교체시 아군 주인공의 위치 기준으로만 넉백이 되는 문제 수정. //if(VersionData.checkCodeVersion(10)) { if (isPlayerSide) { foreach (Monster mon in enemyMonList) { if (mon.isEnabled) { if (Xfloat.lessThan(VectorUtil.Distance(GameManager.me.player.cTransformPosition, mon.cTransformPosition), GameManager.info.setupData.tagKnuckBackValue[0].Get())) { mon.characterEffect.addKnockBack(GameManager.info.setupData.tagKnuckBackValue[1]); if (mon.isPlayer == false) { mon.characterEffect.addStun(GameManager.info.setupData.tagStunTime); } } } } } else { foreach (Monster mon in enemyMonList) { if (mon.isEnabled) { if (Xfloat.lessThan(VectorUtil.Distance(GameManager.me.pvpPlayer.cTransformPosition, mon.cTransformPosition), GameManager.info.setupData.tagKnuckBackValue[0].Get())) { mon.characterEffect.addKnockBack(GameManager.info.setupData.tagKnuckBackValue[1]); if (mon.isPlayer == false) { mon.characterEffect.addStun(GameManager.info.setupData.tagStunTime); } } } } } } /* * else * { * foreach(Monster mon in enemyMonList) * { * if( mon.isEnabled) * { * if( Xfloat.lessThan( VectorUtil.Distance(GameManager.me.player.cTransformPosition, mon.cTransformPosition) , GameManager.info.setupData.tagKnuckBackValue[0].Get() )) * { * mon.characterEffect.addKnockBack(GameManager.info.setupData.tagKnuckBackValue[1]); * } * } * } * } */ }