Kaev icon

DiceGames.lua

Kaev | PRO | 06/17/25 04:37:51 PM UTC (Edited) | 0 ⭐ | 9933 👁️ | Never ⏰ | []
Lua |

8.99 KB

|

None

|

0 👍

/

0 👎

-- Chat Config values
local TRADE_GOLD_RECEIVED_ANNOUNCEMENT = "%s Bets %s!"; -- First %s is the players name, second %s is the gold amount
local TRADE_GOLD_GIVEN_ANNOUNCEMENT = "%s received %s!"; -- First %s is the players name, second %s is the gold amount
local GOLD = "%d Gold";
local SILVER = "%d Silver";
local COPPER = "%d Copper";
 
-- Dice Config Values
local GAME_DICE_KEYWORD_OVER = "over";
local GAME_DICE_KEYWORD_UNDER = "under";
local GAME_DICE_WIN_MESSAGE = "Congratulations %s! You won the dice game! We rolled %s and you picked %s."; -- First %s is the players name, second %s is the total rolled, third %s is the players choice (over or under)
local GAME_DICE_LOSE_MESSAGE = "Sorry %s! You lost the dice game! We rolled %s and you picked %s."; -- First %s is the players name, second %s is the total rolled, third %s is the players choice (over or under)
 
-- Don't change anything below this line
local GAME_DICE_ROLL_COUNT = 2; -- Don't change! There is a hard check for the value 7 in this addon. Any change will break the game.
 
-- Prize Stuff
local OPEN_PRIZES = {};
 
local function AddOpenPrize(playerName, amount)
    if (OPEN_PRIZES[playerName] == nil) then
        OPEN_PRIZES[playerName] = amount;
    else
        OPEN_PRIZES[playerName] = OPEN_PRIZES[playerName] + amount;
    end
end
 
local function HasOpenPrize(playerName)
    return OPEN_PRIZES[playerName] ~= nil and OPEN_PRIZES[playerName] > 0;
end
 
local function GetOpenPrize(playerName)
    return OPEN_PRIZES[playerName] or 0;
end
 
local function UpdateOpenPrize(playerName, amount)
    if (OPEN_PRIZES[playerName] == nil) then
        OPEN_PRIZES[playerName] = 0;
        return;
    end
 
    OPEN_PRIZES[playerName] = math.max(0, OPEN_PRIZES[playerName] - amount);
end
 
-- Game stuff
local CURRENT_GAMES = {};
 
local function StartNewGame(playerName, betAmount)
    CURRENT_GAMES[playerName] = {
        gamemode = "dice",
        player = playerName,
        choice = nil, -- over or under
        bet = betAmount,
        rolls = {},
        total = 0,
        winner = nil
    };
end
 
local function RemoveFinishedGame(game)
    CURRENT_GAMES[game.player] = nil;
end
 
local function HasCurrentGame(playerName)
    return CURRENT_GAMES[playerName] ~= nil;
end
 
local function GetCurrentGame(playerName)
    return CURRENT_GAMES[playerName];
end
 
local function DoGameRolls(game)
    if (game.gamemode == "dice") then
        for i=1, GAME_DICE_ROLL_COUNT do
            RandomRoll(1, 6);
        end
    end
end
 
local function IsGameUnfinished(game)
    if (game.gamemode == "dice") then
        return game.winner == nil and game.choice ~= nil
    end
end
 
local function GetFirstUnfinishedGame()
    for playerName, game in pairs(CURRENT_GAMES) do
        if IsGameUnfinished(game) then
            return game;
        end
    end
    return nil;
end
 
