using Turbo.Plugins.Default; using System; using System.Linq; using System.Collections.Generic; using System.Text; using SharpDX.DirectInput; using System.Threading; using System.Media; namespace Turbo.Plugins.flower { public class WitchDoctorTeam : BasePlugin, IInGameWorldPainter, IKeyEventHandler, IInGameTopPainter { private bool isRightBuild = false; private string buildError = string.Empty; public TopLabelDecorator nameText { get; set; } public TopLabelDecorator stateText { get; set; } public IKeyEvent ToggleKeyEvent { get; set; } public IKeyEvent WayKeyEvent { get; set; } public IKeyEvent RhythmKeyEvent { get; set; } public IKeyEvent KillKeyEvent { get; set; } public IKeyEvent KeepOnPointKeyEvent { get; set; } public IKeyEvent TestingKeyEvent { get; set; } public IKeyEvent OculusRangeKeyEvent { get; set; } public bool TurnedOn { get; set; } public int HDWay { get; set; }//1:傻瓜方式,2:一轮元素两波 public bool RhythmSpeak { get; set; }//节奏语音提醒 public bool KillSpeak { get; set; }//击杀语音提醒 private bool isTesting = false;//测试模式(城镇里也可以测试) private bool keepOnPoint = false;//16秒方式是否一直炸一个点 private bool isHauntSkill = false;//是否允许放蚀魂 private bool isLocustSwarmPlus = false;//是否补虫群 private int oculusRange = 40;//踩神目的码数,默认40码 private bool isOculusing = false;//是否正在踩神目 private int hdNum = 0;//地上有几个魂淡 private bool isNewRound = true;//是否新的一轮,用于8+8的起手轮 private bool isRound_8 = false;//8+8要求在火1.0开启 private bool isRound_16 = false;//16要求在物理1.3开启 private double leftSecond = 0;//元素戒时间 private int iSpeak = 0; private int killEliteNum = -1; private int killKeep = 0; private int isKeep = 0; private int isMark = 0;//标记时间点 private int markElite = 0;//标记时间点的精英组数 private int markMonsters = 0;//标记时间点的怪物数量 private double markPercent = 0;//标记时间点的大秘进度 public WitchDoctorTeam() { Enabled = true; } public override void Load(IController hud) { base.Load(hud); HDWay = 1; RhythmSpeak = true; KillSpeak = true; ToggleKeyEvent = Hud.Input.CreateKeyEvent(true, Key.F2, false, false, false); WayKeyEvent = Hud.Input.CreateKeyEvent(true, Key.NumberPad0, true, false, false); KeepOnPointKeyEvent = Hud.Input.CreateKeyEvent(true, Key.NumberPad1, true, false, false); TestingKeyEvent = Hud.Input.CreateKeyEvent(true, Key.Multiply, false, true, false);//alt + 小键盘的* RhythmKeyEvent = Hud.Input.CreateKeyEvent(true, Key.NumberPad8, true, false, false); KillKeyEvent = Hud.Input.CreateKeyEvent(true, Key.NumberPad9, true, false, false); OculusRangeKeyEvent = hud.Input.CreateKeyEvent(true, Key.Add, true, false, false); nameText = new TopLabelDecorator(Hud) { TextFont = Hud.Render.CreateFont("tahoma", 8, 255, 150, 150, 150, true, false, true), }; stateText = new TopLabelDecorator(Hud) { TextFont = Hud.Render.CreateFont("tahoma", 8, 255, 255, 69, 0, false, false, true), }; } public void PaintWorld(WorldLayer layer) { IPlayer player = Hud.Game.Me; IsHunDan(player); if (TurnedOn && isRightBuild && string.IsNullOrEmpty(buildError)) { if (isTesting || Hud.Game.SpecialArea == SpecialArea.GreaterRift) { if (Hud.Game.SpecialArea == SpecialArea.GreaterRift) isTesting = false;//大秘中关闭测试模式 PlayHunDan(player); } } } public void PaintTopInGame(ClipState clipState) { if (clipState == ClipState.BeforeClip && Hud.Game.Me.HeroClassDefinition.HeroClass == HeroClass.WitchDoctor) { var text = GetMacroName(); var tip = GetMacroSetting(); nameText.TextFunc = () => text; nameText.HintFunc = () => tip; var layout = nameText.TextFont.GetTextLayout(text); var x1 = Hud.Window.Size.Width * 0.0022f; var y = Hud.Window.Size.Height * (1 - 0.035f); var x2 = layout.Metrics.Width + x1 * 2; nameText.Paint(x1, y, layout.Metrics.Width, layout.Metrics.Height, HorizontalAlign.Center); if (!TurnedOn) text = "未启用"; else { if (!isRightBuild) text = "装备或技能不符合"; else if (!string.IsNullOrEmpty(buildError)) text = buildError; else if (isTesting) text = "测试模式[alt + 小键盘的*]"; else { text = "已启用" + (Hud.Game.SpecialArea == SpecialArea.GreaterRift ? "" : "[非大秘中不生效]"); } } stateText.TextFunc = () => text; stateText.HintFunc = () => GetBuildInfo(); stateText.Paint(x2, y, stateText.TextFont.GetTextLayout(text).Metrics.Width, stateText.TextFont.GetTextLayout(text).Metrics.Height, HorizontalAlign.Left); } } public void OnKeyEvent(IKeyEvent keyEvent) { if (keyEvent.IsPressed) { if (ToggleKeyEvent.Matches(keyEvent)) { TurnedOn = !TurnedOn; if (!TurnedOn) Hud.Interaction.StopAllContinuousActions(); } else if (WayKeyEvent.Matches(keyEvent)) { if (HDWay == 1) HDWay = 2; else HDWay = 1; isRound_16 = false; isRound_8 = false; isTesting = false;//切换方式则暂停测试模式 } else if (KeepOnPointKeyEvent.Matches(keyEvent)) keepOnPoint = !keepOnPoint; else if (RhythmKeyEvent.Matches(keyEvent)) RhythmSpeak = !RhythmSpeak; else if (KillKeyEvent.Matches(keyEvent)) KillSpeak = !KillSpeak; else if (TestingKeyEvent.Matches(keyEvent)) { Hud.Interaction.StopAllContinuousActions(); isTesting = !isTesting; } else if (OculusRangeKeyEvent.Matches(keyEvent)) { oculusRange += 10; if (oculusRange > 50) oculusRange = 0; } } } #region tool public string GetMacroName() { if (HDWay == 1) { return "魂淡组队16秒傻瓜宏"; } else { return "魂淡组队8+8节奏宏"; } } private string GetKeepOnePoint() { if (HDWay == 1) { return "16秒单点埋雷:" + (keepOnPoint ? "是" : "否"); } else { return string.Empty; } } public string GetMacroSetting() { return $@"Flower宏当前设置:   宏名称:{GetMacroName()}   {GetKeepOnePoint()}   神目范围:{oculusRange}码(多少范围内自动去踩,0码则不踩)   节奏提醒:{(RhythmSpeak ? "是" : "否")}   击杀提醒:{(KillSpeak ? "是" : "否")}   【鼠标移到右边的红字可看详细说明】 "; } public string GetBuildInfo() { return @"Flower宏(魂淡组队)使用说明: 【广告】:   非赛季的“非联邦”战队征集队友,有意请来YY:2488 5542;   另请关注斗鱼“TNT”的直播,斗鱼房间号:597372;   关于宏的使用和队伍配合欢迎到YY房间或斗鱼房间咨询 技能要求及推荐键位:   [1] 亡者之握:死即是生 或 巫毒狂舞:舞尸化犬   [2] 牺 牲 :激怒兽群   [3] 灵魂行走:撞魂   [4] 灵魂弹幕:魅魂飞弹   [左]灵魂收割:困魂压迫   [右]蚀 魂 :双生怨魂 或 瘟疫虫群:剧毒虫群   (注:蚀魂 不允许放在左键,其它键位随意调整) 装备要求:   必须有(或萃取):剃头师、观死、全能戒指、空虚戒指   务必让范围伤为0,巅峰里的范围伤不要点 操作指南:   进入大秘后按下F2开启,开启后左下角有是否启用提示   启动宏后,灵魂收割会自动保持   灵行只用于跑神目(血量低于30%自动激活保命),赶路阶段请自行使用保持减伤   强制移动时可打断宏,站定后会根据情况自行进入16秒循环序列,   (周边有5只怪被上了蚀魂时开始进入循环,不足5只怪需要全部有蚀魂) 调整热键:   16秒和8+8切换:Ctrl + (小键盘的0)   16秒埋雷点干预:Ctrl + (小键盘的1)   踩神目的范围:Ctrl + (小键盘的+)[每次10码,最大50码,默认40码]   节奏语音提醒:Ctrl + (小键盘的8)   击杀语音提醒:Ctrl + (小键盘的9) 版本差异:   16秒傻瓜宏:爆狗-→连炸(物理2-毒2)-→出圈则停炸-→10秒自爆(冰3时丢亡者)   8+8 节奏宏:3雷(火1)-→6秒-→爆狗-→亡者-→3雷(毒1)-→神目-→亡者   请队伍根据情况选用版本,两个版本都是只能爆3狗 当前版本:20.04.08.0 作者:Flower "; } private void IsHunDan(IPlayer player) { //魂谈套路:剃头师、观死、全能、空虚是必须的; isRightBuild = player.HeroClassDefinition.HeroClass == HeroClass.WitchDoctor && BaseTool.FindEquipmentOnPlayer(Hud, player, 3525859087) //剃头师 && BaseTool.FindEquipmentOnPlayer(Hud, player, 1003477242) //观死 && BaseTool.FindEquipmentOnPlayer(Hud, player, 417069418) //全能 && BaseTool.FindEquipmentOnPlayer(Hud, player, 1481522298) //空虚 && player.Powers.UsedWitchDoctorPowers.SpiritBarrage != null && player.Powers.UsedWitchDoctorPowers.SoulHarvest != null && player.Powers.UsedWitchDoctorPowers.SpiritWalk != null && player.Powers.UsedWitchDoctorPowers.Sacrifice != null && (player.Powers.UsedWitchDoctorPowers.Haunt != null || player.Powers.UsedWitchDoctorPowers.LocustSwarm != null) //蚀魂或者虫群 //&& (player.Powers.UsedWitchDoctorPowers.GraspOfTheDead != null//留着空余的技能,看自己喜欢来放 //|| player.Powers.UsedWitchDoctorPowers.BigBadVoodoo != null)//亡者或者大巫毒 //&& player.Powers.UsedWitchDoctorPowers.LocustSwarm != null //&& BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_SpiritBarrage.Sno)//魂淡 108506 //&& BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_SoulHarvest.Sno)//收割 67616 //&& BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_SpiritWalk.Sno)//灵行 106237 //&& BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_GraspOfTheDead.Sno)//亡者 69182 //&& BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_Sacrifice.Sno)//牺牲 102572 //&& (BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_Haunt.Sno)//蚀魂 83602 //|| BaseTool.FindThisSkill(Hud, player, Hud.Sno.SnoPowers.WitchDoctor_LocustSwarm.Sno))//虫群 69867 ; if (isRightBuild && player.Powers.UsedWitchDoctorPowers.Haunt != null && player.Powers.UsedWitchDoctorPowers.Haunt.Key == ActionKey.LeftSkill) buildError = "不允许蚀魂在左键"; else if (Hud.Game.Me.Offense.BonusToCold <= 0) buildError = "冰元素加成不能为0"; else if (!string.IsNullOrEmpty(buildError)) buildError = string.Empty; } private IActor GetHunDan(int range) { foreach (var actor in Hud.Game.Actors) { if (actor.NormalizedXyDistanceToMe < range && actor.SnoActor.Sno == ActorSnoEnum._wd_spiritbarragerune_aoe_ghostmodel) { return actor; } } return null; } #endregion #region 技能释放 //保持收割 private void KeepSoulHarvest(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.SoulHarvest; if (skill != null && !skill.IsOnCooldown) { int num = BaseTool.CountMonstersByRange(Hud, 18);//18码内怪物数量 if (skill.BuffIsActive && num > 0)//保持阶段只要有怪就释放 { BaseTool.KeyPressAndRelease(Hud, skill.Key); } else if (num > 5)//没有保持的时候5个怪以上释放 { BaseTool.KeyPressAndRelease(Hud, skill.Key); } } } //用灵行保命 private void DoSpiritWalk(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.SpiritWalk; if (skill == null) return; //30以下的血量则使用灵行保命 if (player.Defense.HealthPct < 30 && !skill.IsOnCooldown) { BaseTool.KeyPressAndRelease(Hud, skill.Key); } } //丢蚀魂 private void DoHaunt(IPlayer player, int numNotHuated) { var skill = player.Powers.UsedWitchDoctorPowers.Haunt; if (skill == null || player.Stats.ResourcePctMana < 30) return; if (isHauntSkill) { //BaseTool.DebugInfo("丢蚀魂", 5); if (numNotHuated > 0 && !Hud.Interaction.IsContinuousActionStarted(skill.Key)) BaseTool.KeyHold(Hud, skill.Key); if (numNotHuated == 0 && Hud.Interaction.IsContinuousActionStarted(skill.Key)) BaseTool.KeyUnHold(Hud, skill.Key); } else if (Hud.Interaction.IsContinuousActionStarted(skill.Key)) { BaseTool.KeyUnHold(Hud, skill.Key); } } //丢虫群 private void DoLocustSwarm(IPlayer player,int numMonster, int numAffected) { var skill = player.Powers.UsedWitchDoctorPowers.LocustSwarm; if (skill == null || player.Stats.ResourcePctMana < 30) return; //物理1.0-1.1、毒3.5-3.6、火0-0.1(一共放三个) if ((leftSecond <= 7 && leftSecond >= 6.9) || (hdNum > 0 && leftSecond <= 0.5 && leftSecond >= 0.4) || (hdNum > 0 && leftSecond <= 12 && leftSecond >= 11.9)) { isHauntSkill = false;//丢虫群的期间不允许丢蚀魂 BaseTool.KeyPressAndRelease(Hud, skill.Key); } else if (isHauntSkill == false) { isHauntSkill = true; } //如果物理和毒的虫群没有按出来,这里补按一下 if ((leftSecond <= 6 && leftSecond >= 5) || (hdNum > 0 && leftSecond <= 15 && leftSecond >= 14)) { if ((numMonster >= 5 && numAffected < 5) || (numMonster < 5 && numMonster != numAffected)) { if (!isLocustSwarmPlus) { BaseTool.KeyPressAndRelease(Hud, skill.Key); isLocustSwarmPlus = true; } } } else { isLocustSwarmPlus = false; } } //放亡者 private void DoGraspOfTheDead(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.GraspOfTheDead; if (skill == null || skill.IsOnCooldown || hdNum == 0) return;//技能CD中或者没有魂淡圈直接返回 if (HDWay == 1) { //火1.0-2.5丢亡者,方便爆炸后产狗 if (leftSecond < 11 && leftSecond > 9.5) { //采用了单点模式的则丢在魂淡上 if (keepOnPoint) { var actorHundan = GetHunDan(40);//获取一个魂淡 if (actorHundan != null) Hud.Interaction.MouseMove(actorHundan.ScreenCoordinate.X, actorHundan.ScreenCoordinate.Y);//鼠标移到魂淡圈的中心点上,然后释放 } BaseTool.KeyPressAndRelease(Hud, skill.Key); } } else { //毒0.0或者火0.0丢亡者(在地上有魂淡的情况下) if ((leftSecond < 4 && leftSecond > 3) || (leftSecond < 12 && leftSecond > 11)) { //这里鼠标不自动移动 BaseTool.KeyPressAndRelease(Hud, skill.Key); } } } //放巫毒 private void DoBigBadVoodo(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.BigBadVoodoo; if (skill == null || skill.IsOnCooldown) return;//技能CD中直接返回 //物理0.0到物理1.0丢巫毒 if (leftSecond < 8 && leftSecond > 7) { BaseTool.KeyPressAndRelease(Hud, skill.Key); } } //爆狗 private void DoSacrifice(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.Sacrifice; if (skill == null) { if (leftSecond <= 6.2) { isRound_16 = true;//没带爆狗,到了元素不能影响丢魂淡 } return; } if (HDWay == 1) { //物理1.5到物理3.5共2秒爆狗(每爆一只狗都是单独的5秒,重叠时间内才增加层数) if (leftSecond <= 6.5 && leftSecond > 4.5) { isHauntSkill = false;//爆狗期间不允许丢蚀魂 //有狗则爆,没有则下一步 int num = BaseTool.CountZombieDog(Hud); if (num > 0) BaseTool.KeyPressAndRelease(Hud, skill.Key); else isRound_16 = true; } } else { //物理3.0到毒1.0共2秒爆狗(每爆一只狗都是单独的5秒,重叠时间内才增加层数) if (isRound_8 && leftSecond < 5 && leftSecond > 3) { isHauntSkill = false; //有狗则爆,没有则下一步 int num = BaseTool.CountZombieDog(Hud); if (num > 0) BaseTool.KeyPressAndRelease(Hud, skill.Key); else isHauntSkill = true;//没有狗了就上蚀魂 } } } //丢魂淡 private void DoSpiritBarrage(IPlayer player) { var skill = player.Powers.UsedWitchDoctorPowers.SpiritBarrage; if (skill == null || player.Stats.ResourcePctMana < 15) return; if (HDWay == 1) { //TODO:爆了狗,但是没有爆完或是被打断了该继续魂淡么(isRound_16?) if (isRound_16 && leftSecond < 6 && leftSecond > 1.5) { isHauntSkill = false;//丢魂淡的期间不允许丢蚀魂 if (BaseTool.GetOculus(Hud).Count() <= 0) { //地上有魂淡且是单点模式,则鼠标自动移到上一个魂淡的位置 if (hdNum > 0 && keepOnPoint) { //TODO:会抢鼠标,改进方便:地上的魂淡圈没有新增之前只移动一次 var actorHundan = GetHunDan(40);//获取一个魂淡 if (actorHundan != null) Hud.Interaction.MouseMove(actorHundan.ScreenCoordinate.X, actorHundan.ScreenCoordinate.Y); } BaseTool.KeyPressAndRelease(Hud, skill.Key);//没有神目一直丢 } else { if (hdNum < 3) { //地上有魂淡且是单点模式,则鼠标自动移到上一个魂淡的位置 if (hdNum > 0 && keepOnPoint) { var actorHundan = GetHunDan(40);//获取一个魂淡 if (actorHundan != null) Hud.Interaction.MouseMove(actorHundan.ScreenCoordinate.X, actorHundan.ScreenCoordinate.Y); } BaseTool.KeyPressAndRelease(Hud, skill.Key);//有神目不足3个魂淡,则一直丢到3个为止 } else { isHauntSkill = true;//丢完魂淡了可以提前丢蚀魂 } } } } else { //火1.0到火2.5埋3个雷来出神目,一般都是1秒就完成了 if (leftSecond < 11 && leftSecond > 9.5) { isHauntSkill = false; int numNew = BaseTool.CountHunDanByTime(Hud, 7, true);//剩余时间>7秒的魂淡个数 //新的一轮丢两个,一个点循环第二轮丢3个 if ((isNewRound && numNew < 2) || (!isNewRound && numNew < 3)) { isRound_8 = true; BaseTool.KeyPressAndRelease(Hud, skill.Key); } else { isHauntSkill = true; if (isNewRound) isNewRound = false; } } //毒1.0到毒2.5埋3个神目雷 if (isRound_8 && leftSecond < 3 && leftSecond > 1.5) { isHauntSkill = false; //剩余时间>7秒的魂淡个数 int numNew = BaseTool.CountHunDanByTime(Hud, 7, true); if (numNew < 3) { BaseTool.KeyPressAndRelease(Hud, skill.Key); } else { isHauntSkill = true; } } } } //踩神目 private void GoToOculus(IPlayer player) { //有灵行的情况下才去踩神目 var skill = player.Powers.UsedWitchDoctorPowers.SpiritWalk; if (skill == null || oculusRange == 0 || hdNum == 0) return; var oculusActor = BaseTool.GetNearestOculus(Hud, oculusRange);//指定码数内的神目 if (oculusActor != null)//有神目(402461) { //8+8模式出神目0.8秒后再去踩 if (HDWay != 1 && Hud.Game.CurrentGameTick - oculusActor.CreatedAtInGameTick < 48) return; if (isOculusing || player.Powers.BuffIsActive(Hud.Sno.SnoPowers.OculusRing.Sno, 2)) { if (!isOculusing) isOculusing = true; } else { //没有踩到,灵行可用,则按下灵行 if (!skill.IsOnCooldown) { BaseTool.KeyPressAndRelease(Hud, skill.Key); } //灵行中去踩 if (skill.BuffIsActive) { //获取踩的坐标点 var pos = BaseTool.GetLocationCrossCircle(Hud, player.FloorCoordinate, oculusActor.FloorCoordinate, 10, true, 0, 0); if (pos != null) { //BaseTool.DebugInfo("踩神目", 6); Hud.Interaction.MouseMove(pos.ToScreenCoordinate().X, pos.ToScreenCoordinate().Y); Hud.Interaction.DoAction(ActionKey.Move); } } } } if (oculusActor == null) isOculusing = false; } //走到高密度怪去 private void GoToMonoster(IPlayer player) { //没有神目且在火元素期间,2秒内尝试;也许不一定好,走的时间可以丢蚀魂 if (!isOculusing && leftSecond < 11 && leftSecond > 9) { var monster = BaseTool.GetDensityMonster(Hud, 15); if (monster != null) { //获取坐标点 var pos = BaseTool.GetLocationCrossCircle(Hud, player.FloorCoordinate, monster.FloorCoordinate, 10, true, 0, 0); if (pos != null) { Hud.Interaction.MouseMove(pos.ToScreenCoordinate().X, pos.ToScreenCoordinate().Y); Hud.Interaction.DoAction(ActionKey.Move); } } } } private int CountMonster(IPlayer player) { if (player.Powers.UsedWitchDoctorPowers.Haunt != null) return BaseTool.CountMonstersByRange(Hud, 40);//带了蚀魂返回40码内的 else return BaseTool.CountMonstersByRange(Hud, 20);//没带蚀魂返回20码内的 } private int CountMonsterAffected(IPlayer player) { if (player.Powers.UsedWitchDoctorPowers.Haunt != null) return Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 40 && (m.Haunted || m.Locust)).Count();//范围内有蚀魂或虫群的怪物 else return Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 20 && m.Locust).Count();//范围内有虫群的怪物 } #endregion #region 节凑提醒、精英击杀提醒 private void Rhythm() { if (!RhythmSpeak) return; if (HDWay == 1) { if (leftSecond < 8 && leftSecond > 7) { if (iSpeak != 1) { BaseTool.SpeechPrompt(Hud, "炸圈", 100); iSpeak = 1; } } if (hdNum >= 3 && leftSecond < 3 && leftSecond > 1) { if (iSpeak != 2) { BaseTool.SpeechPrompt(Hud, "点炮", 100); iSpeak = 2; } } if (leftSecond > 10 && iSpeak > 0) iSpeak = 0;//重置节奏提醒 } else { if (hdNum == 0 && leftSecond < 2) { if (iSpeak != 100) { BaseTool.SpeechPrompt(Hud, "巫医准备", 2000); iSpeak = 100; } } if (hdNum == 0 && leftSecond < 16 && leftSecond > 13) { int n = (int)(leftSecond - 12); if (iSpeak != 333 && n == 3) { BaseTool.SpeechPrompt(Hud, n.ToString(), 10);//3秒 iSpeak = 333; } if (iSpeak != 222 && n == 2) { BaseTool.SpeechPrompt(Hud, n.ToString(), 10);//2秒 iSpeak = 222; } if (iSpeak != 111 && n == 1) { BaseTool.SpeechPrompt(Hud, n.ToString(), 10);//1秒 iSpeak = 111; } } if (leftSecond < 13 && leftSecond > 12) { if (iSpeak != 1) { BaseTool.SpeechPrompt(Hud, "第一发", 10); iSpeak = 1; } } if (hdNum >= 3 && leftSecond < 5 && leftSecond > 4) { if (iSpeak != 2) { BaseTool.SpeechPrompt(Hud, "第二发", 10); iSpeak = 2; } } if (leftSecond < 4 && leftSecond > 2 && iSpeak > 0) iSpeak = 0;//重置节奏提醒 } } private void KillElite(IPlayer player) { if (Hud.Game.SpecialArea != SpecialArea.GreaterRift || !KillSpeak) return; //大秘剩余时间 //var secondsLeft = (Hud.Game.CurrentTimedEventEndTick - Hud.Game.CurrentTimedEventEndTickMod - (double)Hud.Game.CurrentGameTick) / 60.0d; if ((killEliteNum != 0 || isKeep != 0) && Hud.Game.RiftPercentage <= 0) { killEliteNum = 0; isKeep = 0; } var leftSecond = BaseTool.GetHighestElementLeftSecondAssingedPlayer(Hud, player);//元素剩余秒数 if (HDWay == 1) { if (leftSecond < 13 && leftSecond > 5)//冰3.0到物理3.0,共8秒 { //标记时间点:火的时候地上有3个魂淡圈,且巫医的攻速大于2.4;此时记录精英数量、40码内怪物数量、大秘进度 if (leftSecond > 8 && isMark == 0 && hdNum == 3) //if (leftSecond > 8 && isMark == 0 && hdNum > 0) { markElite = BaseTool.CountElite(Hud, 100);//标记时间点有几组精英 markMonsters = Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count();//标记时间点指定码数内有多少怪物 markPercent = Hud.Game.RiftPercentage;//标记时间点的大秘进度 isMark = 1; } if (isMark == 1 && leftSecond <= 8) { int monstersCut = markMonsters - Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count(); //跟标记时间点相比进度变化大于1或者怪物数量少了20个 if (Hud.Game.RiftPercentage - markPercent > 1 || monstersCut >= 20) { DoKillElite(); isMark = 0; } } } else { if (isMark == 1) { isMark = 0; int monstersCut = markMonsters - Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count(); } } } else { if (leftSecond < 12 && leftSecond > 4)//火0.0到物理2.0,共6秒 { //标记时间点:火的时候地上有3个魂淡圈,且巫医的攻速大于2.4;此时记录精英数量、40码内怪物数量、大秘进度 if (leftSecond > 10 && isMark == 0 && hdNum == 3) //if (leftSecond > 8 && isMark == 0 && hdNum > 0) { markElite = BaseTool.CountElite(Hud, 100);//标记时间点有几组精英 markMonsters = Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count();//标记时间点指定码数内有多少怪物 markPercent = Hud.Game.RiftPercentage;//标记时间点的大秘进度 isMark = 1; } if (isMark == 1 && leftSecond <= 5) { int monstersCut = markMonsters - Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count(); //跟标记时间点相比进度变化大于1或者怪物数量少了20个 if (Hud.Game.RiftPercentage - markPercent > 1 || monstersCut >= 20) { DoKillElite(); isMark = 0; } } } else { if (isMark == 1) { isMark = 0; int monstersCut = markMonsters - Hud.Game.AliveMonsters.Where(m => m.NormalizedXyDistanceToMe <= 60).Count(); } } } } private void DoKillElite() { var group = markElite - BaseTool.CountElite(Hud, 100); if (group > 0) { //首杀 if (killEliteNum == 0) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.FirstBloodWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.FirstBlood); else BaseTool.PlaySoundWav(soundPlayer); } if (isKeep == 0) { isKeep = 1; killKeep = 0; } killKeep += group; //连杀7个以上算超神 if (killKeep >= 7) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.GodLikeWav) : null; if (soundPlayer == null) { //string[] sArray = player.Hero.BattleTag.Split('#'); Hud.Sound.Speak(BaseTool.GodLike); } else BaseTool.PlaySoundWav(soundPlayer); } else { //1-6杀单次(一次6杀也是超神) if (group == 1) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.OneKillWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.OneKill); else BaseTool.PlaySoundWav(soundPlayer); } else if (group == 2) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.DoubleKillWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.DoubleKill); else BaseTool.PlaySoundWav(soundPlayer); } else if (group == 3) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.TripleKillWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.TripleKill); else BaseTool.PlaySoundWav(soundPlayer); } else if (group == 4) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.QuatreKillWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.QuatreKill); else BaseTool.PlaySoundWav(soundPlayer); } else if (group == 5) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.PentaKillWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.PentaKill); else BaseTool.PlaySoundWav(soundPlayer); } else if (group >= 6) { SoundPlayer soundPlayer = BaseTool.EnableKillSpeakWav ? Hud.Sound.LoadSoundPlayer(BaseTool.GodLikeWav) : null; if (soundPlayer == null) Hud.Sound.Speak(BaseTool.GodLike); else BaseTool.PlaySoundWav(soundPlayer); } } if (killEliteNum >= 0) killEliteNum += group; } else { isKeep = 0; } } #endregion private void PlayHunDan(IPlayer player) { leftSecond = BaseTool.GetHighestElementLeftSecondAssingedPlayer(Hud, player);//冰元素剩余秒数 if (HDWay == 1 && leftSecond < 12 && leftSecond > 10) isRound_16 = false;//火元素期间重置循环(16秒模式) if (HDWay == 2 && leftSecond > 13) isRound_8 = false;//冰0.0到冰3.0重置循环(8+8模式) hdNum = BaseTool.CountHunDan(Hud);//地上的圈数量,不看剩余时间 KeepSoulHarvest(player);//收割不占抬手,符合条件就释放 DoSpiritWalk(player);//保命灵行 GoToOculus(player);//跑神目 if (!BaseTool.IsMoving(Hud)) { isHauntSkill = true;//先允许丢蚀魂,符合其他技能条件则改为不允许 if (hdNum == 0 && !isNewRound) isNewRound = true; var numMonster = CountMonster(player); var numAffected = CountMonsterAffected(player); //测试模式下,手动设置怪物数量 if (isTesting) { numMonster = 50; numAffected = 10; } //没带虫群只带蚀魂的情况下 if (player.Powers.UsedWitchDoctorPowers.Haunt == null) { if (numMonster == 0) return; if (numAffected == 0) isNewRound = true; } else { if (numMonster == 0 //没怪 || (numMonster >= 5 && numAffected < 5) //超过5个怪,但没有5个以上的蚀魂 || (numMonster < 5 && numMonster != numAffected)) //低于5个怪,但没有上满蚀魂 { isNewRound = true; DoHaunt(player, numMonster - numAffected);//没进入节奏前,丢蚀魂 return; } } //BaseTool.DebugInfo($"魂淡:{hdNum},怪物:{numAffected}/{numMonster}", 0); Rhythm();//节凑提醒 KillElite(player);//击杀提醒 if (HDWay == 1) { DoBigBadVoodo(player);//放巫毒 DoLocustSwarm(player, numMonster, numAffected);//虫群 if (numAffected > 0) { DoSacrifice(player);//物理1.5到物理3.5,爆狗在丢魂淡之前 DoSpiritBarrage(player);//物理2.0到毒2.5,连续丢魂淡 } DoGraspOfTheDead(player);//地上有魂淡的时候丢亡者 DoHaunt(player, numMonster - numAffected);//符合条件就放蚀魂 } else { DoBigBadVoodo(player);//放巫毒 DoLocustSwarm(player, numMonster, numAffected);//虫群) if (numAffected > 0) { DoSpiritBarrage(player);//丢魂淡,火1.0丢2-3个,毒1.0丢3个 DoSacrifice(player);//物理3.0爆狗 } DoGraspOfTheDead(player);//毒0.0或火0.0 DoHaunt(player, numMonster - numAffected);//符合条件就放蚀魂 } } } } }