diff --git a/Assets/PerfectWorld/Prefab/FreeLook Camera.prefab b/Assets/PerfectWorld/Prefab/FreeLook Camera.prefab index 8a581c914f..6c049cf559 100644 --- a/Assets/PerfectWorld/Prefab/FreeLook Camera.prefab +++ b/Assets/PerfectWorld/Prefab/FreeLook Camera.prefab @@ -13,6 +13,7 @@ GameObject: - component: {fileID: 864878593467321995} - component: {fileID: 3005089224860696078} - component: {fileID: 9220823260634167621} + - component: {fileID: 6720462472486200866} m_Layer: 0 m_Name: FreeLook Camera m_TagString: Untagged @@ -228,3 +229,33 @@ MonoBehaviour: DecelTime: 0 PlayerIndex: -1 AutoEnableInputs: 0 +--- !u!114 &6720462472486200866 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 5860545600847923144} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: ca7de3aefa901374ba29464584a3109a, type: 3} + m_Name: + m_EditorClassIdentifier: + CameraRadius: 0.4 + Decollision: + Enabled: 0 + ObstacleLayers: + serializedVersion: 2 + m_Bits: 1 + UseFollowTarget: + Enabled: 0 + YOffset: 0 + Damping: 0.5 + SmoothingTime: 0 + TerrainResolution: + Enabled: 1 + TerrainLayers: + serializedVersion: 2 + m_Bits: 200 + MaximumRaycast: 5 + Damping: 0.25 diff --git a/Assets/PerfectWorld/Prefab/UIManager.prefab b/Assets/PerfectWorld/Prefab/UIManager.prefab index 4d8ddf855c..25810eb002 100644 --- a/Assets/PerfectWorld/Prefab/UIManager.prefab +++ b/Assets/PerfectWorld/Prefab/UIManager.prefab @@ -1590,6 +1590,91 @@ MonoBehaviour: m_FillOrigin: 0 m_UseSpriteMesh: 0 m_PixelsPerUnitMultiplier: 1 +--- !u!1 &738639409605978842 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 3153643710304602267} + - component: {fileID: 7455661376182804299} + m_Layer: 5 + m_Name: BuffIconTemplate + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &3153643710304602267 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 738639409605978842} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: + - {fileID: 6578148550252943588} + m_Father: {fileID: 8852050935391130844} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 20, y: 20} + m_Pivot: {x: 0.5, y: 0.5} +--- !u!114 &7455661376182804299 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 738639409605978842} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 9085046f02f69544eb97fd06b6048fe2, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Navigation: + m_Mode: 3 + m_WrapAround: 0 + m_SelectOnUp: {fileID: 0} + m_SelectOnDown: {fileID: 0} + m_SelectOnLeft: {fileID: 0} + m_SelectOnRight: {fileID: 0} + m_Transition: 1 + m_Colors: + m_NormalColor: {r: 1, g: 1, b: 1, a: 1} + m_HighlightedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1} + m_PressedColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 1} + m_SelectedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1} + m_DisabledColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 0.5019608} + m_ColorMultiplier: 1 + m_FadeDuration: 0.1 + m_SpriteState: + m_HighlightedSprite: {fileID: 0} + m_PressedSprite: {fileID: 0} + m_SelectedSprite: {fileID: 0} + m_DisabledSprite: {fileID: 0} + m_AnimationTriggers: + m_NormalTrigger: Normal + m_HighlightedTrigger: Highlighted + m_PressedTrigger: Pressed + m_SelectedTrigger: Selected + m_DisabledTrigger: Disabled + m_Interactable: 0 + m_TargetGraphic: {fileID: 6217005180551732113} + toggleTransition: 1 + graphic: {fileID: 6763864164606449304} + m_Group: {fileID: 0} + onValueChanged: + m_PersistentCalls: + m_Calls: [] + m_IsOn: 1 --- !u!1 &806379414455135824 GameObject: m_ObjectHideFlags: 0 @@ -3502,8 +3587,8 @@ MonoBehaviour: _cinemachineCamera: {fileID: 0} orbital: {fileID: 0} minSwipeDistance: 0.1 - speedX: 60 - speedY: 500 + speedX: 1 + speedY: 1 --- !u!1 &2011212591958706914 GameObject: m_ObjectHideFlags: 0 @@ -4438,6 +4523,96 @@ MonoBehaviour: isAlert: 0 m_InputValidator: {fileID: 0} m_ShouldActivateOnSelect: 1 +--- !u!1 &2377867497681479792 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 6578148550252943588} + - component: {fileID: 6826588368826931644} + - component: {fileID: 6217005180551732113} + - component: {fileID: 8090153930389623919} + m_Layer: 5 + m_Name: Background + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &6578148550252943588 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2377867497681479792} + m_LocalRotation: {x: -0, y: -0, z: -0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: + - {fileID: 6747015475211827428} + m_Father: {fileID: 3153643710304602267} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 1} + m_AnchorMax: {x: 0, y: 1} + m_AnchoredPosition: {x: 10, y: -10} + m_SizeDelta: {x: 20, y: 20} + m_Pivot: {x: 0.5, y: 0.5} +--- !u!222 &6826588368826931644 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2377867497681479792} + m_CullTransparentMesh: 1 +--- !u!114 &6217005180551732113 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2377867497681479792} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 1 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: 10913, guid: 0000000000000000f000000000000000, type: 0} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 +--- !u!114 &8090153930389623919 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2377867497681479792} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 31a19414c41e5ae4aae2af33fee712f6, type: 3} + m_Name: + m_EditorClassIdentifier: + m_ShowMaskGraphic: 1 --- !u!1 &2392011451943414537 GameObject: m_ObjectHideFlags: 0 @@ -6688,6 +6863,81 @@ MonoBehaviour: m_FillOrigin: 0 m_UseSpriteMesh: 0 m_PixelsPerUnitMultiplier: 1 +--- !u!1 &3519624527311364677 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 6747015475211827428} + - component: {fileID: 2812448684976290498} + - component: {fileID: 6763864164606449304} + m_Layer: 5 + m_Name: Checkmark + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &6747015475211827428 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 3519624527311364677} + m_LocalRotation: {x: -0, y: -0, z: -0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 6578148550252943588} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0.5, y: 0.5} + m_AnchorMax: {x: 0.5, y: 0.5} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 20, y: 20} + m_Pivot: {x: 0.5, y: 0.5} +--- !u!222 &2812448684976290498 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 3519624527311364677} + m_CullTransparentMesh: 1 +--- !u!114 &6763864164606449304 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 3519624527311364677} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 1 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: -2152444580018807177, guid: 7c25a5fa6c0f21a4293b99a5a43b5441, type: 3} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 --- !u!1 &3544484534608324905 GameObject: m_ObjectHideFlags: 0 @@ -11288,6 +11538,93 @@ MonoBehaviour: m_hasFontAssetChanged: 0 m_baseMaterial: {fileID: 0} m_maskOffset: {x: 0, y: 0, z: 0, w: 0} +--- !u!1 &6515304307964713866 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 8852050935391130844} + - component: {fileID: 8312394413417420807} + - component: {fileID: 2927573214519895151} + - component: {fileID: 5686339928735905331} + m_Layer: 5 + m_Name: Panel (1) + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &8852050935391130844 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6515304307964713866} + m_LocalRotation: {x: -0, y: -0, z: -0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: + - {fileID: 3153643710304602267} + m_Father: {fileID: 2907261990866691440} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 1} + m_AnchorMax: {x: 0, y: 1} + m_AnchoredPosition: {x: 133.1923, y: -138.03845} + m_SizeDelta: {x: 0, y: 11} + m_Pivot: {x: 0, y: 0.5} +--- !u!222 &8312394413417420807 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6515304307964713866} + m_CullTransparentMesh: 1 +--- !u!114 &2927573214519895151 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6515304307964713866} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 30649d3a9faa99c48a7b1166b86bf2a0, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Padding: + m_Left: 0 + m_Right: 0 + m_Top: 0 + m_Bottom: 0 + m_ChildAlignment: 0 + m_Spacing: 25 + m_ChildForceExpandWidth: 1 + m_ChildForceExpandHeight: 1 + m_ChildControlWidth: 0 + m_ChildControlHeight: 0 + m_ChildScaleWidth: 0 + m_ChildScaleHeight: 0 + m_ReverseArrangement: 0 +--- !u!114 &5686339928735905331 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6515304307964713866} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 3245ec927659c4140ac4f8d17403cc18, type: 3} + m_Name: + m_EditorClassIdentifier: + m_HorizontalFit: 2 + m_VerticalFit: 0 --- !u!1 &6631939314334477079 GameObject: m_ObjectHideFlags: 0 @@ -22736,27 +23073,30 @@ PrefabInstance: m_AddedGameObjects: - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 7 - addedObject: {fileID: 1389770869284841247} + addedObject: {fileID: 8852050935391130844} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 8 - addedObject: {fileID: 9208725189562257770} + addedObject: {fileID: 1389770869284841247} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 9 - addedObject: {fileID: 1505082503590519222} + addedObject: {fileID: 9208725189562257770} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 10 - addedObject: {fileID: 5191021986578083479} + addedObject: {fileID: 1505082503590519222} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 11 - addedObject: {fileID: 494610354563246192} + addedObject: {fileID: 5191021986578083479} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 12 - addedObject: {fileID: 2090006027067688671} + addedObject: {fileID: 494610354563246192} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 13 - addedObject: {fileID: 5264098290850076161} + addedObject: {fileID: 2090006027067688671} - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} insertIndex: 14 + addedObject: {fileID: 5264098290850076161} + - targetCorrespondingSourceObject: {fileID: 6806681442789174374, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} + insertIndex: 15 addedObject: {fileID: 6421830357984996457} m_AddedComponents: [] m_SourcePrefab: {fileID: 100100000, guid: 76408ccdbeb4c654291462fcff24a8c5, type: 3} diff --git a/Assets/PerfectWorld/Scripts/Camera/CameraController.cs b/Assets/PerfectWorld/Scripts/Camera/CameraController.cs index 947466709a..d85034b7c5 100644 --- a/Assets/PerfectWorld/Scripts/Camera/CameraController.cs +++ b/Assets/PerfectWorld/Scripts/Camera/CameraController.cs @@ -1,48 +1,51 @@ using Unity.Cinemachine; using UnityEngine; using UnityEngine.EventSystems; +using UnityEngine.Serialization; namespace BrewMonster { public class CameraController : MonoBehaviour, IPointerDownHandler, IPointerUpHandler, IDragHandler { public static CameraController Instance; - [SerializeField]private CinemachineCamera _cinemachineCamera; - [SerializeField]private CinemachineOrbitalFollow orbital; - private Vector2 currentPos; + [SerializeField] private CinemachineCamera _cinemachineCamera; + [SerializeField] private CinemachineOrbitalFollow orbital; private bool fingerDown = false; - Vector2 delta = Vector2.zero; - public float minSwipeDistance = 10f; - public float speedX = 1f; - public float speedY = 1f; + [SerializeField, Min(0f)] private float dragDeadZone = 10f; + [SerializeField] private float horizontalRotationPerScreen = 60f; + [SerializeField] private float verticalRotationPerScreen = 500f; + [SerializeField, HideInInspector] private bool _migratedDeadZoneToNormalized; public CinemachineOrbitalFollow Orbital { get => orbital;} void OnEnable() { Instance = this; -#if UNITY_EDITOR - speedX = 500; -#endif + MigrateLegacyDeadZone(); } public void OnDrag(PointerEventData eventData) { - delta = eventData.position - currentPos; - - if (delta.magnitude >= minSwipeDistance) + if (!fingerDown || orbital == null) { - orbital.HorizontalAxis.Value += delta.normalized.x * speedX * Time.deltaTime; + return; + } + + float screenReference = Mathf.Max(1f, Mathf.Min(Screen.width, Screen.height)); + Vector2 normalizedDelta = eventData.delta / screenReference; + float normalizedDeadZone = Mathf.Max(0.0001f, dragDeadZone); + + if (normalizedDelta.sqrMagnitude >= normalizedDeadZone * normalizedDeadZone) + { + orbital.HorizontalAxis.Value += normalizedDelta.x * horizontalRotationPerScreen; //orbital.HorizontalAxis.Value = Mathf.Clamp(orbital.HorizontalAxis.Value, -360f, 360f); - orbital.VerticalAxis.Value -= delta.normalized.y * speedY * Time.deltaTime; + orbital.VerticalAxis.Value -= normalizedDelta.y * verticalRotationPerScreen; orbital.VerticalAxis.Value = Mathf.Clamp(orbital.VerticalAxis.Value, -360f, 360f); } - currentPos = eventData.position; } public void OnPointerDown(PointerEventData eventData) { - currentPos = eventData.position; fingerDown = true; } @@ -51,6 +54,29 @@ namespace BrewMonster fingerDown = false; } + private void OnValidate() + { + MigrateLegacyDeadZone(); + } + + private void MigrateLegacyDeadZone() + { + if (_migratedDeadZoneToNormalized) + { + return; + } + + // Older values were serialized in pixels; convert once to normalized short-side ratio. + if (dragDeadZone > 0.05f) + { + dragDeadZone /= 1080f; + } + + dragDeadZone = Mathf.Max(0.0001f, dragDeadZone); + + _migratedDeadZoneToNormalized = true; + } + private void Update() { //todo: should not always update diff --git a/Assets/PerfectWorld/Scripts/Network/CSNetwork/GPDataType.cs b/Assets/PerfectWorld/Scripts/Network/CSNetwork/GPDataType.cs index 09481fa9a6..7bc1b77fee 100644 --- a/Assets/PerfectWorld/Scripts/Network/CSNetwork/GPDataType.cs +++ b/Assets/PerfectWorld/Scripts/Network/CSNetwork/GPDataType.cs @@ -1588,6 +1588,11 @@ namespace CSNetwork.GPDataType public byte byPackage; public byte bySlot; } + [StructLayout(LayoutKind.Sequential, Pack = 1)] + public struct cmd_pickup_money + { + public int amount; + } [StructLayout(LayoutKind.Sequential, Pack = 1)] public struct cmd_produce_start diff --git a/Assets/PerfectWorld/Scripts/Objet/Shortcut/CECShortcutSet.cs b/Assets/PerfectWorld/Scripts/Objet/Shortcut/CECShortcutSet.cs index cdddcd410b..4fd93fce73 100644 --- a/Assets/PerfectWorld/Scripts/Objet/Shortcut/CECShortcutSet.cs +++ b/Assets/PerfectWorld/Scripts/Objet/Shortcut/CECShortcutSet.cs @@ -762,6 +762,10 @@ namespace BrewMonster /// public int GetShortcutNum() { + if(m_aShortcuts == null || m_aShortcuts.Count == 0) + { + return 0; + } return m_aShortcuts.Count; } diff --git a/Assets/PerfectWorld/Scripts/Task/UI/DlgTask.cs b/Assets/PerfectWorld/Scripts/Task/UI/DlgTask.cs index 9e9d132c3a..6c927e7b96 100644 --- a/Assets/PerfectWorld/Scripts/Task/UI/DlgTask.cs +++ b/Assets/PerfectWorld/Scripts/Task/UI/DlgTask.cs @@ -201,8 +201,7 @@ namespace BrewMonster.Scripts.Task.UI }); trigger.triggers.Add(entry); - } - + } OnInitDialog(); } @@ -513,7 +512,7 @@ namespace BrewMonster.Scripts.Task.UI // Refresh UI immediately to reflect the change // The server confirmation will trigger another refresh, but this gives immediate feedback - RefreshTaskTrace(); + RefreshTaskTrace(true); // Clear selection if the abandoned task was selected if (m_idSelTask == (int)topTaskId) @@ -658,7 +657,7 @@ namespace BrewMonster.Scripts.Task.UI // public bool Tick() { - RefreshTaskTrace(); + //RefreshTaskTrace(); // Time-window task refresh: while in Search view, refresh the list when server time crosses a minute boundary. // This is throttled to avoid rebuilding large task lists every frame. if (m_iType == 1) @@ -758,16 +757,11 @@ namespace BrewMonster.Scripts.Task.UI return true; } + - public void TickTaskTrace() - { - if (m_TaskTraceCounter.IncCounter(EC_Game.GetRealTickTime())) { - m_TaskTraceCounter.Reset(); - RefreshTaskTrace(); - } - } - public void RefreshTaskTrace() + public void RefreshTaskTrace(bool bShowTrace) { + m_bShowTrace = bShowTrace; // Get AUIManager, fallback to GetGameUIMan() if m_pAUIManager is not set yet // 获取AUIManager,如果m_pAUIManager尚未设置则回退到GetGameUIMan() AUIManager auiManager = GetAUIManager(); @@ -782,8 +776,11 @@ namespace BrewMonster.Scripts.Task.UI DlgTaskTrace pDlgTaskTrace = auiManager.GetDialog("Win_QuestMinion") as DlgTaskTrace; if (pDlgTaskTrace == null) return; - if (m_pTog_bShowTrace && !m_bShowTrace) + if (!m_bShowTrace) + { + pDlgTaskTrace.Show(false); return; + } ShowType showType = pDlgTaskTrace.GetShowType(); // bool bShow = showType == ShowType.ST_TRACED || showType == ShowType.ST_TITLE; bool bShow =true;//for test @@ -1379,18 +1376,12 @@ namespace BrewMonster.Scripts.Task.UI if(auiManager != null) { AUIDialog pTrace = auiManager.GetDialog("Win_QuestMinion"); - if(pTrace.IsShow() == true) - { - m_pTog_bShowTrace.isOn = true; - } - else - { - m_pTog_bShowTrace.isOn = false; - } + m_pTog_bShowTrace.SetIsOnWithoutNotify(pTrace.IsShow() == true); + //m_bShowTrace = pTrace.IsShow() == true; } else { - OnCommand_showtrace(null,true); + OnCommand_showtrace(null,false); } if (m_idSelTask != 0) UpdateTask(); diff --git a/Assets/PerfectWorld/Scripts/UI/DlgAward/CDlgAward.cs b/Assets/PerfectWorld/Scripts/UI/DlgAward/CDlgAward.cs index 965c66e850..adf8dc319f 100644 --- a/Assets/PerfectWorld/Scripts/UI/DlgAward/CDlgAward.cs +++ b/Assets/PerfectWorld/Scripts/UI/DlgAward/CDlgAward.cs @@ -401,7 +401,9 @@ namespace BrewMonster.Scripts.UI break; } } - } + + itemInfoPanel.SetActive(false); + } void OnAwardItemClicked(string hint, bool isOn, AwardItem awardItem) { @@ -513,4 +515,4 @@ namespace BrewMonster.Scripts.UI LayoutRebuilder.ForceRebuildLayoutImmediate(parent); } } -} \ No newline at end of file +} diff --git a/Assets/PerfectWorld/Scripts/UI/GamePlay/CdlgQuickBar.cs b/Assets/PerfectWorld/Scripts/UI/GamePlay/CdlgQuickBar.cs index 5157754cd9..b29d19d512 100644 --- a/Assets/PerfectWorld/Scripts/UI/GamePlay/CdlgQuickBar.cs +++ b/Assets/PerfectWorld/Scripts/UI/GamePlay/CdlgQuickBar.cs @@ -50,6 +50,10 @@ namespace BrewMonster } public bool UpdateShortcuts() { + if(AUIImagePictureList == null || AUIImagePictureList.Count == 0) + { + return false; + } CECShortcut pSC; CECSCSkill pSCSkill; AUIImagePicture pCell; @@ -60,13 +64,15 @@ namespace BrewMonster int nCurPanel9 = GetCurPanel1(); int nCurPanel8 = GetCurPanel2(); CECHostPlayer pHost = EC_Game.GetGameRun().GetHostPlayer(); - if (pHost == null) return false; + if (pHost == null) + return false; var a_pSCS = new List(); var a_pszPanel = new List(); GetQuickBarNameAndSC(pHost, a_pszPanel, a_pSCS, nCurPanel9, nCurPanel8); if (a_pSCS == null || a_pSCS.Count < 2) return false; + if(currentListIndex >= a_pSCS.Count ) { currentListIndex = 0; @@ -80,7 +86,12 @@ namespace BrewMonster // } // currentOffsetIndex += a_pSCS[i].GetShortcutNum(); // } - int nSlots = Mathf.Min(a_pSCS[currentListIndex].GetShortcutNum(), AUIImagePictureList.Count); + var shortcutNum = a_pSCS[currentListIndex]?.GetShortcutNum() ?? 0; + if(shortcutNum <= 0) + { + return false; + } + int nSlots = Mathf.Min(shortcutNum, AUIImagePictureList.Count); for (int j = 0; j < nSlots; j++) { pCell = AUIImagePictureList[j]; diff --git a/Assets/Prefabs/UI/item_info.prefab b/Assets/Prefabs/UI/item_info.prefab index f3a0636b48..efc7fa542f 100644 --- a/Assets/Prefabs/UI/item_info.prefab +++ b/Assets/Prefabs/UI/item_info.prefab @@ -36,8 +36,8 @@ RectTransform: m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} m_AnchorMin: {x: 0, y: 1} m_AnchorMax: {x: 0, y: 1} - m_AnchoredPosition: {x: 20, y: -402.765} - m_SizeDelta: {x: 400, y: 805.53} + m_AnchoredPosition: {x: 20, y: -464.01} + m_SizeDelta: {x: 400, y: 928.02} m_Pivot: {x: 0, y: 0.5} --- !u!222 &4376431126769957786 CanvasRenderer: @@ -213,7 +213,7 @@ RectTransform: m_AnchorMin: {x: 0, y: 1} m_AnchorMax: {x: 0, y: 1} m_AnchoredPosition: {x: 547.334, y: -28.5943} - m_SizeDelta: {x: 163.80408, y: 49.0205} + m_SizeDelta: {x: 171, y: 64} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &7968706394531223960 CanvasRenderer: @@ -332,7 +332,7 @@ RectTransform: m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} m_AnchorMin: {x: 0, y: 1} m_AnchorMax: {x: 0, y: 1} - m_AnchoredPosition: {x: 20, y: -805.53} + m_AnchoredPosition: {x: 20, y: -928.02} m_SizeDelta: {x: 450, y: 0} m_Pivot: {x: 0, y: 0.5} --- !u!222 &1207680936664328091 @@ -482,8 +482,8 @@ RectTransform: m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} m_AnchorMin: {x: 0, y: 0} m_AnchorMax: {x: 1, y: 1} - m_AnchoredPosition: {x: 0.000061035156, y: 0} - m_SizeDelta: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 2.5} + m_SizeDelta: {x: -16, y: -15} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &2820616548424895708 CanvasRenderer: @@ -540,15 +540,15 @@ MonoBehaviour: m_faceColor: serializedVersion: 2 rgba: 4294967295 - m_fontSize: 24 - m_fontSizeBase: 24 + m_fontSize: 36 + m_fontSizeBase: 36 m_fontWeight: 400 m_enableAutoSizing: 0 m_fontSizeMin: 18 m_fontSizeMax: 72 m_fontStyle: 0 m_HorizontalAlignment: 2 - m_VerticalAlignment: 512 + m_VerticalAlignment: 8192 m_textAlignment: 65535 m_characterSpacing: 0 m_wordSpacing: 0 @@ -620,8 +620,8 @@ RectTransform: m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} m_AnchorMin: {x: 0, y: 1} m_AnchorMax: {x: 0, y: 1} - m_AnchoredPosition: {x: 547.334, y: -91.01306} - m_SizeDelta: {x: 163.80408, y: 49.0205} + m_AnchoredPosition: {x: 547.334, y: -101} + m_SizeDelta: {x: 171, y: 64} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &7060942486687674079 CanvasRenderer: @@ -746,7 +746,7 @@ RectTransform: m_AnchorMin: {x: 0.5, y: 0.5} m_AnchorMax: {x: 0.5, y: 0.5} m_AnchoredPosition: {x: 220.02612, y: -32.73999} - m_SizeDelta: {x: 450, y: 0} + m_SizeDelta: {x: 450, y: 948.02} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &7489840247554268479 CanvasRenderer: @@ -1025,8 +1025,8 @@ RectTransform: m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} m_AnchorMin: {x: 0, y: 0} m_AnchorMax: {x: 1, y: 1} - m_AnchoredPosition: {x: 0.000061035156, y: 0} - m_SizeDelta: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 2.5} + m_SizeDelta: {x: -16, y: -15} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &3402785809763655235 CanvasRenderer: @@ -1083,15 +1083,15 @@ MonoBehaviour: m_faceColor: serializedVersion: 2 rgba: 4294967295 - m_fontSize: 24 - m_fontSizeBase: 24 + m_fontSize: 36 + m_fontSizeBase: 36 m_fontWeight: 400 m_enableAutoSizing: 0 m_fontSizeMin: 18 m_fontSizeMax: 72 m_fontStyle: 0 m_HorizontalAlignment: 2 - m_VerticalAlignment: 512 + m_VerticalAlignment: 8192 m_textAlignment: 65535 m_characterSpacing: 0 m_wordSpacing: 0 diff --git a/Assets/Scripts/CECHostPlayer.Inventory.cs b/Assets/Scripts/CECHostPlayer.Inventory.cs index ee6d652df0..b965df4f0e 100644 --- a/Assets/Scripts/CECHostPlayer.Inventory.cs +++ b/Assets/Scripts/CECHostPlayer.Inventory.cs @@ -196,6 +196,7 @@ namespace BrewMonster { var money = GPDataTypeHelper.FromBytes(data); SetMoneyAmount(money.amount); + m_iMaxMoney = (int)money.max_amount; EC_InventoryUI ui = GameObject.FindFirstObjectByType(); if (ui != null && ui.gameObject.activeInHierarchy) @@ -797,7 +798,33 @@ namespace BrewMonster // Add money amount private int AddMoneyAmount(int iAmount) { - m_iMoneyCnt += (uint)iAmount; + long next = (long)m_iMoneyCnt + iAmount; + if (next < 0) + { + next = 0; + } + + if(m_iMaxMoney > 0 && next > m_iMaxMoney) + { + next = m_iMaxMoney; + } + + m_iMoneyCnt = (uint)next; + + ulong amount = m_iMoneyCnt; + ulong maxAmount = m_iMaxMoney > 0 ? (ulong)m_iMaxMoney : amount; + + EC_InventoryUI ui = GameObject.FindFirstObjectByType(); + if(ui != null && ui.gameObject.activeInHierarchy) + { + ui.UpdateMoney(amount, maxAmount); + } + else + { + EC_InventoryUI.CacheMoney(amount, maxAmount); + } + + //m_iMoneyCnt += (uint)iAmount; return (int)m_iMoneyCnt; } diff --git a/Assets/Scripts/CECHostPlayer.cs b/Assets/Scripts/CECHostPlayer.cs index 9531539004..37320efbc2 100644 --- a/Assets/Scripts/CECHostPlayer.cs +++ b/Assets/Scripts/CECHostPlayer.cs @@ -544,6 +544,9 @@ namespace BrewMonster case EC_MsgDef.MSG_HST_USEITEM: OnMsgHstUseItem(Msg); break; + case EC_MsgDef.MSG_HST_PICKUPMONEY: + OnMsgHstPickupMoney(Msg); + break; case EC_MsgDef.MSG_HST_ATKRESULT: OnMsgHstAttackResult(Msg); break; case EC_MsgDef.MSG_HST_ATTACKONCE: OnMsgHstAttackOnce(Msg); break; case EC_MsgDef.MSG_HST_ATTACKED: OnMsgHstAttacked(Msg); break; @@ -612,11 +615,206 @@ namespace BrewMonster } }*/ } + + private void OnMsgHstPickupMoney(ECMSG msg) + { + var data = msg.dwParam1 as byte[]; + if (data == null || data.Length == 0) + return; + + cmd_pickup_money pCmd = GPDataTypeHelper.FromBytes(data); + AddMoneyAmount(pCmd.amount); + CECGameRun pGameRun = EC_Game.GetGameRun(); + pGameRun.AddFixedMessage((int)FixedMsg.FIXMSG_PICKUPMONEY); + BubbleText((int)BubbleTextType.BUBBLE_MONEY, (uint)pCmd.amount); + } + + private void BubbleText(int iIndex, uint dwNum, int p1 = 0) + { + bool isHost = IsHostPlayer(); + + if (isHost) + { + CECHostPlayer pHost = EC_Game.GetGameRun().GetHostPlayer(); + if (iIndex == (int)BubbleTextType.BUBBLE_EXP) + { + bool hasBookExp = pHost != null && pHost.m_ReincarnationTome.tome_active != 0; + int msgId = (int)dwNum > 0 ? + (hasBookExp ? (int)FixedMsg.FIXMSG_GOT_BOOKEXP : (int)FixedMsg.FIXMSG_GOTEXP) : + (int)FixedMsg.FIXMSG_LOSTEXP; + EC_Game.GetGameRun()?.AddFixedChannelMsg(msgId, (int)ChatChannel.GP_CHAT_FIGHT, (int)dwNum); + } + + if (iIndex == (int)BubbleTextType.BUBBLE_SP) + { + EC_Game.GetGameRun()?.AddFixedChannelMsg((int)FixedMsg.FIXMSG_GOTSP, (int)ChatChannel.GP_CHAT_FIGHT, (int)dwNum); + } + + if (iIndex == (int)BubbleTextType.BUBBLE_REALMEXP) + { + EC_Game.GetGameRun()?.AddFixedChannelMsg((int)FixedMsg.FIXMSG_GOT_REALMEXP, (int)ChatChannel.GP_CHAT_FIGHT, (int)dwNum); + } + } + + Vector3 vPos; + if (IsInChariot()) + { + var dummy = GetDummyModel((int)PLAYERMODEL_TYPE.PLAYERMODEL_DUMMYTYPE2); + if (dummy != null) + { + // TODO + //vPos = GetPos() + g_vAxisY * (dummy.GetModelAABB().Extents.y * 2.3f); + } + else + { + vPos = EC_Utility.ToVector3(GetPos()) + g_vAxisY * (m_aabb.Extents.y * 2.5f); + } + + //CECBubbleDecal* pBubbleDecal = m_pBubbleTexts->AddDecal(vPos, CECDecal::DCID_ICONDECAL); + //CECIconDecal* pDecal = (CECIconDecal*)pBubbleDecal->GetDecal(); + + //switch (iIndex) + //{ + // case BUBBLE_DAMAGE: + + // if (!bHost) + // dwCol = A3DCOLORRGB(237, 56, 0); + + // if (p1 & 0x0001) + // pDecal->AddIcon(CECImageRes::IMG_DEADLYSTRIKE, 0, dwCol); + // else if (p1 & 0x0002) + // pDecal->AddIcon(CECImageRes::IMG_RETORT, 0, dwCol); + + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // break; + + // case BUBBLE_EXP: + + // pDecal->AddIcon(CECImageRes::IMG_GOTEXP, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // // pDecal->SetScreenPos(80, 70); + // // pDecal->EnableScreenPos(true); + // break; + + // case BUBBLE_SP: + + // pDecal->AddIcon(CECImageRes::IMG_GOTSP, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // // pDecal->SetScreenPos(80, 90); + // // pDecal->EnableScreenPos(true); + // break; + + // case BUBBLE_MONEY: + + // pDecal->AddIcon(CECImageRes::IMG_GOTMONEY, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // break; + + // case BUBBLE_LEVELUP: + + // pDecal->AddIcon(CECImageRes::IMG_LEVELUP, 0, dwCol); + // break; + + // case BUBBLE_HITMISSED: + + // if (!bHost) + // dwCol = A3DCOLORRGB(237, 56, 0); + + // pDecal->AddIcon(CECImageRes::IMG_HITMISSED, 0, dwCol); + // break; + + // case BUBBLE_INVALIDHIT: + + // if (!bHost) + // dwCol = A3DCOLORRGB(237, 56, 0); + + // pDecal->AddIcon(CECImageRes::IMG_INVALIDHIT, 0, dwCol); + // break; + + // case BUBBLE_IMMUNE: + + // if (!bHost) + // dwCol = A3DCOLORRGB(237, 56, 0); + + // pDecal->AddIcon(CECImageRes::IMG_IMMUNE, 0, dwCol); + // break; + + // case BUBBLE_HPWARN: + + // dwCol = A3DCOLORRGB(255, 255, 255); + // pDecal->AddIcon(CECImageRes::IMG_HPWARN, 0, dwCol); + // break; + + // case BUBBLE_MPWARN: + + // dwCol = A3DCOLORRGB(255, 255, 255); + // pDecal->AddIcon(CECImageRes::IMG_MPWARN, 0, dwCol); + // break; + + // case BUBBLE_REBOUND: + + // pDecal->AddIcon(CECImageRes::IMG_REBOUND, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // break; + + // case BUBBLE_BEAT_BACK: + + // pDecal->AddIcon(CECImageRes::IMG_BEAT_BACK, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // break; + + // case BUBBLE_ADD: + + // dwCol = A3DCOLORRGB(126, 206, 244); + // pDecal->AddIcon(CECImageRes::IMG_ADD, 0, dwCol); + // pDecal->AddNumIcons(CECImageRes::IMG_POPUPNUM, dwNum, dwCol); + // break; + + // case BUBBLE_DODGE_DEBUFF: + + // if (!bHost) + // dwCol = A3DCOLORRGB(237, 56, 0); + + // pDecal->AddIcon(CECImageRes::IMG_DODGE_DEBUFF, 0, dwCol); + // break; + + // default: + // return; + } + else + { + vPos = EC_Utility.ToVector3(GetPos()) + g_vAxisY * (m_aabb.Extents.y * 2.5f); + } + } + + private bool IsInChariot() + { + CECGameRun pRun = EC_Game.GetGameRun(); + if(pRun == null) + return false; + + CECHostPlayer pHost = pRun.GetHostPlayer(); + if (pHost && pHost.GetBattleInfo().IsChariotWar() && GetShapeType() == (int)PLAYERMODEL_TYPE.PLAYERMODEL_DUMMYTYPE2 + && GetDummyModel((int)PLAYERMODEL_TYPE.PLAYERMODEL_DUMMYTYPE2)) + { + return true; + } + return false; + } + + private BATTLEINFO m_BattleInfo; + + private BATTLEINFO GetBattleInfo() + { + return m_BattleInfo; + } + private void NotifyUIUpdateTeam(bool showDialog = false) { //try //{ // var ui = EC_Game.GetGameRun()?.GetUIManager()?.GetInGameUIMan(); + // var ui = EC_Game.GetGameRun()?.GetUIManager()?.GetInGameUIMan(); // if (ui is CECGameUIMan gui) // gui.UpdateTeam(false); //} @@ -3319,6 +3517,25 @@ namespace BrewMonster LIES_DISABLEFIGHT = 0x000B, } + public enum BubbleTextType + { + BUBBLE_DAMAGE = 0, + BUBBLE_EXP, + BUBBLE_SP, + BUBBLE_MONEY, + BUBBLE_LEVELUP, + BUBBLE_HITMISSED, + BUBBLE_INVALIDHIT, + BUBBLE_IMMUNE, + BUBBLE_HPWARN, + BUBBLE_MPWARN, + BUBBLE_REBOUND, // ·´µ¯ + BUBBLE_BEAT_BACK, // ·´»÷ + BUBBLE_ADD, // ÎüѪµÄ¼ÓºÅ + BUBBLE_DODGE_DEBUFF, + BUBBLE_REALMEXP, + } + // ½øÈë»ùµØÐÅÏ¢ public struct FACTION_FORTRESS_ENTER { diff --git a/Assets/Scripts/CECUIManager.cs b/Assets/Scripts/CECUIManager.cs index c55d81803a..2849c65333 100644 --- a/Assets/Scripts/CECUIManager.cs +++ b/Assets/Scripts/CECUIManager.cs @@ -106,9 +106,9 @@ public class CECUIManager : MonoSingleton var dlgTaskTraceDialog = inGameUIMan.GetDialog("Win_QuestMinion"); if (dlgTaskDialog != null && dlgTaskDialog is BrewMonster.Scripts.Task.UI.DlgTask dlgTaskForTrace) { - if (dlgTaskTraceDialog != null && dlgTaskTraceDialog.IsShow()) + if (dlgTaskTraceDialog != null) { - dlgTaskForTrace.RefreshTaskTrace(); + dlgTaskForTrace.RefreshTaskTrace(dlgTaskTraceDialog.IsShow()); } dlgTaskForTrace.Tick(); diff --git a/Assets/Scripts/ChatInputHandler.cs b/Assets/Scripts/ChatInputHandler.cs index 52ea285b5f..21b772865b 100644 --- a/Assets/Scripts/ChatInputHandler.cs +++ b/Assets/Scripts/ChatInputHandler.cs @@ -106,6 +106,7 @@ namespace BrewMonster.Scripts.ChatUI if (strText.Length <= 0) { + ClearTextInInputField(); //ChangeFocus(); return; } @@ -133,6 +134,7 @@ namespace BrewMonster.Scripts.ChatUI SaveHistory(resolvedChannel, strText, nPack, nSlot, now); + ClearTextInInputField(); //ChangeFocus(); } @@ -317,6 +319,14 @@ namespace BrewMonster.Scripts.ChatUI private void SendPrivateChat(string target, string msg, int pack, int slot) { Debug.Log($"Whisper to {target}: {msg}"); + + // [Port] C++: CDlgChat::OnCommand_speak → privatechat branch + // Gửi tin nhắn mật (whisper) lên server qua GameSession. + UnityGameSession.Instance.GameSession.SendPrivateChatData(target, msg, 0, 0, pack, slot); + + // Server không echo whisper lại cho chính mình → hiện local echo + string localEcho = $"[Whisper] → {target}: {msg}"; + EventBus.Publish(new GameSession.ChatMessageEvent(localEcho, (byte)ChatChannel.GP_CHAT_WHISPER)); } // ===================================================== @@ -410,9 +420,12 @@ namespace BrewMonster.Scripts.ChatUI private bool IsPlayerBlacklisted(int idPlayer) => false; // Placeholder - private void ChangeFocus() + private void ClearTextInInputField() { inputField.text = ""; + } + private void ChangeFocus() + { inputField.ActivateInputField(); }