Skip to content

Commit

Permalink
work on the inventory manager
Browse files Browse the repository at this point in the history
  • Loading branch information
bierdosenhalter committed Nov 8, 2024
1 parent 9179a11 commit b6eba9e
Show file tree
Hide file tree
Showing 5 changed files with 264 additions and 20 deletions.
2 changes: 1 addition & 1 deletion Client/Database/DatabaseManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ public DatabaseManager(RyzomClient client)
public DatabaseNodeBranch GetNodePtr() { return _serverDatabase; }

/// <summary>
/// Returns the root branch of the database.
/// Returns the root branch of the database.
/// </summary>
public DatabaseNodeBranch GetDb()
{
Expand Down
12 changes: 10 additions & 2 deletions Client/Database/DatabaseNodeBranch.cs
Original file line number Diff line number Diff line change
Expand Up @@ -168,9 +168,9 @@ public override bool AddObserver(IPropertyObserver observer, TextId id)
}

// lookup next element from textid in my index => idx
string str = id.ReadNext();
var str = id.ReadNext();

DatabaseNode pNode = Find(str);
var pNode = Find(str);
// Property not found.
if (pNode == null)
{
Expand Down Expand Up @@ -284,6 +284,14 @@ internal virtual void AttachChild(DatabaseNode node, string nodeName)
_predictDatabaseNode = node;
}

/// <summary>
/// Get the number of nodes.
/// </summary>
internal uint NodeCount()
{
return (ushort)_nodes.Count;
}

/// <summary>
/// Get a database node. Return null if out of bounds (no warning)
/// </summary>
Expand Down
47 changes: 35 additions & 12 deletions Client/Interface/ServerToLocalAutoCopy.cs
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ public class ServerToLocalAutoCopy : IDisposable
private List<Node> _Nodes = new List<Node>();
/// <summary>Sorting of Nodes, by Server Node</summary>
List<NodeServerComp> _ServerNodeMap = new List<NodeServerComp>();
/// <summary> Sorting of Nodes, by Local Node</summary>
/// <summary>Sorting of Nodes, by Local Node</summary>
List<NodeLocalComp> _LocalNodeMap = new List<NodeLocalComp>();
/// <summary>List of nodes to update until next synchonized client-server counter</summary>
private List<Node> _UpdateList = new List<Node>();
Expand All @@ -65,7 +65,7 @@ public void Dispose()
// init the AutoCopy
public void Init(string dbPath)
{
InterfaceManager pIM = _interfaceManger;
var pIM = _interfaceManger;

// Get the synchronisation Counter in Server DB
_ServerCounter = _databaseManager.GetDbProp("SERVER:" + dbPath + ":COUNTER", false);
Expand Down Expand Up @@ -158,24 +158,24 @@ void OnServerChange(DatabaseNode serverNode)
return;
}

DatabaseNodeLeaf serverLeaf = (DatabaseNodeLeaf)serverNode;
var serverLeaf = (DatabaseNodeLeaf)serverNode;
var pIM = _interfaceManger;

// Add the leaf to the update list. only if not the counter
if (serverLeaf != _ServerCounter)
{
// build the map key
Node nodeComp = new Node();
NodeServerComp sc = new NodeServerComp();
var nodeComp = new Node();
var sc = new NodeServerComp();
nodeComp.ServerNode = serverLeaf;
sc.Node = nodeComp;
// try to find the node associated to this server leaf
int index = _ServerNodeMap.IndexOf(sc);
var index = _ServerNodeMap.IndexOf(sc);

// if found
if (index > 0 || _ServerNodeMap[0].Node.ServerNode == serverLeaf)
{
Node node = _ServerNodeMap[index].Node;
var node = _ServerNodeMap[index].Node;
// if this node is not already inserted
if (!node.InsertedInUpdateList)
{
Expand All @@ -190,9 +190,9 @@ void OnServerChange(DatabaseNode serverNode)
if (pIM.localActionCounterSynchronizedWith(_ServerCounter))
{
// update all leaves
for (int i = 0; i < _UpdateList.Count; i++)
for (var i = 0; i < _UpdateList.Count; i++)
{
Node node = _UpdateList[i];
var node = _UpdateList[i];

_LocalUpdating = true;
node.LocalNode.SetValue64(node.ServerNode.GetValue64());
Expand Down Expand Up @@ -238,7 +238,7 @@ public override void Update(DatabaseNode node)
}
}

// A node here is a pair Server<->Local
/// <summary>A node here is a pair Server<->Local</summary>
private class Node
{
public DatabaseNodeLeaf ServerNode;
Expand All @@ -253,7 +253,7 @@ public Node()
}
}

// Struct for comparing nodes, by either Local or Server pointer
/// <summary>Struct for comparing nodes, by either Local or Server pointer</summary>
private class NodeLocalComp : IComparable<NodeLocalComp>
{
public Node Node { get; internal set; }
Expand All @@ -274,6 +274,29 @@ public int CompareTo([AllowNull] NodeLocalComp other)
}
}

void BuildRecursLocalLeaves(DatabaseNodeBranch branch, List<DatabaseNodeLeaf> leaves) { }
void BuildRecursLocalLeaves(DatabaseNodeBranch branch, List<DatabaseNodeLeaf> leaves)
{
for (ushort i = 0; i < branch.NodeCount(); i++)
{
var node = branch.GetNode(i);
if (node != null)
{
if (node is DatabaseNodeLeaf leaf)
{
// just append to list
leaves.Add(leaf);
}
else
{
// recurs if a branch (should be...)
if (node is DatabaseNodeBranch sonBranch)
{
BuildRecursLocalLeaves(sonBranch, leaves);
}
}
}
}

}
}
}
194 changes: 189 additions & 5 deletions Client/Inventory/InventoryManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@
// Copyright 2010 Winch Gate Property Limited
///////////////////////////////////////////////////////////////////

