Merge pull request #83

feat: add autohide after inactivity
This commit is contained in:
Infi
2024-07-13 09:30:04 +02:00
committed by GitHub
6 changed files with 115 additions and 10 deletions
+10
View File
@@ -20,6 +20,8 @@ internal class Configuration : IPluginConfiguration
public bool HideWhenUiHidden = true;
public bool HideInLoadingScreens;
public bool HideInBattle;
public bool HideWhenInactive;
public int InactivityHideTimeout = 10;
public bool ShowHideButton = true;
public bool NativeItemTooltips = true;
public bool PrettierTimestamps = true;
@@ -78,6 +80,8 @@ internal class Configuration : IPluginConfiguration
HideWhenUiHidden = other.HideWhenUiHidden;
HideInLoadingScreens = other.HideInLoadingScreens;
HideInBattle = other.HideInBattle;
HideWhenInactive = other.HideWhenInactive;
InactivityHideTimeout = other.InactivityHideTimeout;
ShowHideButton = other.ShowHideButton;
NativeItemTooltips = other.NativeItemTooltips;
PrettierTimestamps = other.PrettierTimestamps;
@@ -168,6 +172,9 @@ internal class Tab
[NonSerialized]
public uint Unread;
[NonSerialized]
public long LastMessageTime;
[NonSerialized]
public MessageList Messages = new();
@@ -192,7 +199,10 @@ internal class Tab
{
Messages.AddPrune(message, MessageManager.MessageDisplayLimit);
if (unread)
{
Unread += 1;
LastMessageTime = Environment.TickCount64;
}
}
internal void Clear()
-3
View File
@@ -253,9 +253,6 @@ internal sealed unsafe class Chat : IDisposable
LastRefresh = Environment.TickCount64;
}
if (Plugin.ChatLogWindow is { CurrentTab.InputDisabled: true, IsHidden: false })
return;
// Vanilla text input has focus
if (RaptureAtkModule.Instance()->AtkModule.IsTextInputActive())
return;
+36
View File
@@ -2417,6 +2417,24 @@ namespace ChatTwo.Resources {
}
}
/// <summary>
/// Looks up a localized string similar to Hide the chat after a configurable period of inactivity. The current tab and any tabs with unread indicators enabled are considered for activity..
/// </summary>
internal static string Options_HideWhenInactive_Description {
get {
return ResourceManager.GetString("Options_HideWhenInactive_Description", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Hide when inactive.
/// </summary>
internal static string Options_HideWhenInactive_Name {
get {
return ResourceManager.GetString("Options_HideWhenInactive_Name", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Hide {0} when you are not logged in to a character..
/// </summary>
@@ -2453,6 +2471,24 @@ namespace ChatTwo.Resources {
}
}
/// <summary>
/// Looks up a localized string similar to How long to wait (in seconds) before considering the chat log inactive..
/// </summary>
internal static string Options_InactivityHideTimeout_Description {
get {
return ResourceManager.GetString("Options_InactivityHideTimeout_Description", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Inactivity timeout.
/// </summary>
internal static string Options_InactivityHideTimeout_Name {
get {
return ResourceManager.GetString("Options_InactivityHideTimeout_Name", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to The font {0} will use to display Japanese text..
/// </summary>
+12
View File
@@ -406,6 +406,18 @@
<data name="Options_HideWhenUiHidden_Description">
<value>Hide {0} when the game UI is hidden.</value>
</data>
<data name="Options_HideWhenInactive_Name">
<value>Hide when inactive</value>
</data>
<data name="Options_HideWhenInactive_Description">
<value>Hide the chat after a configurable period of inactivity. The current tab and any tabs with unread indicators enabled are considered for activity.</value>
</data>
<data name="Options_InactivityHideTimeout_Name">
<value>Inactivity timeout</value>
</data>
<data name="Options_InactivityHideTimeout_Description">
<value>How long to wait (in seconds) before considering the chat log inactive.</value>
</data>
<data name="Options_KeybindMode_Name">
<value>Keybind mode</value>
</data>
+44 -5
View File
@@ -85,6 +85,9 @@ public sealed class ChatLogWindow : Window
private const uint ChatCloseSfx = 3u;
private bool PlayedClosingSound = true;
private long FrameTime; // set every frame
private long LastActivityTime = Environment.TickCount64;
private readonly ExcelSheet<World> WorldSheet;
private readonly ExcelSheet<LogFilter> LogFilterSheet;
private readonly ExcelSheet<TextCommand> TextCommandSheet;
@@ -148,6 +151,18 @@ public sealed class ChatLogWindow : Window
private void Activated(ChatActivatedArgs args)
{
Activate = true;
PlayedClosingSound = false;
if (Plugin.Config.PlaySounds)
UIModule.PlaySound(ChatOpenSfx);
// Don't set the channel or text content when activating a disabled tab.
if (CurrentTab?.InputDisabled == true)
{
// The closing sound would've been immediately played in this case.
PlayedClosingSound = true;
return;
}
if (args.AddIfNotPresent != null && !Chat.Contains(args.AddIfNotPresent))
Chat += args.AddIfNotPresent;
@@ -203,10 +218,6 @@ public sealed class ChatLogWindow : Window
if (info.Text != null && Chat.Length == 0)
Chat = info.Text;
PlayedClosingSound = false;
if (Plugin.Config.PlaySounds)
UIModule.PlaySound(ChatOpenSfx);
}
private bool IsValidCommand(string command)
@@ -471,7 +482,23 @@ public sealed class ChatLogWindow : Window
public override bool DrawConditions()
{
return !IsHidden;
FrameTime = Environment.TickCount64;
if (IsHidden)
return false;
if (!Plugin.Config.HideWhenInactive || Activate)
{
LastActivityTime = FrameTime;
return true;
}
var currentTab = CurrentTab; // local to avoid calling the getter repeatedly
var lastActivityTime = Plugin.Config.Tabs
.Where(tab => tab.UnreadMode is not UnreadMode.None || tab == currentTab)
.Select(tab => tab.LastMessageTime)
.DefaultIfEmpty(0)
.Max();
lastActivityTime = Math.Max(lastActivityTime, LastActivityTime);
return FrameTime - lastActivityTime <= 1000 * Plugin.Config.InactivityHideTimeout;
}
public override void PreDraw()
@@ -485,6 +512,12 @@ public sealed class ChatLogWindow : Window
public override void PostDraw()
{
// Set Activate to false after draw to avoid repeatedly trying to focus
// the text input in a tab with input disabled. The usual way that
// Activate gets disabled is via the text input callback, but that
// doesn't get called if the input is disabled.
if (CurrentTab?.InputDisabled == true)
Activate = false;
if (Plugin.Config is { OverrideStyle: true, ChosenStyle: not null })
StyleModel.GetConfiguredStyles()?.FirstOrDefault(style => style.Name == Plugin.Config.ChosenStyle)?.Pop();
}
@@ -740,7 +773,10 @@ public sealed class ChatLogWindow : Window
}
if (ImGui.IsItemActive())
{
HandleKeybinds(true);
LastActivityTime = FrameTime;
}
// Only trigger unfocused if we are currently not calling the auto complete
if (!Activate && !ImGui.IsItemActive() && AutoCompleteInfo == null)
@@ -785,6 +821,9 @@ public sealed class ChatLogWindow : Window
UserHide();
}
if (ImGui.IsWindowHovered(ImGuiHoveredFlags.ChildWindows))
LastActivityTime = FrameTime;
if (!showNovice)
return;
+13 -2
View File
@@ -1,7 +1,5 @@
using ChatTwo.Resources;
using ChatTwo.Util;
using Dalamud.Interface.Style;
using Dalamud.Interface.Utility.Raii;
using ImGuiNET;
namespace ChatTwo.Ui.SettingsTabs;
@@ -39,6 +37,19 @@ internal sealed class Display : ISettingsTab
ImGuiUtil.OptionCheckbox(ref Mutable.HideInBattle, Language.Options_HideInBattle_Name, Language.Options_HideInBattle_Description);
ImGui.Spacing();
ImGuiUtil.OptionCheckbox(ref Mutable.HideWhenInactive, Language.Options_HideWhenInactive_Name, Language.Options_HideWhenInactive_Description);
ImGui.Spacing();
if (Mutable.HideWhenInactive)
{
ImGuiUtil.InputIntVertical(Language.Options_InactivityHideTimeout_Name,
Language.Options_InactivityHideTimeout_Description, ref Mutable.InactivityHideTimeout, 1, 10);
// Enforce a minimum of 2 seconds to avoid people soft locking
// themselves.
Mutable.InactivityHideTimeout = Math.Max(2, Mutable.InactivityHideTimeout);
ImGui.Spacing();
}
ImGuiUtil.OptionCheckbox(ref Mutable.PrettierTimestamps, Language.Options_PrettierTimestamps_Name, Language.Options_PrettierTimestamps_Description);
if (Mutable.PrettierTimestamps)