From 576b92fd82f568572bc4beb125fa0ba0191a602f Mon Sep 17 00:00:00 2001
From: asmrobot <asmrobot@hotmail.com>
Date: Wed, 13 Nov 2019 14:59:52 +0000
Subject: [PATCH] add map editor
---
src/RichCreator/StateMachines/KillMonsterStateMachine.cs | 229 ++++++++++++++++++++++++++------------------------------
1 files changed, 106 insertions(+), 123 deletions(-)
diff --git a/src/RichCreator/StateMachines/KillMonsterStateMachine.cs b/src/RichCreator/StateMachines/KillMonsterStateMachine.cs
index 7510a43..b2faf21 100644
--- a/src/RichCreator/StateMachines/KillMonsterStateMachine.cs
+++ b/src/RichCreator/StateMachines/KillMonsterStateMachine.cs
@@ -1,22 +1,19 @@
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Text;
-using System.Threading;
-using System.Threading.Tasks;
+using Emgu.CV;
+using Emgu.CV.Structure;
+using RichCreator.Dnf;
+using RichCreator.Maps.Kalete;
+using RichCreator.StateMachines;
using RichCreator.Utility;
using RichCreator.Utility.Captures;
using RichCreator.Utility.CV;
using RichCreator.Utility.InputControl;
+using RichCreator.Utility.Maps;
+using RichCreator.Utility.Skills;
using RichCreator.Utility.Structs;
-using Emgu.CV;
-using Emgu.CV.Structure;
-using RichCreator.Maps;
-using RichCreator.Maps.Lindong;
-using RichCreator.StateMachines;
using RichCreator.Utilitys;
-using static RichCreator.Utilitys.AttackRectangle;
-using Utils = RichCreator.Utilitys.Utils;
+using System;
+using System.Collections.Generic;
+using System.Threading;
using ZTImage.Collections;
namespace RichCreator.Jobs.StateMachines
@@ -27,12 +24,11 @@
public class KillMonsterStateMachine : StateMachineBase
{
private const Int32 NoMoveMaxMillSecond = 2000;//最大未移动容忍毫秒数
-
+ private MapInfo map;//地图
private HouseInfo house;//当前房间
- private ZTPoint miniMapStart;//小地图区域
- private ZTRectangle GameRect;//游戏区域
+ private DnfRole role;//当前角色控制
+
private Int32 preHouseIndex = 0;//上一房间编号
- private MoveState moveState;//移动状态
private OutOfBounds outOfBounds;//禁区
private bool isSuccess;//退出结果
@@ -43,7 +39,7 @@
//当前状态
private KillMonsterStates currentState = KillMonsterStates.Start;
//是否截图屏幕
- private bool captureScreen = false;
+ private bool needCaptureScreen = false;
//怪
private ZTPoint[] stateMonsters;
@@ -57,35 +53,31 @@
//色彩hsv
private Image<Hsv, byte> hsvImage = null;
- //取消令牌
- private CancellationToken cancellationToken = CancellationToken.None;
#region Find Door Info
//门坐标
private ZTPoint stateDoorPosition;
- //角色位置
- private ZTPoint stateRolePosition;
+
//离开的门朝向
private Direction stateDoorLevelDirect = Direction.None;
- //定位点方框
- private MultiList<ZTRectangle, Int32> stateLocationRectangle = new MultiList<ZTRectangle, int>();
-
+
+ //屏幕定位点
+ private ParametersPoint stateScreenLocation = new ParametersPoint();
#endregion
- public KillMonsterStateMachine(HouseInfo house, ZTPoint miniMapStart, ZTRectangle gameRect, Int32 preHouseIndex, Int32 runningStep, CancellationToken cancellationToken)
+ public KillMonsterStateMachine(MapInfo map,HouseInfo house, DnfRole role,Int32 preHouseIndex, Int32 runningStep)
{
- this.runningStep = runningStep;
+ this.map = map;
this.house = house;
- this.miniMapStart = miniMapStart;
- this.GameRect = gameRect;
+ this.role = role;
+ this.runningStep = runningStep;
this.preHouseIndex = preHouseIndex;
- this.cancellationToken = cancellationToken;
- moveState = new MoveState(this.GameRect, this.house);
- outOfBounds = new OutOfBounds(this.GameRect, moveState);
- hsvImage = new Image<Hsv, byte>(gameRect.End.X - gameRect.Start.X + 1, gameRect.End.Y - gameRect.Start.Y + 1);
+
+ outOfBounds = new OutOfBounds(map.GameRect, role);
+ hsvImage = new Image<Hsv, byte>(map.GameRect.End.X - map.GameRect.Start.X + 1, map.GameRect.End.Y - map.GameRect.Start.Y + 1);
}
@@ -93,7 +85,7 @@
private void SetState(KillMonsterStates current, bool capture)
{
currentState = current;
- captureScreen = capture;
+ needCaptureScreen = capture;
}
/// <summary>
@@ -111,24 +103,26 @@
SetState(KillMonsterStates.FindMonster, true);
}
+ //定位方框列表
+ MultiList<ZTRectangle, Int32> locationRectangles = new MultiList<ZTRectangle, int>();
while (true)
{
- if (cancellationToken.IsCancellationRequested)
+ if (map.CancelToken.IsCancellationRequested)
{
G.Instance.DebugWriter("取消刷图");
- this.moveState.StopMove();
+ this.role.StopMove();
return ZTResult.Cancel;
}
if (DateTime.Now > expireTime)
{
G.Instance.DebugWriter("刷图超时");
- this.moveState.StopMove();
+ this.role.StopMove();
return ZTResult.Timeout;
}
- if (captureScreen)
+ if (needCaptureScreen)
{
using (bitmap = ScreenCapture.Instance.CaptureScreen())
{
@@ -137,7 +131,7 @@
image.Dispose();
}
image = new Image<Rgb, byte>(bitmap);
- image = image.GetSubRect(new System.Drawing.Rectangle(GameRect.Start.X, GameRect.Start.Y, GameRect.End.X - GameRect.Start.X + 1, GameRect.End.Y - GameRect.Start.Y + 1));
+ image = image.GetSubRect(new System.Drawing.Rectangle(map.GameRect.Start.X, map.GameRect.Start.Y, map.GameRect.End.X - map.GameRect.Start.X + 1, map.GameRect.End.Y - map.GameRect.Start.Y + 1));
imageIsChange = true;
}
}
@@ -146,7 +140,7 @@
{
case KillMonsterStates.Start:
//开始
- SingleEntryHouseSkill.ReleaseSkill(this.house.Index, this.preHouseIndex, this.moveState);
+ this.map.EntryHousePrework(this.house.Index, this.preHouseIndex);
SetState(KillMonsterStates.IsLastHouse, true);
break;
case KillMonsterStates.IsLastHouse:
@@ -168,7 +162,7 @@
break;
case KillMonsterStates.HasRewardWindow:
//是否有奖励界面
- if (DnfCVHelper.IsJiangli(image, this.GameRect))
+ if (DnfCVHelper.IsJiangli(image, map.GameRect))
{
SetState(KillMonsterStates.TurnAroundCard, false);
}
@@ -186,7 +180,7 @@
break;
case KillMonsterStates.IsCompletePage:
//是否刷完界面
- if (DnfCVHelper.IsCompleteRoom(image, this.GameRect))
+ if (DnfCVHelper.IsCompleteRoom(image, map.GameRect))
{
this.isSuccess = true;
SetState(KillMonsterStates.Exit, false);
@@ -213,8 +207,9 @@
//主角
CvInvoke.CvtColor(image, hsvImage, Emgu.CV.CvEnum.ColorConversion.Rgb2Hsv);
+
//定位点
- if (!DnfCVHelper.GetLocationPoint(out stateLocationRectangle, hsvImage, this.GameRect))
+ if (!DnfCVHelper.GetLocationPoint(out locationRectangles, hsvImage, map.GameRect))
{
//找不到定位点
G.Instance.InfoWriter("找不到定位点");
@@ -222,20 +217,20 @@
break;
}
-
-
-
- this.stateRolePosition = DnfCVHelper.FindRole(hsvImage, this.GameRect);
- if (this.stateRolePosition .Equals( ZTPoint.Empty))
+ this.stateScreenLocation = new ParametersPoint(locationRectangles[0].Item1.GetCenterPoint(), locationRectangles[0].Item2);
+
+ ZTPoint rolePosition = DnfCVHelper.FindRole(hsvImage, map.GameRect);
+ if (rolePosition .Equals( ZTPoint.Empty))
{
SetState(KillMonsterStates.FindRoleMove, false);
}
else
{
- if (this.moveState.IsFindRoleMoving)
+ if (this.role.IsMoveIntent(Utility.Dnf.MoveIntent.FindRoleMove))
{
- this.moveState.StopMove();
+ this.role.StopMove();
}
+ role.UpdatePosition(rolePosition);
SetState(KillMonsterStates.FindMonster, false);
}
break;
@@ -245,7 +240,7 @@
break;
case KillMonsterStates.FindMonster:
//找怪
- this.stateMonsters = LindongCVHelper.FindMonster(hsvImage, this.GameRect);
+ this.stateMonsters = LindongCVHelper.FindMonster(hsvImage, map.GameRect);
if (this.stateMonsters.Length > 0)
{
@@ -259,8 +254,13 @@
break;
case KillMonsterStates.PickupThing:
//拾取物品
- SetState(KillMonsterStates.FindDoor, false);
+ SetState(KillMonsterStates.ToNextGatePoint, false);
//todo: PickupThing();
+ break;
+ case KillMonsterStates.ToNextGatePoint:
+ //移到进门点
+ SetState(KillMonsterStates.FindDoor, false);
+ //todo:ToNextGatePoint
break;
case KillMonsterStates.FindDoor:
//查找门, 是否找到门
@@ -289,7 +289,7 @@
case KillMonsterStates.Exit:
//结束
G.Instance.DebugWriter("退出状态");
- this.moveState.StopMove();
+ this.role.StopMove();
if (this.isSuccess)
{
return ZTResult.Success;
@@ -309,22 +309,17 @@
/// </summary>
private void FindRoleMove()
{
- this.moveState.FindRoleMove();
- SetState(KillMonsterStates.FindRole, true);
-
- //if (this.stateMonsters.Length > 0)
+ //if (this.stateMonsters != null && this.stateMonsters.Length > 0)
//{
- // this.moveState.StopMove();
+ // this.role.StopMove();
// G.Instance.DebugWriter("找不到角色,Send X");
// G.Instance.InputControl.PressKey(1000, HIDCode.X);
- // SetState(KillMonsterStates.FindMonster, true);
+ // SetState(KillMonsterStates.FindRole, true);
+
// return;
//}
- //else
- //{
- // this.moveState.FindRoleMove();
- // SetState(KillMonsterStates.IsLastHouse, true);
- //}
+ this.role.FindRoleMove();
+ SetState(KillMonsterStates.FindRole, true);
}
/// <summary>
@@ -333,21 +328,21 @@
private void PickupThing()
{
//拾取物品,获取最近一个物品位置并步行过去
- ZTPoint thingItemPosition = GetNearlyThingItem(image, stateRolePosition);
+ ZTPoint thingItemPosition = GetNearlyThingItem(image, role.Position);
if (!thingItemPosition .Equals( ZTPoint.Empty))
{
- if (this.moveState.IsMoving && !this.moveState.IsPickupMoving)
+ if (this.role.IsMoving && !this.role.IsMoveIntent(Utility.Dnf.MoveIntent.PickupMove))
{
- this.moveState.StopMove();
+ this.role.StopMove();
}
- this.moveState.PickupMove(this.stateRolePosition, thingItemPosition);
+ this.role.PickupMove(this.role.Position, thingItemPosition);
//return new KillMonsterStateResult(STATE_FindMonster, true);
}
- if (this.moveState.IsPickupMoving)
+ if (this.role.IsMoveIntent(Utility.Dnf.MoveIntent.PickupMove))
{
- this.moveState.StopMove();
+ this.role.StopMove();
}
}
@@ -357,13 +352,13 @@
private void FindDoor()
{
//查找真实的门
- this.stateDoorPosition = LindongCVHelper.FindDoor(out stateDoorLevelDirect, hsvImage, this.house.DoorDirection, this.GameRect);
+ this.stateDoorPosition = LindongCVHelper.FindDoor(out stateDoorLevelDirect, hsvImage, this.house.DoorDirection, map.GameRect);
if (!this.stateDoorPosition .Equals(ZTPoint.Empty))
{
//找到门,向门移动
- if (this.moveState.IsFindDoorMoving)
+ if (this.role.IsMoveIntent(Utility.Dnf.MoveIntent.FindDoorMove))
{
- this.moveState.StopMove();
+ this.role.StopMove();
}
G.Instance.InfoWriter("已找到门,位置:" + stateDoorPosition.ToString());
SetState(KillMonsterStates.EntryDoor, false);
@@ -390,69 +385,69 @@
case Direction.Up:
//门在上方
limitLine = stateDoorPosition.Y + YLevelOffset;
- if (stateRolePosition.Y < limitLine)
+ if (role.Position.Y < limitLine)
{
//下移
- this.moveState.SyncMove(new ZTPoint(0, limitLine - stateRolePosition.Y));
+ this.role.SyncMove(new ZTPoint(0, limitLine - role.Position.Y));
}
//垂直对齐
- diff = stateDoorPosition.X - stateRolePosition.X;
- this.moveState.SyncMove(new ZTPoint(diff, 0));
+ diff = stateDoorPosition.X - role.Position.X;
+ this.role.SyncMove(new ZTPoint(diff, 0));
//移动y,进入
- this.moveState.SyncMove(new ZTPoint(0, this.GameRect.Start.Y - stateRolePosition.Y));
+ this.role.SyncMove(new ZTPoint(0, map.GameRect.Start.Y - role.Position.Y));
break;
case Direction.Right:
//门在右侧
limitLine = stateDoorPosition.X - XLevelOffset;
- if (stateRolePosition.X > limitLine)
+ if (role.Position.X > limitLine)
{
//如果角色位于门右侧,先向左移
- this.moveState.SyncMove(new ZTPoint(limitLine - stateRolePosition.X, 0));
+ this.role.SyncMove(new ZTPoint(limitLine - role.Position.X, 0));
}
//水平对齐
- diff = stateDoorPosition.Y - stateRolePosition.Y;
- this.moveState.SyncMove(new ZTPoint(0, diff));
+ diff = stateDoorPosition.Y - role.Position.Y;
+ this.role.SyncMove(new ZTPoint(0, diff));
//移动x,进入
- this.moveState.SyncMove(new ZTPoint(this.GameRect.End.X - stateRolePosition.X, 0));
+ this.role.SyncMove(new ZTPoint(map.GameRect.End.X - role.Position.X, 0));
break;
case Direction.Bottom:
//门在下方
limitLine = stateDoorPosition.Y - YLevelOffset;
- if (stateRolePosition.Y > limitLine)
+ if (role.Position.Y > limitLine)
{
//如果角色在门下方,先向上移
- this.moveState.SyncMove(new ZTPoint(0, limitLine - stateRolePosition.Y));
+ this.role.SyncMove(new ZTPoint(0, limitLine - role.Position.Y));
}
//垂直对齐
- diff = stateDoorPosition.X - stateRolePosition.X;
- this.moveState.SyncMove(new ZTPoint(diff, 0));
+ diff = stateDoorPosition.X - role.Position.X;
+ this.role.SyncMove(new ZTPoint(diff, 0));
//移动y,进入
- this.moveState.SyncMove(new ZTPoint(0, this.GameRect.End.Y - stateRolePosition.Y));
+ this.role.SyncMove(new ZTPoint(0, map.GameRect.End.Y - role.Position.Y));
break;
case Direction.Left:
//门在左侧
limitLine = stateDoorPosition.X + XLevelOffset;
- if (stateRolePosition.X < limitLine)
+ if (role.Position.X < limitLine)
{
//如果角色位于门左侧,先向右移
- this.moveState.SyncMove(new ZTPoint(limitLine - stateRolePosition.X, 0));
+ this.role.SyncMove(new ZTPoint(limitLine - role.Position.X, 0));
}
//水平对齐
- diff = stateDoorPosition.Y - stateRolePosition.Y;
- this.moveState.SyncMove(new ZTPoint(0, diff));
+ diff = stateDoorPosition.Y - role.Position.Y;
+ this.role.SyncMove(new ZTPoint(0, diff));
//移动x,进入
- this.moveState.SyncMove(new ZTPoint(this.GameRect.Start.X - stateRolePosition.X, 0));
+ this.role.SyncMove(new ZTPoint(map.GameRect.Start.X - role.Position.X, 0));
break;
}
SetState(KillMonsterStates.IsLastHouse, true);
@@ -465,13 +460,13 @@
private void FindDoorMove()
{
Int32 areaID = 0;
- if (this.outOfBounds.InOutOfBound(this.house.Index, stateRolePosition, out areaID))
+ if (this.outOfBounds.InOutOfBound(this.house.Index, role.Position, out areaID))
{
this.outOfBounds.MoveToCommonBound(areaID);
}
else
{
- this.moveState.FindDoorMove(stateRolePosition);
+ this.role.FindDoorMove(role.Position);
}
SetState(KillMonsterStates.IsLastHouse, true);
}
@@ -492,7 +487,7 @@
//计算攻击移动距离
bool needMove = false;
- attackMoveDistance = AttackRectangle.GetMoveDistance(this.GameRect, stateRolePosition, stateMonsters, attackSkill, out roleDirection, out needMove);
+ attackMoveDistance = AttackRectangle.GetMoveDistance(map.GameRect, role.Position, stateMonsters, attackSkill, out roleDirection, out needMove);
if (!needMove)
{
G.Instance.DebugWriter(string.Format("不需移动直接发技能,距离:{0}", attackMoveDistance.ToString()));
@@ -517,7 +512,7 @@
{
G.Instance.InputControl.PressKey(100, roleDirection);
}
- this.moveState.StopMove();
+ this.role.StopMove();
@@ -547,13 +542,13 @@
{
SkillInfo attackSkill = this.house.Skills.SyncPeek();
//没有移动,可能有障碍物
- if (stateRolePosition .Equals( this.roleLastPosition))
+ if (role.Position .Equals( this.roleLastPosition))
{
if (FindRoleLastNoMoveStart && (DateTime.Now - FindRoleLastNoMoveTime).TotalMilliseconds > NoMoveMaxMillSecond)
{
//开始计时 并且 超过最大未移动容忍时间
- G.Instance.DebugWriter("find role no mvoe:" + stateRolePosition.ToString());
- this.moveState.StopMove();
+ G.Instance.DebugWriter("find role no mvoe:" + role.Position.ToString());
+ this.role.StopMove();
G.Instance.InputControl.PressKey(RandomUtils.KeyPressDuration, HIDCode.X);
FindRoleLastNoMoveTime = DateTime.Now;
}
@@ -567,12 +562,12 @@
else
{
//移动了 取消计时
- this.roleLastPosition = stateRolePosition;
+ this.roleLastPosition = role.Position;
FindRoleLastNoMoveStart = false;
}
- G.Instance.DebugWriter("attack move :" + attackMoveDistance.ToString() + ",role:" + stateRolePosition.ToString() + ",monster1:" + stateMonsters[0].ToString() + ",skill:" + attackSkill.Key.ToString());
- this.moveState.AttackMove(attackMoveDistance);
+ G.Instance.DebugWriter("attack move :" + attackMoveDistance.ToString() + ",role:" + role.Position.ToString() + ",monster1:" + stateMonsters[0].ToString() + ",skill:" + attackSkill.Key.ToString());
+ this.role.AttackMove(attackMoveDistance);
SetState(KillMonsterStates.FindRole, true);
}
#endregion
@@ -584,7 +579,7 @@
/// <returns></returns>
public ZTPoint GetNearlyThingItem(Image<Rgb, byte> image, ZTPoint rolePosition)
{
- List<ZTPoint> points = DnfCVHelper.GetThingItemPoints(image, this.GameRect);
+ List<ZTPoint> points = DnfCVHelper.GetThingItemPoints(image, map.GameRect);
if (points.Count <= 0)
{
return ZTPoint.Empty;
@@ -644,14 +639,14 @@
{
Thread.Sleep(2000);
Int32 number = RandomUtils.G(1, 4);
- ZTPoint willPosition = this.GameRect.Start.Add(CardList[number - 1]);
+ ZTPoint willPosition = map.GameRect.Start.Add(CardList[number - 1]);
G.Instance.InputControl.MoveToAndClick(RandomUtils.PointRange(willPosition, 10));
//判断黄金版是否可以翻
- if (DnfCVHelper.HasMowangqiyueCard(this.GameRect))
+ if (DnfCVHelper.HasMowangqiyueCard(map.GameRect))
{
number = RandomUtils.G(5, 8);
- willPosition = this.GameRect.Start.Add(CardList[number - 1]);
+ willPosition = map.GameRect.Start.Add(CardList[number - 1]);
G.Instance.InputControl.MoveToAndClick(RandomUtils.PointRange(willPosition, 10));
}
@@ -665,26 +660,13 @@
/// <returns></returns>
private bool HouseIsChange()
{
- Int32 houseIndex;
- if (!LindongCVHelper.GetCurrentHouseIndex(out houseIndex, image, this.miniMapStart))
+ Int32 houseIndex = 0;
+ if (!map.MiniMap.GetCurrentHouseIndexWaitTimeout(out houseIndex, image, map.CancelToken, 30 * 1000))
{
- //得不到房间
- if (!FuncUtils.TimeoutCancelableWrap(30 * 1000, cancellationToken, () =>
- {
- using (bitmap = ScreenCapture.Instance.CaptureScreen())
- {
- image = new Image<Rgb, byte>(bitmap);
- image = image.GetSubRect(new System.Drawing.Rectangle(GameRect.Start.X, GameRect.Start.Y, GameRect.End.X - GameRect.Start.X + 1, GameRect.End.Y - GameRect.Start.Y + 1));
- return LindongCVHelper.GetCurrentHouseIndex(out houseIndex, image, this.miniMapStart);
- }
- }, 50))
- {
- throw new Exception("找不到默认房间");
- }
+ throw new Exception("找不到默认房间");
}
if (houseIndex != this.house.Index)
{
- this.moveState.StopMove();
return true;
}
return false;
@@ -707,6 +689,7 @@
FindRoleMove,//让主角移动(原:有怪攻击一下,无怪移动一下)
FindMonster,//找怪
PickupThing,//拾取物品
+ ToNextGatePoint,//移到进门点
FindDoor,//查找门, 是否找到门
EntryDoor,//向门移动, 进门
FindDoorMove,//找门移动
--
Gitblit v1.9.3