Compare commits
35 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2f383c3ebe | ||
|
|
5dfd859542 | ||
|
|
beb737b267 | ||
|
|
68c0bf1334 | ||
|
|
05daa59e40 | ||
|
|
c3a6f2c88d | ||
|
|
dc0265f614 | ||
|
|
ba0e1cea08 | ||
|
|
1dea9b713e | ||
|
|
23c57aedc4 | ||
|
|
15bf87feb4 | ||
|
|
9c0379631f | ||
|
|
44475fda50 | ||
|
|
071885b04c | ||
|
|
27c3231084 | ||
|
|
2b98bf6891 | ||
|
|
b6b8e7bddf | ||
|
|
9f8cc48e34 | ||
|
|
ae6013adf6 | ||
|
|
2b67f44788 | ||
|
|
ad74729c4a | ||
|
|
4f3a6a8205 | ||
|
|
71e80f5c48 | ||
|
|
77f667ccfd | ||
|
|
97e964473b | ||
|
|
d5d89a759e | ||
|
|
e5c87e5d68 | ||
|
|
5559c06d2b | ||
|
|
53bea001ba | ||
|
|
a401a18c04 | ||
|
|
213f6e9f6d | ||
|
|
4570c4b5f4 | ||
|
|
e6c1120323 | ||
|
|
0d35d04a20 | ||
|
|
5fb9ec7637 |
182
.gitea/lightless-tag-and-release.yml
Normal file
182
.gitea/lightless-tag-and-release.yml
Normal file
@@ -0,0 +1,182 @@
|
||||
name: Tag and Release Lightless
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ master ]
|
||||
|
||||
env:
|
||||
PLUGIN_NAME: LightlessSync
|
||||
DOTNET_VERSION: 9.x
|
||||
|
||||
jobs:
|
||||
tag-and-release:
|
||||
runs-on: ubuntu-22.04
|
||||
permissions:
|
||||
contents: write
|
||||
|
||||
steps:
|
||||
- name: Checkout Lightless
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: 0
|
||||
submodules: true
|
||||
|
||||
- name: Setup .NET 9 SDK
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: 9.x
|
||||
|
||||
- name: Download Dalamud
|
||||
run: |
|
||||
cd /
|
||||
mkdir -p root/.xlcore/dalamud/Hooks/dev
|
||||
curl -O https://goatcorp.github.io/dalamud-distrib/stg/latest.zip
|
||||
unzip latest.zip -d /root/.xlcore/dalamud/Hooks/dev
|
||||
|
||||
- name: Lets Build Lightless!
|
||||
run: |
|
||||
dotnet restore
|
||||
dotnet build --configuration Release --no-restore
|
||||
dotnet publish --configuration Release --no-build
|
||||
|
||||
- name: Get version
|
||||
id: package_version
|
||||
uses: KageKirin/get-csproj-version@v0
|
||||
with:
|
||||
file: LightlessSync/LightlessSync.csproj
|
||||
|
||||
- name: Display version
|
||||
run: |
|
||||
echo "Version: ${{ steps.package_version.outputs.version }}"
|
||||
|
||||
- name: Prepare Lightless Client
|
||||
run: |
|
||||
PUBLISH_PATH="/workspace/Lightless-Sync/LightlessClient/LightlessSync/bin/x64/Release/publish/"
|
||||
if [ -d "$PUBLISH_PATH" ]; then
|
||||
rm -rf "$PUBLISH_PATH"
|
||||
echo "Removed $PUBLISH_PATH"
|
||||
else
|
||||
echo "$PUBLISH_PATH does not exist, nothing to remove."
|
||||
fi
|
||||
|
||||
mkdir -p output
|
||||
(cd /workspace/Lightless-Sync/LightlessClient/LightlessSync/bin/x64/Release/ && zip -r $OLDPWD/output/LightlessClient.zip *)
|
||||
|
||||
- name: Create Git tag if not exists
|
||||
run: |
|
||||
tag="${{ steps.package_version.outputs.version }}"
|
||||
git fetch --tags
|
||||
if ! git tag -l "$tag" | grep -q "$tag"; then
|
||||
echo "Tag $tag does not exist. Creating and pushing..."
|
||||
git config user.name "GitHub Action"
|
||||
git config user.email "action@github.com"
|
||||
git tag "$tag"
|
||||
git push origin "$tag"
|
||||
else
|
||||
echo "Tag $tag already exists. Skipping tag creation."
|
||||
fi
|
||||
|
||||
- name: Create Release
|
||||
id: create_release
|
||||
run: |
|
||||
echo "=== Searching for existing release ${{ steps.package_version.outputs.version }}==="
|
||||
|
||||
release_id=$(curl -s -H "Authorization: token ${{ secrets.GITEA_TOKEN }}" \
|
||||
"https://git.lightless-sync.org/api/v1/repos/${GITHUB_REPOSITORY}/releases/tags/${{ steps.package_version.outputs.version }}" | jq -r .id)
|
||||
|
||||
if [ "$release_id" != "null" ]; then
|
||||
echo "=== Deleting existing release ${{ steps.package_version.outputs.version }}==="
|
||||
curl -X DELETE -H "Authorization: token ${{ secrets.GITEA_TOKEN }}" \
|
||||
"https://git.lightless-sync.org/api/v1/repos/${GITHUB_REPOSITORY}/releases/$release_id"
|
||||
fi
|
||||
|
||||
echo "=== Creating new release ${{ steps.package_version.outputs.version }}==="
|
||||
response=$(
|
||||
curl --fail-with-body -X POST \
|
||||
-H "Content-Type: application/json" \
|
||||
-H "Authorization: token ${{ secrets.GITEA_TOKEN }}" \
|
||||
-d '{
|
||||
"tag_name": "${{ steps.package_version.outputs.version }}",
|
||||
"name": "${{ steps.package_version.outputs.version }}",
|
||||
"draft": false,
|
||||
"prerelease": false
|
||||
}' \
|
||||
"https://git.lightless-sync.org/api/v1/repos/${GITHUB_REPOSITORY}/releases"
|
||||
)
|
||||
|
||||
release_id=$(echo "$response" | jq -r .id)
|
||||
echo "release_id=$release_id" >> "$GITHUB_OUTPUT"
|
||||
|
||||
- name: Upload Assets to release
|
||||
run: |
|
||||
curl --fail-with-body -s -X POST \
|
||||
-H "Authorization: token ${{ secrets.GITEA_TOKEN }}" \
|
||||
-F "attachment=@output/LightlessClient.zip" \
|
||||
"https://git.lightless-sync.org/api/v1/repos/${GITHUB_REPOSITORY}/releases/${{ steps.create_release.outputs.release_id }}/assets"
|
||||
|
||||
- name: Clone plugin hosting repo
|
||||
run: |
|
||||
mkdir LightlessSyncRepo
|
||||
cd LightlessSyncRepo
|
||||
git clone https://git.lightless-sync.org/${{ gitea.repository_owner }}/LightlessSync.git
|
||||
env:
|
||||
GIT_TERMINAL_PROMPT: 0
|
||||
|
||||
- name: Update plogonmaster.json with version
|
||||
env:
|
||||
VERSION: ${{ steps.package_version.outputs.version }}
|
||||
run: |
|
||||
set -e
|
||||
|
||||
pluginJsonPath="${PLUGIN_NAME}/bin/x64/Release/${PLUGIN_NAME}.json"
|
||||
repoJsonPath="LightlessSyncRepo/LightlessSync/plogonmaster.json"
|
||||
version="${VERSION}"
|
||||
downloadUrl="https://git.lightless-sync.org/${{ gitea.repository_owner }}/LightlessClient/releases/download/$version/LightlessClient.zip"
|
||||
|
||||
# Read plugin JSON
|
||||
pluginJson=$(cat "$pluginJsonPath")
|
||||
internalName=$(jq -r '.InternalName' <<< "$pluginJson")
|
||||
dalamudApiLevel=$(jq -r '.DalamudApiLevel' <<< "$pluginJson")
|
||||
|
||||
# Read repo JSON (force array if not already)
|
||||
repoJsonRaw=$(cat "$repoJsonPath")
|
||||
if echo "$repoJsonRaw" | jq 'type' | grep -q '"array"'; then
|
||||
repoJson="$repoJsonRaw"
|
||||
else
|
||||
repoJson="[$repoJsonRaw]"
|
||||
fi
|
||||
|
||||
# Update matching plugin entry
|
||||
updatedRepoJson=$(jq \
|
||||
--arg internalName "$internalName" \
|
||||
--arg dalamudApiLevel "$dalamudApiLevel" \
|
||||
--arg version "$version" \
|
||||
--arg downloadUrl "$downloadUrl" \
|
||||
'
|
||||
map(
|
||||
if .InternalName == $internalName
|
||||
then
|
||||
.DalamudApiLevel = $dalamudApiLevel
|
||||
| .AssemblyVersion = $version
|
||||
| .DownloadLinkInstall = $downloadUrl
|
||||
| .DownloadLinkTesting = $downloadUrl
|
||||
| .DownloadLinkUpdate = $downloadUrl
|
||||
else
|
||||
.
|
||||
end
|
||||
)
|
||||
' <<< "$repoJson")
|
||||
|
||||
# Write back to file
|
||||
echo "$updatedRepoJson" > "$repoJsonPath"
|
||||
# Output the content of the file
|
||||
cat "$repoJsonPath"
|
||||
|
||||
- name: Commit and push to LightlessSync
|
||||
run: |
|
||||
cd LightlessSyncRepo/LightlessSync
|
||||
git config user.name "github-actions"
|
||||
git config user.email "github-actions@github.com"
|
||||
git add .
|
||||
git diff-index --quiet HEAD || git commit -m "Update ${{ env.PLUGIN_NAME }} to ${{ steps.package_version.outputs.version }}"
|
||||
git push https://x-access-token:${{ secrets.AUTOMATION_TOKEN }}@git.lightless-sync.org/${{ gitea.repository_owner }}/LightlessSync.git HEAD:main
|
||||
140
.github/workflows/lightless-tag-and-release.yml
vendored
Normal file
140
.github/workflows/lightless-tag-and-release.yml
vendored
Normal file
@@ -0,0 +1,140 @@
|
||||
name: Tag and Release Lightless
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ master ]
|
||||
|
||||
env:
|
||||
PLUGIN_NAME: LightlessSync
|
||||
DOTNET_VERSION: 9.x
|
||||
|
||||
jobs:
|
||||
tag-and-release:
|
||||
runs-on: windows-2022
|
||||
permissions:
|
||||
contents: write
|
||||
|
||||
steps:
|
||||
- name: Checkout Lightless
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: 0
|
||||
submodules: true
|
||||
|
||||
- name: Setup .NET 9 SDK
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: 9.x
|
||||
|
||||
- name: Download Dalamud
|
||||
run: |
|
||||
Invoke-WebRequest -Uri https://goatcorp.github.io/dalamud-distrib/stg/latest.zip -OutFile latest.zip
|
||||
Expand-Archive -Force latest.zip "$env:AppData\XIVLauncher\addon\Hooks\dev"
|
||||
|
||||
- name: Lets Build Lightless!
|
||||
run: |
|
||||
dotnet restore
|
||||
dotnet build --configuration Release --no-restore
|
||||
dotnet publish --configuration Release --no-build
|
||||
|
||||
- name: Get version
|
||||
id: package_version
|
||||
uses: KageKirin/get-csproj-version@v0
|
||||
with:
|
||||
file: LightlessSync/LightlessSync.csproj
|
||||
|
||||
- name: Display version
|
||||
run: |
|
||||
echo "Version: ${{ steps.package_version.outputs.version }}"
|
||||
|
||||
- name: Prepare Lightless Client
|
||||
run: |
|
||||
$publishPath = "${{ env.PLUGIN_NAME }}/bin/x64/Release/publish"
|
||||
if (Test-Path $publishPath) {
|
||||
Remove-Item -Recurse -Force $publishPath
|
||||
Write-Host "Removed $publishPath"
|
||||
} else {
|
||||
Write-Host "$publishPath does not exist, nothing to remove."
|
||||
}
|
||||
mkdir output
|
||||
Compress-Archive -Path ${{ env.PLUGIN_NAME }}/bin/x64/Release/* -DestinationPath output/LightlessClient.zip
|
||||
|
||||
- name: Create Git tag if not exists
|
||||
shell: pwsh
|
||||
run: |
|
||||
$tag = "${{ steps.package_version.outputs.version }}"
|
||||
git fetch --tags
|
||||
if (-not (git tag -l $tag)) {
|
||||
Write-Host "Tag $tag does not exist. Creating and pushing..."
|
||||
git config user.name "GitHub Action"
|
||||
git config user.email "action@github.com"
|
||||
git tag $tag
|
||||
git push origin $tag
|
||||
} else {
|
||||
Write-Host "Tag $tag already exists. Skipping tag creation."
|
||||
}
|
||||
|
||||
- name: Create GitHub Release
|
||||
uses: softprops/action-gh-release@v2
|
||||
with:
|
||||
tag_name: ${{ steps.package_version.outputs.version }}
|
||||
name: ${{ steps.package_version.outputs.version }}
|
||||
draft: false
|
||||
prerelease: false
|
||||
files: output/LightlessClient.zip
|
||||
|
||||
- name: Clone plugin hosting repo
|
||||
run: |
|
||||
mkdir LightlessSyncRepo
|
||||
cd LightlessSyncRepo
|
||||
git clone https://github.com/${{ github.repository_owner }}/LightlessSync.git
|
||||
env:
|
||||
GIT_TERMINAL_PROMPT: 0
|
||||
|
||||
- name: Update plogonmaster.json with version
|
||||
shell: pwsh
|
||||
env:
|
||||
VERSION: ${{ steps.package_version.outputs.version }}
|
||||
run: |
|
||||
$pluginJsonPath = "${{ env.PLUGIN_NAME }}/bin/x64/Release/${{ env.PLUGIN_NAME }}.json"
|
||||
$pluginJson = Get-Content $pluginJsonPath | ConvertFrom-Json
|
||||
$repoJsonPath = "LightlessSyncRepo/LightlessSync/plogonmaster.json"
|
||||
$repoJsonRaw = Get-Content $repoJsonPath -Raw
|
||||
$repoJson = $repoJsonRaw | ConvertFrom-Json
|
||||
$version = $env:VERSION
|
||||
$downloadUrl = "https://github.com/${{ github.repository_owner }}/LightlessClient/releases/download/$version/LightlessClient.zip"
|
||||
|
||||
if (-not ($repoJson -is [System.Collections.IEnumerable])) {
|
||||
$repoJson = @($repoJson)
|
||||
}
|
||||
|
||||
foreach ($plugin in $repoJson) {
|
||||
if ($plugin.InternalName -eq $pluginJson.InternalName) {
|
||||
$plugin.DalamudApiLevel = $pluginJson.DalamudApiLevel
|
||||
$plugin.AssemblyVersion = $version
|
||||
$plugin.DownloadLinkInstall = $downloadUrl
|
||||
$plugin.DownloadLinkTesting = $downloadUrl
|
||||
$plugin.DownloadLinkUpdate = $downloadUrl
|
||||
}
|
||||
}
|
||||
|
||||
$repoJson | ConvertTo-Json -Depth 100 | Set-Content $repoJsonPath
|
||||
|
||||
# Convert to JSON and force array brackets if necessary
|
||||
$repoJsonString = $repoJson | ConvertTo-Json -Depth 100
|
||||
|
||||
# If the output is not an array, wrap it manually
|
||||
if ($repoJsonString.Trim().StartsWith('{')) {
|
||||
$repoJsonString = "[$repoJsonString]"
|
||||
}
|
||||
|
||||
$repoJsonString | Set-Content $repoJsonPath
|
||||
|
||||
- name: Commit and push to LightlessSync
|
||||
run: |
|
||||
cd LightlessSyncRepo/LightlessSync
|
||||
git config user.name "github-actions"
|
||||
git config user.email "github-actions@github.com"
|
||||
git add .
|
||||
git commit -m "Update ${{ env.PLUGIN_NAME }} to ${{ steps.package_version.outputs.version }}"
|
||||
git push https://x-access-token:${{ secrets.LIGHTLESS_TOKEN }}@github.com/${{ github.repository_owner }}/LightlessSync.git HEAD:main
|
||||
@@ -27,9 +27,9 @@ public sealed class IpcCallerMoodles : IIpcCaller
|
||||
|
||||
_moodlesApiVersion = pi.GetIpcSubscriber<int>("Moodles.Version");
|
||||
_moodlesOnChange = pi.GetIpcSubscriber<IPlayerCharacter, object>("Moodles.StatusManagerModified");
|
||||
_moodlesGetStatus = pi.GetIpcSubscriber<nint, string>("Moodles.GetStatusManagerByPtr");
|
||||
_moodlesSetStatus = pi.GetIpcSubscriber<nint, string, object>("Moodles.SetStatusManagerByPtr");
|
||||
_moodlesRevertStatus = pi.GetIpcSubscriber<nint, object>("Moodles.ClearStatusManagerByPtr");
|
||||
_moodlesGetStatus = pi.GetIpcSubscriber<nint, string>("Moodles.GetStatusManagerByPtrV2");
|
||||
_moodlesSetStatus = pi.GetIpcSubscriber<nint, string, object>("Moodles.SetStatusManagerByPtrV2");
|
||||
_moodlesRevertStatus = pi.GetIpcSubscriber<nint, object>("Moodles.ClearStatusManagerByPtrV2");
|
||||
|
||||
_moodlesOnChange.Subscribe(OnMoodlesChange);
|
||||
|
||||
@@ -47,7 +47,7 @@ public sealed class IpcCallerMoodles : IIpcCaller
|
||||
{
|
||||
try
|
||||
{
|
||||
APIAvailable = _moodlesApiVersion.InvokeFunc() == 1;
|
||||
APIAvailable = _moodlesApiVersion.InvokeFunc() == 3;
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
||||
@@ -30,12 +30,12 @@ public sealed class IpcCallerPetNames : IIpcCaller
|
||||
_dalamudUtil = dalamudUtil;
|
||||
_lightlessMediator = lightlessMediator;
|
||||
|
||||
_petnamesReady = pi.GetIpcSubscriber<object>("PetRenamer.Ready");
|
||||
_petnamesDisposing = pi.GetIpcSubscriber<object>("PetRenamer.Disposing");
|
||||
_petnamesReady = pi.GetIpcSubscriber<object>("PetRenamer.OnReady");
|
||||
_petnamesDisposing = pi.GetIpcSubscriber<object>("PetRenamer.OnDisposing");
|
||||
_apiVersion = pi.GetIpcSubscriber<(uint, uint)>("PetRenamer.ApiVersion");
|
||||
_enabled = pi.GetIpcSubscriber<bool>("PetRenamer.Enabled");
|
||||
_enabled = pi.GetIpcSubscriber<bool>("PetRenamer.IsEnabled");
|
||||
|
||||
_playerDataChanged = pi.GetIpcSubscriber<string, object>("PetRenamer.PlayerDataChanged");
|
||||
_playerDataChanged = pi.GetIpcSubscriber<string, object>("PetRenamer.OnPlayerDataChanged");
|
||||
_getPlayerData = pi.GetIpcSubscriber<string>("PetRenamer.GetPlayerData");
|
||||
_setPlayerData = pi.GetIpcSubscriber<string, object>("PetRenamer.SetPlayerData");
|
||||
_clearPlayerData = pi.GetIpcSubscriber<ushort, object>("PetRenamer.ClearPlayerData");
|
||||
@@ -56,7 +56,7 @@ public sealed class IpcCallerPetNames : IIpcCaller
|
||||
APIAvailable = _enabled?.InvokeFunc() ?? false;
|
||||
if (APIAvailable)
|
||||
{
|
||||
APIAvailable = _apiVersion?.InvokeFunc() is { Item1: 3, Item2: >= 1 };
|
||||
APIAvailable = _apiVersion?.InvokeFunc() is { Item1: 4, Item2: >= 0 };
|
||||
}
|
||||
}
|
||||
catch
|
||||
@@ -84,7 +84,7 @@ public sealed class IpcCallerPetNames : IIpcCaller
|
||||
{
|
||||
string localNameData = _getPlayerData.InvokeFunc();
|
||||
return string.IsNullOrEmpty(localNameData) ? string.Empty : localNameData;
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.LogWarning(e, "Could not obtain Pet Nicknames data");
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
using LightlessSync.LightlessConfiguration.Configurations;
|
||||
using LightlessSync.LightlessConfiguration;
|
||||
using Microsoft.Extensions.Hosting;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.Reflection;
|
||||
@@ -13,6 +13,8 @@ public class LightlessConfig : ILightlessConfiguration
|
||||
public bool EnableDtrEntry { get; set; } = false;
|
||||
public bool ShowUidInDtrTooltip { get; set; } = true;
|
||||
public bool PreferNoteInDtrTooltip { get; set; } = false;
|
||||
public bool IsNameplateColorsEnabled { get; set; } = false;
|
||||
public DtrEntry.Colors NameplateColors { get; set; } = new(Foreground: 0xE69138u, Glow: 0xFFBA47u);
|
||||
public bool UseColorsInDtr { get; set; } = true;
|
||||
public DtrEntry.Colors DtrColorsDefault { get; set; } = default;
|
||||
public DtrEntry.Colors DtrColorsNotConnected { get; set; } = new(Glow: 0x0428FFu);
|
||||
@@ -60,4 +62,6 @@ public class LightlessConfig : ILightlessConfiguration
|
||||
public int Version { get; set; } = 1;
|
||||
public NotificationLocation WarningNotification { get; set; } = NotificationLocation.Both;
|
||||
public bool UseFocusTarget { get; set; } = false;
|
||||
public bool overrideFriendColor { get; set; } = false;
|
||||
public bool overridePartyColor { get; set; } = false;
|
||||
}
|
||||
@@ -1,5 +1,4 @@
|
||||
using LightlessSync.API.Data.Enum;
|
||||
using LightlessSync.LightlessConfiguration.Configurations;
|
||||
|
||||
namespace LightlessSync.LightlessConfiguration.Configurations;
|
||||
|
||||
@@ -151,6 +151,7 @@ public class LightlessPlugin : MediatorSubscriberBase, IHostedService
|
||||
_runtimeServiceScope.ServiceProvider.GetRequiredService<TransientResourceManager>();
|
||||
_runtimeServiceScope.ServiceProvider.GetRequiredService<VisibleUserDataDistributor>();
|
||||
_runtimeServiceScope.ServiceProvider.GetRequiredService<NotificationService>();
|
||||
_runtimeServiceScope.ServiceProvider.GetRequiredService<NameplateService>();
|
||||
|
||||
#if !DEBUG
|
||||
if (_lightlessConfigService.Current.LogLevel != LogLevel.Information)
|
||||
@@ -3,7 +3,7 @@
|
||||
<PropertyGroup>
|
||||
<Authors></Authors>
|
||||
<Company></Company>
|
||||
<Version>1.11.1</Version>
|
||||
<Version>1.11.5</Version>
|
||||
<Description></Description>
|
||||
<Copyright></Copyright>
|
||||
<PackageProjectUrl>https://github.com/Light-Public-Syncshells/LightlessClient</PackageProjectUrl>
|
||||
|
||||
@@ -8,7 +8,6 @@ using LightlessSync.PlayerData.Handlers;
|
||||
using LightlessSync.Services;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using CharacterData = LightlessSync.PlayerData.Data.CharacterData;
|
||||
|
||||
namespace LightlessSync.PlayerData.Factories;
|
||||
|
||||
|
||||
@@ -119,6 +119,7 @@ public sealed class PairHandler : DisposableMediatorSubscriberBase
|
||||
Mediator.Publish(new EventMessage(new Event(PlayerName, Pair.UserData, nameof(PairHandler),
|
||||
EventSeverity.Informational, text)));
|
||||
Mediator.Publish(new RefreshUiMessage());
|
||||
Mediator.Publish(new VisibilityChange());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,6 +48,7 @@ public class Pair
|
||||
public long LastAppliedDataTris { get; set; } = -1;
|
||||
public long LastAppliedApproximateVRAMBytes { get; set; } = -1;
|
||||
public string Ident => _onlineUserIdentDto?.Ident ?? string.Empty;
|
||||
public uint PlayerCharacterId => CachedPlayer?.PlayerCharacterId ?? uint.MaxValue;
|
||||
|
||||
public UserData UserData => UserPair.User;
|
||||
|
||||
@@ -71,8 +72,8 @@ public class Pair
|
||||
Name = openProfileSeString,
|
||||
OnClicked = (a) => _mediator.Publish(new ProfileOpenStandaloneMessage(this)),
|
||||
UseDefaultPrefix = false,
|
||||
PrefixChar = 'M',
|
||||
PrefixColor = 526
|
||||
PrefixChar = 'L',
|
||||
PrefixColor = 708
|
||||
});
|
||||
|
||||
args.AddMenuItem(new MenuItem()
|
||||
@@ -80,8 +81,8 @@ public class Pair
|
||||
Name = reapplyDataSeString,
|
||||
OnClicked = (a) => ApplyLastReceivedData(forced: true),
|
||||
UseDefaultPrefix = false,
|
||||
PrefixChar = 'M',
|
||||
PrefixColor = 526
|
||||
PrefixChar = 'L',
|
||||
PrefixColor = 708
|
||||
});
|
||||
|
||||
args.AddMenuItem(new MenuItem()
|
||||
@@ -89,8 +90,8 @@ public class Pair
|
||||
Name = changePermissions,
|
||||
OnClicked = (a) => _mediator.Publish(new OpenPermissionWindow(this)),
|
||||
UseDefaultPrefix = false,
|
||||
PrefixChar = 'M',
|
||||
PrefixColor = 526
|
||||
PrefixChar = 'L',
|
||||
PrefixColor = 708
|
||||
});
|
||||
|
||||
args.AddMenuItem(new MenuItem()
|
||||
@@ -98,8 +99,8 @@ public class Pair
|
||||
Name = cyclePauseState,
|
||||
OnClicked = (a) => _mediator.Publish(new CyclePauseMessage(UserData)),
|
||||
UseDefaultPrefix = false,
|
||||
PrefixChar = 'M',
|
||||
PrefixColor = 526
|
||||
PrefixChar = 'L',
|
||||
PrefixColor = 708
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using Dalamud.Game.ClientState.Objects;
|
||||
using Dalamud.Game;
|
||||
using Dalamud.Game.ClientState.Objects;
|
||||
using Dalamud.Interface.ImGuiFileDialog;
|
||||
using Dalamud.Interface.Windowing;
|
||||
using Dalamud.Plugin;
|
||||
@@ -12,6 +13,7 @@ using LightlessSync.PlayerData.Factories;
|
||||
using LightlessSync.PlayerData.Pairs;
|
||||
using LightlessSync.PlayerData.Services;
|
||||
using LightlessSync.Services;
|
||||
using LightlessSync.Services.CharaData;
|
||||
using LightlessSync.Services.Events;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using LightlessSync.Services.ServerConfiguration;
|
||||
@@ -28,8 +30,6 @@ using Microsoft.Extensions.Logging;
|
||||
using NReco.Logging.File;
|
||||
using System.Net.Http.Headers;
|
||||
using System.Reflection;
|
||||
using LightlessSync.Services.CharaData;
|
||||
using Dalamud.Game;
|
||||
|
||||
namespace LightlessSync;
|
||||
|
||||
@@ -41,7 +41,7 @@ public sealed class Plugin : IDalamudPlugin
|
||||
IFramework framework, IObjectTable objectTable, IClientState clientState, ICondition condition, IChatGui chatGui,
|
||||
IGameGui gameGui, IDtrBar dtrBar, IPluginLog pluginLog, ITargetManager targetManager, INotificationManager notificationManager,
|
||||
ITextureProvider textureProvider, IContextMenu contextMenu, IGameInteropProvider gameInteropProvider, IGameConfig gameConfig,
|
||||
ISigScanner sigScanner)
|
||||
ISigScanner sigScanner, INamePlateGui namePlateGui)
|
||||
{
|
||||
if (!Directory.Exists(pluginInterface.ConfigDirectory.FullName))
|
||||
Directory.CreateDirectory(pluginInterface.ConfigDirectory.FullName);
|
||||
@@ -130,6 +130,7 @@ public sealed class Plugin : IDalamudPlugin
|
||||
s.GetRequiredService<CharaDataManager>(),
|
||||
s.GetRequiredService<LightlessMediator>()));
|
||||
collection.AddSingleton<SelectPairForTagUi>();
|
||||
collection.AddSingleton<RenameTagUi>();
|
||||
collection.AddSingleton((s) => new EventAggregator(pluginInterface.ConfigDirectory.FullName,
|
||||
s.GetRequiredService<ILogger<EventAggregator>>(), s.GetRequiredService<LightlessMediator>()));
|
||||
collection.AddSingleton((s) => new DalamudUtilService(s.GetRequiredService<ILogger<DalamudUtilService>>(),
|
||||
@@ -228,6 +229,8 @@ public sealed class Plugin : IDalamudPlugin
|
||||
s.GetRequiredService<CacheMonitor>(), s.GetRequiredService<FileDialogManager>(), s.GetRequiredService<LightlessConfigService>(), s.GetRequiredService<DalamudUtilService>(),
|
||||
pluginInterface, textureProvider, s.GetRequiredService<Dalamud.Localization>(), s.GetRequiredService<ServerConfigurationManager>(), s.GetRequiredService<TokenProvider>(),
|
||||
s.GetRequiredService<LightlessMediator>()));
|
||||
collection.AddScoped((s) => new NameplateService(s.GetRequiredService<ILogger<NameplateService>>(), s.GetRequiredService<LightlessConfigService>(), namePlateGui, clientState,
|
||||
s.GetRequiredService<PairManager>(), s.GetRequiredService<LightlessMediator>()));
|
||||
|
||||
collection.AddHostedService(p => p.GetRequiredService<ConfigurationSaveService>());
|
||||
collection.AddHostedService(p => p.GetRequiredService<LightlessMediator>());
|
||||
|
||||
@@ -1,10 +1,4 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace LightlessSync.Services.CharaData
|
||||
namespace LightlessSync.Services.CharaData
|
||||
{
|
||||
internal class CharaDataTogetherManager
|
||||
{
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
using Dalamud.Utility;
|
||||
using Lumina.Excel.Sheets;
|
||||
using LightlessSync.API.Dto.CharaData;
|
||||
using Lumina.Excel.Sheets;
|
||||
using System.Globalization;
|
||||
using System.Numerics;
|
||||
using System.Text;
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
using Lumina.Data.Files;
|
||||
using LightlessSync.API.Data;
|
||||
using LightlessSync.API.Data;
|
||||
using LightlessSync.API.Data.Enum;
|
||||
using LightlessSync.FileCache;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using LightlessSync.UI;
|
||||
using LightlessSync.Utils;
|
||||
using Lumina.Data.Files;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
namespace LightlessSync.Services;
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
using Dalamud.Game;
|
||||
using Dalamud.Game.ClientState.Conditions;
|
||||
using Dalamud.Game.ClientState.Conditions;
|
||||
using Dalamud.Game.ClientState.Objects;
|
||||
using Dalamud.Game.ClientState.Objects.SubKinds;
|
||||
using Dalamud.Game.ClientState.Objects.Types;
|
||||
@@ -10,13 +9,13 @@ using FFXIVClientStructs.FFXIV.Client.Game.Character;
|
||||
using FFXIVClientStructs.FFXIV.Client.Game.Control;
|
||||
using FFXIVClientStructs.FFXIV.Client.Graphics.Scene;
|
||||
using FFXIVClientStructs.FFXIV.Client.UI.Agent;
|
||||
using Lumina.Excel.Sheets;
|
||||
using LightlessSync.API.Dto.CharaData;
|
||||
using LightlessSync.Interop;
|
||||
using LightlessSync.LightlessConfiguration;
|
||||
using LightlessSync.PlayerData.Handlers;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using LightlessSync.Utils;
|
||||
using Lumina.Excel.Sheets;
|
||||
using Microsoft.Extensions.Hosting;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.Numerics;
|
||||
@@ -135,7 +134,7 @@ public class DalamudUtilService : IHostedService, IMediatorSubscriber
|
||||
_cid = RebuildCID();
|
||||
}
|
||||
|
||||
private Lazy<ulong> RebuildCID() => new(GetCID);
|
||||
private Lazy<ulong> RebuildCID() => new(GetCID);
|
||||
|
||||
public bool IsWine { get; init; }
|
||||
|
||||
|
||||
80
LightlessSync/Services/LightlessProfileManager.cs
Normal file
80
LightlessSync/Services/LightlessProfileManager.cs
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -93,5 +93,7 @@ public record GPoseLobbyReceiveCharaData(CharaDataDownloadDto CharaDataDownloadD
|
||||
public record GPoseLobbyReceivePoseData(UserData UserData, PoseData PoseData) : MessageBase;
|
||||
public record GPoseLobbyReceiveWorldData(UserData UserData, WorldData WorldData) : MessageBase;
|
||||
public record OpenCharaDataHubWithFilterMessage(UserData UserData) : MessageBase;
|
||||
|
||||
public record VisibilityChange : MessageBase;
|
||||
#pragma warning restore S2094
|
||||
#pragma warning restore MA0048 // File name must match type name
|
||||
91
LightlessSync/Services/NameplateService.cs
Normal file
91
LightlessSync/Services/NameplateService.cs
Normal file
@@ -0,0 +1,91 @@
|
||||
using Dalamud.Game.ClientState.Objects.Enums;
|
||||
using Dalamud.Game.Gui.NamePlate;
|
||||
using Dalamud.Game.Text.SeStringHandling;
|
||||
using Dalamud.Plugin.Services;
|
||||
using Dalamud.Utility;
|
||||
using LightlessSync.LightlessConfiguration;
|
||||
using LightlessSync.PlayerData.Pairs;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using LightlessSync.UI;
|
||||
using Microsoft.Extensions.Logging;
|
||||
namespace LightlessSync.Services;
|
||||
|
||||
public class NameplateService : DisposableMediatorSubscriberBase
|
||||
{
|
||||
private readonly LightlessConfigService _configService;
|
||||
private readonly IClientState _clientState;
|
||||
private readonly INamePlateGui _namePlateGui;
|
||||
private readonly PairManager _pairManager;
|
||||
|
||||
public NameplateService(ILogger<NameplateService> logger,
|
||||
LightlessConfigService configService,
|
||||
INamePlateGui namePlateGui,
|
||||
IClientState clientState,
|
||||
PairManager pairManager,
|
||||
LightlessMediator lightlessMediator) : base(logger, lightlessMediator)
|
||||
{
|
||||
_configService = configService;
|
||||
_namePlateGui = namePlateGui;
|
||||
_clientState = clientState;
|
||||
_pairManager = pairManager;
|
||||
_namePlateGui.OnNamePlateUpdate += OnNamePlateUpdate;
|
||||
_namePlateGui.RequestRedraw();
|
||||
Mediator.Subscribe<VisibilityChange>(this, (_) => _namePlateGui.RequestRedraw());
|
||||
|
||||
}
|
||||
|
||||
private void OnNamePlateUpdate(INamePlateUpdateContext context, IReadOnlyList<INamePlateUpdateHandler> handlers)
|
||||
{
|
||||
|
||||
if (!_configService.Current.IsNameplateColorsEnabled && !_clientState.IsPvPExcludingDen) return;
|
||||
var visibleUsersIds = _pairManager.GetOnlineUserPairs().Where(u => u.IsVisible && u.PlayerCharacterId != uint.MaxValue).Select(u => (ulong)u.PlayerCharacterId).ToHashSet();
|
||||
var colors = _configService.Current.NameplateColors;
|
||||
|
||||
foreach (var handler in handlers)
|
||||
{
|
||||
var playerCharacter = handler.PlayerCharacter;
|
||||
if (playerCharacter == null) { continue; }
|
||||
var isInParty = playerCharacter.StatusFlags.HasFlag(StatusFlags.PartyMember);
|
||||
var isFriend = playerCharacter.StatusFlags.HasFlag(StatusFlags.Friend);
|
||||
bool partyColorAllowed = (_configService.Current.overridePartyColor && isInParty);
|
||||
bool friendColorAllowed = (_configService.Current.overrideFriendColor && isFriend);
|
||||
|
||||
if (visibleUsersIds.Contains(handler.GameObjectId) &&
|
||||
!(
|
||||
(isInParty && !partyColorAllowed) ||
|
||||
(isFriend && !friendColorAllowed)
|
||||
))
|
||||
{
|
||||
handler.NameParts.TextWrap = CreateTextWrap(colors);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void RequestRedraw()
|
||||
{
|
||||
_namePlateGui.RequestRedraw();
|
||||
}
|
||||
|
||||
private static (SeString, SeString) CreateTextWrap(DtrEntry.Colors color)
|
||||
{
|
||||
var left = new Lumina.Text.SeStringBuilder();
|
||||
var right = new Lumina.Text.SeStringBuilder();
|
||||
|
||||
left.PushColorRgba(color.Foreground);
|
||||
right.PopColor();
|
||||
|
||||
left.PushEdgeColorRgba(color.Glow);
|
||||
right.PopEdgeColor();
|
||||
|
||||
return (left.ToReadOnlySeString().ToDalamudString(), right.ToReadOnlySeString().ToDalamudString());
|
||||
}
|
||||
|
||||
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
base.Dispose(disposing);
|
||||
_namePlateGui.OnNamePlateUpdate -= OnNamePlateUpdate;
|
||||
_namePlateGui.RequestRedraw();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,187 +8,187 @@ namespace LightlessSync.UI;
|
||||
|
||||
internal sealed partial class CharaDataHubUi
|
||||
{
|
||||
private static string GetAccessTypeString(AccessTypeDto dto) => dto switch
|
||||
{
|
||||
AccessTypeDto.AllPairs => "All Pairs",
|
||||
AccessTypeDto.ClosePairs => "Direct Pairs",
|
||||
AccessTypeDto.Individuals => "Specified",
|
||||
AccessTypeDto.Public => "Everyone"
|
||||
};
|
||||
private static string GetAccessTypeString(AccessTypeDto dto) => dto switch
|
||||
{
|
||||
AccessTypeDto.AllPairs => "All Pairs",
|
||||
AccessTypeDto.ClosePairs => "Direct Pairs",
|
||||
AccessTypeDto.Individuals => "Specified",
|
||||
AccessTypeDto.Public => "Everyone"
|
||||
};
|
||||
|
||||
private static string GetShareTypeString(ShareTypeDto dto) => dto switch
|
||||
{
|
||||
ShareTypeDto.Private => "Code Only",
|
||||
ShareTypeDto.Shared => "Shared"
|
||||
};
|
||||
private static string GetShareTypeString(ShareTypeDto dto) => dto switch
|
||||
{
|
||||
ShareTypeDto.Private => "Code Only",
|
||||
ShareTypeDto.Shared => "Shared"
|
||||
};
|
||||
|
||||
private static string GetWorldDataTooltipText(PoseEntryExtended poseEntry)
|
||||
{
|
||||
if (!poseEntry.HasWorldData) return "This Pose has no world data attached.";
|
||||
return poseEntry.WorldDataDescriptor;
|
||||
}
|
||||
private static string GetWorldDataTooltipText(PoseEntryExtended poseEntry)
|
||||
{
|
||||
if (!poseEntry.HasWorldData) return "This Pose has no world data attached.";
|
||||
return poseEntry.WorldDataDescriptor;
|
||||
}
|
||||
|
||||
|
||||
private void GposeMetaInfoAction(Action<CharaDataMetaInfoExtendedDto?> gposeActionDraw, string actionDescription, CharaDataMetaInfoExtendedDto? dto, bool hasValidGposeTarget, bool isSpawning)
|
||||
{
|
||||
StringBuilder sb = new StringBuilder();
|
||||
private void GposeMetaInfoAction(Action<CharaDataMetaInfoExtendedDto?> gposeActionDraw, string actionDescription, CharaDataMetaInfoExtendedDto? dto, bool hasValidGposeTarget, bool isSpawning)
|
||||
{
|
||||
StringBuilder sb = new StringBuilder();
|
||||
|
||||
sb.AppendLine(actionDescription);
|
||||
bool isDisabled = false;
|
||||
sb.AppendLine(actionDescription);
|
||||
bool isDisabled = false;
|
||||
|
||||
void AddErrorStart(StringBuilder sb)
|
||||
{
|
||||
sb.Append(UiSharedService.TooltipSeparator);
|
||||
sb.AppendLine("Cannot execute:");
|
||||
}
|
||||
void AddErrorStart(StringBuilder sb)
|
||||
{
|
||||
sb.Append(UiSharedService.TooltipSeparator);
|
||||
sb.AppendLine("Cannot execute:");
|
||||
}
|
||||
|
||||
if (dto == null)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- No metainfo present");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!dto?.CanBeDownloaded ?? false)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Character is not downloadable");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!_uiSharedService.IsInGpose)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires to be in GPose");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!hasValidGposeTarget && !isSpawning)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires a valid GPose target");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (isSpawning && !_charaDataManager.BrioAvailable)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires Brio to be installed.");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (dto == null)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- No metainfo present");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!dto?.CanBeDownloaded ?? false)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Character is not downloadable");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!_uiSharedService.IsInGpose)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires to be in GPose");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!hasValidGposeTarget && !isSpawning)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires a valid GPose target");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (isSpawning && !_charaDataManager.BrioAvailable)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires Brio to be installed.");
|
||||
isDisabled = true;
|
||||
}
|
||||
|
||||
using (ImRaii.Group())
|
||||
{
|
||||
using var dis = ImRaii.Disabled(isDisabled);
|
||||
gposeActionDraw.Invoke(dto);
|
||||
}
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
UiSharedService.AttachToolTip(sb.ToString());
|
||||
}
|
||||
}
|
||||
using (ImRaii.Group())
|
||||
{
|
||||
using var dis = ImRaii.Disabled(isDisabled);
|
||||
gposeActionDraw.Invoke(dto);
|
||||
}
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
UiSharedService.AttachToolTip(sb.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
private void GposePoseAction(Action poseActionDraw, string poseDescription, bool hasValidGposeTarget)
|
||||
{
|
||||
StringBuilder sb = new StringBuilder();
|
||||
private void GposePoseAction(Action poseActionDraw, string poseDescription, bool hasValidGposeTarget)
|
||||
{
|
||||
StringBuilder sb = new StringBuilder();
|
||||
|
||||
sb.AppendLine(poseDescription);
|
||||
bool isDisabled = false;
|
||||
sb.AppendLine(poseDescription);
|
||||
bool isDisabled = false;
|
||||
|
||||
void AddErrorStart(StringBuilder sb)
|
||||
{
|
||||
sb.Append(UiSharedService.TooltipSeparator);
|
||||
sb.AppendLine("Cannot execute:");
|
||||
}
|
||||
void AddErrorStart(StringBuilder sb)
|
||||
{
|
||||
sb.Append(UiSharedService.TooltipSeparator);
|
||||
sb.AppendLine("Cannot execute:");
|
||||
}
|
||||
|
||||
if (!_uiSharedService.IsInGpose)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires to be in GPose");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!hasValidGposeTarget)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires a valid GPose target");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!_charaDataManager.BrioAvailable)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires Brio to be installed.");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!_uiSharedService.IsInGpose)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires to be in GPose");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!hasValidGposeTarget)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires a valid GPose target");
|
||||
isDisabled = true;
|
||||
}
|
||||
if (!_charaDataManager.BrioAvailable)
|
||||
{
|
||||
if (!isDisabled) AddErrorStart(sb);
|
||||
sb.AppendLine("- Requires Brio to be installed.");
|
||||
isDisabled = true;
|
||||
}
|
||||
|
||||
using (ImRaii.Group())
|
||||
{
|
||||
using var dis = ImRaii.Disabled(isDisabled);
|
||||
poseActionDraw.Invoke();
|
||||
}
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
UiSharedService.AttachToolTip(sb.ToString());
|
||||
}
|
||||
}
|
||||
using (ImRaii.Group())
|
||||
{
|
||||
using var dis = ImRaii.Disabled(isDisabled);
|
||||
poseActionDraw.Invoke();
|
||||
}
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
UiSharedService.AttachToolTip(sb.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
private void SetWindowSizeConstraints(bool? inGposeTab = null)
|
||||
{
|
||||
SizeConstraints = new()
|
||||
{
|
||||
MinimumSize = new((inGposeTab ?? false) ? 400 : 1000, 500),
|
||||
MaximumSize = new((inGposeTab ?? false) ? 400 : 1000, 2000)
|
||||
};
|
||||
}
|
||||
private void SetWindowSizeConstraints(bool? inGposeTab = null)
|
||||
{
|
||||
SizeConstraints = new()
|
||||
{
|
||||
MinimumSize = new((inGposeTab ?? false) ? 400 : 1000, 500),
|
||||
MaximumSize = new((inGposeTab ?? false) ? 400 : 1000, 2000)
|
||||
};
|
||||
}
|
||||
|
||||
private void UpdateFilteredFavorites()
|
||||
{
|
||||
_ = Task.Run(async () =>
|
||||
{
|
||||
if (_charaDataManager.DownloadMetaInfoTask != null)
|
||||
{
|
||||
await _charaDataManager.DownloadMetaInfoTask.ConfigureAwait(false);
|
||||
}
|
||||
Dictionary<string, (CharaDataFavorite, CharaDataMetaInfoExtendedDto?, bool)> newFiltered = [];
|
||||
foreach (var favorite in _configService.Current.FavoriteCodes)
|
||||
{
|
||||
var uid = favorite.Key.Split(":")[0];
|
||||
var note = _serverConfigurationManager.GetNoteForUid(uid) ?? string.Empty;
|
||||
bool hasMetaInfo = _charaDataManager.TryGetMetaInfo(favorite.Key, out var metaInfo);
|
||||
bool addFavorite =
|
||||
(string.IsNullOrEmpty(_filterCodeNote)
|
||||
|| (note.Contains(_filterCodeNote, StringComparison.OrdinalIgnoreCase)
|
||||
|| uid.Contains(_filterCodeNote, StringComparison.OrdinalIgnoreCase)))
|
||||
&& (string.IsNullOrEmpty(_filterDescription)
|
||||
|| (favorite.Value.CustomDescription.Contains(_filterDescription, StringComparison.OrdinalIgnoreCase)
|
||||
|| (metaInfo != null && metaInfo!.Description.Contains(_filterDescription, StringComparison.OrdinalIgnoreCase))))
|
||||
&& (!_filterPoseOnly
|
||||
|| (metaInfo != null && metaInfo!.HasPoses))
|
||||
&& (!_filterWorldOnly
|
||||
|| (metaInfo != null && metaInfo!.HasWorldData));
|
||||
if (addFavorite)
|
||||
{
|
||||
newFiltered[favorite.Key] = (favorite.Value, metaInfo, hasMetaInfo);
|
||||
}
|
||||
}
|
||||
private void UpdateFilteredFavorites()
|
||||
{
|
||||
_ = Task.Run(async () =>
|
||||
{
|
||||
if (_charaDataManager.DownloadMetaInfoTask != null)
|
||||
{
|
||||
await _charaDataManager.DownloadMetaInfoTask.ConfigureAwait(false);
|
||||
}
|
||||
Dictionary<string, (CharaDataFavorite, CharaDataMetaInfoExtendedDto?, bool)> newFiltered = [];
|
||||
foreach (var favorite in _configService.Current.FavoriteCodes)
|
||||
{
|
||||
var uid = favorite.Key.Split(":")[0];
|
||||
var note = _serverConfigurationManager.GetNoteForUid(uid) ?? string.Empty;
|
||||
bool hasMetaInfo = _charaDataManager.TryGetMetaInfo(favorite.Key, out var metaInfo);
|
||||
bool addFavorite =
|
||||
(string.IsNullOrEmpty(_filterCodeNote)
|
||||
|| (note.Contains(_filterCodeNote, StringComparison.OrdinalIgnoreCase)
|
||||
|| uid.Contains(_filterCodeNote, StringComparison.OrdinalIgnoreCase)))
|
||||
&& (string.IsNullOrEmpty(_filterDescription)
|
||||
|| (favorite.Value.CustomDescription.Contains(_filterDescription, StringComparison.OrdinalIgnoreCase)
|
||||
|| (metaInfo != null && metaInfo!.Description.Contains(_filterDescription, StringComparison.OrdinalIgnoreCase))))
|
||||
&& (!_filterPoseOnly
|
||||
|| (metaInfo != null && metaInfo!.HasPoses))
|
||||
&& (!_filterWorldOnly
|
||||
|| (metaInfo != null && metaInfo!.HasWorldData));
|
||||
if (addFavorite)
|
||||
{
|
||||
newFiltered[favorite.Key] = (favorite.Value, metaInfo, hasMetaInfo);
|
||||
}
|
||||
}
|
||||
|
||||
_filteredFavorites = newFiltered;
|
||||
});
|
||||
}
|
||||
_filteredFavorites = newFiltered;
|
||||
});
|
||||
}
|
||||
|
||||
private void UpdateFilteredItems()
|
||||
{
|
||||
if (_charaDataManager.GetSharedWithYouTask == null)
|
||||
{
|
||||
_filteredDict = _charaDataManager.SharedWithYouData
|
||||
.SelectMany(k => k.Value)
|
||||
.Where(k =>
|
||||
(!_sharedWithYouDownloadableFilter || k.CanBeDownloaded)
|
||||
&& (string.IsNullOrEmpty(_sharedWithYouDescriptionFilter) || k.Description.Contains(_sharedWithYouDescriptionFilter, StringComparison.OrdinalIgnoreCase)))
|
||||
.GroupBy(k => k.Uploader)
|
||||
.ToDictionary(k =>
|
||||
{
|
||||
var note = _serverConfigurationManager.GetNoteForUid(k.Key.UID);
|
||||
if (note == null) return k.Key.AliasOrUID;
|
||||
return $"{note} ({k.Key.AliasOrUID})";
|
||||
}, k => k.ToList(), StringComparer.OrdinalIgnoreCase)
|
||||
.Where(k => (string.IsNullOrEmpty(_sharedWithYouOwnerFilter) || k.Key.Contains(_sharedWithYouOwnerFilter, StringComparison.OrdinalIgnoreCase)))
|
||||
.OrderBy(k => k.Key, StringComparer.OrdinalIgnoreCase).ToDictionary();
|
||||
}
|
||||
}
|
||||
private void UpdateFilteredItems()
|
||||
{
|
||||
if (_charaDataManager.GetSharedWithYouTask == null)
|
||||
{
|
||||
_filteredDict = _charaDataManager.SharedWithYouData
|
||||
.SelectMany(k => k.Value)
|
||||
.Where(k =>
|
||||
(!_sharedWithYouDownloadableFilter || k.CanBeDownloaded)
|
||||
&& (string.IsNullOrEmpty(_sharedWithYouDescriptionFilter) || k.Description.Contains(_sharedWithYouDescriptionFilter, StringComparison.OrdinalIgnoreCase)))
|
||||
.GroupBy(k => k.Uploader)
|
||||
.ToDictionary(k =>
|
||||
{
|
||||
var note = _serverConfigurationManager.GetNoteForUid(k.Key.UID);
|
||||
if (note == null) return k.Key.AliasOrUID;
|
||||
return $"{note} ({k.Key.AliasOrUID})";
|
||||
}, k => k.ToList(), StringComparer.OrdinalIgnoreCase)
|
||||
.Where(k => (string.IsNullOrEmpty(_sharedWithYouOwnerFilter) || k.Key.Contains(_sharedWithYouOwnerFilter, StringComparison.OrdinalIgnoreCase)))
|
||||
.OrderBy(k => k.Key, StringComparer.OrdinalIgnoreCase).ToDictionary();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -63,7 +63,7 @@ internal sealed partial class CharaDataHubUi
|
||||
ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextUnformatted("GPose Lobby");
|
||||
ImGui.SameLine();
|
||||
UiSharedService.ColorTextWrapped(_charaDataGposeTogetherManager.CurrentGPoseLobbyId, ImGuiColors.ParsedGreen);
|
||||
UiSharedService.ColorTextWrapped(_charaDataGposeTogetherManager.CurrentGPoseLobbyId, UIColors.Get("LightlessBlue"));
|
||||
ImGui.SameLine();
|
||||
if (_uiSharedService.IconButton(FontAwesomeIcon.Clipboard))
|
||||
{
|
||||
@@ -130,7 +130,7 @@ internal sealed partial class CharaDataHubUi
|
||||
ImGui.AlignTextToFramePadding();
|
||||
var note = _serverConfigurationManager.GetNoteForUid(user.UserData.UID);
|
||||
var userText = note == null ? user.UserData.AliasOrUID : $"{note} ({user.UserData.AliasOrUID})";
|
||||
UiSharedService.ColorText(userText, ImGuiColors.ParsedGreen);
|
||||
UiSharedService.ColorText(userText, UIColors.Get("LightlessBlue"));
|
||||
|
||||
var buttonsize = _uiSharedService.GetIconButtonSize(FontAwesomeIcon.ArrowRight).X;
|
||||
var buttonsize2 = _uiSharedService.GetIconButtonSize(FontAwesomeIcon.Plus).X;
|
||||
@@ -165,7 +165,7 @@ internal sealed partial class CharaDataHubUi
|
||||
UiSharedService.AttachToolTip(user.WorldDataDescriptor + UiSharedService.TooltipSeparator);
|
||||
|
||||
ImGui.SameLine();
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Map, sameMapAndServer.SameMap ? ImGuiColors.ParsedGreen : ImGuiColors.DalamudRed);
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Map, sameMapAndServer.SameMap ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed);
|
||||
if (ImGui.IsItemClicked(ImGuiMouseButton.Left) && user.WorldData != null)
|
||||
{
|
||||
_dalamudUtilService.SetMarkerAndOpenMap(new(user.WorldData.Value.PositionX, user.WorldData.Value.PositionY, user.WorldData.Value.PositionZ), user.Map);
|
||||
@@ -175,12 +175,12 @@ internal sealed partial class CharaDataHubUi
|
||||
+ "Note: For GPose synchronization to work properly, you must be on the same map.");
|
||||
|
||||
ImGui.SameLine();
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Globe, sameMapAndServer.SameServer ? ImGuiColors.ParsedGreen : ImGuiColors.DalamudRed);
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Globe, sameMapAndServer.SameServer ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed);
|
||||
UiSharedService.AttachToolTip((sameMapAndServer.SameMap ? "You are on the same server." : "You are not on the same server.") + UiSharedService.TooltipSeparator
|
||||
+ "Note: GPose synchronization is not dependent on the current server, but you will have to spawn a character for the other lobby users.");
|
||||
|
||||
ImGui.SameLine();
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Running, sameMapAndServer.SameEverything ? ImGuiColors.ParsedGreen : ImGuiColors.DalamudRed);
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Running, sameMapAndServer.SameEverything ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed);
|
||||
UiSharedService.AttachToolTip(sameMapAndServer.SameEverything ? "You are in the same instanced area." : "You are not the same instanced area." + UiSharedService.TooltipSeparator +
|
||||
"Note: Users not in your instance, but on the same map, will be drawn as floating wisps." + Environment.NewLine
|
||||
+ "Note: GPose synchronization is not dependent on the current instance, but you will have to spawn a character for the other lobby users.");
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
using Dalamud.Bindings.ImGui;
|
||||
using Dalamud.Interface.Colors;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface;
|
||||
using Dalamud.Interface.Colors;
|
||||
using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using LightlessSync.API.Dto.CharaData;
|
||||
using LightlessSync.Services.CharaData.Models;
|
||||
using System.Numerics;
|
||||
@@ -241,7 +241,7 @@ internal sealed partial class CharaDataHubUi
|
||||
ImGui.SameLine(pos);
|
||||
if (!dataDto.HasMissingFiles)
|
||||
{
|
||||
UiSharedService.ColorTextWrapped("All files to download this character data are present on the server", ImGuiColors.HealerGreen);
|
||||
UiSharedService.ColorTextWrapped("All files to download this character data are present on the server", UIColors.Get("LightlessBlue"));
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -769,7 +769,7 @@ internal sealed partial class CharaDataHubUi
|
||||
}
|
||||
else if (_charaDataManager.DataCreationTask != null && _charaDataManager.DataCreationTask.IsCompleted)
|
||||
{
|
||||
var color = _charaDataManager.DataCreationTask.Result.Success ? ImGuiColors.HealerGreen : ImGuiColors.DalamudRed;
|
||||
var color = _charaDataManager.DataCreationTask.Result.Success ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed;
|
||||
UiSharedService.ColorTextWrapped(_charaDataManager.DataCreationTask.Result.Output, color);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
using Dalamud.Bindings.ImGui;
|
||||
using Dalamud.Interface.Colors;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface;
|
||||
using Dalamud.Interface.Colors;
|
||||
using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using System.Numerics;
|
||||
|
||||
namespace LightlessSync.UI;
|
||||
@@ -112,7 +112,7 @@ internal partial class CharaDataHubUi
|
||||
var noteText = pose.Key.MetaInfo.IsOwnData ? "YOU" : (userNote == null ? pose.Key.MetaInfo.Uploader.AliasOrUID : $"{userNote} ({pose.Key.MetaInfo.Uploader.AliasOrUID})");
|
||||
ImGui.TextUnformatted("Pose by");
|
||||
ImGui.SameLine();
|
||||
UiSharedService.ColorText(noteText, ImGuiColors.ParsedGreen);
|
||||
UiSharedService.ColorText(noteText, UIColors.Get("LightlessBlue"));
|
||||
using (ImRaii.Group())
|
||||
{
|
||||
UiSharedService.ColorText("Character Data Description", ImGuiColors.DalamudGrey);
|
||||
@@ -176,7 +176,7 @@ internal partial class CharaDataHubUi
|
||||
Vector2 coneBase2 = circleCenter + baseDir2 * circleRadius;
|
||||
|
||||
// Draw the cone as a filled triangle
|
||||
drawList.AddTriangleFilled(circleCenter, coneBase1, coneBase2, UiSharedService.Color(ImGuiColors.ParsedGreen));
|
||||
drawList.AddTriangleFilled(circleCenter, coneBase1, coneBase2, UiSharedService.Color(UIColors.Get("LightlessBlue")));
|
||||
drawList.AddCircle(circleCenter, circleDiameter / 2, UiSharedService.Color(ImGuiColors.DalamudWhite), 360, 2);
|
||||
var distance = pose.Value.Distance.ToString("0.0") + "y";
|
||||
var textSize = ImGui.CalcTextSize(distance);
|
||||
|
||||
@@ -383,7 +383,7 @@ internal sealed partial class CharaDataHubUi : WindowMediatorSubscriberBase
|
||||
UiSharedService.AttachToolTip($"Target the GPose Character {CharaName(actor.Name.TextValue)}");
|
||||
ImGui.AlignTextToFramePadding();
|
||||
var pos = ImGui.GetCursorPosX();
|
||||
using (ImRaii.PushColor(ImGuiCol.Text, ImGuiColors.HealerGreen, actor.Address == (_dalamudUtilService.GetGposeTargetGameObjectAsync().GetAwaiter().GetResult()?.Address ?? nint.Zero)))
|
||||
using (ImRaii.PushColor(ImGuiCol.Text, UIColors.Get("LightlessBlue"), actor.Address == (_dalamudUtilService.GetGposeTargetGameObjectAsync().GetAwaiter().GetResult()?.Address ?? nint.Zero)))
|
||||
{
|
||||
ImGui.TextUnformatted(CharaName(actor.Name.TextValue));
|
||||
}
|
||||
|
||||
@@ -38,6 +38,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
private readonly PairManager _pairManager;
|
||||
private readonly SelectTagForPairUi _selectGroupForPairUi;
|
||||
private readonly SelectPairForTagUi _selectPairsForGroupUi;
|
||||
private readonly RenameTagUi _renameTagUi;
|
||||
private readonly IpcManager _ipcManager;
|
||||
private readonly ServerConfigurationManager _serverManager;
|
||||
private readonly TopTabMenu _tabMenu;
|
||||
@@ -56,7 +57,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
|
||||
public CompactUi(ILogger<CompactUi> logger, UiSharedService uiShared, LightlessConfigService configService, ApiController apiController, PairManager pairManager,
|
||||
ServerConfigurationManager serverManager, LightlessMediator mediator, FileUploadManager fileTransferManager,
|
||||
TagHandler tagHandler, DrawEntityFactory drawEntityFactory, SelectTagForPairUi selectTagForPairUi, SelectPairForTagUi selectPairForTagUi,
|
||||
TagHandler tagHandler, DrawEntityFactory drawEntityFactory, SelectTagForPairUi selectTagForPairUi, SelectPairForTagUi selectPairForTagUi, RenameTagUi renameTagUi,
|
||||
PerformanceCollectorService performanceCollectorService, IpcManager ipcManager)
|
||||
: base(logger, mediator, "###LightlessSyncMainUI", performanceCollectorService)
|
||||
{
|
||||
@@ -70,6 +71,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
_drawEntityFactory = drawEntityFactory;
|
||||
_selectGroupForPairUi = selectTagForPairUi;
|
||||
_selectPairsForGroupUi = selectPairForTagUi;
|
||||
_renameTagUi = renameTagUi;
|
||||
_ipcManager = ipcManager;
|
||||
_tabMenu = new TopTabMenu(Mediator, _apiController, _pairManager, _uiSharedService);
|
||||
|
||||
@@ -149,10 +151,10 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
var uidTextSize = ImGui.CalcTextSize(unsupported);
|
||||
ImGui.SetCursorPosX((ImGui.GetWindowContentRegionMax().X + ImGui.GetWindowContentRegionMin().X) / 2 - uidTextSize.X / 2);
|
||||
ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextColored(ImGuiColors.DalamudRed, unsupported);
|
||||
ImGui.TextColored(UIColors.Get("DimRed"), unsupported);
|
||||
}
|
||||
UiSharedService.ColorTextWrapped($"Your Lightless Sync installation is out of date, the current version is {ver.Major}.{ver.Minor}.{ver.Build}. " +
|
||||
$"It is highly recommended to keep Lightless Sync up to date. Open /xlplugins and update the plugin.", ImGuiColors.DalamudRed);
|
||||
$"It is highly recommended to keep Lightless Sync up to date. Open /xlplugins and update the plugin.", UIColors.Get("DimRed"));
|
||||
}
|
||||
|
||||
if (!_ipcManager.Initialized)
|
||||
@@ -164,12 +166,12 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
var uidTextSize = ImGui.CalcTextSize(unsupported);
|
||||
ImGui.SetCursorPosX((ImGui.GetWindowContentRegionMax().X + ImGui.GetWindowContentRegionMin().X) / 2 - uidTextSize.X / 2);
|
||||
ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextColored(ImGuiColors.DalamudRed, unsupported);
|
||||
ImGui.TextColored(UIColors.Get("DimRed"), unsupported);
|
||||
}
|
||||
var penumAvailable = _ipcManager.Penumbra.APIAvailable;
|
||||
var glamAvailable = _ipcManager.Glamourer.APIAvailable;
|
||||
|
||||
UiSharedService.ColorTextWrapped($"One or more Plugins essential for Lightless operation are unavailable. Enable or update following plugins:", ImGuiColors.DalamudRed);
|
||||
UiSharedService.ColorTextWrapped($"One or more Plugins essential for Lightless operation are unavailable. Enable or update following plugins:", UIColors.Get("DimRed"));
|
||||
using var indent = ImRaii.PushIndent(10f);
|
||||
if (!penumAvailable)
|
||||
{
|
||||
@@ -185,7 +187,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
}
|
||||
|
||||
using (ImRaii.PushId("header")) DrawUIDHeader();
|
||||
ImGui.Separator();
|
||||
_uiSharedService.ColoredSeparator(UIColors.Get("LightlessPurple"), 2f);
|
||||
using (ImRaii.PushId("serverstatus")) DrawServerStatus();
|
||||
ImGui.Separator();
|
||||
|
||||
@@ -198,6 +200,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
using (ImRaii.PushId("transfers")) DrawTransfers();
|
||||
_transferPartHeight = ImGui.GetCursorPosY() - pairlistEnd - ImGui.GetTextLineHeight();
|
||||
using (ImRaii.PushId("group-user-popup")) _selectPairsForGroupUi.Draw(_pairManager.DirectPairs);
|
||||
using (ImRaii.PushId("group-user-edit")) _renameTagUi.Draw(_pairManager.DirectPairs);
|
||||
using (ImRaii.PushId("grouping-popup")) _selectGroupForPairUi.Draw();
|
||||
}
|
||||
|
||||
@@ -276,7 +279,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
{
|
||||
ImGui.SetCursorPosX((ImGui.GetWindowContentRegionMin().X + UiSharedService.GetWindowContentRegionWidth()) / 2 - (userSize.X + textSize.X) / 2 - ImGui.GetStyle().ItemSpacing.X / 2);
|
||||
if (!printShard) ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextColored(ImGuiColors.ParsedGreen, userCount);
|
||||
ImGui.TextColored(UIColors.Get("LightlessPurple"), userCount);
|
||||
ImGui.SameLine();
|
||||
if (!printShard) ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextUnformatted("Users Online");
|
||||
@@ -284,7 +287,7 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
else
|
||||
{
|
||||
ImGui.AlignTextToFramePadding();
|
||||
ImGui.TextColored(ImGuiColors.DalamudRed, "Not connected to any server");
|
||||
ImGui.TextColored(UIColors.Get("DimRed"), "Not connected to any server");
|
||||
}
|
||||
|
||||
if (printShard)
|
||||
@@ -587,21 +590,21 @@ public class CompactUi : WindowMediatorSubscriberBase
|
||||
{
|
||||
return _apiController.ServerState switch
|
||||
{
|
||||
ServerState.Connecting => ImGuiColors.DalamudYellow,
|
||||
ServerState.Reconnecting => ImGuiColors.DalamudRed,
|
||||
ServerState.Connected => ImGuiColors.ParsedGreen,
|
||||
ServerState.Disconnected => ImGuiColors.DalamudYellow,
|
||||
ServerState.Disconnecting => ImGuiColors.DalamudYellow,
|
||||
ServerState.Unauthorized => ImGuiColors.DalamudRed,
|
||||
ServerState.VersionMisMatch => ImGuiColors.DalamudRed,
|
||||
ServerState.Offline => ImGuiColors.DalamudRed,
|
||||
ServerState.RateLimited => ImGuiColors.DalamudYellow,
|
||||
ServerState.NoSecretKey => ImGuiColors.DalamudYellow,
|
||||
ServerState.MultiChara => ImGuiColors.DalamudYellow,
|
||||
ServerState.OAuthMisconfigured => ImGuiColors.DalamudRed,
|
||||
ServerState.OAuthLoginTokenStale => ImGuiColors.DalamudRed,
|
||||
ServerState.NoAutoLogon => ImGuiColors.DalamudYellow,
|
||||
_ => ImGuiColors.DalamudRed
|
||||
ServerState.Connecting => UIColors.Get("LightlessYellow"),
|
||||
ServerState.Reconnecting => UIColors.Get("DimRed"),
|
||||
ServerState.Connected => UIColors.Get("LightlessPurple"),
|
||||
ServerState.Disconnected => UIColors.Get("LightlessYellow"),
|
||||
ServerState.Disconnecting => UIColors.Get("LightlessYellow"),
|
||||
ServerState.Unauthorized => UIColors.Get("DimRed"),
|
||||
ServerState.VersionMisMatch => UIColors.Get("DimRed"),
|
||||
ServerState.Offline => UIColors.Get("DimRed"),
|
||||
ServerState.RateLimited => UIColors.Get("LightlessYellow"),
|
||||
ServerState.NoSecretKey => UIColors.Get("LightlessYellow"),
|
||||
ServerState.MultiChara => UIColors.Get("LightlessYellow"),
|
||||
ServerState.OAuthMisconfigured => UIColors.Get("DimRed"),
|
||||
ServerState.OAuthLoginTokenStale => UIColors.Get("DimRed"),
|
||||
ServerState.NoAutoLogon => UIColors.Get("LightlessYellow"),
|
||||
_ => UIColors.Get("DimRed")
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@@ -13,13 +13,15 @@ public class DrawFolderTag : DrawFolderBase
|
||||
{
|
||||
private readonly ApiController _apiController;
|
||||
private readonly SelectPairForTagUi _selectPairForTagUi;
|
||||
private readonly RenameTagUi _renameTagUi;
|
||||
|
||||
public DrawFolderTag(string id, IImmutableList<DrawUserPair> drawPairs, IImmutableList<Pair> allPairs,
|
||||
TagHandler tagHandler, ApiController apiController, SelectPairForTagUi selectPairForTagUi, UiSharedService uiSharedService)
|
||||
TagHandler tagHandler, ApiController apiController, SelectPairForTagUi selectPairForTagUi, RenameTagUi renameTagUi, UiSharedService uiSharedService)
|
||||
: base(id, drawPairs, allPairs, tagHandler, uiSharedService)
|
||||
{
|
||||
_apiController = apiController;
|
||||
_selectPairForTagUi = selectPairForTagUi;
|
||||
_renameTagUi = renameTagUi;
|
||||
}
|
||||
|
||||
protected override bool RenderIfEmpty => _id switch
|
||||
@@ -100,12 +102,15 @@ public class DrawFolderTag : DrawFolderBase
|
||||
protected override void DrawMenu(float menuWidth)
|
||||
{
|
||||
ImGui.TextUnformatted("Group Menu");
|
||||
if (_uiSharedService.IconTextButton(FontAwesomeIcon.Users, "Select Pairs", menuWidth, true))
|
||||
if (_uiSharedService.IconTextButton(FontAwesomeIcon.Users, "Select Pairs", menuWidth, isInPopup: true))
|
||||
{
|
||||
_selectPairForTagUi.Open(_id);
|
||||
}
|
||||
UiSharedService.AttachToolTip("Select Individual Pairs for this Pair Group");
|
||||
if (_uiSharedService.IconTextButton(FontAwesomeIcon.Trash, "Delete Pair Group", menuWidth, true) && UiSharedService.CtrlPressed())
|
||||
if (_uiSharedService.IconTextButton(FontAwesomeIcon.Edit, "Rename Pair Group", menuWidth, isInPopup: true))
|
||||
{
|
||||
_renameTagUi.Open(_id);
|
||||
}
|
||||
if (_uiSharedService.IconTextButton(FontAwesomeIcon.Trash, "Delete Pair Group", menuWidth, isInPopup: true) && UiSharedService.CtrlPressed())
|
||||
{
|
||||
_tagHandler.RemoveTag(_id);
|
||||
}
|
||||
|
||||
@@ -202,7 +202,7 @@ public class DrawUserPair
|
||||
}
|
||||
else if (!_pair.IsOnline)
|
||||
{
|
||||
using var _ = ImRaii.PushColor(ImGuiCol.Text, ImGuiColors.DalamudRed);
|
||||
using var _ = ImRaii.PushColor(ImGuiCol.Text, UIColors.Get("DimRed"));
|
||||
_uiSharedService.IconText(_pair.IndividualPairStatus == API.Data.Enum.IndividualPairStatus.OneSided
|
||||
? FontAwesomeIcon.ArrowsLeftRight
|
||||
: (_pair.IndividualPairStatus == API.Data.Enum.IndividualPairStatus.Bidirectional
|
||||
@@ -211,7 +211,7 @@ public class DrawUserPair
|
||||
}
|
||||
else if (_pair.IsVisible)
|
||||
{
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Eye, ImGuiColors.ParsedGreen);
|
||||
_uiSharedService.IconText(FontAwesomeIcon.Eye, UIColors.Get("LightlessBlue"));
|
||||
userPairText = _pair.UserData.AliasOrUID + " is visible: " + _pair.PlayerName + Environment.NewLine + "Click to target this player";
|
||||
if (ImGui.IsItemClicked())
|
||||
{
|
||||
@@ -220,7 +220,7 @@ public class DrawUserPair
|
||||
}
|
||||
else
|
||||
{
|
||||
using var _ = ImRaii.PushColor(ImGuiCol.Text, ImGuiColors.HealerGreen);
|
||||
using var _ = ImRaii.PushColor(ImGuiCol.Text, UIColors.Get("PairBlue"));
|
||||
_uiSharedService.IconText(_pair.IndividualPairStatus == API.Data.Enum.IndividualPairStatus.Bidirectional
|
||||
? FontAwesomeIcon.User : FontAwesomeIcon.Users);
|
||||
userPairText = _pair.UserData.AliasOrUID + " is online";
|
||||
|
||||
93
LightlessSync/UI/Components/RenameTagUi.cs
Normal file
93
LightlessSync/UI/Components/RenameTagUi.cs
Normal file
@@ -0,0 +1,93 @@
|
||||
using Dalamud.Bindings.ImGui;
|
||||
using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using LightlessSync.PlayerData.Pairs;
|
||||
using LightlessSync.UI.Handlers;
|
||||
|
||||
using System.Numerics;
|
||||
|
||||
namespace LightlessSync.UI.Components;
|
||||
|
||||
public class RenameTagUi
|
||||
{
|
||||
private readonly TagHandler _tagHandler;
|
||||
private readonly UiSharedService _uiSharedService;
|
||||
private string _desiredName = string.Empty;
|
||||
private bool _opened = false;
|
||||
private HashSet<string> _peopleInGroup = new(StringComparer.Ordinal);
|
||||
private bool _show = false;
|
||||
private string _tag = string.Empty;
|
||||
|
||||
public RenameTagUi(TagHandler tagHandler, UiSharedService uiSharedService)
|
||||
{
|
||||
_tagHandler = tagHandler;
|
||||
_uiSharedService = uiSharedService;
|
||||
}
|
||||
|
||||
public void Draw(List<Pair> pairs)
|
||||
{
|
||||
var workHeight = ImGui.GetMainViewport().WorkSize.Y / ImGuiHelpers.GlobalScale;
|
||||
var minSize = new Vector2(300, workHeight < 110 ? workHeight : 110) * ImGuiHelpers.GlobalScale;
|
||||
var maxSize = new Vector2(300, 110) * ImGuiHelpers.GlobalScale;
|
||||
|
||||
var popupName = $"Renaming Group {_tag}";
|
||||
|
||||
if (!_show)
|
||||
{
|
||||
_opened = false;
|
||||
}
|
||||
|
||||
if (_show && !_opened)
|
||||
{
|
||||
ImGui.SetNextWindowSize(minSize);
|
||||
UiSharedService.CenterNextWindow(minSize.X, minSize.Y, ImGuiCond.Always);
|
||||
ImGui.OpenPopup(popupName);
|
||||
_opened = true;
|
||||
}
|
||||
|
||||
ImGui.SetNextWindowSizeConstraints(minSize, maxSize);
|
||||
if (ImGui.BeginPopupModal(popupName, ref _show, ImGuiWindowFlags.Popup | ImGuiWindowFlags.Modal))
|
||||
{
|
||||
ImGui.TextUnformatted($"Renaming {_tag}");
|
||||
|
||||
ImGui.InputTextWithHint("##desiredname", "Enter new group name", ref _desiredName, 255, ImGuiInputTextFlags.None);
|
||||
using (ImRaii.Disabled(string.IsNullOrEmpty(_desiredName)))
|
||||
{
|
||||
if (_uiSharedService.IconTextButton(Dalamud.Interface.FontAwesomeIcon.Plus, "Rename Group"))
|
||||
{
|
||||
RenameTag(pairs, _tag, _desiredName);
|
||||
_show = false;
|
||||
}
|
||||
}
|
||||
ImGui.EndPopup();
|
||||
}
|
||||
else
|
||||
{
|
||||
_show = false;
|
||||
}
|
||||
}
|
||||
|
||||
public void Open(string tag)
|
||||
{
|
||||
_peopleInGroup = _tagHandler.GetOtherUidsForTag(tag);
|
||||
_tag = tag;
|
||||
_desiredName = "";
|
||||
_show = true;
|
||||
}
|
||||
public void RenameTag(List<Pair> pairs, string oldTag, string newTag)
|
||||
{
|
||||
//Removal of old tag
|
||||
_tagHandler.RemoveTag(oldTag);
|
||||
|
||||
//Creation of new tag and adding of old group pairs in new one.
|
||||
_tagHandler.AddTag(newTag);
|
||||
foreach (Pair pair in pairs)
|
||||
{
|
||||
var isInTag = _peopleInGroup.Contains(pair.UserData.UID);
|
||||
if (isInTag)
|
||||
{
|
||||
_tagHandler.AddTagToPairedUid(pair.UserData.UID, newTag);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -169,7 +169,7 @@ public class DownloadUi : WindowMediatorSubscriberBase
|
||||
var dlProgressPercent = transferredBytes / (double)totalBytes;
|
||||
drawList.AddRectFilled(dlBarStart,
|
||||
dlBarEnd with { X = dlBarStart.X + (float)(dlProgressPercent * dlBarWidth) },
|
||||
UiSharedService.Color(50, 205, 50, transparency), 1);
|
||||
UiSharedService.Color(173, 138, 245, transparency), 1);
|
||||
|
||||
if (_configService.Current.TransferBarsShowText)
|
||||
{
|
||||
|
||||
@@ -23,11 +23,12 @@ public class DrawEntityFactory
|
||||
private readonly PlayerPerformanceConfigService _playerPerformanceConfigService;
|
||||
private readonly CharaDataManager _charaDataManager;
|
||||
private readonly SelectTagForPairUi _selectTagForPairUi;
|
||||
private readonly RenameTagUi _renameTagUi;
|
||||
private readonly TagHandler _tagHandler;
|
||||
private readonly IdDisplayHandler _uidDisplayHandler;
|
||||
|
||||
public DrawEntityFactory(ILogger<DrawEntityFactory> logger, ApiController apiController, IdDisplayHandler uidDisplayHandler,
|
||||
SelectTagForPairUi selectTagForPairUi, LightlessMediator mediator,
|
||||
SelectTagForPairUi selectTagForPairUi, RenameTagUi renameTagUi, LightlessMediator mediator,
|
||||
TagHandler tagHandler, SelectPairForTagUi selectPairForTagUi,
|
||||
ServerConfigurationManager serverConfigurationManager, UiSharedService uiSharedService,
|
||||
PlayerPerformanceConfigService playerPerformanceConfigService, CharaDataManager charaDataManager)
|
||||
@@ -36,6 +37,7 @@ public class DrawEntityFactory
|
||||
_apiController = apiController;
|
||||
_uidDisplayHandler = uidDisplayHandler;
|
||||
_selectTagForPairUi = selectTagForPairUi;
|
||||
_renameTagUi = renameTagUi;
|
||||
_mediator = mediator;
|
||||
_tagHandler = tagHandler;
|
||||
_selectPairForTagUi = selectPairForTagUi;
|
||||
@@ -58,8 +60,8 @@ public class DrawEntityFactory
|
||||
Dictionary<Pair, List<GroupFullInfoDto>> filteredPairs,
|
||||
IImmutableList<Pair> allPairs)
|
||||
{
|
||||
return new(tag, filteredPairs.Select(u => CreateDrawPair(tag, u.Key, u.Value, null)).ToImmutableList(),
|
||||
allPairs, _tagHandler, _apiController, _selectPairForTagUi, _uiSharedService);
|
||||
return new(tag, filteredPairs.Select(u => CreateDrawPair(tag, u.Key, u.Value, currentGroup: null)).ToImmutableList(),
|
||||
allPairs, _tagHandler, _apiController, _selectPairForTagUi, _renameTagUi, _uiSharedService);
|
||||
}
|
||||
|
||||
public DrawUserPair CreateDrawPair(string id, Pair user, List<GroupFullInfoDto> groups, GroupFullInfoDto? currentGroup)
|
||||
|
||||
@@ -4,9 +4,9 @@ using Dalamud.Interface.Utility;
|
||||
using Dalamud.Interface.Utility.Raii;
|
||||
using Dalamud.Utility;
|
||||
using LightlessSync.FileCache;
|
||||
using LightlessSync.Localization;
|
||||
using LightlessSync.LightlessConfiguration;
|
||||
using LightlessSync.LightlessConfiguration.Models;
|
||||
using LightlessSync.Localization;
|
||||
using LightlessSync.Services;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using LightlessSync.Services.ServerConfiguration;
|
||||
@@ -308,7 +308,7 @@ public partial class IntroUi : WindowMediatorSubscriberBase
|
||||
}
|
||||
else
|
||||
{
|
||||
UiSharedService.ColorTextWrapped($"OAuth2 is connected. Linked to: Discord User {_serverConfigurationManager.GetDiscordUserFromToken(selectedServer)}", ImGuiColors.HealerGreen);
|
||||
UiSharedService.ColorTextWrapped($"OAuth2 is connected. Linked to: Discord User {_serverConfigurationManager.GetDiscordUserFromToken(selectedServer)}", UIColors.Get("LightlessBlue"));
|
||||
UiSharedService.TextWrapped("Now press the update UIDs button to get a list of all of your UIDs on the server.");
|
||||
_uiShared.DrawUpdateOAuthUIDsButton(selectedServer);
|
||||
var playerName = _dalamudUtilService.GetPlayerName();
|
||||
|
||||
@@ -25,7 +25,7 @@ internal class JoinSyncshellUI : WindowMediatorSubscriberBase
|
||||
private string _syncshellPassword = string.Empty;
|
||||
|
||||
public JoinSyncshellUI(ILogger<JoinSyncshellUI> logger, LightlessMediator mediator,
|
||||
UiSharedService uiSharedService, ApiController apiController, PerformanceCollectorService performanceCollectorService)
|
||||
UiSharedService uiSharedService, ApiController apiController, PerformanceCollectorService performanceCollectorService)
|
||||
: base(logger, mediator, "Join existing Syncshell###LightlessSyncJoinSyncshell", performanceCollectorService)
|
||||
{
|
||||
_uiSharedService = uiSharedService;
|
||||
|
||||
@@ -102,7 +102,7 @@ public class PermissionWindowUI : WindowMediatorSubscriberBase
|
||||
{
|
||||
_ownPermissions.SetDisableAnimations(disableAnimations);
|
||||
}
|
||||
_uiSharedService.DrawHelpText("Disabling sounds will remove all animations synced with this user on both sides." + UiSharedService.TooltipSeparator
|
||||
_uiSharedService.DrawHelpText("Disabling animations will remove all animations synced with this user on both sides." + UiSharedService.TooltipSeparator
|
||||
+ "Note: this is bidirectional, either user disabling animation sync will stop animation sync on both sides.");
|
||||
using (ImRaii.PushIndent(indentSize, false))
|
||||
{
|
||||
@@ -116,7 +116,7 @@ public class PermissionWindowUI : WindowMediatorSubscriberBase
|
||||
{
|
||||
_ownPermissions.SetDisableVFX(disableVfx);
|
||||
}
|
||||
_uiSharedService.DrawHelpText("Disabling sounds will remove all VFX synced with this user on both sides." + UiSharedService.TooltipSeparator
|
||||
_uiSharedService.DrawHelpText("Disabling VFX will remove all VFX synced with this user on both sides." + UiSharedService.TooltipSeparator
|
||||
+ "Note: this is bidirectional, either user disabling VFX sync will stop VFX sync on both sides.");
|
||||
using (ImRaii.PushIndent(indentSize, false))
|
||||
{
|
||||
|
||||
@@ -110,7 +110,7 @@ public class PopoutProfileUi : WindowMediatorSubscriberBase
|
||||
var rectMax = drawList.GetClipRectMax();
|
||||
|
||||
using (_uiSharedService.UidFont.Push())
|
||||
UiSharedService.ColorText(_pair.UserData.AliasOrUID, ImGuiColors.HealerGreen);
|
||||
UiSharedService.ColorText(_pair.UserData.AliasOrUID, UIColors.Get("LightlessBlue"));
|
||||
|
||||
ImGuiHelpers.ScaledDummy(spacing.Y, spacing.Y);
|
||||
var textPos = ImGui.GetCursorPosY();
|
||||
@@ -123,7 +123,7 @@ public class PopoutProfileUi : WindowMediatorSubscriberBase
|
||||
UiSharedService.ColorText(note, ImGuiColors.DalamudGrey);
|
||||
}
|
||||
string status = _pair.IsVisible ? "Visible" : (_pair.IsOnline ? "Online" : "Offline");
|
||||
UiSharedService.ColorText(status, (_pair.IsVisible || _pair.IsOnline) ? ImGuiColors.HealerGreen : ImGuiColors.DalamudRed);
|
||||
UiSharedService.ColorText(status, (_pair.IsVisible || _pair.IsOnline) ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed);
|
||||
if (_pair.IsVisible)
|
||||
{
|
||||
ImGui.SameLine();
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -77,7 +77,7 @@ public class StandaloneProfileUi : WindowMediatorSubscriberBase
|
||||
var headerSize = ImGui.GetCursorPosY() - ImGui.GetStyle().WindowPadding.Y;
|
||||
|
||||
using (_uiSharedService.UidFont.Push())
|
||||
UiSharedService.ColorText(Pair.UserData.AliasOrUID, ImGuiColors.HealerGreen);
|
||||
UiSharedService.ColorText(Pair.UserData.AliasOrUID, UIColors.Get("LightlessBlue"));
|
||||
|
||||
ImGuiHelpers.ScaledDummy(new Vector2(spacing.Y, spacing.Y));
|
||||
var textPos = ImGui.GetCursorPosY() - headerSize;
|
||||
@@ -118,7 +118,7 @@ public class StandaloneProfileUi : WindowMediatorSubscriberBase
|
||||
UiSharedService.ColorText(note, ImGuiColors.DalamudGrey);
|
||||
}
|
||||
string status = Pair.IsVisible ? "Visible" : (Pair.IsOnline ? "Online" : "Offline");
|
||||
UiSharedService.ColorText(status, (Pair.IsVisible || Pair.IsOnline) ? ImGuiColors.HealerGreen : ImGuiColors.DalamudRed);
|
||||
UiSharedService.ColorText(status, (Pair.IsVisible || Pair.IsOnline) ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudRed);
|
||||
if (Pair.IsVisible)
|
||||
{
|
||||
ImGui.SameLine();
|
||||
|
||||
35
LightlessSync/UI/UIColors.cs
Normal file
35
LightlessSync/UI/UIColors.cs
Normal file
@@ -0,0 +1,35 @@
|
||||
using System.Globalization;
|
||||
using System.Numerics;
|
||||
|
||||
namespace LightlessSync.UI
|
||||
{
|
||||
internal static class UIColors
|
||||
{
|
||||
private static readonly Dictionary<string, string> HexColors = new(StringComparer.OrdinalIgnoreCase)
|
||||
{
|
||||
{ "LightlessPurple", "#ad8af5" },
|
||||
{ "LightlessBlue", "#a6c2ff" },
|
||||
{ "LightlessYellow", "#ffe97a" },
|
||||
{ "PairBlue", "#88a2db" },
|
||||
{ "DimRed", "#d44444" },
|
||||
};
|
||||
|
||||
public static Vector4 Get(string name)
|
||||
{
|
||||
if (!HexColors.TryGetValue(name, out var hex))
|
||||
throw new ArgumentException($"Color '{name}' not found in UIColors.");
|
||||
|
||||
return HexToRgba(hex);
|
||||
}
|
||||
|
||||
public static Vector4 HexToRgba(string hexColor)
|
||||
{
|
||||
hexColor = hexColor.TrimStart('#');
|
||||
int r = int.Parse(hexColor.Substring(0, 2), NumberStyles.HexNumber);
|
||||
int g = int.Parse(hexColor.Substring(2, 2), NumberStyles.HexNumber);
|
||||
int b = int.Parse(hexColor.Substring(4, 2), NumberStyles.HexNumber);
|
||||
int a = hexColor.Length == 8 ? int.Parse(hexColor.Substring(6, 2), NumberStyles.HexNumber) : 255;
|
||||
return new Vector4(r / 255f, g / 255f, b / 255f, a / 255f);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -12,9 +12,9 @@ using Dalamud.Plugin.Services;
|
||||
using Dalamud.Utility;
|
||||
using LightlessSync.FileCache;
|
||||
using LightlessSync.Interop.Ipc;
|
||||
using LightlessSync.Localization;
|
||||
using LightlessSync.LightlessConfiguration;
|
||||
using LightlessSync.LightlessConfiguration.Models;
|
||||
using LightlessSync.Localization;
|
||||
using LightlessSync.PlayerData.Pairs;
|
||||
using LightlessSync.Services;
|
||||
using LightlessSync.Services.Mediator;
|
||||
@@ -114,6 +114,15 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
SizePx = 35
|
||||
}));
|
||||
});
|
||||
|
||||
MediumFont = _pluginInterface.UiBuilder.FontAtlas.NewDelegateFontHandle(e =>
|
||||
{
|
||||
e.OnPreBuild(tk => tk.AddDalamudAssetFont(Dalamud.DalamudAsset.NotoSansJpMedium, new()
|
||||
{
|
||||
SizePx = 22,
|
||||
}));
|
||||
});
|
||||
|
||||
GameFont = _pluginInterface.UiBuilder.FontAtlas.NewGameFontHandle(new(GameFontFamilyAndSize.Axis12));
|
||||
IconFont = _pluginInterface.UiBuilder.IconFontFixedWidthHandle;
|
||||
}
|
||||
@@ -133,6 +142,8 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
public string PlayerName => _dalamudUtil.GetPlayerName();
|
||||
|
||||
public IFontHandle UidFont { get; init; }
|
||||
public IFontHandle MediumFont { get; init; }
|
||||
|
||||
public Dictionary<ushort, string> WorldData => _dalamudUtil.WorldData.Value;
|
||||
public uint WorldId => _dalamudUtil.GetHomeWorldId();
|
||||
|
||||
@@ -305,7 +316,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
}
|
||||
}
|
||||
|
||||
public static Vector4 GetBoolColor(bool input) => input ? ImGuiColors.ParsedGreen : ImGuiColors.DalamudRed;
|
||||
public static Vector4 GetBoolColor(bool input) => input ? UIColors.Get("LightlessBlue") : UIColors.Get("DimRed");
|
||||
|
||||
public static string GetNotes(List<Pair> pairs)
|
||||
{
|
||||
@@ -394,7 +405,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
}
|
||||
|
||||
public static Vector4 UploadColor((long, long) data) => data.Item1 == 0 ? ImGuiColors.DalamudGrey :
|
||||
data.Item1 == data.Item2 ? ImGuiColors.ParsedGreen : ImGuiColors.DalamudYellow;
|
||||
data.Item1 == data.Item2 ? UIColors.Get("LightlessBlue") : ImGuiColors.DalamudYellow;
|
||||
|
||||
public bool ApplyNotesFromClipboard(string notes, bool overwrite)
|
||||
{
|
||||
@@ -434,9 +445,82 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
FontText(text, UidFont, color);
|
||||
}
|
||||
|
||||
public void UnderlinedBigText(
|
||||
string text,
|
||||
Vector4? textColor = null,
|
||||
Vector4? underlineColor = null,
|
||||
float underlineThickness = 2f)
|
||||
{
|
||||
using var font = UidFont.Push();
|
||||
|
||||
var drawList = ImGui.GetWindowDrawList();
|
||||
var textSize = ImGui.CalcTextSize(text);
|
||||
var pos = ImGui.GetCursorScreenPos();
|
||||
var text_color = textColor ?? ImGuiColors.DalamudWhite;
|
||||
var line_color = underlineColor ?? text_color;
|
||||
|
||||
ImGui.PushStyleColor(ImGuiCol.Text, text_color);
|
||||
ImGui.TextUnformatted(text);
|
||||
ImGui.PopStyleColor();
|
||||
|
||||
var lineY = pos.Y + textSize.Y + 2f;
|
||||
drawList.AddLine(
|
||||
new Vector2(pos.X, lineY),
|
||||
new Vector2(pos.X + textSize.X, lineY),
|
||||
ImGui.GetColorU32(line_color),
|
||||
underlineThickness * ImGuiHelpers.GlobalScale
|
||||
);
|
||||
}
|
||||
|
||||
public void ColoredSeparator(Vector4? color = null, float thickness = 1f, float indent = 0f)
|
||||
{
|
||||
var drawList = ImGui.GetWindowDrawList();
|
||||
var min = ImGui.GetCursorScreenPos();
|
||||
var max = new Vector2(min.X + ImGui.GetContentRegionAvail().X, min.Y);
|
||||
|
||||
min.X += indent;
|
||||
max.X -= indent;
|
||||
|
||||
drawList.AddLine(
|
||||
min,
|
||||
new Vector2(max.X, min.Y),
|
||||
ImGui.GetColorU32(color ?? ImGuiColors.DalamudGrey),
|
||||
thickness * ImGuiHelpers.GlobalScale
|
||||
);
|
||||
|
||||
ImGui.Dummy(new Vector2(0, thickness * ImGuiHelpers.GlobalScale));
|
||||
}
|
||||
|
||||
public void MediumText(string text, Vector4? color = null)
|
||||
{
|
||||
FontText(text, MediumFont, color);
|
||||
}
|
||||
|
||||
public bool MediumTreeNode(string label, Vector4? textColor = null, float lineWidth = 2f, ImGuiTreeNodeFlags flags = ImGuiTreeNodeFlags.SpanAvailWidth)
|
||||
{
|
||||
using var font = MediumFont.Push();
|
||||
var lineColor = textColor ?? ImGuiColors.DalamudWhite;
|
||||
|
||||
var textSize = ImGui.CalcTextSize(label);
|
||||
var cursorScreen = ImGui.GetCursorScreenPos();
|
||||
var cursorLocal = ImGui.GetCursorPos();
|
||||
|
||||
ImGui.GetWindowDrawList().AddLine(
|
||||
new Vector2(cursorScreen.X, cursorScreen.Y),
|
||||
new Vector2(cursorScreen.X, cursorScreen.Y + textSize.Y),
|
||||
ImGui.GetColorU32(lineColor),
|
||||
lineWidth * ImGuiHelpers.GlobalScale
|
||||
);
|
||||
|
||||
ImGui.SetCursorPosX(cursorLocal.X + 6f);
|
||||
using var color = ImRaii.PushColor(ImGuiCol.Text, lineColor);
|
||||
|
||||
return ImGui.TreeNodeEx(label, flags);
|
||||
}
|
||||
|
||||
public void BooleanToColoredIcon(bool value, bool inline = true)
|
||||
{
|
||||
using var colorgreen = ImRaii.PushColor(ImGuiCol.Text, ImGuiColors.HealerGreen, value);
|
||||
using var colorgreen = ImRaii.PushColor(ImGuiCol.Text, UIColors.Get("LightlessBlue"), value);
|
||||
using var colorred = ImRaii.PushColor(ImGuiCol.Text, ImGuiColors.DalamudRed, !value);
|
||||
|
||||
if (inline) ImGui.SameLine();
|
||||
@@ -645,7 +729,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
{
|
||||
if (_discordOAuthCheck.Result != null)
|
||||
{
|
||||
ColorTextWrapped("Server is compatible with Discord OAuth2", ImGuiColors.HealerGreen);
|
||||
ColorTextWrapped("Server is compatible with Discord OAuth2", UIColors.Get("LightlessBlue"));
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -678,7 +762,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
selectedServer.OAuthToken = _discordOAuthGetCode.Result;
|
||||
_discordOAuthGetCode = null;
|
||||
_serverConfigurationManager.Save();
|
||||
ColorTextWrapped("Success", ImGuiColors.HealerGreen);
|
||||
ColorTextWrapped("Success", UIColors.Get("LightlessBlue"));
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -708,7 +792,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
|
||||
if (tokenExpiry > DateTime.UtcNow)
|
||||
{
|
||||
ColorTextWrapped($"OAuth2 is enabled, linked to: Discord User {_serverConfigurationManager.GetDiscordUserFromToken(selectedServer)}", ImGuiColors.HealerGreen);
|
||||
ColorTextWrapped($"OAuth2 is enabled, linked to: Discord User {_serverConfigurationManager.GetDiscordUserFromToken(selectedServer)}", UIColors.Get("LightlessBlue"));
|
||||
TextWrapped($"The OAuth2 token will expire on {tokenExpiry:yyyy-MM-dd} and automatically renew itself during login on or after {(tokenExpiry - TimeSpan.FromDays(7)):yyyy-MM-dd}.");
|
||||
using (ImRaii.Disabled(!CtrlPressed()))
|
||||
{
|
||||
@@ -740,7 +824,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
if (foundUids > 0)
|
||||
{
|
||||
ColorTextWrapped($"Found {foundUids} associated UIDs on the server, Primary UID: {primaryUid.Key} (Vanity UID: {vanity})",
|
||||
ImGuiColors.HealerGreen);
|
||||
UIColors.Get("LightlessBlue"));
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1085,6 +1169,7 @@ public partial class UiSharedService : DisposableMediatorSubscriberBase
|
||||
|
||||
UidFont.Dispose();
|
||||
GameFont.Dispose();
|
||||
MediumFont.Dispose();
|
||||
}
|
||||
|
||||
private static void CenterWindow(float width, float height, ImGuiCond cond = ImGuiCond.None)
|
||||
|
||||
@@ -8,7 +8,6 @@ using LightlessSync.LightlessConfiguration.Models;
|
||||
using LightlessSync.Services.Mediator;
|
||||
using Microsoft.AspNetCore.SignalR.Client;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using static FFXIVClientStructs.FFXIV.Client.Game.UI.MapMarkerData.Delegates;
|
||||
|
||||
namespace LightlessSync.WebAPI;
|
||||
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
using LightlessSync.API.Data;
|
||||
using LightlessSync.API.Dto.CharaData;
|
||||
using LightlessSync.Services.CharaData.Models;
|
||||
using Microsoft.AspNetCore.SignalR.Client;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 770 KiB After Width: | Height: | Size: 206 KiB |
Submodule PenumbraAPI updated: af41b1787a...953dd227af
@@ -1,6 +1,6 @@
|
||||
# Lightless Sync Dalamud Plugin
|
||||
|
||||
Available at [This dalamud Repo](https://raw.githubusercontent.com/Light-Public-Syncshells/repo/main/plogonmaster.json)
|
||||
Available at [This dalamud Repo](https://raw.githubusercontent.com/Light-Public-Syncshells/LightlessSync/refs/heads/main/plogonmaster.json)
|
||||
|
||||
# [Lightless Sync Discord](https://discord.gg/dsbjcXMnhA)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user