using System;
using Client.Database;
using Client.Stream;

namespace Client.Inventory
{
Expand All @@ -19,7 +21,7 @@ namespace Client.Inventory
/// <date>September 2003</date>
public class InventoryManager
{
private RyzomClient _client;
private readonly RyzomClient _client;

const uint MAX_TEMPINV_ENTRIES = 16;
const uint MAX_BAGINV_ENTRIES = 500;
Expand All @@ -33,12 +35,51 @@ public class InventoryManager
const uint MAX_PLAYER_INV_ENTRIES = 500;

// db path for the local inventory
//#define LOCAL_INVENTORY "LOCAL:INVENTORY"
//#define SERVER_INVENTORY "SERVER:INVENTORY"
public const string LOCAL_INVENTORY = "LOCAL:INVENTORY";
public const string SERVER_INVENTORY = "SERVER:INVENTORY";

// db path for all the inventories (without the SERVER: prefix)
public readonly string[] InventoryDBs;
public readonly uint[] InventoryIndexes;
private readonly string[] InventoryDBs = {
"INVENTORY:BAG",
"INVENTORY:PACK_ANIMAL0",
"INVENTORY:PACK_ANIMAL1",
"INVENTORY:PACK_ANIMAL2",
"INVENTORY:PACK_ANIMAL3",
"INVENTORY:TEMP",
"EXCHANGE:GIVE",
"EXCHANGE:RECEIVE",
"TRADING",
"INVENTORY:SHARE",
"GUILD:INVENTORY",
"INVENTORY:ROOM"
};

public enum INVENTORIES : ushort
{
// TODO : remove handling, merge it with equipement
handling = 0,
temporary, // 1
equipment, // 2
bag, // 3
pet_animal, // 4 Character can have 5 pack animal
pet_animal1 = pet_animal, // for toString => TInventory convertion
pet_animal2,
pet_animal3,
pet_animal4,
max_pet_animal, // 8
NUM_INVENTORY = max_pet_animal, // 8
UNDEFINED = NUM_INVENTORY, // 8

exchange, // 9 This is not a bug : exchange is a fake inventory
exchange_proposition, // 10 and should not count in the number of inventory
// same for botChat trading.
trading, // 11
reward_sharing, // 12 fake inventory, not in database.xml. Used by the item info protocol only
guild, // 13 (warning: number stored in guild saved file)
player_room, // 14
NUM_ALL_INVENTORY // warning: distinct from NUM_INVENTORY
}

public readonly uint NumInventories = new uint();

// LOCAL INVENTORY
Expand Down Expand Up @@ -71,6 +112,9 @@ public class InventoryManager
// Cache to know if bag is locked or not, because of item worn
private bool[] BagItemEquipped = new bool[MAX_BAGINV_ENTRIES];

// ***************************************************************************
// db path for all the inventories (without the SERVER: prefix)

public InventoryManager(RyzomClient client)
{
_client = client;
Expand Down Expand Up @@ -110,5 +154,145 @@ internal void SortBag()
{
// TODO
}

public void equip(in string bagPath, in string invPath)
{
//if (isSwimming() || isStunned() || isDead() || isRiding())
//{
// return;
//}

var pIM = _client.GetInterfaceManager();

if (bagPath.Length == 0 || invPath.Length == 0)
{
return;
}

// Get inventory and slot
var sIndexInBag = bagPath.Substring(bagPath.LastIndexOf(':') + 1, bagPath.Length);
ushort.TryParse(sIndexInBag, out var indexInBag);

var inventory = (ushort)INVENTORIES.UNDEFINED;
ushort invSlot = 0xffff;

if (invPath.StartsWith("LOCAL:INVENTORY:HAND", StringComparison.InvariantCultureIgnoreCase))
{
inventory = (ushort)INVENTORIES.handling;
ushort.TryParse(invPath.Substring(21, invPath.Length), out invSlot);
}
else if (invPath.StartsWith("LOCAL:INVENTORY:EQUIP", StringComparison.InvariantCultureIgnoreCase))
{
inventory = (ushort)INVENTORIES.equipment;
ushort.TryParse(invPath.Substring(22, invPath.Length), out invSlot);
}

// Hands management : check if we have to unequip left hand because of incompatibility with right hand item
var oldRightIndexInBag = _client.GetDatabaseManager().GetDbProp(invPath + ":INDEX_IN_BAG").GetValue16();

if (inventory == (ushort)INVENTORIES.handling && invSlot == 0)
{
// TODO DatabaseCtrlSheet pCSLeftHand = CWidgetManager.getInstance().getElementFromId(CTRL_HAND_LEFT) as DatabaseCtrlSheet;
object pCSLeftHand = null;

if (pCSLeftHand == null)
{
return;
}

// get sheet of left item
uint leftSheet = 0;
var pNL = _client.GetDatabaseManager().GetDbProp(LOCAL_INVENTORY + ":HAND:1:INDEX_IN_BAG", false);

if (pNL == null)
{
return;
}
if (pNL.GetValue32() > 0)
{
var pNL2 = _client.GetDatabaseManager().GetDbProp(LOCAL_INVENTORY + ":BAG:" + (pNL.GetValue32() - 1) + ":SHEET", false);
if (pNL2 == null)
{
return;
}
leftSheet = (uint)pNL2.GetValue32();
}

// get sheet of previous right hand item
uint lastRightSheet = 0;
if (oldRightIndexInBag > 0)
{
pNL = _client.GetDatabaseManager().GetDbProp(LOCAL_INVENTORY + ":BAG:" + (oldRightIndexInBag - 1) + ":SHEET", false);
if (pNL == null)
{
return;
}
lastRightSheet = (uint)pNL.GetValue32();
}

// get sheet of new right hand item
uint rightSheet = 0;
if (indexInBag + 1 > 0)
{
pNL = _client.GetDatabaseManager().GetDbProp(LOCAL_INVENTORY + ":BAG:" + (indexInBag) + ":SHEET", false);
if (pNL == null)
{
return;
}
rightSheet = (uint)pNL.GetValue32();
}

//// TODO If incompatible -> remove
//if (!GetInventory().IsLeftHandItemCompatibleWithRightHandItem(leftSheet, rightSheet, lastRightSheet))
//{
// GetInventory().Unequip(LOCAL_INVENTORY+ ":HAND:1");
//}
}

// update the equip DB pointer
_client.GetDatabaseManager().GetDbProp(invPath + ":INDEX_IN_BAG").SetValue16((short)(indexInBag + 1));

//// TODO Yoyo add: when the user equip an item, the action are invalid during some time
//if (indexInBag < MAX_BAGINV_ENTRIES)
//{
// ItemSheet pIS = _client.GetSheetManager().Get(_client.GetSheetIdFactory().SheetId(GetBagItem(indexInBag).getSheetID())) as ItemSheet;
// if (pIS != null)
// {
// PhraseManager pPM = PhraseManager.getInstance();
// pPM.setEquipInvalidation(NetMngr.getCurrentServerTick(), pIS.EquipTime);
// }
//}

//// TODO Update trade window if any
//if ((BotChatPageAll != null) && (BotChatPageAll.Trade != null))
//{
// BotChatPageAll.Trade.invalidateCoords();
//}

// Send message to the server
if (inventory != (short)INVENTORIES.UNDEFINED)
{
var @out = new BitMemoryStream();
const string sMsg = "ITEM:EQUIP";

if (_client.GetNetworkManager().GetMessageHeaderManager().PushNameToStream(sMsg, @out))
{
// Fill the message (equipped inventory, equipped inventory slot, bag slot)
@out.Serial(ref inventory);
@out.Serial(ref invSlot);
@out.Serial(ref indexInBag);
_client.GetNetworkManager().Push(@out);

// TODO pIM.IncLocalSyncActionCounter();

//nlinfo("impulseCallBack : %s %d %d %d sent", sMsg.c_str(), inventory, invSlot, indexInBag);
}
else
{
_client.Log.Warn($"Don't know message name {sMsg}");
}
}
}

}
}
Loading

0 comments on commit b6eba9e

Please sign in to comment.