diff --git a/Assets/PerfectWorld/Scripts/Managers/EC_InventoryUI.cs b/Assets/PerfectWorld/Scripts/Managers/EC_InventoryUI.cs
index 389d947ae2..8743a04f9c 100644
--- a/Assets/PerfectWorld/Scripts/Managers/EC_InventoryUI.cs
+++ b/Assets/PerfectWorld/Scripts/Managers/EC_InventoryUI.cs
@@ -15,6 +15,8 @@ using System.Text;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
+using BrewMonster.Scripts.UI.Inventory;
+using CSNetwork.Protocols.RPCData;
namespace BrewMonster.Scripts.Managers
{
@@ -166,6 +168,7 @@ namespace BrewMonster.Scripts.Managers
ShowDetailPanel(false);
ShowSplitPanel(false);
RefreshAll();
+ RefreshCharacterModelPreview();
}
private void WireSplitUI()
@@ -688,6 +691,7 @@ namespace BrewMonster.Scripts.Managers
Debug.Log($"[InventoryUI] Equip request sent for item {currentSelectedItem.m_tid} from slot {currentSelectedSlot} to equip location {equipLocation}");
// Refresh inventory after equip
RefreshAll();
+ RefreshCharacterModelPreview();
});
}
@@ -713,6 +717,7 @@ namespace BrewMonster.Scripts.Managers
Debug.Log($"[InventoryUI] Unequip request sent for item {currentSelectedItem.m_tid} from equip location {equipLocation} to inventory slot {emptySlot}");
// Refresh inventory after unequip
RefreshAll();
+ RefreshCharacterModelPreview();
});
}
@@ -738,6 +743,7 @@ namespace BrewMonster.Scripts.Managers
// Refresh inventory after drop
RefreshAll();
+ RefreshCharacterModelPreview();
}
///
@@ -1617,6 +1623,61 @@ namespace BrewMonster.Scripts.Managers
return false;
}
+ public void RefreshCharacterModelPreview()
+ {
+ var preview = PlayerModelPreview.Instance;
+ if (preview != null)
+ {
+ RoleInfo roleInfo = BuildCurrentPreviewRoleInfo();
+ if (roleInfo != null)
+ {
+ preview.ReloadRoleModel(roleInfo);
+ }
+ }
+
+ var inventoryPreview = FindFirstObjectByType();
+ if (inventoryPreview != null)
+ {
+ inventoryPreview.QueueRefresh();
+ }
+ }
+
+ private RoleInfo BuildCurrentPreviewRoleInfo()
+ {
+ RoleInfo roleInfo = UnityGameSession.Instance != null ? UnityGameSession.Instance.GetRoleInfo() : null;
+ if (roleInfo == null)
+ return null;
+
+ RoleInfo snapshot = roleInfo.Clone();
+ if (snapshot.equipment == null)
+ snapshot.equipment = new List();
+ else
+ snapshot.equipment.Clear();
+
+ CECHostPlayer host = CECGameRun.Instance?.GetHostPlayer();
+ var equipInv = host?.GetInventory(InventoryConst.IVTRTYPE_EQUIPPACK);
+ if (equipInv == null)
+ return snapshot;
+
+ int size = equipInv.GetSize();
+ for (int i = 0; i < size; i++)
+ {
+ EC_IvtrItem item = equipInv.GetItem(i, false);
+ if (item == null)
+ continue;
+
+ snapshot.equipment.Add(new GRoleInventory
+ {
+ id = (uint)item.GetTemplateID(),
+ pos = i,
+ count = item.GetCount(),
+ max_count = Math.Max(1, item.GetPileLimitInstance())
+ });
+ }
+
+ return snapshot;
+ }
+
private bool IsPointerOverDetailPanel(Vector2 screenPosition)
{
var panelRect = detailPanelRoot.transform as RectTransform;
diff --git a/Assets/PerfectWorld/Scripts/Players/PlayerModelPreview.cs b/Assets/PerfectWorld/Scripts/Players/PlayerModelPreview.cs
index dbff7fb706..082a34a4d8 100644
--- a/Assets/PerfectWorld/Scripts/Players/PlayerModelPreview.cs
+++ b/Assets/PerfectWorld/Scripts/Players/PlayerModelPreview.cs
@@ -15,6 +15,9 @@ namespace BrewMonster.Scripts
private int _loadVersion;
+ private bool _hasRequestedPlayerModelId;
+ private int _requestedPlayerModelId;
+
private void Awake()
{
if (modelRoot == null)
@@ -50,20 +53,19 @@ namespace BrewMonster.Scripts
if (version != _loadVersion)
{
- if (model != null)
- Destroy(model);
+ Destroy(model);
return;
}
- if (model == null)
- continue;
-
model.transform.SetParent(modelRoot, false);
model.transform.localPosition = Vector3.zero;
model.transform.localRotation = Quaternion.identity;
model.SetActive(false);
+
playerModels.Add(model);
playerModelIds.Add(role.roleid);
+
+ ApplyRequestedModelVisibility();
}
}
@@ -72,13 +74,36 @@ namespace BrewMonster.Scripts
///
public void ShowPlayerModel(int playerModelId)
{
+ //int n = Mathf.Min(playerModels.Count, playerModelIds.Count);
+ //for (int i = 0; i < n; i++)
+ //{
+ // GameObject go = playerModels[i];
+ // if (go == null)
+ // continue;
+ // go.SetActive(playerModelIds[i] == playerModelId);
+ //}
+ _hasRequestedPlayerModelId = true;
+ _requestedPlayerModelId = playerModelId;
+
+ ApplyRequestedModelVisibility();
+ }
+
+ ///
+ /// Applies the visibility of player models based on the requested player model id.
+ ///
+ private void ApplyRequestedModelVisibility()
+ {
+ if(!_hasRequestedPlayerModelId)
+ return;
+
int n = Mathf.Min(playerModels.Count, playerModelIds.Count);
for (int i = 0; i < n; i++)
{
GameObject go = playerModels[i];
- if (go == null)
+ if(go == null)
continue;
- go.SetActive(playerModelIds[i] == playerModelId);
+
+ go.SetActive(playerModelIds[i] == _requestedPlayerModelId);
}
}
@@ -307,5 +332,14 @@ namespace BrewMonster.Scripts
}
return skeletonBuilder;
}
+
+ public void ReloadRoleModel(RoleInfo roleInfo)
+ {
+ if (roleInfo == null)
+ return;
+
+ ShowAllPlayerModels(new List { roleInfo });
+ ShowPlayerModel(roleInfo.roleid);
+ }
}
}
diff --git a/Assets/PerfectWorld/Scripts/UI/Inventory/InventoryCharacterPreview.cs b/Assets/PerfectWorld/Scripts/UI/Inventory/InventoryCharacterPreview.cs
index 3ae85ac9ee..8b127d6206 100644
--- a/Assets/PerfectWorld/Scripts/UI/Inventory/InventoryCharacterPreview.cs
+++ b/Assets/PerfectWorld/Scripts/UI/Inventory/InventoryCharacterPreview.cs
@@ -27,21 +27,23 @@ namespace BrewMonster.Scripts.UI.Inventory
[SerializeField] private Vector3 previewLocalPosition = Vector3.zero;
[SerializeField] private Vector3 previewLocalEuler;
[SerializeField] private Vector3 previewLocalScale = Vector3.one;
- [SerializeField] private float previewHeightOffset = 0.12f;
- [Tooltip("Copy the preview root layer onto the cloned hierarchy so the preview camera can isolate it.")]
- [SerializeField] private bool inheritPreviewLayer = true;
[Header("Camera Output")]
[SerializeField] private RawImage previewFrame;
[SerializeField] private RenderTexture previewRenderTexture;
[SerializeField] private bool autoFocusCamera = true;
- [SerializeField] private Vector3 cameraFocusOffset = new Vector3(0f, 1.5f, 0f);
+ [SerializeField] private Vector3 cameraFocusOffset = new Vector3(0f, 0f, 0f);
[Header("Camera Framing")]
- [SerializeField] private float previewCameraDistance = 1.4f;
- [SerializeField] private Vector3 previewCameraOffset = new Vector3(0f, 0.5f, 0f);
+ [SerializeField] private float previewCameraDistance = 3.3f;
+ [SerializeField] private Vector3 previewCameraOffset = new Vector3(0.15f, 0.8f, 0f);
[SerializeField] private bool overrideFieldOfView = true;
- [SerializeField][Range(10f, 60f)] private float previewFieldOfView = 38f;
+ [SerializeField][Range(10f, 60f)] private float previewFieldOfView = 33f;
+
+ [SerializeField] private bool autoFrameByBounds = true;
+ [SerializeField][Range(1f, 2f)] private float autoFramePadding = 1.15f;
+ [SerializeField] private float minAutoCameraDistance = 1.25f;
+ [SerializeField] private float maxAutoCameraDistance = 8f;
private bool _cameraStateCached;
private Vector3 _cachedCameraPosition;
@@ -95,17 +97,27 @@ namespace BrewMonster.Scripts.UI.Inventory
// Check if origin model structure has changed (equipment models are child objects)
// This detects equipment changes in realtime since all equipment is attached as children
Transform currentOriginRoot = ResolveSourceModelRoot();
- if (currentOriginRoot != null)
+ if (currentOriginRoot == null)
{
- int currentChildCount = CountAllChildren(currentOriginRoot);
-
- // Refresh if origin model changed or child count changed (equipment added/removed)
- if (_lastOriginModelRoot != currentOriginRoot || _lastOriginModelChildCount != currentChildCount)
+ if (_previewInstance == null)
{
- _lastOriginModelRoot = currentOriginRoot;
- _lastOriginModelChildCount = currentChildCount;
QueueRefresh();
}
+ if(_refreshQueued)
+ {
+ _refreshQueued = false;
+ BuildPreviewModel();
+ }
+ return;
+ }
+
+ int currentChildCount = CountAllChildren(currentOriginRoot);
+
+ if (_lastOriginModelRoot != currentOriginRoot || _lastOriginModelChildCount != currentChildCount)
+ {
+ _lastOriginModelRoot = currentOriginRoot;
+ _lastOriginModelChildCount = currentChildCount;
+ QueueRefresh();
}
if (_refreshQueued)
@@ -226,9 +238,19 @@ namespace BrewMonster.Scripts.UI.Inventory
Transform sourceRoot = ResolveSourceModelRoot();
if (sourceRoot == null)
{
+ _previewInstance = null;
+ _lastOriginModelRoot = null;
+ _lastOriginModelChildCount = 0;
+
+ QueueRefresh();
return;
}
+ if (!sourceRoot.gameObject.activeSelf)
+ {
+ sourceRoot.gameObject.SetActive(true);
+ }
+
// Use resolved source root, not sourceModelRoot field directly.
_previewInstance = sourceRoot.gameObject;
Transform instanceTransform = _previewInstance.transform;
@@ -238,15 +260,11 @@ namespace BrewMonster.Scripts.UI.Inventory
instanceTransform.SetParent(previewRoot, false);
}
- instanceTransform.localPosition = previewLocalPosition + Vector3.up * previewHeightOffset;
+ instanceTransform.localPosition = previewLocalPosition + Vector3.up;
instanceTransform.localRotation = Quaternion.Euler(previewLocalEuler);
instanceTransform.localScale = previewLocalScale;
- if (inheritPreviewLayer)
- {
- ApplyLayerRecursive(instanceTransform, previewRoot.gameObject.layer);
- }
-
+ ApplyLayerRecursive(instanceTransform, previewRoot.gameObject.layer);
EnsureCameraFocus(instanceTransform);
EnsureCameraBindings();
}
diff --git a/Assets/Prefabs/UI/InventoryUI.prefab b/Assets/Prefabs/UI/InventoryUI.prefab
index aa4e06d0f5..d2316b9ab4 100644
--- a/Assets/Prefabs/UI/InventoryUI.prefab
+++ b/Assets/Prefabs/UI/InventoryUI.prefab
@@ -500,10 +500,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 588.35, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &9112205963990496432
CanvasRenderer:
@@ -907,10 +907,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 479.18, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &3997873020355048166
CanvasRenderer:
@@ -1238,10 +1238,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 370.01, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &4479228720555407959
CanvasRenderer:
@@ -4929,10 +4929,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 42.5, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &7052320096474271168
CanvasRenderer:
@@ -11098,16 +11098,14 @@ MonoBehaviour:
previewLocalPosition: {x: 0, y: 0, z: 100}
previewLocalEuler: {x: 0, y: 0, z: 0}
previewLocalScale: {x: 1, y: 1, z: 1}
- inheritPreviewLayer: 1
previewFrame: {fileID: 6707240765686952970}
previewRenderTexture: {fileID: 8400000, guid: 42c3c43cd0c3b704cb6cf0dd1051d9ff, type: 2}
autoFocusCamera: 1
cameraFocusOffset: {x: 0, y: 0, z: 0}
- previewCameraDistance: 1.4
- previewCameraOffset: {x: 0, y: 0.1, z: 0}
+ previewCameraDistance: 3.3
+ previewCameraOffset: {x: 0.06, y: 1.07, z: 0}
overrideFieldOfView: 1
- previewFieldOfView: 25
- freezeAnimation: 1
+ previewFieldOfView: 44
--- !u!1 &5473020210238587200
GameObject:
m_ObjectHideFlags: 0
@@ -14072,10 +14070,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 151.67, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &4452551064742165538
CanvasRenderer:
@@ -19519,10 +19517,10 @@ RectTransform:
m_Children: []
m_Father: {fileID: 7166820878650541780}
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: 0, y: 0}
+ m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMax: {x: 0, y: 1}
+ m_AnchoredPosition: {x: 260.84, y: -59.5}
+ m_SizeDelta: {x: 85, y: 85}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &5155025384962724770
CanvasRenderer:
diff --git a/Assets/Scripts/CECHostPlayer.Inventory.cs b/Assets/Scripts/CECHostPlayer.Inventory.cs
index 3bcf0669ed..678fdb5fb3 100644
--- a/Assets/Scripts/CECHostPlayer.Inventory.cs
+++ b/Assets/Scripts/CECHostPlayer.Inventory.cs
@@ -517,6 +517,7 @@ namespace BrewMonster
if (ui != null)
{
ui.RefreshAll();
+ ui.RefreshCharacterModelPreview();
}
UpdateEquipSkins();