본문 바로가기
이미지 매크로

C# .NET 매크로 프로그램 만들기. (타이머 만들기)

by 업무자동화 2024. 4. 25.
반응형

유료 매크로 프로그램 다운로드

http://ngmsoftware.com/bbs/board.php?bo_table=product_review 

 

엔지엠소프트웨어

엔지엠 매크로는 복잡한 반복작업을 자동화할 수 있습니다. PC 게임, 모바일 게임을 최적으로 지원하며 모든 PC 프로그램 및 업무에 적용할 수 있습니다.

www.ngmsoftware.com

#매크로 #메크로 #매크로프로그램 #엔지엠소프트웨어 #엔지엠에디터 #엔지엠플레이어 #비활성매크로 #하드웨어매크로 #기계식매크로 #마우스광클릭 #키보드매크로 #이미지서치 #이미지매치 #블로그 #카페 #인스타그램 #유튜브 #소셜네트워크 #카카오톡 #텔레그램 #자동화

 

 

  • 엔지엠 커뮤니티 월 이용료: 4,500원, 1년 이용료: 55,000원 (전체 기능의 80프로)
  • 엔지엠 얼티밋 월 이용료: 6,500원, 1년 이용료: 77,000원 (전체 기능의 90프로)
  • 엔지엠 엔터프라이즈 월 이용료: 9,200원, 1년 이용료: 110,000원 (전체 기능 사용)

안녕하세요. 엔지엠소프트웨어입니다. 타이머 액션은 등록한 시점부터 시간이 흐르기 시작해서 조건의 타이머 체크 액션에서 설정한 시간이 지났는지를 확인할 수 있도록 해줍니다. 예를 들어서 타이머를 등록하고, 60초가 지났는지 체크할 수 있는데요. 시간이 지났다면 타이머 체크 액션은 참이 됩니다. 여러개의 타이머를 등록해두고, 타이머에 따라서 조건을 만들고 로직을 처리할 수 있습니다. 우선, 타이머를 어떻게 등록할 수 있는지 알아보고, 다음 시간에 타이머 체크를 만들면서 테스트 해볼께요.

 

아래와 같이 타이머 액션을 하나 추가했습니다.

public class AddTimerModel : BaseModel

 

현재 타이머가 등록된 시간을 확인할 수 있도록 속성을 하나 만들어줍니다.

[LocalizedCategory("Data")]
[LocalizedDisplayName("Result")]
[LocalizedDescription("Result")]
[Browsable(true)]
[DefaultValue(null)]
[EditorAttribute(typeof(MultilineStringEditor), typeof(UITypeEditor))]
public string? Result { get; set; }

 

사용자가 설정해야 할 속성은 총 5개입니다. 타이머를 등록하거나 수정 또는 삭제할 수 있는 AddUpdateRemove 옵션을 제공해야 합니다.

[LocalizedCategory("Action")]
[LocalizedDisplayName("ProcessOption")]
[LocalizedDescription("ProcessOption")]
[Browsable(true)]
[DefaultValue(typeof(Definition.AddUpdateRemove), "Add")]
public Ai.Definition.AddUpdateRemove ProcessOption { get; set; } = Definition.AddUpdateRemove.Add;

[LocalizedCategory("Action")]
[LocalizedDisplayName("IsFirstStart")]
[LocalizedDescription("IsFirstStart")]
[Browsable(true)]
[DefaultValue(false)]
public bool IsFirstStart { get; set; }

[LocalizedCategory("Action")]
[LocalizedDisplayName("TimerName")]
[LocalizedDescription("TimerName")]
[Browsable(true)]
[DefaultValue(false)]
public string? TimerName { get; set; }

[LocalizedCategory("Action")]
[LocalizedDisplayName("IsGlobal")]
[LocalizedDescription("IsGlobal")]
[Browsable(true)]
[DefaultValue(false)]
public bool IsGlobal { get; set; }

[LocalizedCategory("Action")]
[LocalizedDisplayName("IsParent")]
[LocalizedDescription("IsParent")]
[Browsable(true)]
[DefaultValue(false)]
public bool IsParent { get; set; }

 

엔지엠 매크로는 글로벌하게 모든 스크립트가 접근 가능한 메모리 영역이 있고, 플레이어가 실행하는 서브 스크립트 영역이 있습니다. 그리고, 자기 자신을 가리키는 스크립트가 있는데요. 이들의 관계에 따라서 다른 메모리 공간에 타이머가 등록됩니다. 모든 스크립트가 접근 가능한 영역은 IsGlobal로 설정 가능합니다. 그리고, 자기 자신을 만든 부모 플레이어는 IsParent 속성을 True로 설정하면 됩니다.

 

타이머를 각각 관리하기 위해 전역(Global), 부모(Parent), Self(자신)에 저장이 가능합니다. 타이머를 체크할 때도 각각의 영역에 맞는 곳에서 가져와야 합니다. 그리고, 이전 엔지엠 매크로에서는 아이디를 사용하다보니 여러가지 문제가 발생했습니다. 엔지엠 매크로의 아이디는 액션이 이동할 때 사용하는 유니크한 아이디입니다. 따라서, 사용자 제약으로 인해 동일한 아이디를 설정할 수 없도록 되어 있습니다. 그렇다보니 타이머 a를 등록하고, 동일한 스크립트에서 타이머 a를 수정하는 작업이 안됩니다. 물론, 복사 붙여넣기로 우회해서 사용할 수 있습니다. 다만, 이런식으로 사용하는건 규칙에 위배되기 때문에 좋은 방식은 아닙니다.

 

