InstanceUnit.API.cs 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682
  1. using CommonAI.Data;
  2. using CommonAI.Zone.Formula;
  3. using CommonAI.Zone.Helper;
  4. using CommonAI.ZoneClient;
  5. using CommonAI.ZoneServer.JSGModule;
  6. using CommonLang.Property;
  7. using System;
  8. using System.Collections.Generic;
  9. using System.Diagnostics;
  10. using System.Text;
  11. namespace CommonAI.Zone.Instance
  12. {
  13. partial class InstanceUnit
  14. {
  15. //-----------------------------------------------------------------------------------------------------------
  16. #region _sync_fields_
  17. protected readonly SyncUnitInfo mSyncInfo;
  18. private UnitFieldChangedEvent mSyncFields;
  19. private int m_dummy_0, m_dummy_1, m_dummy_2, m_dummy_3, m_dummy_4, m_dummy_5, m_dummy_6;
  20. //是否触发过破碎效果
  21. private bool isTriggerBroken = false;
  22. public void SetMaxHP(int value, bool auto_update_hp = false)
  23. {
  24. if (__mCurrentHP.SetMax(value, auto_update_hp))
  25. {
  26. syncFields(UnitFieldChangedEvent.MASK_HP | UnitFieldChangedEvent.MASK_MAX_HP);
  27. }
  28. }
  29. [DescAttribute("最大血量")]
  30. public int MaxHP
  31. {
  32. get { return __mCurrentHP.Max; }
  33. set
  34. {
  35. if (__mCurrentHP.SetMax(value, true))
  36. {
  37. syncFields(UnitFieldChangedEvent.MASK_HP | UnitFieldChangedEvent.MASK_MAX_HP);
  38. }
  39. }
  40. }
  41. [DescAttribute("最大能量")]
  42. public int MaxMP
  43. {
  44. get { return __mCurrentMP.Max; }
  45. set
  46. {
  47. if (__mCurrentMP.SetMax(value, true))
  48. {
  49. syncFields(UnitFieldChangedEvent.MASK_MP | UnitFieldChangedEvent.MASK_MAX_MP);
  50. }
  51. }
  52. }
  53. [DescAttribute("当前血量")]
  54. public int CurrentHP
  55. {
  56. get { return __mCurrentHP.Value; }
  57. set
  58. {
  59. if (!IsDead() && __mCurrentHP.SetValue(value))
  60. {
  61. syncFields(UnitFieldChangedEvent.MASK_HP);
  62. }
  63. }
  64. }
  65. [DescAttribute("当前能量")]
  66. public int CurrentMP
  67. {
  68. get { return __mCurrentMP.Value; }
  69. set
  70. {
  71. if (!IsDead() && __mCurrentMP.SetValue(value))
  72. {
  73. syncFields(UnitFieldChangedEvent.MASK_MP);
  74. }
  75. }
  76. }
  77. [DescAttribute("当前血量百分比")]
  78. public float CurrentHP_Pct { get { return __mCurrentHP.Value * 100f / __mCurrentHP.Max; } }
  79. [DescAttribute("当前能量百分比")]
  80. public float CurrentMP_Pct { get { return __mCurrentMP.Value * 100f / __mCurrentMP.Max; } }
  81. [DescAttribute("当前金币")]
  82. public int CurrentMoney
  83. {
  84. get { return mMoney; }
  85. set
  86. {
  87. if (mMoney != value)
  88. {
  89. int add = value - mMoney;
  90. mMoney = value;
  91. syncFields(UnitFieldChangedEvent.MASK_MONEY);
  92. Parent.cb_unitGotMoneyCallBack(this, add);
  93. }
  94. }
  95. }
  96. [DescAttribute("当前等级")]
  97. public int Level
  98. {
  99. get { return mLevel; }
  100. set
  101. {
  102. if (mLevel != value)
  103. {
  104. mLevel = value;
  105. syncFields(UnitFieldChangedEvent.MASK_LEVEL);
  106. }
  107. }
  108. }
  109. [DescAttribute("单位职业")]
  110. public int UnitPro()
  111. {
  112. return (int)this.Virtual.GetUnitPro();
  113. }
  114. [DescAttribute("性别0-男1-女")]
  115. public int UnitSex()
  116. {
  117. return (int)this.Virtual.GetUnitSex();
  118. }
  119. [DescAttribute("玩家职业")]
  120. public int PlayerPro()
  121. {
  122. if (this.IsPlayer)
  123. {
  124. return (int)this.Virtual.GetUnitPro();
  125. }
  126. return 0;
  127. }
  128. private void DoAddHP(int hp)
  129. {
  130. if (!IsDead())
  131. {
  132. if (__mCurrentHP.Add(hp))
  133. {
  134. syncFields(UnitFieldChangedEvent.MASK_HP);
  135. // 触发破碎效果
  136. if (this.Info.HitBreakPrecent > 0 && !this.isTriggerBroken)
  137. {
  138. int precent = (int)((double)this.CurrentHP / this.MaxHP * 100);
  139. if (precent <= this.Info.HitBreakPrecent)
  140. {
  141. //Console.WriteLine("触发破碎");
  142. this.isTriggerBroken = true;
  143. UnitHitBreak hitBreak = new UnitHitBreak(this.ID);
  144. this.Parent.queueObjectEvent(this, hitBreak);
  145. }
  146. }
  147. }
  148. }
  149. }
  150. private void DoAddMP(int mp, bool force = false)
  151. {
  152. if (IsDead() || (mp < 0 && !this.Virtual.IsCanReduceMP(force)))
  153. {
  154. return;
  155. }
  156. if (__mCurrentMP.Add(mp))
  157. {
  158. syncFields(UnitFieldChangedEvent.MASK_MP);
  159. //进入破定状态
  160. if (__mCurrentMP.Value == 0 && this.CurrentActionStatus != UnitActionStatus.BreakShield)
  161. {
  162. this.changeState(new StateBreakShield(this), true);
  163. }
  164. //System.Console.WriteLine("更新定力值:" + this.Info.Name + ", " + __mCurrentMP.Value);
  165. }
  166. }
  167. public void AddSP(int st)
  168. {
  169. // if (!IsDead)
  170. // {
  171. // if (__mCurrentSP.Add(st))
  172. // {
  173. // syncFields(UnitFieldChangedEvent.MASK_SP);
  174. // }
  175. // }
  176. }
  177. public int AddHP(int hp, InstanceUnit sender, bool sendHit = true, AttackSource source = null)
  178. {
  179. int finalHP = ReduceHP(-hp, sender, sendHit);
  180. //排除怪物回血
  181. #if JSG_DMG_LOG
  182. if(this.IsPlayer)
  183. {
  184. int atkPropID = (source == null || source.Attack == null || source.Attack.Properties == null) ? 0 : source.Attack.Properties.GetAttackID();
  185. if (atkPropID != 9999901 && (finalHP < -100000000 || finalHP > 100000000) && !(this.IsMonster && hp == this.MaxHP))
  186. {
  187. string stackInfo = new StackTrace().ToString();
  188. log.Error("伤害异常: " + finalHP + ", ID" + this.Info.ID + ", " + (sender == null ? "-1" : sender.PlayerUUID)
  189. + JSGModule.GetAttackSourceDes(source) + ", " + stackInfo);
  190. }
  191. }
  192. #endif
  193. return finalHP;
  194. }
  195. public void AddHP_Pct(float percent, InstanceUnit sender)
  196. {
  197. AddHP((int)(percent / 100f * MaxHP), sender);
  198. }
  199. /// <summary>
  200. /// 直接设置移动速度
  201. /// </summary>
  202. /// <param name="speed"></param>
  203. public void SetMoveSpeed(float speed)
  204. {
  205. if (speed < 0)
  206. {
  207. speed = 0;
  208. }
  209. if (speed != __mCurrentMoveSpeedSEC)
  210. {
  211. __mCurrentMoveSpeedSEC = speed;
  212. syncFields(UnitFieldChangedEvent.MASK_SPEED);
  213. }
  214. }
  215. /// <summary>
  216. /// 直接设置攻速
  217. /// </summary>
  218. /// <param name="speed"></param>
  219. public void SetAttackSpeed(int speed)
  220. {
  221. if (speed <= 0)
  222. {
  223. speed = GlobalData.DEFAULT_ATTACK_SPEED;
  224. }
  225. if (speed != __mCurrentAttackSpeed)
  226. {
  227. __mCurrentAttackSpeed = speed;
  228. }
  229. }
  230. public int GetAttackSpeed()
  231. {
  232. return this.__mCurrentAttackSpeed;
  233. }
  234. /// <summary>
  235. /// 直接设置当前技能cd减少
  236. /// </summary>
  237. /// <param name="value"></param>
  238. public void SetSkillCdReduce(float value)
  239. {
  240. if (value < 0)
  241. {
  242. value = 0;
  243. }
  244. if (value != __mCurrentSkillCdReduce)
  245. {
  246. __mCurrentSkillCdReduce = value;
  247. syncFields(UnitFieldChangedEvent.MASK_SKILL_CD_ACC);
  248. }
  249. }
  250. /// <summary>
  251. /// 直接设置受到控制效果的持续时间减少
  252. /// </summary>
  253. /// <param name="value"></param>
  254. public void SetControledTimeReduce(float value)
  255. {
  256. if (value < 0)
  257. {
  258. value = 0;
  259. }
  260. if (value != __mCurrentControledTimeReduce)
  261. {
  262. __mCurrentControledTimeReduce = value;
  263. syncFields(UnitFieldChangedEvent.MASK_CONTROLED_ACC);
  264. }
  265. }
  266. public void SetControledTimeAdd(float value)
  267. {
  268. if (value < 0)
  269. {
  270. value = 0;
  271. }
  272. if (value != __mControledTimeAdd)
  273. {
  274. __mControledTimeAdd = value;
  275. syncFields(UnitFieldChangedEvent.MASK_CONTROLED_ACC);
  276. }
  277. }
  278. /// <summary>
  279. /// 设置所有技能动作速度加成
  280. /// </summary>
  281. /// <param name="rate"></param>
  282. public void SetSkillActionSpeedRate(float rate)
  283. {
  284. if (rate < 0)
  285. {
  286. rate = 0;
  287. }
  288. if (rate != __mSkillActionSpeedRate)
  289. {
  290. __mSkillActionSpeedRate = rate;
  291. }
  292. }
  293. /** 是否满血 */
  294. public bool IsFullHP()
  295. {
  296. return this.CurrentHP == this.MaxHP;
  297. }
  298. /// <summary>
  299. /// 设置当前快速施法速度(基准0)(1是1倍速)
  300. /// </summary>
  301. /// <param name="fcr"></param>
  302. public void SetFastCastRate(float fcr)
  303. {
  304. if (mFastCastRate != fcr)
  305. {
  306. mFastCastRate = fcr;
  307. syncFields(UnitFieldChangedEvent.MASK_FCR);
  308. }
  309. }
  310. public int Dummy_0
  311. {
  312. get { return m_dummy_0; }
  313. set
  314. {
  315. if (m_dummy_0 != value)
  316. {
  317. m_dummy_0 = value;
  318. syncFields(UnitFieldChangedEvent.MASK_DUMMY_0);
  319. }
  320. }
  321. }
  322. public int Dummy_1
  323. {
  324. get { return m_dummy_1; }
  325. set
  326. {
  327. if (m_dummy_1 != value)
  328. {
  329. m_dummy_1 = value;
  330. syncFields(UnitFieldChangedEvent.MASK_DUMMY_1);
  331. }
  332. }
  333. }
  334. public int Dummy_2
  335. {
  336. get { return m_dummy_2; }
  337. set
  338. {
  339. if (m_dummy_2 != value)
  340. {
  341. m_dummy_2 = value;
  342. syncFields(UnitFieldChangedEvent.MASK_DUMMY_2);
  343. }
  344. }
  345. }
  346. public int Dummy_3
  347. {
  348. get { return m_dummy_3; }
  349. set
  350. {
  351. if (m_dummy_3 != value)
  352. {
  353. m_dummy_3 = value;
  354. syncFields(UnitFieldChangedEvent.MASK_DUMMY_3);
  355. }
  356. }
  357. }
  358. public int Dummy_4
  359. {
  360. get { return m_dummy_4; }
  361. set
  362. {
  363. if (m_dummy_4 != value)
  364. {
  365. m_dummy_4 = value;
  366. syncFields(UnitFieldChangedEvent.MASK_DUMMY_4);
  367. }
  368. }
  369. }
  370. public int Dummy_5
  371. {
  372. get { return m_dummy_5; }
  373. set
  374. {
  375. if (m_dummy_5 != value)
  376. {
  377. m_dummy_5 = value;
  378. syncFields(UnitFieldChangedEvent.MASK_DUMMY_5);
  379. }
  380. }
  381. }
  382. public void syncFields(uint mask)
  383. {
  384. if (mSyncFields == null)
  385. {
  386. mSyncFields = new UnitFieldChangedEvent();
  387. }
  388. mSyncFields.mask |= mask;
  389. }
  390. private void updateSyncFields()
  391. {
  392. if (mSyncFields != null)
  393. {
  394. GenSyncFields(mSyncFields);
  395. queueEvent(mSyncFields);
  396. mSyncFields = null;
  397. }
  398. }
  399. public void GenSyncFields(UnitFieldChangedEvent sync)
  400. {
  401. sync.currentHP = __mCurrentHP.Value;
  402. sync.currentMP = __mCurrentMP.Value;
  403. sync.maxHP = __mCurrentHP.Max;
  404. sync.maxMP = __mCurrentMP.Max;
  405. sync.maxSP = 0;
  406. sync.currentSP = 0;
  407. sync.currentSpeed = __mCurrentMoveSpeedSEC;
  408. sync.currentFCR = mFastCastRate;
  409. sync.currentMoney = mMoney;
  410. sync.level = mLevel;
  411. sync.dummy_0 = m_dummy_0;
  412. sync.dummy_1 = m_dummy_1;
  413. sync.dummy_2 = m_dummy_2;
  414. sync.dummy_3 = m_dummy_3;
  415. sync.dummy_4 = m_dummy_4;
  416. sync.dummy_5 = m_dummy_5;
  417. }
  418. public override SyncObjectInfo GenSyncInfo(bool net)
  419. {
  420. return GenSyncUnitInfo(net);
  421. }
  422. public SyncUnitInfo GenSyncUnitInfo(bool net = false)
  423. {
  424. mSyncInfo.status = (byte)CurrentActionStatus;
  425. mSyncInfo.sub_status = (byte)CurrentActionSubstate;
  426. mSyncInfo.sub_flag = mSubStateExt;
  427. mSyncInfo.Force = mForce;
  428. mSyncInfo.Level = mLevel;
  429. mSyncInfo.x = X;
  430. mSyncInfo.y = Y;
  431. mSyncInfo.direction = this.Direction;
  432. if (net)
  433. {
  434. mSyncInfo.CurrentBuffStatus = this.GetCurrentBuffStatus();
  435. mSyncInfo.fields.mask = UnitFieldChangedEvent.MASK_ALL;
  436. GenSyncFields(mSyncInfo.fields);
  437. }
  438. return mSyncInfo;
  439. }
  440. /// <summary>
  441. /// 设置单位显示信息
  442. /// </summary>
  443. /// <param name="visible_data"></param>
  444. public void SetVisibleInfo(IUnitVisibleData visible_data)
  445. {
  446. mSyncInfo.VisibleInfo = visible_data;
  447. }
  448. public void SetDiaplayerName(String name)
  449. {
  450. if (mSyncInfo.VisibleInfo != null)
  451. {
  452. mSyncInfo.VisibleInfo.setVisibleName(name);
  453. }
  454. this.mSyncInfo.Name = name;
  455. }
  456. public override String GetTemplateData()
  457. {
  458. return "Unit:" + this.mInfo.ID;
  459. }
  460. //设置自动拾取范围
  461. public virtual void SetAutoPickRange(int value) { }
  462. #endregion
  463. //-----------------------------------------------------------------------------------------------------------
  464. #region script_support
  465. public string get_name()
  466. {
  467. return mName;
  468. }
  469. public int get_force()
  470. {
  471. return mForce;
  472. }
  473. public int get_level()
  474. {
  475. return mLevel;
  476. }
  477. public bool is_dead()
  478. {
  479. return IsDead();
  480. }
  481. public bool is_enable()
  482. {
  483. return Enable;
  484. }
  485. public bool is_paused()
  486. {
  487. return IsPaused;
  488. }
  489. public bool is_none_block()
  490. {
  491. return IsNoneBlock;
  492. }
  493. public bool is_none_skill()
  494. {
  495. return IsNoneSkill;
  496. }
  497. public uint get_id()
  498. {
  499. return ID;
  500. }
  501. public UnitInfo get_info()
  502. {
  503. return mInfo;
  504. }
  505. public Random get_random()
  506. {
  507. return RandomN;
  508. }
  509. public float get_x()
  510. {
  511. return X;
  512. }
  513. public float get_y()
  514. {
  515. return Y;
  516. }
  517. public float get_direction()
  518. {
  519. return Direction;
  520. }
  521. public float set_direction(float d)
  522. {
  523. this.faceTo(d);
  524. return d;
  525. }
  526. public string get_unit_tag()
  527. {
  528. return UnitTag;
  529. }
  530. public string set_unit_tag(string str)
  531. {
  532. UnitTag = str;
  533. return str;
  534. }
  535. public int get_max_hp()
  536. {
  537. return MaxHP;
  538. }
  539. public int set_max_hp(int max)
  540. {
  541. MaxHP = max;
  542. return max;
  543. }
  544. public int get_max_mp()
  545. {
  546. return MaxMP;
  547. }
  548. //public int set_max_mp(int mp)
  549. //{
  550. // MaxMP = mp;
  551. // return mp;
  552. //}
  553. public int get_current_hp()
  554. {
  555. return __mCurrentHP.Value;
  556. }
  557. public int set_current_hp(int hp)
  558. {
  559. CurrentHP = hp;
  560. return hp;
  561. }
  562. public int get_current_mp()
  563. {
  564. return __mCurrentMP.Value;
  565. }
  566. //public int set_current_mp(int mp)
  567. //{
  568. // CurrentMP = mp;
  569. // return mp;
  570. //}
  571. public int set_level(int lv)
  572. {
  573. Level = lv;
  574. return lv;
  575. }
  576. //public void add_mp(int mp)
  577. //{
  578. // AddMP(mp);
  579. //}
  580. public void add_hp(int hp)
  581. {
  582. AddHP(hp, this);
  583. }
  584. public void add_sp(int sp)
  585. {
  586. AddSP(sp);
  587. }
  588. public void add_buff(int buffID)
  589. {
  590. AddBuff(buffID);
  591. }
  592. public void clear_buff()
  593. {
  594. clearBuffs();
  595. }
  596. public void use_item(int itemTemplateID)
  597. {
  598. ItemTemplate item = Templates.getItem(itemTemplateID);
  599. if (item != null)
  600. {
  601. UseItem(item);
  602. }
  603. }
  604. #endregion
  605. }
  606. }