123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579 |
- Auction = {}
- AuctionConst = {
- AUCTION_WAY = 1,
- AUCTION_TIMER = 201,
- AUCTION_DIVIDEND = 14001002, -- 分红比例
- AUCTION_SUCCESS_EMAIL = 106001,
- AUCTION_FAIL_EMAIL = 106002, -- 拍卖失败返还邮件
- AUCTION_DIVIDE_EMAIL = 106012, -- 拍卖分红邮件
- AUCTION_GOODS = "U$AuctionGoods",
- CAN_DISTRIBUTE_IDS = "U$DistributeIds",
- CAN_REWARD_UNIONS = "R$CanRewardUnions",
- }
- local SortType = {
- ASC_BY_TIME = 1, -- 按照时间升序
- DESC_BY_TIME = 2, -- 按照时间降序
- ASC_BY_PRICE = 3, -- 按照价格升序
- DESC_BY_PRICE = 4, -- 按照价格降序
- }
- function Auction.NoticeClientToStartAuction(actor, unionId, myHurtMember, canRewardUnions)
- -- unionId = 18015998178004993
- -- myHurtMember = {
- -- 18015998177937409 ,
- -- 18015998178037760
- -- }
- -- canRewardUnions = {18015998178004993}
- local goods = ConfigDataManager.getTable("cfg_stall", "way", AuctionConst.AUCTION_WAY)
- local openDays = getbaseinfo(actor, "serveropendays")
- local auctionGoods, closetDay = Auction.GetClosetGoodsData(goods, openDays)
- local idAndCount = {}
- for _, goodsInfo in ipairs(auctionGoods) do
- local probability = goodsInfo["probability"]
- local cfgid = goodsInfo['id']
- local count = goodsInfo['number']
- if probability ~= "" and probability ~= nil then
- probability = tonumber(probability)
- local num = math.random(1, 10000)
- if probability >= num then
- idAndCount[tonumber(cfgid)] = tonumber(count)
- end
- else
- idAndCount[tonumber(cfgid)] = tonumber(count)
- end
- end
- local itemInfos = saveunionitem(actor, DuplicateType.WAR_ALLIANCE, idAndCount)
- -- lg("返回的道具信息", itemInfos)
- local items = {}
- for index, itemInfo in ipairs(itemInfos) do
- local id = itemInfo["id"]
- local itemcfgid = itemInfo["itemcfgid"]
- local rank = itemInfo["rank"]
- local grade = itemInfo["grade"]
- local entrysize = itemInfo["entrysize"]
- local stalls = ConfigDataManager.getTable("cfg_stall", "id", itemcfgid, "startday", closetDay, "way",
- TRADE_WAY.GARD_BOSS)
- local itemStall = stalls[1]
- local bidderid = 0
- local itemname = itemStall["name"]
- local type = itemStall["type"]
- local subtype = itemStall["subtype"]
- local count = itemStall["number"]
- local state = ""
- local oneprice = itemStall["fixedprice"]
- local price = itemStall["startingprice"]
- local increment = itemStall["auction"]
- local cointype = itemStall["money"]
- local time = itemStall["time"]
- local now = getbaseinfo("now")
- local endTime = now + time * 60 * 1000
- local career = itemStall["job"]
- local item = {
- itemid = id,
- itemcfgid = itemcfgid,
- bidderid = bidderid,
- rank = rank,
- grade = grade or 1,
- entrysize = tonumber(entrysize),
- itemname = itemname,
- type = tonumber(type),
- subtype = tonumber(subtype),
- count = tonumber(count),
- state = state,
- price = tonumber(price),
- oneprice = tonumber(oneprice),
- increment = tonumber(increment),
- cointype = tonumber(cointype),
- time = time * 60,
- endtime = endTime,
- career = career,
- }
- table.insert(items, item)
- end
- -- lg("获取到拍卖行物品信息", items)
- local guild = getmyguild(actor)
- if not guild then
- return
- end
- local myUnionGoods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- myUnionGoods = myUnionGoods == "" and {} or myUnionGoods
- if next(myUnionGoods) ~= nil then
- for _, item in ipairs(items) do
- table.insert(myUnionGoods, item)
- end
- else
- myUnionGoods = items
- end
- setguilddef(guild, AuctionConst.AUCTION_GOODS, myUnionGoods)
- -- lg("我的战盟伤害成员:", myHurtMember)
- setguilddef(guild, AuctionConst.CAN_DISTRIBUTE_IDS, myHurtMember)
- -- lg("可参与竞拍的战盟", canRewardUnions)
- setsysvar(actor, AuctionConst.CAN_REWARD_UNIONS, canRewardUnions)
- Auction.SendOpenAuctionMessage(actor, myHurtMember)
- GlobalTimer.setontimerex(AuctionConst.AUCTION_TIMER, 3)
- end
- function Auction.GetClosetGoodsData(goods, openDays)
- local closestDay = 0
- local minDiff = 99999
- for _, goodsInfo in ipairs(goods) do
- local startDay = goodsInfo["startday"]
- startDay = tonumber(startDay)
- local diff = math.abs(startDay - openDays)
- if startDay <= openDays then
- if diff < minDiff then
- minDiff = diff
- closestDay = startDay
- end
- end
- end
- local closestElements = {}
- for _, goodsInfo in ipairs(goods) do
- local startDay = goodsInfo["startday"]
- startDay = tonumber(startDay)
- if startDay == closestDay then
- table.insert(closestElements, goodsInfo)
- end
- end
- return closestElements, closestDay
- end
- function Auction.SendOpenAuctionMessage(actor, myHurtMember)
- for _, player in ipairs(myHurtMember) do
- local role = getactor(actor, player)
- local mapId = getbaseinfo(role, "unimapid")
- if mapId ~= 0 then
- WarAlliance.ResTaskPhaseUpdate(role, mapId)
- end
- sendluamsg(role, LuaMessageIdToClient.RES_WAR_ALLIANCE_OPEN_AUCTION, { 1 })
- end
- end
- function ontimerex201()
- local guilds = getsysvar(AuctionConst.CAN_REWARD_UNIONS)
- if guilds == nil or guilds == "" or next(guilds) == nil then
- return
- end
- -- lg("可参与竞拍的战盟:", unionIds)
- for _, guild in ipairs(guilds) do
- local unionId = tonumber(guild:toString())
- local goods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- goods = goods == "" and {} or goods
- -- lg("当前战盟拍卖行物品信息:", goods)
- if next(goods) ~= nil then
- local removeIndices = {}
- for i, goodsInfo in ipairs(goods) do
- local endTime = goodsInfo["endtime"]
- local now = getbaseinfo("now")
- if endTime < now then
- table.insert(removeIndices, i)
- end
- end
- -- lg("本次拍卖行过期商品索引:", removeIndices)
- for i = #removeIndices, 1, -1 do
- local indexToRemove = removeIndices[i]
- Auction.OnTimeSettleAuction(goods[indexToRemove], guild)
- table.remove(goods, indexToRemove)
- end
- end
- setguilddef(guild, AuctionConst.AUCTION_GOODS, goods)
- end
- local allHadExpired = true
- for _, guild in ipairs(guilds) do
- local goods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- if next(goods) ~= nil then
- allHadExpired = false
- break
- end
- end
- if allHadExpired then
- GlobalTimer.setofftimer(AuctionConst.AUCTION_TIMER)
- end
- end
- -- 筛选商品
- function Auction.GetSomeGoods(actor, msgData, isCheck)
- local type = msgData[1]
- local subType = msgData[2]
- local sort = msgData[3]
- local career = msgData[4]
- local rank = msgData[5]
- local grade = msgData[6]
- local guild = getmyguild(actor)
- if not guild then
- return {}
- end
- local myUnionGoods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- myUnionGoods = myUnionGoods == "" and {} or myUnionGoods
- if next(myUnionGoods) == nil then
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_AUCTION_GOODS, myUnionGoods)
- return myUnionGoods
- end
- local filteredGoods = Auction.FilterGoods(myUnionGoods, type, subType, career, grade, rank)
- Auction.SortGoods(filteredGoods, sort)
- -- 添加我的竞拍信息
- for _, goods in ipairs(filteredGoods) do
- local bidder = goods["bidderid"]
- if bidder == 0 then
- goods["state"] = ""
- elseif bidder:toString() == actor:toString() then
- goods["state"] = "我的竞拍"
- else
- goods["state"] = "竞拍中"
- end
- end
- if isCheck then
- return filteredGoods
- else
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_AUCTION_GOODS, filteredGoods)
- end
- end
- function Auction.FilterGoods(myUnionGoods, type, subType, career, grade, rank)
- local filteredGoods = {}
- -- lg("筛选商品:", "type", type, "career", career, "grade", grade, "rank", rank)
- for _, goods in ipairs(myUnionGoods) do
- if (type ~= 0 and type ~= tonumber(goods["type"])) then
- goto continue
- end
- if (subType ~= 0 and subType ~= tonumber(goods["subtype"])) then
- goto continue
- end
- if (career ~= 0) then
- local careers = goods["career"]
- local careerArr = string.splitByAll(careers, "#")
- local baseCareer = careerArr[1]
- local isCareerMatch = career == tonumber(baseCareer)
- if not isCareerMatch then
- goto continue
- end
- end
- if (rank ~= 0 and rank ~= tonumber(goods["rank"])) then
- goto continue
- end
- if (grade ~= 0 and grade ~= tonumber(goods["grade"])) then
- goto continue
- end
- local endTime = goods["endtime"]
- if tonumber(endTime) <= getbaseinfo("now") then
- goto continue
- end
- table.insert(filteredGoods, goods)
- ::continue::
- end
- return filteredGoods
- end
- function Auction.SortGoods(filteredGoods, sortType)
- local function compare(a, b)
- if sortType == SortType.ASC_BY_TIME then
- return a["time"] < b["time"]
- elseif sortType == SortType.DESC_BY_TIME then
- return a["time"] > b["time"]
- elseif sortType == SortType.ASC_BY_PRICE then
- return a["price"] < b["price"]
- elseif sortType == SortType.DESC_BY_PRICE then
- return a["price"] > b["price"]
- end
- end
- table.sort(filteredGoods, compare)
- end
- function Auction.GetGoodsDetailInfo(actor, msgData)
- local itemId = msgData["itemId"]
- local type = msgData["type"]
- goodsdetailinfo(actor, itemId, AuctionConst.AUCTION_WAY, actor:toString())
- end
- -- @description 玩家竞价
- function Auction.PlayerBidOnItem(actor, msgData)
- local goodsId = msgData["goodsId"]
- local guild = getmyguild(actor)
- if guild == nil then
- tipinfo(actor, "您不是战盟成员,无法参与竞拍")
- return
- end
- local hasQualify = Auction.CheckHQualify(actor)
- if not hasQualify then
- tipinfo(actor, "战盟boss未通关,无法参与竞拍")
- return
- end
- local result = Auction.BiddingGoods(actor, goodsId, guild)
- local biddingResult
- if result then
- info("玩家竞价成功", actor:toString(), goodsId)
- biddingResult = { opt = "bidding", ret = true }
- else
- info("玩家竞价失败", actor:toString(), goodsId)
- biddingResult = { opt = "bidding", ret = false }
- end
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_OPT_INFO, biddingResult)
- end
- function Auction.BiddingGoods(actor, goodsId, guild)
- local unionId = tonumber(guild:toString())
- local myUnionGoods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- myUnionGoods = myUnionGoods == "" and {} or myUnionGoods
- local currGoods
- for _, goods in ipairs(myUnionGoods) do
- if tostring(goodsId) == tostring(goods["itemid"]) then
- currGoods = goods
- break
- end
- end
- if currGoods == nil then
- tipinfo(actor, "该商品已被购买或已下架")
- return false
- end
- local lastBidder = currGoods["bidderid"]
- if lastBidder ~= 0 and lastBidder:toString() == actor:toString() then
- tipinfo(actor, "您已经参与竞价,请勿重复参与")
- return false
- end
- local bidPrice = currGoods["price"]
- local onePrice = currGoods["oneprice"]
- local newPrice = Auction.CalculateNewPrice(currGoods)
- local coinType = currGoods["cointype"]
- local coinCount = getbagitemcountbyid(actor, coinType)
- if coinCount < newPrice then
- local coinName = ConfigDataManager.getTableValue("cfg_item", "name", "id", coinType)
- tipinfo(actor, "您的" .. coinName .. "不足")
- return false
- end
- if lastBidder ~= 0 then
- Auction.SendBidFaileMail(lastBidder, goodsId, coinType, bidPrice)
- end
- if newPrice == onePrice then
- tipinfo(actor, "当前价格达到一口价,转为一口价购买")
- local itemCfgId = tonumber(currGoods["itemcfgid"])
- local itemName = ConfigDataManager.getTableValue("cfg_item", "name", "id", itemCfgId)
- local result = moveunionitem(actor, goodsId, unionId, actor:toString(), AuctionConst.AUCTION_SUCCESS_EMAIL,
- itemName)
- if result then
- removeitemfrombag(actor, coinType, newPrice,0,9999,'战盟BOSS竞拍')
- local myHurtMembers = getguilddef(guild, AuctionConst.CAN_DISTRIBUTE_IDS)
- Auction.DistributeProfits(actor, itemCfgId, coinType, newPrice, myHurtMembers)
- end
- for i = #myUnionGoods, 1, -1 do
- local goods = myUnionGoods[i]
- if tostring(goods["itemid"]) == tostring(goodsId) then
- table.remove(myUnionGoods, i)
- end
- end
- setguilddef(guild, AuctionConst.AUCTION_GOODS, myUnionGoods)
- return true
- end
- removeitemfrombag(actor, coinType, newPrice,0,9999,'战盟BOSS竞拍')
- currGoods["price"] = newPrice
- currGoods["bidderid"] = actor
- setguilddef(guild, AuctionConst.AUCTION_GOODS, myUnionGoods)
- return true
- end
- function Auction.CalculateNewPrice(currGoods)
- local bidPrice = currGoods["price"]
- local increment = currGoods["increment"]
- local onePrice = currGoods["oneprice"]
- local newPrice = math.ceil(bidPrice * (1 + increment * 0.0001))
- if newPrice > onePrice then
- newPrice = onePrice
- end
- return newPrice
- end
- -- @description 玩家一口价购买
- function Auction.PlayerBuyNow(actor, msgData)
- local goodsId = msgData["goodsId"]
- -- 检查玩家是否属于战盟
- local guild = getmyguild(actor)
- if guild == nil then
- tipinfo(actor, "您不是战盟成员,无法参与竞拍")
- return
- end
- -- 检查战盟通关条件
- local hasQualify = Auction.CheckHQualify(actor)
- if not hasQualify then
- tipinfo(actor, "战盟通关条件不符合,无法一口价购买")
- return
- end
- -- 一口价购买
- local result = Auction.BuyGoods(actor, goodsId, guild)
- local buyResult;
- if result then
- info("玩家一口价购买成功", actor:toString(), goodsId)
- buyResult = { opt = "buy", ret = true }
- else
- info("玩家一口价购买失败", actor:toString(), goodsId)
- buyResult = { opt = "buy", ret = false }
- end
- -- lg("玩家一口价购买结果:", buyResult)
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_OPT_INFO, buyResult)
- end
- function Auction.BuyGoods(actor, goodsId, guild)
- local unionId = tonumber(guild:toString())
- local myUnionGoods = getguilddef(guild, AuctionConst.AUCTION_GOODS) or {}
- myUnionGoods = myUnionGoods == "" and {} or myUnionGoods
- local currGoods
- for _, goods in ipairs(myUnionGoods) do
- if tostring(goodsId) == tostring(goods["itemid"]) then
- currGoods = goods
- break
- end
- end
- if currGoods == nil then
- tipinfo(actor, "该商品已被购买或已下架")
- return false
- end
- local lastBidder = currGoods["bidderid"]
- if lastBidder ~= 0 and lastBidder:toString() == actor:toString() then
- tipinfo(actor, "您已经参与竞价,请勿重复参与")
- return false
- end
- local bidPrice = currGoods["price"]
- local newPrice = currGoods["oneprice"]
- local coinType = currGoods["cointype"]
- local coinCount = getbagitemcountbyid(actor, coinType)
- if coinCount < newPrice then
- local coinName = ConfigDataManager.getTableValue("cfg_item", "name", "id", coinType)
- tipinfo(actor, "您的" .. coinName .. "不足")
- return false
- end
- if lastBidder ~= 0 then
- Auction.SendBidFaileMail(lastBidder, goodsId, coinType, bidPrice)
- end
- local itemCfgId = tonumber(currGoods["itemcfgid"])
- local itemName = ConfigDataManager.getTableValue("cfg_item", "name", "id", itemCfgId)
- local result = moveunionitem(actor, goodsId, unionId, actor:toString(), AuctionConst.AUCTION_SUCCESS_EMAIL, itemName)
- if result then
- removeitemfrombag(actor, coinType, newPrice,0,9999,'战盟BOSS竞拍')
- local myHurtMembers = getguilddef(guild, AuctionConst.CAN_DISTRIBUTE_IDS) or {}
- Auction.DistributeProfits(actor, itemCfgId, coinType, newPrice, myHurtMembers)
- end
- for i = #myUnionGoods, 1, -1 do
- local goods = myUnionGoods[i]
- if tostring(goods["itemid"]) == tostring(goodsId) then
- table.remove(myUnionGoods, i)
- end
- end
- setguilddef(guild, AuctionConst.AUCTION_GOODS, myUnionGoods)
- return true
- end
- function Auction.ShowAutionPanel(actor)
- local result = Auction.CheckHQualify(actor)
- if result then
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_SHOW_AUCTION_PANEL, { true })
- else
- sendluamsg(actor, LuaMessageIdToClient.RES_WAR_ALLIANCE_SHOW_AUCTION_PANEL, { false })
- end
- end
- -- 检查自己的战盟是否通关
- function Auction.CheckHQualify(actor)
- local allianceId = getbaseinfo(actor, "guildid")
- if allianceId == 0 then
- return false
- end
- local goods = Auction.GetSomeGoods(actor, { 0, 0, 0, 0, 0, 0 }, true)
- return #goods > 0
- end
- function Auction.OnTimeSettleAuction(goodsInfo, guild)
- -- lg("开始结算拍卖,商品信息", goodsInfo)
- if goodsInfo == nil then
- return
- end
- local unionId = tonumber(guild:toString())
- local bidder = goodsInfo["bidderid"]
- local goodsId = goodsInfo["itemid"]
- info("结算拍卖,商品信息,竞拍者:", bidder)
- local result
- if bidder == 0 then
- -- lg("结算无购买者","goodsId",goodsId,"unionId",unionId)
- result = moveunionitem(goodsId, unionId)
- else
- local myHurtMembers = getguilddef(guild, AuctionConst.CAN_DISTRIBUTE_IDS)
- local cointype = tonumber(goodsInfo["cointype"])
- local price = tonumber(goodsInfo["price"])
- local itemcfgid = tonumber(goodsInfo["itemcfgid"])
- local itemName = ConfigDataManager.getTableValue("cfg_item", "name", "id", itemcfgid)
- info("结算有购买者", "unionId", unionId, "bidder", bidder)
- result = moveunionitem(bidder, goodsId, unionId, bidder:toString(), AuctionConst.AUCTION_SUCCESS_EMAIL, itemName)
- -- lg("删除结果:", result)
- if result then
- Auction.DistributeProfits(bidder, itemcfgid, cointype, price, myHurtMembers)
- end
- end
- end
- function Auction.DistributeProfits(actor, itemCfgId, coinType, price, canBuyIds)
- info("分红信息:","角色:",actor, "道具:",itemCfgId, "分红成员:",canBuyIds)
- if array.simpleContains(canBuyIds, actor:toString()) then
- for _, member in ipairs(canBuyIds) do
- local memberActor = getactor(actor, member)
- if memberActor:toString() ~= actor:toString() then
- Auction.ActDistribute(memberActor, itemCfgId, coinType, price, #canBuyIds - 1)
- end
- end
- else
- for _, member in ipairs(canBuyIds) do
- local memberActor = getactor(actor, member)
- Auction.ActDistribute(memberActor, itemCfgId, coinType, price, #canBuyIds)
- end
- end
- end
- function Auction.ActDistribute(actor, itemCfgId, coinType, price, personCount)
- local dividendRatio = ConfigDataManager.getTableValue("cfg_repGlobal", "value", "id", AuctionConst.AUCTION_DIVIDEND)
- dividendRatio = tonumber(dividendRatio) * 0.0001
- local profitPerMember = price * dividendRatio
- profitPerMember = math.floor(profitPerMember)
- Auction.SendDivideMail(actor, itemCfgId, coinType, profitPerMember, personCount)
- end
- -- @description 发送分红邮件
- function Auction.SendDivideMail(actor, itemCfgId, coinType, profitPerMember, personCount)
- local itemName = ConfigDataManager.getTableValue("cfg_item", "name", "id", itemCfgId)
- local priceTypeName = ConfigDataManager.getTableValue("cfg_item", "name", "id", coinType)
- local totalDivide = profitPerMember * personCount
- local param = itemName .. "#" .. priceTypeName .. "#" .. totalDivide .. "#" .. profitPerMember
- sendconfigmailbyrid(actor, actor:toString(),
- AuctionConst.AUCTION_DIVIDE_EMAIL, { [tonumber(coinType)] = tonumber(profitPerMember) }, param)
- end
- -- @description 发送竞价失败邮件
- function Auction.SendBidFaileMail(lastBidder, goodsId, costType, costNum)
- -- lg("发送竞价失败邮件:", lastBidder, goodsId, costType, costNum)
- local itemName = ConfigDataManager.getTableValue("cfg_item", "name", "id", goodsId)
- local costName = ConfigDataManager.getTableValue("cfg_item", "name", "id", costType)
- local param = itemName .. "#" .. costName
- sendconfigmailbyrid(lastBidder, lastBidder:toString(),
- AuctionConst.AUCTION_FAIL_EMAIL, { [tonumber(costType)] = tonumber(costNum) }, param)
- end
- function Auction.combineGlobalVar(varName,varData)
- local data = {}
- for sid, var in pairs(varData) do
- table.AddRanage(data, var)
- end
- setsysvar(varName, data)
- end
- function clearauction(actor)
- local guild = getmyguild(actor)
- setguilddef(guild, AuctionConst.AUCTION_GOODS, {})
- setguilddef(guild, AuctionConst.CAN_DISTRIBUTE_IDS, {})
- setsysvar(actor, AuctionConst.CAN_REWARD_UNIONS, {})
- end
|