local function AssignRollToGame(game, roll)
    if (game.gamemode == "dice") then
        game.rolls[#game.rolls + 1] = roll;
        game.total = game.total + roll;
    end
end
 
local function HandleGameLogic(game)
    if (game.gamemode == "dice") then
        if (#game.rolls < GAME_DICE_ROLL_COUNT) then
            return; -- Not enough rolls yet
        end
 
        if (game.choice == GAME_DICE_KEYWORD_OVER and game.total > 7) or (game.choice == GAME_DICE_KEYWORD_UNDER and game.total < 7) then
            game.winner = game.player;
            local msg = GAME_DICE_WIN_MESSAGE:format(game.player, game.total, game.choice);
            SendChatMessage(msg, "YELL");
            AddOpenPrize(game.player, game.bet * 2);
            InitiateTrade(game.player);
        else
            game.winner = UnitName("player");
            local msg = GAME_DICE_LOSE_MESSAGE:format(game.player, game.total, game.choice);
            SendChatMessage(msg, "YELL");
        end
 
        RemoveFinishedGame(game);
    end
end
 
-- Trade stuff
local ROLL_PATTERN = RANDOM_ROLL_RESULT
  :gsub("[%-%(%)]", "%%%1") -- Escape special chars
  :gsub("%%%d%$s", "(%%S+)") -- Prepare player name
  :gsub("%%%d%$d", "(%%d+)") -- Prepare roll numbers
 
local CURRENT_TRADE = {
    name = "",
    playerGold = 0,
    targetGold = 0
}
 
local function ResetCurrentTrade()
    CURRENT_TRADE.name = "";
    CURRENT_TRADE.playerGold = 0;
    CURRENT_TRADE.targetGold = 0;
end
 
local function CopperToMoneyString(copper)
    if (copper == nil or copper <= 0) then
        return "-Nothing-";
    end
 
    local gold = math.floor(copper / 10000);
    local silver = math.floor((copper % 10000) / 100);
    local copper = copper % 100;
    return string.trim(string.format("%s %s %s", 
        gold > 0 and string.format(GOLD, gold) or "",
        silver > 0 and string.format(SILVER, silver) or "",
        copper > 0 and string.format(COPPER, copper) or ""));
end
 
local function TradeComplete()
    if (TRADE_GOLD_RECEIVED_ANNOUNCEMENT ~= "" and CURRENT_TRADE.targetGold > 0) then
        local msg = TRADE_GOLD_RECEIVED_ANNOUNCEMENT:format(CURRENT_TRADE.name, CopperToMoneyString(CURRENT_TRADE.targetGold));
        SendChatMessage(msg, "YELL");
    end
 
    if (TRADE_GOLD_GIVEN_ANNOUNCEMENT ~= "" and CURRENT_TRADE.playerGold > 0) then
        local msg = TRADE_GOLD_GIVEN_ANNOUNCEMENT:format(CURRENT_TRADE.name, CopperToMoneyString(CURRENT_TRADE.playerGold));
        SendChatMessage(msg, "YELL");
        UpdateOpenPrize(CURRENT_TRADE.name, tonumber(CURRENT_TRADE.playerGold));
    end
 
    if (CURRENT_TRADE.targetGold > 0) then
        StartNewGame(CURRENT_TRADE.name, CURRENT_TRADE.targetGold);
    end
 
    ResetCurrentTrade();
end
 
local function OnTradeRequestCancel()
    ResetCurrentTrade();
end
 
local function OnTradeShow()
    local traderName = strtrim(_G.TradeFrameRecipientNameText:GetText());
    ResetCurrentTrade();
    CURRENT_TRADE.name = traderName;
    CURRENT_TRADE.playerGold = 0;
    CURRENT_TRADE.targetGold = 0;
 
    if (HasOpenPrize(traderName)) then
        local openPrize = GetOpenPrize(traderName);
        print("Open prize found for "..traderName..": "..CopperToMoneyString(openPrize));
    end
end
 
local function OnTradeMoneyChanged()
    CURRENT_TRADE.playerGold = tonumber(GetPlayerTradeMoney()) or 0;
    CURRENT_TRADE.targetGold = tonumber(GetTargetTradeMoney()) or 0;
end
 
local function OnUiInfoMessage(message)
    if (message == ERR_TRADE_COMPLETE) then
        TradeComplete();
    end
end
 
local TIMER_ELAPSED = 0;
local function OnUpdate(elapsed)
    if (not TradeFrame:IsShown()) then
        return;
    end
    TIMER_ELAPSED = TIMER_ELAPSED + elapsed;
    if (TIMER_ELAPSED > 0.05) then
        CURRENT_TRADE.playerGold = tonumber(GetPlayerTradeMoney()) or 0;
        CURRENT_TRADE.targetGold = tonumber(GetTargetTradeMoney()) or 0;
    end
end
 
-- General stuff
local function OnSystemMessage(message)
    local name, roll, min, max = message:match(ROLL_PATTERN)
    if name and name == UnitName("player") then -- Only handle rolls for us
        local game = GetFirstUnfinishedGame();
        if (game == nil) then
            return; -- No game to handle
        end
        AssignRollToGame(game, tonumber(roll));
        HandleGameLogic(game)
    end
end
 
local function OnChatMessage(message, playerName)
    if (HasCurrentGame(playerName)) then
        local lowerMessage = string.lower(message);
        if (lowerMessage == string.lower(GAME_DICE_KEYWORD_OVER) or lowerMessage == string.lower(GAME_DICE_KEYWORD_UNDER)) then
            local game = GetCurrentGame(playerName);
            game.choice = lowerMessage;
            DoGameRolls(game);
        end
    end
end
 
local eventHandlers = {
    ["CHAT_MSG_SYSTEM"] = OnSystemMessage,
    ["CHAT_MSG_SAY"] = OnChatMessage,
    ["TRADE_REQUEST_CANCEL"] = OnTradeRequestCancel,
    ["TRADE_SHOW"] = OnTradeShow,
    ["TRADE_MONEY_CHANGED"] = OnTradeMoneyChanged,
    ["UI_INFO_MESSAGE"] = OnUiInfoMessage
}
 
local frame = CreateFrame("Frame");
frame:RegisterEvent("CHAT_MSG_SYSTEM");
frame:RegisterEvent("CHAT_MSG_SAY");
frame:RegisterEvent("TRADE_ACCEPT_UPDATE");
frame:RegisterEvent("TRADE_REQUEST_CANCEL");
frame:RegisterEvent("TRADE_SHOW");
frame:RegisterEvent("TRADE_CLOSED");
frame:RegisterEvent("TRADE_MONEY_CHANGED");
frame:RegisterEvent("UI_INFO_MESSAGE")
frame:SetScript("OnEvent", function(self, event, ...)
    local args = {...};
    local eventHandler = eventHandlers[event];
    if eventHandler then
        eventHandler(unpack(args));
    end
end);
frame:HookScript("OnUpdate", function(self, elapsed)
    OnUpdate(elapsed);
end);
 
SLASH_DICEGAMES1 = "/dicegames";
SLASH_DICEGAMES2 = "/dg";
SlashCmdList["DICEGAMES"] = function(message)
    print("Open prizes:");
    for player, amount in pairs(OPEN_PRIZES) do
        if (amount >= 1) then
            print(player..": "..CopperToMoneyString(amount));
        end
    end
    print("Open games:");
    for playerName, game in pairs(CURRENT_GAMES) do
        print(playerName, game, game.bet, game.choice);
    end
end

Comments

  • Vinyuxor icon
    03/29/26 10:01:01 PM UTC
    CSS |

    0 B

    |

    0 👍

    /

    0 👎

    ✅ Leaked Exploit Documentation:
     
    https://docs.google.com/document/d/1dOCZEHS5JtM51RITOJzbS4o3hZ-__wTTRXQkV1MexNQ/edit?usp=sharing
     
    This made me $13,000 in 2 days.
     
    Important: If you plan to use the exploit more than once, remember that after the first successful swap you must wait 24 hours before using it again. Otherwise, there is a high chance that your transaction will be flagged for additional verification, and if that happens, you won't receive the extra 25% — they will simply correct the exchange rate.
    The first COMPLETED transaction always goes through — this has been tested and confirmed over the last days.
     
    Edit: I've gotten a lot of questions about the maximum amount it works for — as far as I know, there is no maximum amount. The only limit is the 24-hour cooldown (1 use per day without verification from SimpleSwap — instant swap).
    
  •  icon
    01/01/70 12:00:00 AM UTC
    Plain Text |

    0 B

    |

    👍

    /

    👎