Skip to content

Commit

Permalink
add mode toggle and full text copy
Browse files Browse the repository at this point in the history
  • Loading branch information
dit-zy committed Nov 20, 2023
1 parent 3c07326 commit 97f835c
Show file tree
Hide file tree
Showing 7 changed files with 124 additions and 24 deletions.
3 changes: 3 additions & 0 deletions ScoutHelper/Configuration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@ public class Configuration : IPluginConfiguration {
public string BearSiteTrainUrl { get; set; } = "https://tracker.beartoolkit.com/train";
public string BearTrainName { get; set; } = "Scout Helper Train";

public string CopyTemplate { get; set; } = Constants.DefaultCopyTemplate;
public bool CopyFormattedText { get; set; } = false;

public void Initialize(DalamudPluginInterface pluginInterface) {
this._pluginInterface = pluginInterface;
}
Expand Down
2 changes: 2 additions & 0 deletions ScoutHelper/Constants.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ public static class Constants {
public static readonly string PluginVersion;
public static readonly string PluginNamespace = PluginName.Replace(" ", "");
#endregion

public const string DefaultCopyTemplate = "{patch} {#}/{#available} {world} [{tracker}]({link})";

#region web constants
public static readonly MediaTypeWithQualityHeaderValue MediaTypeJson =
Expand Down
2 changes: 1 addition & 1 deletion ScoutHelper/Managers/BearManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ IList<TrainMob> trainMobs
}

public static class BearExtensions {
private static readonly IDictionary<Patch, string> BearPatchNames = new Dictionary<Patch, string> {
private static readonly IReadOnlyDictionary<Patch, string> BearPatchNames = new Dictionary<Patch, string> {
{Patch.ARR, "ARR"},
{Patch.HW, "HW"},
{Patch.SB, "SB"},
Expand Down
2 changes: 1 addition & 1 deletion ScoutHelper/Models/TrainMob.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ public record struct TrainMob(
uint MobId,
uint TerritoryId,
uint MapId,
uint Instance,
uint? Instance,
Vector2 Position,
bool Dead,
DateTime LastSeenUtc
Expand Down
2 changes: 2 additions & 0 deletions ScoutHelper/Plugin.cs
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,8 @@ public void Dispose() {
MainWindow.Dispose();

HuntHelperManager.Dispose();

Conf.Save();
}

private static void OnLanguageChanged(string languageCode) {
Expand Down
36 changes: 32 additions & 4 deletions ScoutHelper/Utils.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,14 @@
using System.Collections.Immutable;
using System.IO;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using ScoutHelper.Models;

namespace ScoutHelper;

public static class Utils {
public static string WorldName {
get => Plugin.ClientState.LocalPlayer?.CurrentWorld?.GameData?.Name.ToString() ?? "Not Found";
}
public static string WorldName => Plugin.ClientState.LocalPlayer?.CurrentWorld?.GameData?.Name.ToString() ?? "Not Found";

public static string DataFilePath(string dataFilename) => Path.Combine(
Plugin.PluginInterface.AssemblyLocation.Directory?.FullName!,
Expand All @@ -27,6 +28,33 @@ public static void CreateTooltip(string text, float width = 12f) {
ImGui.EndTooltip();
}

public static string FormatTemplate(string textTemplate, IList<TrainMob> trainList, string bear, string url) {

var regex = new Regex(@"\\?\{[^}]+\\?\}", RegexOptions.Compiled | RegexOptions.IgnoreCase);
var matches = regex.Matches(textTemplate);

if (matches.Count == 0) {
return textTemplate;
}

var s = new StringBuilder(textTemplate.Length);
var i = 0;
foreach (Match match in matches) {
var m = match.Value;
if (m[0] == '\\' || m[^2] == '\\') continue;

s.Append(textTemplate.AsSpan(i, match.Index - i));

i = match.Index + match.Length;
}

if (i < textTemplate.Length) {
s.Append(textTemplate.AsSpan(i));
}

return s.ToString();
}

#region extensions
public static void TaggedPrint(this IChatGui chatGui, string message) {
chatGui.Print(message, Plugin.Name);
Expand All @@ -36,7 +64,7 @@ public static void TaggedPrintError(this IChatGui chatGui, string message) {
chatGui.PrintError(message, Plugin.Name);
}

public static IDictionary<K, V> VerifyEnumDictionary<K, V>(this IDictionary<K, V> enumDict) where K : struct, Enum {
public static IReadOnlyDictionary<K, V> VerifyEnumDictionary<K, V>(this IDictionary<K, V> enumDict) where K : struct, Enum {
var allEnumsAreInDict = (Enum.GetValuesAsUnderlyingType<K>() as K[])!.All(enumDict.ContainsKey);
if (!allEnumsAreInDict) {
throw new Exception($"All values of enum [{typeof(K).Name}] must be in the dictionary.");
Expand Down
101 changes: 83 additions & 18 deletions ScoutHelper/Windows/MainWindow.cs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
using CSharpFunctionalExtensions;
using Dalamud.Interface.Utility;
using Dalamud.Interface.Windowing;
using Dalamud.Plugin.Services;
using ImGuiNET;
using ScoutHelper.Localization;
using ScoutHelper.Managers;
using ScoutHelper.Models;
using System;
using System.Collections.Generic;
using System.Linq;
Expand All @@ -14,8 +14,12 @@ namespace ScoutHelper.Windows;

public class MainWindow : Window, IDisposable {

private HuntHelperManager HuntHelperManager { get; init; }
private BearManager BearManager { get; init; }
private HuntHelperManager HuntHelperManager { get; }
private BearManager BearManager { get; }

private readonly Vector2 _buttonSize;
private bool _copyFormattedText = Plugin.Conf.CopyFormattedText;
private string _textTemplate = Plugin.Conf.CopyTemplate;

public MainWindow(HuntHelperManager huntHelperManager, BearManager bearManager) : base(
Strings.MainWindowTitle,
Expand All @@ -25,41 +29,92 @@ public MainWindow(HuntHelperManager huntHelperManager, BearManager bearManager)
MinimumSize = new Vector2(64, 32),
MaximumSize = new Vector2(float.MaxValue, float.MaxValue),
};

_buttonSize = new List<string> {
Strings.BearButton,
Strings.SirenButton
}
.Select(ImGuiHelpers.GetButtonSize)
.MaxBy(size => size.X);
_buttonSize.X += 4*ImGui.GetFontSize(); // add some horizontal padding


HuntHelperManager = huntHelperManager;
BearManager = bearManager;
}

public void Dispose() {
Plugin.Conf.CopyFormattedText = _copyFormattedText;
Plugin.Conf.Save();

GC.SuppressFinalize(this);
}

public override void Draw() {
var buttonSize = new List<string> {
Strings.BearButton,
Strings.SirenButton
}
.Select(ImGuiHelpers.GetButtonSize)
.MaxBy(size => size.X);
buttonSize.X += ImGui.GetFontSize();

if (ImGui.Button(Strings.BearButton, buttonSize)) {
DrawModeButtons();

ImGui.Dummy(new Vector2(0, ImGui.GetStyle().FramePadding.Y));
ImGui.Separator();
ImGui.Dummy(new Vector2(0, ImGui.GetStyle().FramePadding.Y));

DrawGeneratorButtons();
}

private unsafe void DrawModeButtons() {
ImGuiHelpers.CenteredText("MODE");

var modeButtonSize = new Vector2(
_buttonSize.X / 2,
_buttonSize.Y - 4
);
var activeColor = new Vector4(0, 183, 165, 255)/255;
var inactiveColor = *ImGui.GetStyleColorVec4(ImGuiCol.Button);
var modeLink = !_copyFormattedText;
var modeFull = !modeLink;
var modeLinkColor = modeLink ? activeColor : inactiveColor;
var modeFullColor = modeFull ? activeColor : inactiveColor;

ImGui.PushStyleColor(ImGuiCol.Button, modeLinkColor);
ImGui.PushStyleColor(ImGuiCol.ButtonHovered, modeLinkColor);
ImGui.PushStyleColor(ImGuiCol.ButtonActive, modeLinkColor*0.9f);
if (ImGui.Button("link", modeButtonSize)) {
_copyFormattedText = !_copyFormattedText;
}
ImGui.PopStyleColor(3);

ImGui.SameLine();

ImGui.SetCursorPosX(ImGui.GetWindowWidth() - ImGui.GetStyle().WindowPadding.X - modeButtonSize.X);
ImGui.PushStyleColor(ImGuiCol.Button, modeFullColor);
ImGui.PushStyleColor(ImGuiCol.ButtonHovered, modeFullColor);
ImGui.PushStyleColor(ImGuiCol.ButtonActive, modeFullColor*0.9f);
if (ImGui.Button("full text", modeButtonSize)) {
_copyFormattedText = !_copyFormattedText;
}
ImGui.PopStyleColor(3);
}

private void DrawGeneratorButtons() {
ImGuiHelpers.CenteredText("GENERATORS");

if (ImGui.Button(Strings.BearButton, _buttonSize)) {
GenerateBearLink();
}
if (ImGui.IsItemHovered()) {
Utils.CreateTooltip(Strings.BearButtonTooltip);
}

ImGui.BeginDisabled(true);
if (ImGui.Button(Strings.SirenButton, buttonSize)) { }
if (ImGui.Button(Strings.SirenButton, _buttonSize)) { }
ImGui.EndDisabled();
if (ImGui.IsItemHovered(ImGuiHoveredFlags.AllowWhenDisabled)) {
Utils.CreateTooltip(Strings.SirenButtonTooltip);
}
}

private void GenerateBearLink() {
Plugin.ChatGui.TaggedPrint("Generating Bear link...");
IList<TrainMob> trainList = null!;

HuntHelperManager
.GetTrainList()
Expand All @@ -68,16 +123,26 @@ private void GenerateBearLink() {
"No mobs in the train :T"
)
.Bind(
train => BearManager.GenerateBearLink(Utils.WorldName, train)
)
train => {
trainList = train;
return BearManager.GenerateBearLink(Utils.WorldName, train);
})
.ContinueWith(
apiResponseTask => {
apiResponseTask
.Result.Match(
bearTrainLink => {
Plugin.ChatGui.TaggedPrint($"Copied link to clipboard: {bearTrainLink.Url}");
Plugin.ChatGui.TaggedPrint($"Bear train link: {bearTrainLink.Url}");
Plugin.ChatGui.TaggedPrint($"Train admin password: {bearTrainLink.Pass}");
ImGui.SetClipboardText(bearTrainLink.Url);
if (_copyFormattedText) {
var fullText = Utils.FormatTemplate(_textTemplate, trainList, "bear", bearTrainLink.Url);
ImGui.SetClipboardText(fullText);
Plugin.ChatGui.TaggedPrint($"Copied full text to clipboard: {fullText}");
}
else {
ImGui.SetClipboardText(bearTrainLink.Url);
Plugin.ChatGui.TaggedPrint("Copied link to clipboard");
}
},
errorMessage => {
Plugin.ChatGui.TaggedPrintError(errorMessage);
Expand Down

0 comments on commit 97f835c

Please sign in to comment.