Add CESHOP

This commit is contained in:
HungDK
2025-12-03 16:43:11 +07:00
parent 9a4c1f9295
commit 010c66ca47
19 changed files with 1153 additions and 0 deletions
+8
View File
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 1be878d234498514c8356a798b2e4515
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,230 @@
// Filename : CECBackShop.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
using System.Collections.Generic;
using UnityEngine;
using BrewMonster.Network;
namespace PerfectWorld.Scripts.Shop
{
// CECBackShop
public class CECBackShop : CECShopArrayItems
{
private CECShopItemCategory m_fashionShopCategory = new CECShopItemCategory();
private static CECBackShop s_instance;
private GShopLoader m_shopLoader;
private CECBackShop() : base(null)
{
// Initialize with empty list first
m_pItems = new List<GShopItem>();
// Try to get shop loader data (may not be available immediately)
RefreshShopData();
if (IsFashionShopEnabled())
{
m_fashionShopCategory.InitFromQShopConfig(CECQShopConfig.CID_BACKSHOP_FASHION);
}
}
public void RefreshShopData()
{
// Initialize with shop loader data
GameObject shopLoaderObj = GameObject.FindFirstObjectByType<GShopLoader>()?.gameObject;
if (shopLoaderObj != null)
{
m_shopLoader = shopLoaderObj.GetComponent<GShopLoader>();
if (m_shopLoader != null && m_shopLoader.secondaryShop != null && m_shopLoader.secondaryShop.items != null)
{
m_pItems = m_shopLoader.secondaryShop.items;
}
}
}
public static CECBackShop Instance()
{
if (s_instance == null)
{
s_instance = new CECBackShop();
}
return s_instance;
}
public override bool GetFromServer(int beginIndex, int endIndex)
{
bool result = false;
// TODO: Implement cooldown check (GP_CT_GET_DIVIDEND_MALL_PRICE)
// For now, always allow if indices are provided
if (beginIndex == 0 && endIndex == 0)
{
// Request all prices
// TODO: Implement UnityGameSession.RequestGetDividendMallItemPrice(0, 0)
result = true;
}
else if (beginIndex != 0 || endIndex != 0)
{
// Request specific range
// TODO: Implement UnityGameSession.RequestGetDividendMallItemPrice(beginIndex, endIndex)
result = true;
}
return result;
}
public override uint GetLocalTimeStamp()
{
if (m_shopLoader != null && m_shopLoader.secondaryShop != null)
{
return m_shopLoader.secondaryShop.timestamp;
}
return 0;
}
public override uint GetServerTimeStamp()
{
// TODO: Get from game run state
// return g_pGame->GetGameRun()->GetGShopTimeStamp2();
return GetLocalTimeStamp(); // Stub for now
}
public bool UpdateFromServer() // TODO: Add S2C::cmd_dividend_mall_item_price parameter when available
{
// TODO: Implement server update logic when S2C command structure is available
// For now, this is a stub
/*
List<GShopItem> items = new List<GShopItem>(m_pItems);
if (!ApplyChangesFromServer(items, pCmd))
{
return false;
}
if (IsSame(items, m_pItems))
{
return true;
}
m_pItems = items;
OnItemChange();
*/
return true;
}
private bool ApplyChangesFromServer(List<GShopItem> pItems) // TODO: Add S2C::cmd_dividend_mall_item_price parameter when available
{
// TODO: Implement when S2C command structure is available
/*
int i = 0;
for (i = pCmd->start_index; i < pCmd->end_index; i++)
{
if (i < pItems.Count)
{
GShopItem data = pItems[i];
for (int j = 0; j < 4; j++)
{
if (data.buy != null && j < data.buy.Length && data.buy[j].type != -1)
{
GShopBuyOption buyOption = data.buy[j];
buyOption.type = -1;
buyOption.price = 0;
data.buy[j] = buyOption;
}
}
pItems[i] = data;
}
}
for (i = 0; i < pCmd->count; i++)
{
const S2C::cmd_dividend_mall_item_price::good_info& tempList = pCmd->list[i];
if (tempList.good_index < pItems.Count)
{
GShopItem data = pItems[tempList.good_index];
if (data.id == (uint)tempList.good_id)
{
if (data.buy != null && tempList.good_slot < data.buy.Length)
{
GShopBuyOption buyOption = data.buy[tempList.good_slot];
buyOption.price = tempList.good_price;
buyOption.status = tempList.good_status;
buyOption.time = tempList.expire_time;
buyOption.type = 3;
data.buy[tempList.good_slot] = buyOption;
}
pItems[tempList.good_index] = data;
}
else
{
Debug.Assert(data.id == (uint)tempList.good_id);
return false;
}
}
}
*/
return true;
}
public override int GetCash()
{
// TODO: Integrate with CECHostPlayer.GetDividend()
// For now, return 0 as stub
// return CECHostPlayer.Instance().GetDividend();
return 0;
}
public override bool Buy(int itemIndex, int buyIndex)
{
bool bOK = false;
if (ReadyToBuy(itemIndex, buyIndex))
{
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue)
{
GShopItem item = pItem.Value;
if (!CECShopItemOwnerNPC.HasOwnerNPC(item))
{
// Regular dividend mall shopping
// TODO: Implement UnityGameSession.RequestDividendMallShopping(1, itemIndex, item.id, buyIndex)
// For now, use regular mall shopping as fallback
UnityGameSession.Instance.RequestMallShopping(1, (int)item.id, itemIndex, buyIndex);
}
else
{
// NPC server dividend mall shopping
// TODO: Implement UnityGameSession.RequestNPCSevDividendMallShopping(1, itemIndex, item.id, buyIndex)
UnityGameSession.Instance.RequestMallShopping(1, (int)item.id, itemIndex, buyIndex);
}
CECQShopConfig.Instance().OnItemBuyed(item.id);
// TODO: CECShoppingItemsMover::Instance().OnItemBuyed(this, itemIndex, buyIndex);
bOK = true;
}
}
else
{
Debug.Assert(false, "Item not ready to buy");
}
return bOK;
}
public override bool IsFashionShopEnabled()
{
return CECUIConfig.Instance().GetGameUI().bEnableBackShopFashionShop;
}
public override bool IsFashionShopFlashSaleEnabled()
{
return CECUIConfig.Instance().GetGameUI().bEnableBackShopFashionShopFlashSale;
}
public override string GetFashionShopFlashSaleTitle()
{
return CECUIConfig.Instance().GetGameUI().strBackShopFashionShopFlashSaleTitle;
}
public override CECShopItemCategory GetFashionShopCategory()
{
return m_fashionShopCategory;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 01372a5632621c3438a20d995d97bdee
@@ -0,0 +1,228 @@
// Filename : CECQShop.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
using System.Collections.Generic;
using UnityEngine;
using BrewMonster.Network;
namespace PerfectWorld.Scripts.Shop
{
// CECQShop
public class CECQShop : CECShopArrayItems
{
private CECShopItemCategory m_fashionShopCategory = new CECShopItemCategory();
private static CECQShop s_instance;
private GShopLoader m_shopLoader;
private CECQShop() : base(null)
{
// Initialize with empty list first
m_pItems = new List<GShopItem>();
// Try to get shop loader data (may not be available immediately)
RefreshShopData();
if (IsFashionShopEnabled())
{
m_fashionShopCategory.InitFromQShopConfig(CECQShopConfig.CID_QSHOP_FASHION);
}
}
public void RefreshShopData()
{
// Initialize with shop loader data
GameObject shopLoaderObj = GameObject.FindFirstObjectByType<GShopLoader>()?.gameObject;
if (shopLoaderObj != null)
{
m_shopLoader = shopLoaderObj.GetComponent<GShopLoader>();
if (m_shopLoader != null && m_shopLoader.primaryShop != null && m_shopLoader.primaryShop.items != null)
{
m_pItems = m_shopLoader.primaryShop.items;
}
}
}
public static CECQShop Instance()
{
if (s_instance == null)
{
s_instance = new CECQShop();
}
return s_instance;
}
public override bool GetFromServer(int beginIndex, int endIndex)
{
bool result = false;
// TODO: Implement cooldown check (GP_CT_GET_MALL_PRICE)
// For now, always allow if indices are provided
if (beginIndex == 0 && endIndex == 0)
{
// Request all prices
// TODO: Implement UnityGameSession.RequestGetMallItemPrice(0, 0)
result = true;
}
else if (beginIndex != 0 || endIndex != 0)
{
// Request specific range
// TODO: Implement UnityGameSession.RequestGetMallItemPrice(beginIndex, endIndex)
result = true;
}
return result;
}
public override uint GetLocalTimeStamp()
{
if (m_shopLoader != null && m_shopLoader.primaryShop != null)
{
return m_shopLoader.primaryShop.timestamp;
}
return 0;
}
public override uint GetServerTimeStamp()
{
// TODO: Get from game run state
// return g_pGame->GetGameRun()->GetGShopTimeStamp();
return GetLocalTimeStamp(); // Stub for now
}
public bool UpdateFromServer() // TODO: Add S2C::cmd_mall_item_price parameter when available
{
// TODO: Implement server update logic when S2C command structure is available
// For now, this is a stub
/*
List<GShopItem> items = new List<GShopItem>(m_pItems);
if (!ApplyChangesFromServer(items, pCmd))
{
return false;
}
if (IsSame(items, m_pItems))
{
return true;
}
m_pItems = items;
OnItemChange();
*/
return true;
}
private bool ApplyChangesFromServer(List<GShopItem> pItems) // TODO: Add S2C::cmd_mall_item_price parameter when available
{
// TODO: Implement when S2C command structure is available
/*
int i = 0;
for (i = pCmd->start_index; i < pCmd->end_index; i++)
{
if (i < pItems.Count)
{
GShopItem data = pItems[i];
for (int j = 0; j < 4; j++)
{
if (data.buy != null && j < data.buy.Length && data.buy[j].type != -1)
{
GShopBuyOption buyOption = data.buy[j];
buyOption.type = -1;
buyOption.price = 0;
data.buy[j] = buyOption;
}
}
pItems[i] = data;
}
}
for (i = 0; i < pCmd->count; i++)
{
const S2C::cmd_mall_item_price::good_item& tempList = pCmd->list[i];
if (tempList.good_index < pItems.Count)
{
GShopItem data = pItems[tempList.good_index];
if (data.id == (uint)tempList.good_id)
{
if (data.buy != null && tempList.good_slot < data.buy.Length)
{
GShopBuyOption buyOption = data.buy[tempList.good_slot];
buyOption.price = tempList.goods_price;
buyOption.status = tempList.good_status;
buyOption.time = tempList.expire_time;
buyOption.type = 3;
data.buy[tempList.good_slot] = buyOption;
}
pItems[tempList.good_index] = data;
}
else
{
Debug.Assert(data.id == (uint)tempList.good_id);
return false;
}
}
}
*/
return true;
}
public override int GetCash()
{
// TODO: Integrate with CECHostPlayer.GetCash()
// For now, return 0 as stub
// return CECHostPlayer.Instance().GetCash();
return 0;
}
public override bool Buy(int itemIndex, int buyIndex)
{
bool bOK = false;
if (ReadyToBuy(itemIndex, buyIndex))
{
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue)
{
GShopItem item = pItem.Value;
if (!CECShopItemOwnerNPC.HasOwnerNPC(item))
{
// Regular mall shopping
UnityGameSession.Instance.RequestMallShopping(1, (int)item.id, itemIndex, buyIndex);
}
else
{
// NPC server mall shopping
// TODO: Implement UnityGameSession.RequestNPCSevMallShopping(1, itemIndex, item.id, buyIndex)
UnityGameSession.Instance.RequestMallShopping(1, (int)item.id, itemIndex, buyIndex);
}
CECQShopConfig.Instance().OnItemBuyed(item.id);
// TODO: CECShoppingItemsMover::Instance().OnItemBuyed(this, itemIndex, buyIndex);
bOK = true;
}
}
else
{
Debug.Assert(false, "Item not ready to buy");
}
return bOK;
}
public override bool IsFashionShopEnabled()
{
return CECUIConfig.Instance().GetGameUI().bEnableQShopFashionShop;
}
public override bool IsFashionShopFlashSaleEnabled()
{
return CECUIConfig.Instance().GetGameUI().bEnableQShopFashionShopFlashSale;
}
public override string GetFashionShopFlashSaleTitle()
{
return CECUIConfig.Instance().GetGameUI().strQShopFashionShopFlashSaleTitle;
}
public override CECShopItemCategory GetFashionShopCategory()
{
return m_fashionShopCategory;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 2d753dbecaf480345acbcb47feb6340f
@@ -0,0 +1,40 @@
// Filename : CECQShopConfig.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
namespace PerfectWorld.Scripts.Shop
{
// Stub implementation - to be properly implemented later
public class CECQShopConfig
{
public const int CID_QSHOP_FASHION = 0; // Stub value
public const int CID_BACKSHOP_FASHION = 1; // Stub value
private static CECQShopConfig s_instance;
public static CECQShopConfig Instance()
{
if (s_instance == null)
{
s_instance = new CECQShopConfig();
}
return s_instance;
}
public void FindCategory(int idCategory, out int mainType, out int subType)
{
// Stub implementation - to be properly implemented later
mainType = -1;
subType = -1;
}
public void OnItemBuyed(uint goodsId)
{
// Stub implementation - to be properly implemented later
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: c8e321ee92225d04ab0eb82b965fe32d
@@ -0,0 +1,60 @@
// Filename : CECShopArrayItems.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System.Collections.Generic;
using System.Linq;
namespace PerfectWorld.Scripts.Shop
{
public abstract class CECShopArrayItems : CECShopBase
{
protected List<GShopItem> m_pItems;
public CECShopArrayItems(List<GShopItem> pItems)
{
m_pItems = pItems;
}
public override int GetCount()
{
return m_pItems != null ? m_pItems.Count : 0;
}
public override GShopItem? GetItem(int index)
{
if (m_pItems != null && index >= 0 && index < m_pItems.Count)
{
return m_pItems[index];
}
return null;
}
public static bool IsSame(List<GShopItem> lhs, List<GShopItem> rhs)
{
bool result = false;
if (lhs == rhs)
{
result = true;
}
else if (lhs != null && rhs != null)
{
if (lhs.Count == rhs.Count)
{
result = true;
for (int u = 0; u < lhs.Count; ++u)
{
if (!CECShopBase.IsSame(lhs[u], rhs[u]))
{
result = false;
break;
}
}
}
}
return result;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: f70fb69e0e992a24c8e03b2558f3ee6f
@@ -0,0 +1,356 @@
// Filename : CECShopBase.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
using System.Linq;
using BrewMonster;
namespace PerfectWorld.Scripts.Shop
{
// 封装 gshop 和 backshop 等的数据访问 / Encapsulates data access for gshop and backshop etc.
public static class CECShopConstants
{
public const int CECSHOP_INVALID_PRICE = -1;
public const int BUY_COUNT = 4;
}
public abstract class CECShopBase : CECObservable<CECShopBase>
{
private CECShopItemOwnerNPC m_ownerNPC = new CECShopItemOwnerNPC(0);
// CECShopBase
public void OnItemChange()
{
CECShopBaseChange change = new CECShopBaseChange((uint)CECShopBaseChange.ChangeMask.ITEM_CHANGED);
NotifyObservers(change);
}
public bool ValidateTimeStamp()
{
return GetLocalTimeStamp() == GetServerTimeStamp();
}
public void SetOwnerNPCID(uint ownerNPCID)
{
if (ownerNPCID == m_ownerNPC.GetOwnerNPCID())
{
return;
}
m_ownerNPC.SetOwnerNPCID(ownerNPCID);
OnItemChange();
}
public uint GetOwnerNPCID()
{
return m_ownerNPC.GetOwnerNPCID();
}
public bool HasOwnerNPC()
{
return !m_ownerNPC.IsEmpty();
}
public CECShopItemOwnerNPC GetOwnerNPC()
{
return m_ownerNPC;
}
public bool MatchOwnerNPC(GShopItem rhs)
{
return m_ownerNPC.MatchItem(rhs);
}
public bool IsValid(int itemIndex, int buyIndex)
{
bool bValid = false;
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue)
{
if (buyIndex >= 0 && buyIndex < CECShopConstants.BUY_COUNT)
{
bValid = true;
}
}
return bValid;
}
public bool ReadyToBuy(int itemIndex, int buyIndex)
{
bool result = false;
int[] buyType = new int[CECShopConstants.BUY_COUNT];
if (IsValid(itemIndex, buyIndex) && CalcBuyType(itemIndex, buyType))
{
for (int i = 0; i < CECShopConstants.BUY_COUNT; ++i)
{
if (buyType[i] == buyIndex)
{
result = true;
break;
}
}
}
return result;
}
public bool CalcBuyType(int itemIndex, int[] buyTypes)
{
bool bOK = false;
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue)
{
GShopItem item = pItem.Value;
int[] typeDefault = new int[CECShopConstants.BUY_COUNT];
int[] typeNew = new int[CECShopConstants.BUY_COUNT];
int index1 = 0;
int index2 = 0;
for (int i = 0; i < CECShopConstants.BUY_COUNT; i++)
{
typeDefault[i] = -1;
typeNew[i] = -1;
if (item.buy != null && i < item.buy.Length)
{
if (item.buy[i].type == 3 && item.buy[i].price > 0)
{
typeNew[index1] = i;
index1++;
}
else if (item.buy[i].type == -1 && item.buy[i].price > 0)
{
typeDefault[index2] = i;
index2++;
}
}
}
if (index1 > 0)
{
Array.Copy(typeNew, buyTypes, CECShopConstants.BUY_COUNT);
bOK = true;
}
else if (index2 > 0)
{
Array.Copy(typeDefault, buyTypes, CECShopConstants.BUY_COUNT);
bOK = true;
}
}
return bOK;
}
public bool HasSameBuyType(int itemIndexA, int itemIndexB)
{
int[] typeA = new int[CECShopConstants.BUY_COUNT];
int[] typeB = new int[CECShopConstants.BUY_COUNT];
if (CalcBuyType(itemIndexA, typeA) &&
CalcBuyType(itemIndexB, typeB) &&
typeA.SequenceEqual(typeB))
{
GShopItem? pItemA = GetItem(itemIndexA);
GShopItem? pItemB = GetItem(itemIndexB);
if (pItemA.HasValue && pItemB.HasValue)
{
GShopItem itemA = pItemA.Value;
GShopItem itemB = pItemB.Value;
for (int i = 0; i < CECShopConstants.BUY_COUNT; ++i)
{
int buyIndex = typeA[i];
if (buyIndex != -1)
{
bool priceAValid = (itemA.buy != null && buyIndex < itemA.buy.Length && itemA.buy[buyIndex].price != 0);
bool priceBValid = (itemB.buy != null && buyIndex < itemB.buy.Length && itemB.buy[buyIndex].price != 0);
if (priceAValid != priceBValid)
{
return false;
}
if (!priceAValid)
{
continue;
}
if (itemA.buy[buyIndex].time != itemB.buy[buyIndex].time)
{
return false;
}
}
}
return true;
}
}
return false;
}
public bool CalcBuyIndex(int itemIndex, out int buyIndex, int cash = -1)
{
buyIndex = -1;
bool bOK = false;
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue)
{
GShopItem item = pItem.Value;
// 参考实现 CDlgQShopItem::SetItem / Reference implementation CDlgQShopItem::SetItem
// 判断要显示的购买方式 / Determine which purchase method to display
int[] m_TypeDefault = new int[CECShopConstants.BUY_COUNT];
int[] m_TypeNew = new int[CECShopConstants.BUY_COUNT];
int index1 = 0;
int index2 = 0;
for (int i = 0; i < CECShopConstants.BUY_COUNT; i++)
{
m_TypeDefault[i] = -1;
m_TypeNew[i] = -1;
if (item.buy != null && i < item.buy.Length)
{
if (item.buy[i].type == 3 && item.buy[i].price > 0)
{
m_TypeNew[index1] = i;
index1++;
}
else if (item.buy[i].type == -1 && item.buy[i].price > 0)
{
m_TypeDefault[index2] = i;
index2++;
}
}
}
int m_BuyType = -1;
if (index1 > 0)
{
m_BuyType = 0;
}
else
{
m_BuyType = 1;
}
if (cash == -1)
{
cash = GetCash();
}
for (int i = 0; i < CECShopConstants.BUY_COUNT; i++)
{
int BuyIndex = 0;
if (m_BuyType == 0)
{
BuyIndex = m_TypeNew[i];
}
else
{
BuyIndex = m_TypeDefault[i];
}
if (BuyIndex != -1 && item.buy != null && BuyIndex < item.buy.Length)
{
uint price = item.buy[BuyIndex].price;
if (price != 0 && price <= cash)
{
bOK = true;
buyIndex = BuyIndex;
break;
}
}
}
}
return bOK;
}
public int GetPrice(int itemIndex, int buyIndex)
{
int price = CECShopConstants.CECSHOP_INVALID_PRICE;
if (IsValid(itemIndex, buyIndex))
{
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue && pItem.Value.buy != null && buyIndex < pItem.Value.buy.Length)
{
price = (int)pItem.Value.buy[buyIndex].price;
}
}
else
{
UnityEngine.Debug.Assert(false);
}
return price;
}
public uint GetStatus(int itemIndex, int buyIndex)
{
uint status = 0xFFFFFFFF; // -1 as uint
if (IsValid(itemIndex, buyIndex))
{
GShopItem? pItem = GetItem(itemIndex);
if (pItem.HasValue && pItem.Value.buy != null && buyIndex < pItem.Value.buy.Length)
{
status = pItem.Value.buy[buyIndex].status;
}
}
else
{
UnityEngine.Debug.Assert(false);
}
return status;
}
public static bool IsSame(GShopItem lhs, GShopItem rhs)
{
bool result = false;
if (lhs.mainType != rhs.mainType ||
lhs.subType != rhs.subType ||
lhs.id != rhs.id ||
lhs.num != rhs.num ||
lhs.idGift != rhs.idGift ||
lhs.giftNum != rhs.giftNum)
{
return false;
}
result = true;
if (lhs.buy != null && rhs.buy != null)
{
int buyCount = Math.Min(lhs.buy.Length, rhs.buy.Length);
for (int i = 0; i < buyCount && i < CECShopConstants.BUY_COUNT; ++i)
{
if (lhs.buy[i].type != rhs.buy[i].type ||
lhs.buy[i].price != rhs.buy[i].price ||
lhs.buy[i].time != rhs.buy[i].time ||
lhs.buy[i].status != rhs.buy[i].status)
{
result = false;
break;
}
}
}
return result;
}
public static int GetOriginalPrice(int finalPrice, uint discountStatus)
{
int result = finalPrice;
if (discountStatus >= 4 && discountStatus <= 12)
{
float originalPrice = finalPrice * (10.0f / (discountStatus - 3));
if (CECUIConfig.Instance().GetGameUI().bEnableCeilPriceBeforeDiscountToGold)
{
result = (int)Math.Ceiling(originalPrice) + 99;
result /= 100;
result *= 100;
}
else
{
result = (int)Math.Ceiling(originalPrice);
}
}
return result;
}
// Abstract methods
public abstract bool GetFromServer(int beginIndex, int endIndex);
public abstract uint GetLocalTimeStamp();
public abstract uint GetServerTimeStamp();
public abstract int GetCount();
public abstract GShopItem? GetItem(int index);
public abstract int GetCash();
public abstract bool Buy(int itemIndex, int buyIndex);
public abstract bool IsFashionShopEnabled();
public abstract CECShopItemCategory GetFashionShopCategory();
public abstract bool IsFashionShopFlashSaleEnabled();
public abstract string GetFashionShopFlashSaleTitle();
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 16ba0a2da752c6a49ad053e4af8be921
@@ -0,0 +1,36 @@
// Filename : CECShopBaseChange.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using BrewMonster;
namespace PerfectWorld.Scripts.Shop
{
// 封装 CECShopBase 的变化 / Encapsulates changes to CECShopBase
public class CECShopBaseChange : CECObservableChange
{
public enum ChangeMask
{
ITEM_CHANGED = 0x01,
}
private uint m_changeMask;
public CECShopBaseChange(uint changeMask)
{
m_changeMask = changeMask;
}
public uint GetChangeMask()
{
return m_changeMask;
}
public bool ItemChanged()
{
return (GetChangeMask() & (uint)ChangeMask.ITEM_CHANGED) != 0;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: e995fc9c415a8a143a75c18021965074
@@ -0,0 +1,59 @@
// Filename : CECShopItemCategory.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
namespace PerfectWorld.Scripts.Shop
{
// 封装 GSHOP_ITEM 的分类信息 / Encapsulates category information for GSHOP_ITEM
public class CECShopItemCategory
{
private int m_mainType;
private int m_subType;
public CECShopItemCategory(int mainType = -1, int subType = -1)
{
m_mainType = mainType;
m_subType = subType;
}
public void InitFromQShopConfig(int idCategory)
{
int mainType = -1;
int subType = -1;
CECQShopConfig.Instance().FindCategory(idCategory, out mainType, out subType);
SetCategory(mainType, subType);
}
public void SetCategory(int mainType, int subType)
{
m_mainType = mainType;
m_subType = subType;
}
public int GetMainType()
{
return m_mainType;
}
public int GetSubType()
{
return m_subType;
}
public bool MatchMainType(int mainType)
{
return m_mainType >= 0 && m_mainType == mainType;
}
public bool MatchItem(GShopItem item)
{
// 匹配主类型有效时检查 / Check when main type matching is valid
return MatchMainType(item.mainType)
&& (m_subType < 0 || item.subType == m_subType); // 子类型小于0时表示不限制子类型 / When sub type < 0, means no sub type restriction
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: c8734b057cb3bec4d83b03b28b652b6a
@@ -0,0 +1,79 @@
// Filename : CECShopItemOwnerNPC.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
using System;
namespace PerfectWorld.Scripts.Shop
{
// 封装 GSHOP_ITEM 的挂靠 NPC 查询 / Encapsulates NPC ownership query for GSHOP_ITEM
public class CECShopItemOwnerNPC
{
private const int TREASURE_ITEM_OWNER_NPC_COUNT = 8;
private uint m_ownerNPCID;
public CECShopItemOwnerNPC(uint ownerNPCID = 0)
{
m_ownerNPCID = ownerNPCID;
}
public void SetOwnerNPCID(uint ownerNPCID)
{
m_ownerNPCID = ownerNPCID;
}
public uint GetOwnerNPCID()
{
return m_ownerNPCID;
}
public bool IsEmpty()
{
return GetOwnerNPCID() == 0;
}
public bool Equals(CECShopItemOwnerNPC rhs)
{
return GetOwnerNPCID() == rhs.GetOwnerNPCID();
}
public bool MatchID(uint id)
{
return id == m_ownerNPCID;
}
public bool MatchItem(GShopItem item)
{
if (IsEmpty())
{
return !HasOwnerNPC(item);
}
bool result = false;
if (item.ownerNpcs != null)
{
for (int i = 0; i < TREASURE_ITEM_OWNER_NPC_COUNT && i < item.ownerNpcs.Length; ++i)
{
if (MatchID(item.ownerNpcs[i]))
{
result = true; // 找到了 / Found
break;
}
if (item.ownerNpcs[i] == 0)
{
break; // 已经到最后一个了,后面都是0 / Already reached the last one, rest are 0
}
}
}
return result;
}
public static bool HasOwnerNPC(GShopItem item)
{
// 编辑器保证数组中,第一个是非零的在前 / Editor ensures that in the array, the first non-zero is at the front
return item.ownerNpcs != null && item.ownerNpcs.Length > 0 && item.ownerNpcs[0] != 0;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: f4bc2fd669173534b9f94313c78af59e
@@ -0,0 +1,39 @@
// Filename : CECUIConfig.cs
// Creator : Xu Wenbin
// Date : 2013/12/11
// Converted to C#: 2024
namespace PerfectWorld.Scripts.Shop
{
// Stub implementation - to be properly implemented later
public class CECUIConfig
{
private static CECUIConfig s_instance;
public static CECUIConfig Instance()
{
if (s_instance == null)
{
s_instance = new CECUIConfig();
}
return s_instance;
}
public GameUIConfig GetGameUI()
{
return new GameUIConfig();
}
}
public class GameUIConfig
{
public bool bEnableQShopFashionShop = false;
public bool bEnableQShopFashionShopFlashSale = false;
public string strQShopFashionShopFlashSaleTitle = "";
public bool bEnableBackShopFashionShop = false;
public bool bEnableBackShopFashionShopFlashSale = false;
public string strBackShopFashionShopFlashSaleTitle = "";
public bool bEnableCeilPriceBeforeDiscountToGold = false;
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 28ee6f77dbdc1204eb2a2f933941e610