auto album

This commit is contained in:
辉鸭蛋 2025-01-02 01:05:03 +08:00
parent f9d0bd4521
commit 02f2c1321a
10 changed files with 213 additions and 18 deletions

View File

@ -128,6 +128,9 @@
<None Update="GameTask\AutoWood\Assets\1920x1080\**">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Update="GameTask\AutoMusicGame\Assets\1920x1080\**">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Update="GameTask\GameLoading\Assets\1920x1080\**">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 505 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

View File

@ -0,0 +1,46 @@
using BetterGenshinImpact.Core.Recognition;
using BetterGenshinImpact.GameTask.Model;
using BetterGenshinImpact.Helpers.Extensions;
using OpenCvSharp;
namespace BetterGenshinImpact.GameTask.AutoMusicGame.Assets;
public class AutoMusicAssets : BaseAssets<AutoMusicAssets>
{
public RecognitionObject UiLeftTopAlbumIcon;
public RecognitionObject BtnPause;
public RecognitionObject AlbumMusicComplate;
public RecognitionObject BtnList;
private AutoMusicAssets()
{
UiLeftTopAlbumIcon = new RecognitionObject
{
Name = "UiLeftTopAlbumIcon",
RecognitionType = RecognitionTypes.TemplateMatch,
TemplateImageMat = GameTaskManager.LoadAssetImage(@"AutoMusicGame", "ui_left_top_album_icon.png"),
RegionOfInterest = new Rect(0, 0, (int)(150 * AssetScale), (int)(120 * AssetScale)),
}.InitTemplate();
BtnPause = new RecognitionObject
{
Name = "BtnPause",
RecognitionType = RecognitionTypes.TemplateMatch,
TemplateImageMat = GameTaskManager.LoadAssetImage(@"AutoMusicGame", "btn_pause.png"),
RegionOfInterest = CaptureRect.CutRightTop(0.2, 0.2),
}.InitTemplate();
AlbumMusicComplate = new RecognitionObject
{
Name = "AlbumMusicComplate",
RecognitionType = RecognitionTypes.TemplateMatch,
TemplateImageMat = GameTaskManager.LoadAssetImage(@"AutoMusicGame", "album_music_complate.png"),
RegionOfInterest = new Rect( (int)(900 * AssetScale),(int)(320 * AssetScale), (int)(100 * AssetScale), (int)(80 * AssetScale)),
}.InitTemplate();
BtnList = new RecognitionObject
{
Name = "BtnList",
RecognitionType = RecognitionTypes.TemplateMatch,
TemplateImageMat = GameTaskManager.LoadAssetImage(@"AutoMusicGame", "btn_list.png"),
RegionOfInterest = CaptureRect.CutRightBottom(0.4, 0.2),
}.InitTemplate();
}
}

View File

@ -0,0 +1,91 @@
using System;
using System.Threading;
using System.Threading.Tasks;
using BetterGenshinImpact.GameTask.AutoMusicGame.Assets;
using BetterGenshinImpact.GameTask.Common.BgiVision;
using BetterGenshinImpact.GameTask.Model.Area;
using Microsoft.Extensions.Logging;
using static BetterGenshinImpact.GameTask.Common.TaskControl;
namespace BetterGenshinImpact.GameTask.AutoMusicGame;
/// <summary>
/// 自动音乐专辑
/// </summary>
public class AutoAlbumTask(AutoMusicGameParam taskParam) : ISoloTask
{
public string Name => "自动音游专辑";
public async Task Start(CancellationToken ct)
{
try
{
AutoMusicGameTask.Init();
Logger.LogInformation("开始自动演奏整个专辑未完成的音乐");
await StartOneAlbum(ct);
}
catch (Exception e)
{
Logger.LogError("自动音乐专辑任务异常:{Msg}", e.Message);
}
}
public async Task StartOneAlbum(CancellationToken ct)
{
// 12个音乐
for (int i = 0; i < 13; i++)
{
using var iconRa = CaptureToRectArea().Find(AutoMusicAssets.Instance.UiLeftTopAlbumIcon);
if (!iconRa.IsExist())
{
throw new Exception("当前未处于专辑界面,请在专辑界面运行本任务");
}
using var doneRa = CaptureToRectArea().Find(AutoMusicAssets.Instance.AlbumMusicComplate);
if (doneRa.IsExist())
{
Logger.LogInformation("当前音乐{Num}所有奖励已领取,切换下一首", i + 1);
GameCaptureRegion.GameRegion1080PPosClick(310, 220);
await Delay(800, ct);
continue;
}
Logger.LogInformation("当前音乐{Num}存在未领取奖励,前往演奏", i + 1);
Bv.ClickWhiteConfirmButton(CaptureToRectArea());
await Delay(800, ct);
// 点击传说
GameCaptureRegion.GameRegion1080PPosClick(1400, 600);
await Delay(200, ct);
// 演奏
Bv.ClickWhiteConfirmButton(CaptureToRectArea());
await Delay(500, ct);
CancellationTokenSource cts = new();
ct.Register(cts.Cancel);
// 演奏结束检查任务
var checkTask = Task.Run(async () =>
{
while (!cts.Token.IsCancellationRequested)
{
await Delay(5000, ct); // n秒检查一次
using var listRa = CaptureToRectArea().Find(AutoMusicAssets.Instance.BtnList);
if (listRa.IsExist())
{
listRa.Click();
return;
}
}
}, cts.Token);
// 演奏任务
var musicTask = new AutoMusicGameTask(taskParam).StartWithOutInit(cts.Token);
// 等待任意一个任务完成
await Task.WhenAny(checkTask, musicTask);
Logger.LogInformation("当前音乐{Num}演奏结束", i + 1);
await Delay(2000, ct);
}
Logger.LogInformation("当前专辑所有音乐演奏结束");
}
}

