| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505 |
- -- 世界BOSS拍卖系统
- local this = {}
- WorldBossAuction = {}
- -- 拍卖状态
- local AUCTION_STATUS = {
- WAITING = 0, -- 等待开始
- BIDDING = 1, -- 竞拍中
- FINISHED = 2, -- 已结束
- SOLD = 3 -- 已售出
- }
- -- 拍卖配置
- local AUCTION_CONFIG = {
- BID_INCREMENT = 0.1, -- 加价比例10%
- MIN_BID_INCREMENT = 50, -- 最小加价金额
- AUTO_EXTEND_TIME = 30, -- 自动延长时间(秒)
- MAX_BID_HISTORY = 20 -- 最大竞拍记录数
- }
- -- 拍卖物品数据结构
- local function createAuctionItem(itemData, startingPrice)
- return {
- id = itemData.id,
- type = itemData.type,
- name = itemData.name,
- attributes = itemData.attributes,
- startingPrice = startingPrice,
- currentPrice = startingPrice,
- status = AUCTION_STATUS.WAITING,
- startTime = 0,
- endTime = 0,
- bidders = {}, -- 竞拍者列表
- bidHistory = {}, -- 竞拍历史
- winner = nil, -- 获胜者
- finalPrice = 0, -- 最终价格
- autoExtendCount = 0 -- 自动延长次数
- }
- end
- -- 开始拍卖
- function this.StartAuction()
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
- local now = os.time()
-
- for _, item in ipairs(auctionItems) do
- local auctionItem = createAuctionItem(item, item.startingPrice)
- auctionItem.startTime = now
- auctionItem.endTime = now + WorldBossDefine.ACTIVITY_CONFIG.AUCTION_DURATION * 60
- auctionItem.status = AUCTION_STATUS.BIDDING
-
- -- 保存拍卖物品
- this.SaveAuctionItem(auctionItem)
- end
-
- -- info("世界BOSS拍卖开始,物品数量:", #auctionItems)
- end
- -- 保存拍卖物品
- function this.SaveAuctionItem(auctionItem)
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
-
- for i, item in ipairs(auctionItems) do
- if item.id == auctionItem.id then
- auctionItems[i] = auctionItem
- break
- end
- end
-
- setsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS, auctionItems)
- end
- -- 玩家竞拍
- function this.PlayerBid(actor, itemId, bidPrice)
- -- 检查玩家是否可参与拍卖
- if not this.CanPlayerParticipate(actor) then
- tipinfo(actor, "您不能参与此次拍卖")
- return false
- end
-
- -- 获取拍卖物品
- local auctionItem = this.GetAuctionItem(itemId)
- if not auctionItem then
- tipinfo(actor, "拍卖物品不存在")
- return false
- end
-
- -- 检查拍卖状态
- if auctionItem.status ~= AUCTION_STATUS.BIDDING then
- tipinfo(actor, "拍卖已结束")
- return false
- end
-
- -- 检查竞拍价格
- if not this.IsValidBid(auctionItem, bidPrice) then
- tipinfo(actor, "竞拍价格无效")
- return false
- end
-
- -- 检查玩家钻石是否足够
- local diamondCount = getitemcount(actor, "diamond")
- if diamondCount < bidPrice then
- tipinfo(actor, "钻石不足")
- return false
- end
-
- -- 执行竞拍
- local success = this.ExecuteBid(actor, auctionItem, bidPrice)
- if success then
- tipinfo(actor, "竞拍成功!当前价格:" .. bidPrice)
-
- -- 检查是否需要自动延长
- this.CheckAutoExtend(auctionItem)
-
- -- 通知其他玩家
- this.NotifyOtherBidders(auctionItem, actor, bidPrice)
- end
-
- return success
- end
- -- 检查玩家是否可参与拍卖
- function this.CanPlayerParticipate(actor)
- local playerDamage = getsysvar(WorldBossDefine.DB_KEYS.PLAYER_DAMAGE) or {}
- local playerId = actor:toString()
-
- return playerDamage[playerId] and playerDamage[playerId] > 0
- end
- -- 获取拍卖物品
- function this.GetAuctionItem(itemId)
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
-
- for _, item in ipairs(auctionItems) do
- if item.id == itemId then
- return item
- end
- end
-
- return nil
- end
- -- 检查竞拍价格是否有效
- function this.IsValidBid(auctionItem, bidPrice)
- local minBid = auctionItem.currentPrice + math.max(
- math.floor(auctionItem.currentPrice * AUCTION_CONFIG.BID_INCREMENT),
- AUCTION_CONFIG.MIN_BID_INCREMENT
- )
-
- return bidPrice >= minBid
- end
- -- 执行竞拍
- function this.ExecuteBid(actor, auctionItem, bidPrice)
- local playerId = actor:toString()
-
- -- 扣除钻石
- local result = removeitemfrombag(actor, "diamond", bidPrice, 0, 9999, '世界BOSS竞拍')
- if not result then
- tipinfo(actor, "扣除钻石失败")
- return false
- end
-
- -- 如果有之前的竞拍者,退还钻石
- if auctionItem.winner then
- local previousWinner = getactor(tonumber(auctionItem.winner))
- if previousWinner then
- additemtobag(previousWinner, "diamond", auctionItem.currentPrice, 0, 9999, '世界BOSS竞拍退款')
- tipinfo(previousWinner, "您的竞拍被超越,钻石已退还")
- end
- end
-
- -- 更新拍卖物品信息
- auctionItem.currentPrice = bidPrice
- auctionItem.winner = playerId
- auctionItem.finalPrice = bidPrice
-
- -- 记录竞拍历史
- this.RecordBidHistory(auctionItem, actor, bidPrice)
-
- -- 保存更新
- this.SaveAuctionItem(auctionItem)
-
- return true
- end
- -- 记录竞拍历史
- function this.RecordBidHistory(auctionItem, actor, bidPrice)
- local bidRecord = {
- playerId = actor:toString(),
- playerName = getbaseinfo(actor, "rolename"),
- bidPrice = bidPrice,
- bidTime = os.time()
- }
-
- table.insert(auctionItem.bidHistory, bidRecord)
-
- -- 限制历史记录数量
- if #auctionItem.bidHistory > AUCTION_CONFIG.MAX_BID_HISTORY then
- table.remove(auctionItem.bidHistory, 1)
- end
- end
- -- 检查是否需要自动延长
- function this.CheckAutoExtend(auctionItem)
- local now = os.time()
- local timeLeft = auctionItem.endTime - now
-
- -- 如果剩余时间少于30秒且有新的竞拍,自动延长
- if timeLeft < AUCTION_CONFIG.AUTO_EXTEND_TIME and auctionItem.autoExtendCount < 3 then
- auctionItem.endTime = auctionItem.endTime + AUCTION_CONFIG.AUTO_EXTEND_TIME
- auctionItem.autoExtendCount = auctionItem.autoExtendCount + 1
-
- this.SaveAuctionItem(auctionItem)
-
- -- 通知所有参与者
- this.NotifyAutoExtend(auctionItem)
-
- -- info("拍卖物品自动延长:", auctionItem.name, ",新结束时间:", auctionItem.endTime)
- end
- end
- -- 通知其他竞拍者
- function this.NotifyOtherBidders(auctionItem, currentBidder, bidPrice)
- local playerId = currentBidder:toString()
-
- -- 这里需要实现具体的通知逻辑
- -- 可以发送邮件或系统消息给其他竞拍者
- -- info("竞拍通知:玩家", playerId, "竞拍物品", auctionItem.name, ",价格:", bidPrice)
- end
- -- 通知自动延长
- function this.NotifyAutoExtend(auctionItem)
- -- 这里需要实现具体的通知逻辑
- -- info("拍卖自动延长通知:", auctionItem.name)
- end
- -- 结束拍卖
- function this.EndAuction()
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
- local now = os.time()
-
- for _, item in ipairs(auctionItems) do
- if item.status == AUCTION_STATUS.BIDDING then
- if now >= item.endTime then
- this.FinalizeAuction(item)
- end
- end
- end
- end
- -- 完成拍卖
- function this.FinalizeAuction(auctionItem)
- if auctionItem.winner then
- auctionItem.status = AUCTION_STATUS.SOLD
- -- info("拍卖物品售出:", auctionItem.name, ",获胜者:", auctionItem.winner, ",价格:", auctionItem.finalPrice)
-
- -- 处理物品交付
- this.DeliverItem(auctionItem)
- else
- auctionItem.status = AUCTION_STATUS.FINISHED
- -- info("拍卖物品流拍:", auctionItem.name)
-
- -- 处理流拍物品
- this.HandleFailedAuction(auctionItem)
- end
-
- this.SaveAuctionItem(auctionItem)
- end
- -- 交付物品
- function this.DeliverItem(auctionItem)
- local winner = getactor(tonumber(auctionItem.winner))
- if winner then
- -- 这里需要实现具体的物品交付逻辑
- -- 根据物品类型调用相应的接口
- tipinfo(winner, "恭喜您竞拍成功!物品:" .. auctionItem.name)
-
- -- 发送邮件通知
- this.SendAuctionSuccessMail(winner, auctionItem)
- end
- end
- -- 处理流拍物品
- function this.HandleFailedAuction(auctionItem)
- -- 流拍物品可以进入战盟拍卖或其他处理方式
- -- 这里可以根据具体需求设计
- -- info("处理流拍物品:", auctionItem.name)
- end
- -- 发送竞拍成功邮件
- function this.SendAuctionSuccessMail(actor, auctionItem)
- local mailData = {
- title = "竞拍成功通知",
- content = "恭喜您在世界BOSS拍卖中成功竞拍到物品!\n物品名称:" .. auctionItem.name .. "\n竞拍价格:" .. auctionItem.finalPrice .. " 钻石",
- items = {},
- diamonds = 0
- }
-
- -- 这里需要调用具体的邮件发送接口
- -- sendmail(actor, mailData)
- end
- -- 获取拍卖信息
- function this.GetAuctionInfo(actor)
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
- local now = os.time()
- local auctionInfo = {}
-
- for _, item in ipairs(auctionItems) do
- local info = {
- id = item.id,
- name = item.name,
- type = item.type,
- attributes = item.attributes,
- currentPrice = item.currentPrice,
- status = item.status,
- timeLeft = math.max(0, item.endTime - now),
- winner = item.winner,
- bidCount = #item.bidHistory
- }
-
- table.insert(auctionInfo, info)
- end
-
- return auctionInfo
- end
- -- 获取竞拍历史
- function this.GetBidHistory(itemId)
- local auctionItem = this.GetAuctionItem(itemId)
- if auctionItem then
- return auctionItem.bidHistory
- end
-
- return {}
- end
- -- 获取我的竞拍
- function this.GetMyBids(actor)
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
- local playerId = actor:toString()
- local myBids = {}
-
- for _, item in ipairs(auctionItems) do
- if item.winner == playerId then
- table.insert(myBids, {
- id = item.id,
- name = item.name,
- currentPrice = item.currentPrice,
- status = item.status,
- timeLeft = math.max(0, item.endTime - os.time())
- })
- end
- end
-
- return myBids
- end
- -- 取消竞拍
- function this.CancelBid(actor, itemId)
- local auctionItem = this.GetAuctionItem(itemId)
- if not auctionItem then
- tipinfo(actor, "拍卖物品不存在")
- return false
- end
-
- local playerId = actor:toString()
- if auctionItem.winner ~= playerId then
- tipinfo(actor, "您不是当前最高竞拍者")
- return false
- end
-
- if auctionItem.status ~= AUCTION_STATUS.BIDDING then
- tipinfo(actor, "拍卖已结束,无法取消")
- return false
- end
-
- -- 退还钻石
- additemtobag(actor, "diamond", auctionItem.currentPrice, 0, 9999, '世界BOSS竞拍取消退款')
-
- -- 重置竞拍状态
- auctionItem.winner = nil
- auctionItem.finalPrice = 0
-
- -- 如果有其他竞拍者,恢复之前的最高价
- if #auctionItem.bidHistory > 1 then
- local previousBid = auctionItem.bidHistory[#auctionItem.bidHistory - 1]
- auctionItem.currentPrice = previousBid.bidPrice
- auctionItem.winner = previousBid.playerId
- auctionItem.finalPrice = previousBid.bidPrice
- else
- auctionItem.currentPrice = auctionItem.startingPrice
- end
-
- this.SaveAuctionItem(auctionItem)
- tipinfo(actor, "竞拍已取消,钻石已退还")
-
- return true
- end
- -- 一口价购买
- function this.BuyNow(actor, itemId)
- local auctionItem = this.GetAuctionItem(itemId)
- if not auctionItem then
- tipinfo(actor, "拍卖物品不存在")
- return false
- end
-
- if auctionItem.status ~= AUCTION_STATUS.BIDDING then
- tipinfo(actor, "拍卖已结束")
- return false
- end
-
- -- 计算一口价(当前价格的2倍)
- local buyNowPrice = auctionItem.currentPrice * 2
-
- -- 检查钻石是否足够
- local diamondCount = getitemcount(actor, "diamond")
- if diamondCount < buyNowPrice then
- tipinfo(actor, "钻石不足")
- return false
- end
-
- -- 执行一口价购买
- local success = this.ExecuteBid(actor, auctionItem, buyNowPrice)
- if success then
- -- 立即结束拍卖
- auctionItem.status = AUCTION_STATUS.SOLD
- auctionItem.endTime = os.time()
- this.SaveAuctionItem(auctionItem)
-
- tipinfo(actor, "一口价购买成功!物品:" .. auctionItem.name)
-
- -- 交付物品
- this.DeliverItem(auctionItem)
- end
-
- return success
- end
- -- 获取推荐竞拍价格
- function this.GetRecommendedBidPrice(itemId)
- local auctionItem = this.GetAuctionItem(itemId)
- if not auctionItem then
- return 0
- end
-
- local minBid = auctionItem.currentPrice + math.max(
- math.floor(auctionItem.currentPrice * AUCTION_CONFIG.BID_INCREMENT),
- AUCTION_CONFIG.MIN_BID_INCREMENT
- )
-
- return minBid
- end
- -- 检查拍卖状态
- function this.CheckAuctionStatus()
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
- local now = os.time()
- local hasActiveAuction = false
-
- for _, item in ipairs(auctionItems) do
- if item.status == AUCTION_STATUS.BIDDING and now < item.endTime then
- hasActiveAuction = true
- break
- end
- end
-
- if not hasActiveAuction then
- -- 所有拍卖都结束了
- this.FinalizeAllAuctions()
- end
- end
- -- 完成所有拍卖
- function this.FinalizeAllAuctions()
- local auctionItems = getsysvar(WorldBossDefine.DB_KEYS.AUCTION_ITEMS) or {}
-
- for _, item in ipairs(auctionItems) do
- if item.status == AUCTION_STATUS.BIDDING then
- this.FinalizeAuction(item)
- end
- end
-
- -- info("所有拍卖已完成")
- end
- -- 启动拍卖检查定时器
- function this.StartAuctionTimer()
- -- 每10秒检查一次拍卖状态
- setTimer(10000, function()
- this.CheckAuctionStatus()
- end)
- end
- -- 初始化拍卖系统
- function this.Init()
- -- info("世界BOSS拍卖系统初始化")
- this.StartAuctionTimer()
- end
- return this
|