diff --git a/src/Game.Client/Assets/Programs/Editor/Tests/PlayMode/InputSystemServiceRebindPlayModeTests.cs b/src/Game.Client/Assets/Programs/Editor/Tests/PlayMode/InputSystemServiceRebindPlayModeTests.cs index 14dad5b80..fdaca8531 100644 --- a/src/Game.Client/Assets/Programs/Editor/Tests/PlayMode/InputSystemServiceRebindPlayModeTests.cs +++ b/src/Game.Client/Assets/Programs/Editor/Tests/PlayMode/InputSystemServiceRebindPlayModeTests.cs @@ -24,7 +24,7 @@ public override void Setup() base.Setup(); _keyboard = InputSystem.AddDevice(); _gamepad = InputSystem.AddDevice(); - _service = new InputSystemService(); + _service = new InputSystemService(new LocalizationService()); } public override void TearDown() @@ -56,7 +56,7 @@ public IEnumerator SaveLoadBindingOverrides_RoundTrip_RestoresOverride() Assert.That(json, Is.Not.Null.And.Not.Empty); // 別インスタンスへロードして再現 - var service2 = new InputSystemService(); + var service2 = new InputSystemService(new LocalizationService()); service2.Startup(); yield return null; service2.LoadBindingOverrides(json); diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/Abstractions/IInputSystemService.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/Abstractions/IInputSystemService.cs index 19c3c34be..3d3b2f084 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/Abstractions/IInputSystemService.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/Abstractions/IInputSystemService.cs @@ -28,8 +28,19 @@ public interface IInputSystemService : IGameService /// InputActionAsset InputActionAsset { get; } + /// + /// 操作スキーマ変更イベント + /// Observable OnControlSchemeChanged { get; } + /// + /// 操作デバイス切替イベント + /// + Observable<(InputDevice device, InputDeviceChange deviceChange)> OnDeviceChanged { get; } + + /// + /// キーバインド変更イベント + /// Observable OnBindingChanged { get; } /// diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/InputSystemService.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/InputSystemService.cs index 3454437fa..049a207ea 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/InputSystemService.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/InputSystemService.cs @@ -4,37 +4,45 @@ using Game.Shared.Bootstrap; using Game.Shared.Constants; using Game.Shared.Input; -using Game.Shared.Localization; +using Game.Shared.Services.Interfaces; using R3; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.InputSystem; +using UnityEngine.UI; namespace Game.Core.Services { public class InputSystemService : IInputSystemService, IDisposable { + private readonly ILocalizationService _localizationService; + private ProjectDefaultInputSystem _inputSystem; private bool _isInitialized; + private string _controlScheme = InputControlSchemes.DefaultControlScheme; + private GameObject _selectedGameObject; public ProjectDefaultInputSystem.PlayerActions Player => _inputSystem.Player; public ProjectDefaultInputSystem.UIActions UI => _inputSystem.UI; - public InputActionAsset InputActionAsset => _inputSystem?.asset; - private string _controlScheme = InputControlSchemes.DefaultControlScheme; - private GameObject _selectedGameObject; - private readonly Subject _onControlSchemeChanged = new(); public Observable OnControlSchemeChanged => _onControlSchemeChanged; + public Observable<(InputDevice device, InputDeviceChange deviceChange)> OnDeviceChanged + => Observable.FromEvent, (InputDevice, InputDeviceChange)>( + h => (a, b) => h((a, b)), + h => InputSystem.onDeviceChange += h, + h => InputSystem.onDeviceChange -= h); + private readonly Subject _onBindingChanged = new(); public Observable OnBindingChanged => _onBindingChanged; #region Setup - public InputSystemService() + public InputSystemService(ILocalizationService localizationService) { + _localizationService = localizationService; } public void Startup() @@ -112,9 +120,9 @@ public IDisposable BlockInputActions(params InputAction[] actions) #endregion - public void ResolveSelectable(GameObject selectedGameObject = null) + private void ResolveSelectable(GameObject selectedGameObject = null) { - var allSelectables = InputSystemHelper.GetAllSelectables(); + var allSelectables = GetAllSelectables(); if (allSelectables.Length > 0) { GameObject go = null; @@ -149,6 +157,22 @@ public void ResolveSelectable(GameObject selectedGameObject = null) Debug.Log("[InputService] No Selectables found"); } + private static Selectable[] GetAllSelectables() + { + Selectable[] allSelectables = Array.Empty(); + int allCount = Selectable.allSelectableCount; + if (allCount > 0) + allSelectables = new Selectable[allCount]; + else + return allSelectables; + + int count = Selectable.AllSelectablesNoAlloc(allSelectables); + if (count > 0) return allSelectables; + + allSelectables = Selectable.allSelectablesArray; + return allSelectables; + } + public GameObject GetSelectedGameObject() { return EventSystem.current.currentSelectedGameObject; @@ -218,7 +242,7 @@ public string GetBindingDisplayString(string scheme, string actionName, string p { // 既定の英語表示・デバイスレイアウト・controlPath を取得し、family 別ローカライズ名へ変換(未登録は英語へフォールバック) var raw = action.GetBindingDisplayString(index, out var deviceLayoutName, out var controlPath); - parts.Add(InputControlsLocalizer.Localize(deviceLayoutName, controlPath, raw)); + parts.Add(_localizationService.GetStringByInputControls(deviceLayoutName, controlPath, raw)); } return string.Join("/", parts); } diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs new file mode 100644 index 000000000..c63a8791d --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs @@ -0,0 +1,8 @@ +using Game.Shared.Services; + +namespace Game.Core.Services +{ + public class LocalizationService : LocalizationServiceBase, IGameService + { + } +} diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs.meta b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs.meta new file mode 100644 index 000000000..8ca57695a --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/Services/LocalizationService.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 57a1a758931e43a2a525ea10fc7d399b +timeCreated: 1783839611 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindView.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindingView.cs similarity index 98% rename from src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindView.cs rename to src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindingView.cs index 33a2ace57..158eeea8e 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindView.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindingView.cs @@ -10,7 +10,7 @@ namespace Game.Core.UI /// 現在のバインド表示と「変更」ボタンを持ち、押下を Observable で通知する。 /// リバインド実行・重複判定などの入力ロジックは持たず、表示更新のみを担う。 /// - public class InputActionRebindView : MonoBehaviour + public class InputActionRebindingView : MonoBehaviour { [Header("Identity")] [SerializeField] private string _scheme; // コントロールスキーム(Keyboard&Mouse / Gamepad) diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindView.cs.meta b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindingView.cs.meta similarity index 100% rename from src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindView.cs.meta rename to src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/InputActionRebindingView.cs.meta diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/SliderIndexSelector.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/SliderIndexSelector.cs index 65d31ecfb..dc869926a 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/SliderIndexSelector.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Core/UI/SliderIndexSelector.cs @@ -18,7 +18,7 @@ public class SliderIndexSelector : MonoBehaviour private bool _initialized; private readonly Subject _onValueChanged = new(); - public Observable OnValueChanged => _onValueChanged.AsObservable(); + public Observable OnValueChanged => _onValueChanged; /// 選択中の index。 public int Index => Mathf.RoundToInt(_slider.value); diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialog.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialog.cs index 30ea79e40..1b0e18613 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialog.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialog.cs @@ -2,15 +2,13 @@ using Cysharp.Threading.Tasks; using Game.Core.Services; using Game.Horror.SaveData; -using Game.Horror.Services; using Game.Horror.Services.Interfaces; using Game.MVC.Core.Enums; using Game.MVC.Core.Scenes; using Game.Shared.Constants; using Game.Shared.Extensions; -using Game.Shared.Input; -using Game.Shared.Localization; using Game.Shared.Services; +using Game.Shared.Services.Interfaces; using R3; using UnityEngine; @@ -22,6 +20,7 @@ public class HorrorOptionDialog : GameDialogScene(); _audioService = GameServiceManager.Resolve(); + _localizationService = GameServiceManager.Resolve(); _optionSaveRepository = GameServiceManager.Resolve(); _optionService = GameServiceManager.Resolve(); return base.PreInitialize(); @@ -240,10 +240,10 @@ public override UniTask Startup() .AddTo(Disposables); // ロケール変更でバインド表示名を再ローカライズ - LocalizationEvents.OnLocaleChanged.Subscribe(_ => RefreshBindingDisplays()).AddTo(Disposables); + _localizationService.OnLocaleChanged.Subscribe(_ => RefreshBindingDisplays()).AddTo(Disposables); // コントローラー接続/切替に追従して family 別表示を更新する - InputSystemEvents.OnDeviceChanged.Subscribe(_ => RefreshBindingDisplays()).AddTo(Disposables); + _inputService.OnDeviceChanged.Subscribe(_ => RefreshBindingDisplays()).AddTo(Disposables); return base.Startup(); } diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialogComponent.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialogComponent.cs index a57aed9c0..6d7195398 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialogComponent.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorOptionDialogComponent.cs @@ -33,7 +33,7 @@ public class HorrorOptionDialogComponent : GameSceneComponent [SerializeField] private SliderBooleanSelector _crouchMode; [Header("Options - Control")] - [SerializeField] private InputActionRebindView[] _rebindViews; + [SerializeField] private InputActionRebindingView[] _rebindViews; [SerializeField] private Button _resetKeyboardBindingsButton; [SerializeField] private Button _resetGamepadBindingsButton; @@ -85,7 +85,7 @@ public class HorrorOptionDialogComponent : GameSceneComponent #region Controls /// キーリバインド行(アクション×スキーム単位)。Dialog 側が購読・表示更新する。 - public IReadOnlyList RebindViews => _rebindViews; + public IReadOnlyList RebindViews => _rebindViews; /// スキーム別リセットボタン押下。値は対象スキーム(KBM / Gamepad)。 public Observable OnResetSchemeBindingsRequested => Observable.Merge( diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorSaveDataDialogComponent.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorSaveDataDialogComponent.cs index 1ab1217fd..27cd681c2 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorSaveDataDialogComponent.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Dialogs/HorrorSaveDataDialogComponent.cs @@ -3,8 +3,8 @@ using Game.Core.Services; using Game.Horror.SaveData; using Game.MVC.Core.Scenes; -using Game.Shared.Localization; using Game.Shared.Services; +using Game.Shared.Services.Interfaces; using R3; using UnityEngine; @@ -27,6 +27,7 @@ public Observable OnSlotSelected public void SetSlotInfos(IReadOnlyList slots) { var database = GameServiceManager.Resolve().Database; + var localization = GameServiceManager.Resolve(); foreach (var slot in slots) { @@ -42,7 +43,7 @@ public void SetSlotInfos(IReadOnlyList slots) if (slot.HasData) { if (database.HorrorInteractionMasterTable.TryFindById(slot.SavepointId, out var master)) - savepointName = InteractionsLocalizer.Localize(master.InteractionLocalizeKey); + savepointName = localization.GetStringByInteractions(master.InteractionLocalizeKey); else Debug.LogError($"[{GetType().Name}] HorrorInteractionMaster not found: SavepointId={slot.SavepointId}"); diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/HorrorGameLauncher.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/HorrorGameLauncher.cs index be8bbda6d..58e54288c 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/HorrorGameLauncher.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/HorrorGameLauncher.cs @@ -9,6 +9,7 @@ using Game.Shared.Enums; using Game.Shared.SaveData; using Game.Shared.Services; +using Game.Shared.Services.Interfaces; namespace Game.Horror { @@ -27,6 +28,8 @@ public async UniTask StartupAsync() // 各種サービス取得・初期化 var assetService = new AddressableAssetService(); GameServiceManager.Register(assetService); + var localizationService = new LocalizationService(); + GameServiceManager.Register(localizationService); var dbService = new ScriptableDatabaseService(assetService); GameServiceManager.Register(dbService); @@ -58,7 +61,7 @@ public async UniTask StartupAsync() HorrorOptionHelper.ApplySaveData(optionSaveRepository.Data); // キーリバインドのオーバーライドを起動時に適用 - var inputSystemService = new InputSystemService(); + var inputSystemService = new InputSystemService(localizationService); GameServiceManager.Register(inputSystemService); inputSystemService.LoadBindingOverrides(optionSaveRepository.Data.InputBindingOverridesJson); diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractableBase.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractableBase.cs index 27e6756b1..93c60218e 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractableBase.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractableBase.cs @@ -7,6 +7,7 @@ using Game.Shared.Scriptable.Database; using Game.Shared.Scriptable.Database.Tables; using Game.Shared.Services; +using Game.Shared.Services.Interfaces; using UnityEngine; namespace Game.Horror.Interaction @@ -36,6 +37,7 @@ public abstract class InteractableBase : MonoBehaviour, IInteractable protected IHorrorInteractionService InteractionService { get; private set; } protected IHorrorInventoryService InventoryService { get; private set; } + private ILocalizationService _localizationService; private IScriptableDatabaseService _databaseService; protected ScriptableDatabase Database => _databaseService.Database; @@ -54,6 +56,7 @@ protected virtual void Start() InteractionService = GameServiceManager.Resolve(); InventoryService = GameServiceManager.Resolve(); + _localizationService = GameServiceManager.Resolve(); _databaseService = GameServiceManager.Resolve(); if (_databaseService.Database.HorrorInteractionMasterTable.TryFindById(_interactionId, out var master)) { @@ -132,7 +135,7 @@ public UniTask TryShowRejectionMessage() if (Master == null || string.IsNullOrEmpty(Master.RejectionMessageLocalizeKey)) return UniTask.FromResult(false); - var message = InteractionMessagesLocalizer.Localize(Master.RejectionMessageLocalizeKey); + var message = _localizationService.GetStringByInteractionMessages(Master.RejectionMessageLocalizeKey); return HorrorMessageDialog.RunAsync(message); } diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractionPromptView.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractionPromptView.cs index 5be15b65d..7e3aba339 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractionPromptView.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Interaction/InteractionPromptView.cs @@ -1,8 +1,7 @@ using Game.Core.Services; using Game.Shared.Enums; -using Game.Shared.Input; -using Game.Shared.Localization; using Game.Shared.Scriptable.Database.Tables; +using Game.Shared.Services.Interfaces; using R3; using TMPro; using UnityEngine; @@ -44,6 +43,7 @@ public class InteractionPromptView : MonoBehaviour private HorrorInteractionMaster _master; private IInputSystemService _inputService; + private ILocalizationService _localizationService; private Camera _viewCamera; private bool _interactionToggle; @@ -52,15 +52,17 @@ public void Initialize(HorrorInteractionMaster master) { _master = master; _inputService = GameServiceManager.Resolve(); + _localizationService = GameServiceManager.Resolve(); - LocalizationEvents.OnLocaleChanged.Subscribe(_ => SetInteractionText()).AddTo(this); + _localizationService.OnLocaleChanged.Subscribe(_ => SetInteractionText()).AddTo(this); SetInteractionText(); _inputService.OnControlSchemeChanged.Subscribe(_ => SetInputBindingText()).AddTo(this); + _inputService.OnDeviceChanged.Subscribe(_ => SetInputBindingText()).AddTo(this); _inputService.OnBindingChanged .Where(x => x == _inputService.Player.Interact) - .Subscribe(_ => SetInputBindingText()).AddTo(this); - InputSystemEvents.OnDeviceChanged.Subscribe(_ => SetInputBindingText()).AddTo(this); + .Subscribe(_ => SetInputBindingText()) + .AddTo(this); SetInputBindingText(); _inputTypeRoot.SetActive(master.InputType == InteractionInputType.Hold); @@ -71,8 +73,8 @@ public void Initialize(HorrorInteractionMaster master) private void SetInteractionText() { _interactionText.text = !_interactionToggle - ? ContextActionsLocalizer.Localize(_master.InteractionVerbLocalizeKey) - : ContextActionsLocalizer.Localize(_master.ReinteractionVerbLocalizeKey); + ? _localizationService.GetStringByContextActions(_master.InteractionVerbLocalizeKey) + : _localizationService.GetStringByContextActions(_master.ReinteractionVerbLocalizeKey); } private void SetInputBindingText() diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Inventory/HorrorInventoryContextActionView.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Inventory/HorrorInventoryContextActionView.cs index 88ec05195..e26ef07b1 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Inventory/HorrorInventoryContextActionView.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/Horror/Inventory/HorrorInventoryContextActionView.cs @@ -1,5 +1,7 @@ +using Game.Core.Services; using Game.Shared.Enums; using Game.Shared.Localization; +using Game.Shared.Services.Interfaces; using R3; using TMPro; using UnityEngine; @@ -24,7 +26,10 @@ public class HorrorInventoryContextActionView : MonoBehaviour public void Initialize(InventoryContextActionType contextAction) { if (_label != null) - _label.text = ContextActionsLocalizer.Localize(contextAction.ToString()); + { + var localization = GameServiceManager.Resolve(); + _label.text = localization.GetStringByContextActions(contextAction.ToString()); + } _button.OnClickAsObservable() .Subscribe(_ => _onClicked.OnNext(contextAction)) diff --git a/src/Game.Client/Assets/Programs/Runtime/MVC/ScoreTimeAttack/ScoreTimeAttackGameLauncher.cs b/src/Game.Client/Assets/Programs/Runtime/MVC/ScoreTimeAttack/ScoreTimeAttackGameLauncher.cs index 041c139e3..d09f41a43 100644 --- a/src/Game.Client/Assets/Programs/Runtime/MVC/ScoreTimeAttack/ScoreTimeAttackGameLauncher.cs +++ b/src/Game.Client/Assets/Programs/Runtime/MVC/ScoreTimeAttack/ScoreTimeAttackGameLauncher.cs @@ -8,6 +8,7 @@ using Game.Shared.Enums; using Game.Shared.SaveData; using Game.Shared.Services; +using Game.Shared.Services.Interfaces; namespace Game.ScoreTimeAttack { @@ -26,6 +27,8 @@ public async UniTask StartupAsync() // 2. 各種サービス取得・初期化 var assetService = new AddressableAssetService(); GameServiceManager.Register(assetService); + var localizationService = new LocalizationService(); + GameServiceManager.Register(localizationService); var masterDataService = new MasterDataService(assetService); await masterDataService.LoadMasterDataAsync(); @@ -35,7 +38,7 @@ public async UniTask StartupAsync() await audioService.LoadAsync(); GameServiceManager.Register(audioService); GameServiceManager.Register(new MessagePipeService()); - var inputSystemService = new InputSystemService(); + var inputSystemService = new InputSystemService(localizationService); GameServiceManager.Register(inputSystemService); // 3. 共通オブジェクト読み込み diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Constants/LocalizationConstants.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Constants/LocalizationConstants.cs index 1bc934ac9..b554360b1 100644 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Constants/LocalizationConstants.cs +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Constants/LocalizationConstants.cs @@ -6,5 +6,6 @@ public static class LocalizationConstants public const string ContextActionsTable = "ContextActions"; public const string InteractionMessagesTable = "InteractionMessages"; public const string InteractionsTable = "Interactions"; + public const string UITextsTable = "UITexts"; } } diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs deleted file mode 100644 index f5d8e867b..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using UnityEngine.UI; - -namespace Game.Shared.Input -{ - public static class InputSystemHelper - { - public static Selectable[] GetAllSelectables() - { - Selectable[] allSelectables = Array.Empty(); - int allCount = Selectable.allSelectableCount; - if (allCount > 0) - allSelectables = new Selectable[allCount]; - else - return allSelectables; - - int count = Selectable.AllSelectablesNoAlloc(allSelectables); - if (count > 0) return allSelectables; - - allSelectables = Selectable.allSelectablesArray; - return allSelectables; - } - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs.meta deleted file mode 100644 index 47ae8a4fe..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Input/InputSystemHelper.cs.meta +++ /dev/null @@ -1,3 +0,0 @@ -fileFormatVersion: 2 -guid: 4318b2bacdb74eb7bf9b383889c56a89 -timeCreated: 1779548363 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs deleted file mode 100644 index b95ce0eb3..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs +++ /dev/null @@ -1,10 +0,0 @@ -using Game.Shared.Constants; - -namespace Game.Shared.Localization -{ - public static class ContextActionsLocalizer - { - public static string Localize(string localizeKey) - => LocalizationHelper.GetLocalizedString(LocalizationConstants.ContextActionsTable , localizeKey); - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs.meta deleted file mode 100644 index e040f0718..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/ContextActionsLocalizer.cs.meta +++ /dev/null @@ -1,3 +0,0 @@ -fileFormatVersion: 2 -guid: 067b77b998b44b3f9b947e728dfe2288 -timeCreated: 1782405768 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs deleted file mode 100644 index 5f725117d..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs +++ /dev/null @@ -1,45 +0,0 @@ -using Game.Shared.Constants; -using UnityEngine.InputSystem; - -namespace Game.Shared.Localization -{ - /// - /// 入力コントロールの表示名をローカライズする。 - /// controlPath("space", "buttonSouth", "dpad/up" 等、デバイス接頭辞なし)をキーに - /// StringTable "InputControls" を引き、未登録キーは Unity 既定の英語表示へフォールバックする。 - /// ゲームパッドは接続デバイスの family(xbox/ps/switch)でプレフィックス付きキーを優先的に引く。 - /// - public static class InputControlsLocalizer - { - /// - /// controlPath をキーに InputControls からローカライズ名を引く。 - /// family プレフィックス付きキー → 無印キー → fallback(raw) の順に解決する。 - /// - /// 解決済みコントロールのデバイスレイアウト名(family 判定用。null/空可)。 - /// - /// - public static string Localize(string deviceLayoutName, string controlPath, string fallback) - { - if (string.IsNullOrEmpty(controlPath)) return fallback; - - var prefix = ResolveFamilyPrefix(deviceLayoutName); - if (prefix.Length > 0) - { - var localized = LocalizationHelper.GetLocalizedString(LocalizationConstants.InputControlsTable, prefix + controlPath); - if (!string.IsNullOrEmpty(localized)) return localized; - } - - return LocalizationHelper.GetLocalizedString(LocalizationConstants.InputControlsTable, controlPath) ?? fallback; - } - - /// デバイスレイアウトを family プレフィックスへ分類する(未知/未接続は空=無印)。 - private static string ResolveFamilyPrefix(string deviceLayoutName) - { - if (string.IsNullOrEmpty(deviceLayoutName)) return string.Empty; - if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "DualShockGamepad")) return "ps/"; - if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "SwitchProControllerHID")) return "switch/"; - if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "XInputController")) return "xbox/"; - return string.Empty; - } - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs.meta deleted file mode 100644 index 8d65c65d9..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InputControlsLocalizer.cs.meta +++ /dev/null @@ -1,2 +0,0 @@ -fileFormatVersion: 2 -guid: d473c5fa06c90354db647a4416b6ef39 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs deleted file mode 100644 index 298a94918..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs +++ /dev/null @@ -1,10 +0,0 @@ -using Game.Shared.Constants; - -namespace Game.Shared.Localization -{ - public static class InteractionMessagesLocalizer - { - public static string Localize(string localizeKey) - => LocalizationHelper.GetLocalizedString(LocalizationConstants.InteractionMessagesTable , localizeKey); - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs.meta deleted file mode 100644 index c9499ba9d..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionMessagesLocalizer.cs.meta +++ /dev/null @@ -1,3 +0,0 @@ -fileFormatVersion: 2 -guid: 1f663bc4007c4bfb84d1aa4e02d93009 -timeCreated: 1782615025 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs deleted file mode 100644 index 053ba98cd..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs +++ /dev/null @@ -1,10 +0,0 @@ -using Game.Shared.Constants; - -namespace Game.Shared.Localization -{ - public static class InteractionsLocalizer - { - public static string Localize(string localizeKey) - => LocalizationHelper.GetLocalizedString(LocalizationConstants.InteractionsTable , localizeKey); - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs.meta deleted file mode 100644 index bf20e2d49..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/InteractionsLocalizer.cs.meta +++ /dev/null @@ -1,2 +0,0 @@ -fileFormatVersion: 2 -guid: 5414b5e2773a7e947aca9c76bf831c2e \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs deleted file mode 100644 index 845e42d9b..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs +++ /dev/null @@ -1,13 +0,0 @@ -using UnityEngine.Localization.Settings; - -namespace Game.Shared.Localization -{ - public static class LocalizationHelper - { - public static string GetLocalizedString(string tableName, string localizeKey) - { - var entry = LocalizationSettings.StringDatabase.GetTableEntry(tableName, localizeKey).Entry; - return entry != null ? entry.GetLocalizedString() : null; - } - } -} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs.meta deleted file mode 100644 index 97d94febd..000000000 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizationHelper.cs.meta +++ /dev/null @@ -1,3 +0,0 @@ -fileFormatVersion: 2 -guid: 0b9d02fcbdf84f5386bf473f2af555e3 -timeCreated: 1782405235 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizeStrings.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizeStrings.cs index 112db4647..ed33db59d 100644 --- a/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizeStrings.cs +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Localization/LocalizeStrings.cs @@ -12,7 +12,7 @@ public class LocalizeStrings : MonoBehaviour private string[] _strings; private readonly Subject _onChangedLocale = new(); - public Observable OnChangedLocale => _onChangedLocale.AsObservable(); + public Observable OnChangedLocale => _onChangedLocale; private void Awake() { diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces.meta new file mode 100644 index 000000000..f00649d57 --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: dd82cac6cabc487cbb4d122a00721195 +timeCreated: 1783838320 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs new file mode 100644 index 000000000..048b33b4b --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs @@ -0,0 +1,24 @@ +using R3; +using UnityEngine.Localization; + +namespace Game.Shared.Services.Interfaces +{ + public interface ILocalizationService + { + Locale SelectedLocale { get; } + + Observable OnLocaleChanged { get; } + + string GetLocalizedString(string tableName, string localizeKey); + + string GetStringByContextActions(string localizeKey); + + string GetStringByInputControls(string deviceLayoutName, string controlPath, string fallback); + + string GetStringByInteractions(string localizeKey); + + string GetStringByInteractionMessages(string localizeKey); + + string GetStringByUITexts(string localizeKey); + } +} diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs.meta new file mode 100644 index 000000000..426294826 --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/Interfaces/ILocalizationService.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 04a73b56f27c4cbd858b32a6e2c74974 +timeCreated: 1783838329 \ No newline at end of file diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs new file mode 100644 index 000000000..23f40f424 --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs @@ -0,0 +1,71 @@ +using System; +using Game.Shared.Constants; +using Game.Shared.Services.Interfaces; +using R3; +using UnityEngine.InputSystem; +using UnityEngine.Localization; +using UnityEngine.Localization.Settings; + +namespace Game.Shared.Services +{ + public abstract class LocalizationServiceBase : ILocalizationService + { + public Locale SelectedLocale => LocalizationSettings.SelectedLocale; + + public Observable OnLocaleChanged + => Observable.FromEvent, Locale>( + h => h, + h => LocalizationSettings.SelectedLocaleChanged += h, + h => LocalizationSettings.SelectedLocaleChanged -= h); + + public string GetLocalizedString(string tableName, string localizeKey) + { + var entry = LocalizationSettings.StringDatabase.GetTableEntry(tableName, localizeKey).Entry; + return entry != null ? entry.GetLocalizedString() : null; + } + + public string GetStringByContextActions(string localizeKey) + => GetLocalizedString(LocalizationConstants.ContextActionsTable, localizeKey); + + /// + /// controlPath をキーに InputControls からローカライズ名を引く。 + /// family プレフィックス付きキー → 無印キー → fallback(raw) の順に解決する。 + /// + /// 解決済みコントロールのデバイスレイアウト名(family 判定用。null/空可)。 + /// + /// + public string GetStringByInputControls(string deviceLayoutName, string controlPath, string fallback) + { + if (string.IsNullOrEmpty(controlPath)) return fallback; + + var prefix = ResolveFamilyPrefix(deviceLayoutName); + if (prefix.Length > 0) + { + var localized = GetLocalizedString(LocalizationConstants.InputControlsTable, prefix + controlPath); + if (!string.IsNullOrEmpty(localized)) return localized; + } + + return GetLocalizedString(LocalizationConstants.InputControlsTable, controlPath) ?? fallback; + } + + /// デバイスレイアウトを family プレフィックスへ分類する(未知/未接続は空=無印)。 + private static string ResolveFamilyPrefix(string deviceLayoutName) + { + if (string.IsNullOrEmpty(deviceLayoutName)) return string.Empty; + if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "DualShockGamepad")) return "ps/"; + if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "SwitchProControllerHID")) return "switch/"; + if (InputSystem.IsFirstLayoutBasedOnSecond(deviceLayoutName, "XInputController")) return "xbox/"; + return string.Empty; + } + + public string GetStringByInteractions(string localizeKey) + => GetLocalizedString(LocalizationConstants.InteractionsTable, localizeKey); + + public string GetStringByInteractionMessages(string localizeKey) + => GetLocalizedString(LocalizationConstants.InteractionMessagesTable, localizeKey); + + public string GetStringByUITexts(string localizeKey) + => GetLocalizedString(LocalizationConstants.UITextsTable, localizeKey); + } +} + diff --git a/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs.meta b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs.meta new file mode 100644 index 000000000..e31a4d53e --- /dev/null +++ b/src/Game.Client/Assets/Programs/Runtime/Shared/Services/LocalizationServiceBase.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 0b86c7e4748d4bd4a90130a77d5750a6 +timeCreated: 1783838628 \ No newline at end of file