View File

@ -4,7 +4,6 @@ using OpenCvSharp;
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Diagnostics;
using System.Threading;
using System.Threading.Tasks;
using Vanara.PInvoke;
@ -16,7 +15,7 @@ public class AutoMusicGameTask(AutoMusicGameParam taskParam) : ISoloTask
{
public string Name => "自动音游";
// private readonly ConcurrentDictionary<User32.VK, int> _keyX = new()
// {
// [User32.VK.VK_A] = 417,
@ -29,7 +28,7 @@ public class AutoMusicGameTask(AutoMusicGameParam taskParam) : ISoloTask
//
// private readonly int _keyY = 916;
private readonly ConcurrentDictionary<User32.VK, int> _keyX = new()
{
[User32.VK.VK_A] = 417,
@ -39,17 +38,22 @@ public class AutoMusicGameTask(AutoMusicGameParam taskParam) : ISoloTask
[User32.VK.VK_K] = 1277,
[User32.VK.VK_L] = 1493
};
private readonly int _keyY = 921;
private readonly IntPtr _hWnd = TaskContext.Instance().GameHandle;
public async Task Start(CancellationToken ct)
{
Init();
await StartWithOutInit(ct);
}
public async Task StartWithOutInit(CancellationToken ct)
{
try
{
Init();
Logger.LogInformation("开始自动演奏");
var assetScale = TaskContext.Instance().SystemInfo.AssetScale;
// var taskFactory = new TaskFactory();
var taskList = new List<Task>();
@ -69,6 +73,7 @@ public class AutoMusicGameTask(AutoMusicGameParam taskParam) : ISoloTask
finally
{
Simulation.ReleaseAllKey();
Logger.LogInformation("结束自动演奏");
}
}
@ -231,12 +236,12 @@ public class AutoMusicGameTask(AutoMusicGameParam taskParam) : ISoloTask
Simulation.SendInput.Keyboard.KeyDown(key);
}
private void Init()
public static void Init()
{
LogScreenResolution();
}
private void LogScreenResolution()
public static void LogScreenResolution()
{
var gameScreenSize = SystemControl.GetGameScreenRect(TaskContext.Instance().GameHandle);
if (gameScreenSize.Width * 9 != gameScreenSize.Height * 16)

View File

@ -1176,7 +1176,7 @@
</StackPanel>
</ui:CardExpander>-->
<!-- 活动音游(限时,已失效) -->
<!-- 自动音游 -->
<ui:CardControl Margin="0,0,0,12"
Icon="{ui:SymbolIcon MusicNote224}">
<ui:CardControl.Header>
@ -1188,7 +1188,7 @@
<ui:TextBlock Grid.Row="0"
Grid.Column="0"
FontTypography="Body"
Text="自动音游"
Text="自动音游(千音雅集)"
TextWrapping="Wrap" />
<ui:TextBlock Grid.Row="1"
Grid.Column="0"
@ -1209,6 +1209,42 @@
EnableContent="{Binding SwitchAutoMusicGameButtonText}"
IsChecked="{Binding SwitchAutoMusicGameEnabled}" />
</ui:CardControl>
<!-- 自动音游专辑 -->
<ui:CardControl Margin="0,0,0,12">
<ui:CardControl.Icon>
<ui:FontIcon Glyph="&#xf89f;" Style="{StaticResource FaFontIconStyle}" />
</ui:CardControl.Icon>
<ui:CardControl.Header>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<ui:TextBlock Grid.Row="0"
Grid.Column="0"
FontTypography="Body"
Text="全自动完成专辑下所有乐曲(千音雅集)"
TextWrapping="Wrap" />
<ui:TextBlock Grid.Row="1"
Grid.Column="0"
Foreground="{ui:ThemeResource TextFillColorTertiaryBrush}"
TextWrapping="Wrap">
进入专辑界面使用,自动演奏未完成乐曲 -
<Hyperlink Command="{Binding GoToAutoMusicGameUrlCommand}"
Foreground="{ui:ThemeResource TextFillColorSecondaryBrush}">
点击查看使用教程
</Hyperlink>
</ui:TextBlock>
</Grid>
</ui:CardControl.Header>
<controls:TwoStateButton Margin="0,0,36,0"
DisableCommand="{Binding StopSoloTaskCommand}"
DisableContent="停止"
EnableCommand="{Binding SwitchAutoAlbumCommand}"
EnableContent="{Binding SwitchAutoAlbumButtonText}"
IsChecked="{Binding SwitchAutoAlbumEnabled}" />
</ui:CardControl>
<!--<ui:CardExpander Margin="0,0,0,12" ContentPadding="0" Icon="{ui:SymbolIcon Accessibility24}">

View File

@ -39,8 +39,8 @@ public partial class TaskSettingsPageViewModel : ObservableObject, INavigationAw
private CancellationTokenSource? _cts;
private static readonly object _locker = new();
// [ObservableProperty]
// private string[] _strategyList;
// [ObservableProperty]
// private string[] _strategyList;
[ObservableProperty]
private bool _switchAutoGeniusInvokationEnabled;
@ -83,13 +83,19 @@ public partial class TaskSettingsPageViewModel : ObservableObject, INavigationAw
[ObservableProperty]
private string _switchAutoTrackPathButtonText = "启动";
[ObservableProperty]
private bool _switchAutoMusicGameEnabled;
[ObservableProperty]
private string _switchAutoMusicGameButtonText = "启动";
[ObservableProperty]
private bool _switchAutoAlbumEnabled;
[ObservableProperty]
private string _switchAutoAlbumButtonText = "启动";
[ObservableProperty]
private List<string> _domainNameList;
@ -110,8 +116,7 @@ public partial class TaskSettingsPageViewModel : ObservableObject, INavigationAw
//_combatStrategyList = ["根据队伍自动选择", .. LoadCustomScript(Global.Absolute(@"User\AutoFight"))];
_domainNameList = MapLazyAssets.Instance.DomainNameList;
_autoFightViewModel=new AutoFightViewModel(Config);
_autoFightViewModel = new AutoFightViewModel(Config);
}
[RelayCommand]
@ -264,7 +269,7 @@ public partial class TaskSettingsPageViewModel : ObservableObject, INavigationAw
[RelayCommand]
public void OnOpenFightFolder()
{
_autoFightViewModel?.OnOpenFightFolder();
_autoFightViewModel?.OnOpenFightFolder();
}
[Obsolete]
@ -351,9 +356,18 @@ public partial class TaskSettingsPageViewModel : ObservableObject, INavigationAw
{
await Launcher.LaunchUriAsync(new Uri("https://bgi.huiyadan.com/feats/task/music.html"));
}
[RelayCommand]
public void OnOpenLocalScriptRepo()
public async Task OnSwitchAutoAlbum()
{
SwitchAutoAlbumEnabled = true;
await new TaskRunner(DispatcherTimerOperationEnum.UseSelfCaptureImage)
.RunSoloTaskAsync(new AutoAlbumTask(new AutoMusicGameParam()));
SwitchAutoAlbumEnabled = false;
}
[RelayCommand]
public void OnOpenLocalScriptRepo()
{
_autoFightViewModel.OnOpenLocalScriptRepo();
}