새로운 엔지엠 매크로는 아이디와 같이 사용하지 않도록 타이머 이름이라는 속성을 사용해서 관리할 수 있도록 했습니다. 따라서, 중복된 아이디 체크에 걸리지 않고, 타이머만의 아이디로 접근 및 수정, 삭제가 가능합니다. 사용자의 실수를 줄이기 위해서 어느정도 제약이 필요하기 때문에 아이디는 중복될 수 없도록 하고, 타이머와 같이 관리가 필요한 개체들은 별도의 이름으로 설정하도록 하겠습니다.

 

타이머를 등록하는 코드는 간단하게 구현할 수 있습니다. 중복된 코드가 있어서 뭔가 복잡해 보이지만, 타이머가 등록될 위치에 따라서 저장하도록 처리하면 됩니다. if ~ else if ~ else처럼 각각의 옵션에 따라서 처리되도록 구현되어 있습니다. 아래 코드를 보면 아시겠지만, IsGlobal이 가장 우선 적용되고 그다음에 IsParent가 적용됩니다. 그래서, IsGlobal과 IsParent를 둘다 True로 설정하면 IsGlobal에만 타이머가 등록됩니다.

public override string? Execute(IPlayer player)
{
    Result = null;

    var id = base.Execute(player);

    var timerName = Ai.Common.Helper.GetMatches(player, GetType().GetProperty(nameof(TimerName)), TimerName);

    if (!Ai.Common.Helper.NullCheckAndWriteLine(player, nameof(timerName), timerName))
        return id;

    if (IsGlobal)
    {
        switch (ProcessOption)
        {
            case Definition.AddUpdateRemove.Add:
                System.DateTime currentDT = System.DateTime.Now;
                player.Manager.Timers.Add(timerName, new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now));
                break;
            case Definition.AddUpdateRemove.Update:
                if (player.Manager.Timers.ContainsKey(timerName))
                    player.Manager.Timers[timerName] = new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now);
                break;
            case Definition.AddUpdateRemove.Remove:
                if (player.Manager.Timers.ContainsKey(timerName))
                    player.Manager.Timers.Remove(timerName);
                break;
        }

        Result = player.Manager.Timers[timerName].Item2.ToString("yyyy-MM-dd HH:mm:ss.fff");
    }
    else if (IsParent)
    {
        if (!player.HasParent)
        {
            player.Manager.Output.WarningWriteLine(player.Manager.Client.ResxMessage.GetString("NotFoundParentPlayerCancel"));
            return id;
        }

        switch (ProcessOption)
        {
            case Definition.AddUpdateRemove.Add:
                System.DateTime currentDT = System.DateTime.Now;
                player.Parent.Timers.Add(timerName, new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now));
                break;
            case Definition.AddUpdateRemove.Update:
                if (player.Parent.Timers.ContainsKey(timerName))
                    player.Parent.Timers[timerName] = new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now);
                break;
            case Definition.AddUpdateRemove.Remove:
                if (player.Parent.Timers.ContainsKey(timerName))
                    player.Parent.Timers.Remove(timerName);
                break;
        }

        Result = player.Parent.Timers[timerName].Item2.ToString("yyyy-MM-dd HH:mm:ss.fff");
    }
    else
    {
        switch (ProcessOption)
        {
            case Definition.AddUpdateRemove.Add:
                System.DateTime currentDT = System.DateTime.Now;
                player.Timers.Add(timerName, new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now));
                break;
            case Definition.AddUpdateRemove.Update:
                if (player.Timers.ContainsKey(timerName))
                    player.Timers[timerName] = new Tuple<bool, System.DateTime>(IsFirstStart, System.DateTime.Now);
                break;
            case Definition.AddUpdateRemove.Remove:
                if (player.Timers.ContainsKey(timerName))
                    player.Timers.Remove(timerName);
                break;
        }

        Result = player.Timers[timerName].Item2.ToString("yyyy-MM-dd HH:mm:ss.fff");
    }

    return id;
}

 

타이머는 타이머 이름이 필수 입력 값입니다. 이 값이 없으면 아래 그림과 같이 경고 메세지가 출력창에 표시됩니다.

 

 

[ 각종 자동화 매크로 및 RPA 프로그램 제작 해드립니다. ]

[ 초보자도 쉽게 따라할 수 있는 기초 학습 강좌 보기 ]

 

원본 글 보기

http://ngmsoftware.com/bbs/board.php?bo_table=tip_and_tech 

 

엔지엠소프트웨어

엔지엠 매크로는 복잡한 반복작업을 자동화할 수 있습니다. PC 게임, 모바일 게임을 최적으로 지원하며 모든 PC 프로그램 및 업무에 적용할 수 있습니다.

www.ngmsoftware.com

 

반응형

댓글