├── .gitignore ├── audits └── BetSwirl-Token_Smart_Contract_Security_Report_03.03.22.pdf ├── package.json ├── contracts ├── BetsToken.sol ├── bank │ └── IBank.sol └── games │ ├── IPvPGamesStore.sol │ ├── CoinToss.sol │ ├── Dice.sol │ ├── Roulette.sol │ ├── PvPGamesStore.sol │ ├── RussianRoulette.sol │ └── Keno.sol ├── hardhat.config.js ├── docs ├── bank │ ├── IGame.md │ └── IBank.md ├── games │ ├── IPvPGamesStore.md │ ├── PvPGamesStore.md │ ├── Roulette.md │ ├── CoinToss.md │ ├── Dice.md │ └── Keno.md └── BetsToken.md ├── README.md └── graphs ├── BetsToken.svg ├── CoinToss.svg ├── Dice.svg ├── Roulette.svg ├── RussianRoulette.svg └── PvPGamesStore.svg /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | 3 | #Hardhat files 4 | cache 5 | artifacts 6 | -------------------------------------------------------------------------------- /audits/BetSwirl-Token_Smart_Contract_Security_Report_03.03.22.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/biginfo2012/betswirl-contracts/HEAD/audits/BetSwirl-Token_Smart_Contract_Security_Report_03.03.22.pdf -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "smart-contracts", 3 | "license": "MIT", 4 | "repository": "BetSwirl/Smart-Contracts", 5 | "scripts": { 6 | "compile": "hardhat compile" 7 | }, 8 | "devDependencies": { 9 | "@chainlink/contracts": "^0.6.1", 10 | "@openzeppelin/contracts": "^4.1.0", 11 | "@primitivefi/hardhat-dodoc": "^0.2.3", 12 | "hardhat": "^2.2.1" 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /contracts/BetsToken.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity ^0.8.10; 4 | 5 | import "@openzeppelin/contracts/token/ERC20/ERC20.sol"; 6 | import "@openzeppelin/contracts/access/Ownable.sol"; 7 | import "@openzeppelin/contracts/utils/Multicall.sol"; 8 | 9 | /// @title BetSwirl's ERC20 token 10 | /// @author Romuald Hog 11 | contract BetsToken is ERC20, Ownable, Multicall { 12 | constructor() ERC20("BetSwirl Token", "BETS") { 13 | _mint(msg.sender, 7_777_777_777 ether); 14 | } 15 | 16 | /** 17 | * @dev This function is here to ensure BEP-20 compatibility 18 | */ 19 | function getOwner() external view returns (address) { 20 | return owner(); 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /hardhat.config.js: -------------------------------------------------------------------------------- 1 | require('@primitivefi/hardhat-dodoc') 2 | 3 | module.exports = { 4 | dodoc: { 5 | include: ['Bank', 'Dice', 'CoinToss', 'Roulette', 'Keno', 'RussianRoulette', 'PvPGamesStore', 'BetsToken'] 6 | }, 7 | solidity: { 8 | compilers: [ 9 | { 10 | version: '0.8.17', 11 | settings: { 12 | optimizer: { 13 | enabled: true, 14 | runs: 80000, 15 | }, 16 | }, 17 | }, 18 | ], 19 | overrides: { 20 | 'contracts/games/Keno.sol': { 21 | version: '0.8.17', 22 | settings: { 23 | optimizer: { 24 | enabled: true, 25 | runs: 9999, 26 | }, 27 | }, 28 | }, 29 | }, 30 | }, 31 | } 32 | -------------------------------------------------------------------------------- /docs/bank/IGame.md: -------------------------------------------------------------------------------- 1 | # IGame 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### hasPendingBets 14 | 15 | ```solidity 16 | function hasPendingBets(address token) external view returns (bool) 17 | ``` 18 | 19 | 20 | 21 | 22 | 23 | #### Parameters 24 | 25 | | Name | Type | Description | 26 | |---|---|---| 27 | | token | address | undefined | 28 | 29 | #### Returns 30 | 31 | | Name | Type | Description | 32 | |---|---|---| 33 | | _0 | bool | undefined | 34 | 35 | ### withdrawTokensVRFFees 36 | 37 | ```solidity 38 | function withdrawTokensVRFFees(address token) external nonpayable 39 | ``` 40 | 41 | 42 | 43 | 44 | 45 | #### Parameters 46 | 47 | | Name | Type | Description | 48 | |---|---|---| 49 | | token | address | undefined | 50 | 51 | 52 | 53 | 54 | -------------------------------------------------------------------------------- /contracts/bank/IBank.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | /// @notice Minimal interface for Bank. 6 | /// @author Romuald Hog. 7 | interface IBank { 8 | /// @notice Gets the token's allow status used on the games smart contracts. 9 | /// @param token Address of the token. 10 | /// @return Whether the token is enabled for bets. 11 | function isAllowedToken(address token) external view returns (bool); 12 | 13 | /// @notice Payouts a winning bet, and allocate the house edge fee. 14 | /// @param user Address of the gamer. 15 | /// @param token Address of the token. 16 | /// @param profit Number of tokens to be sent to the gamer. 17 | /// @param fees Bet amount and bet profit fees amount. 18 | function payout( 19 | address user, 20 | address token, 21 | uint256 profit, 22 | uint256 fees 23 | ) external payable; 24 | 25 | /// @notice Accounts a loss bet. 26 | /// @dev In case of an ERC20, the bet amount should be transfered prior to this tx. 27 | /// @dev In case of the gas token, the bet amount is sent along with this tx. 28 | /// @param tokenAddress Address of the token. 29 | /// @param amount Loss bet amount. 30 | /// @param fees Bet amount and bet profit fees amount. 31 | function cashIn( 32 | address tokenAddress, 33 | uint256 amount, 34 | uint256 fees 35 | ) external payable; 36 | 37 | /// @notice Calculates the max bet amount based on the token balance, the balance risk, and the game multiplier. 38 | /// @param token Address of the token. 39 | /// @param multiplier The bet amount leverage determines the user's profit amount. 10000 = 100% = no profit. 40 | /// @return Maximum bet amount for the token. 41 | /// @dev The multiplier should be at least 10000. 42 | function getMaxBetAmount(address token, uint256 multiplier) 43 | external 44 | view 45 | returns (uint256); 46 | 47 | function getVRFSubId(address token) external view returns (uint64); 48 | 49 | function getTokenOwner(address token) external view returns (address); 50 | 51 | function getMinBetAmount(address token) external view returns (uint256); 52 | } -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # BetSwirl's Smart-Contracts 2 | 3 | ## Contracts 4 | 5 | | Name | Source | Documentation | Code flow | Audit | 6 | | ---------- | ---------------------------------------- | -------------------------- | ------------------------------- | ------------------------------------------------------------------------------------- | 7 | | BETS token | [source](./contracts/BetsToken.sol) | [doc](./docs/BetsToken.md) | [graph](./graphs/BetsToken.svg) | [RD Auditors](./audits/BetSwirl-Token_Smart_Contract_Security_Report_03.03.22.pdf) | 8 | | Bank v4 | [source](./contracts/bank/Bank.sol) | [doc](./docs/bank/Bank.md) | [graph](./graphs/Bank.svg) | [Quillhash](https://github.com/Quillhash/QuillAudit_Reports/blob/master/BetSwirlSmart%20Contract%20Audit%20Report%20-%20QuillAudits.pdf) | 9 | | Keno v1 | [source](./contracts/games/Keno.sol) | [doc](./docs/games/Keno.md) | [graph](./graphs/Keno.svg) | | 10 | | Dice v5 | [source](./contracts/games/Dice.sol) | [doc](./docs/games/Dice.md) | [graph](./graphs/Dice.svg) | [Quillhash](https://github.com/Quillhash/QuillAudit_Reports/blob/master/BetSwirlSmart%20Contract%20Audit%20Report%20-%20QuillAudits.pdf) | 11 | | CoinToss v5 | [source](./contracts/games/CoinToss.sol) | [doc](./docs/games/CoinToss.md) | [graph](./graphs/CoinToss.svg) | [Quillhash](https://github.com/Quillhash/QuillAudit_Reports/blob/master/BetSwirlSmart%20Contract%20Audit%20Report%20-%20QuillAudits.pdf) | 12 | | Roulette v3 | [source](./contracts/games/Roulette.sol) | [doc](./docs/games/Roulette.md) | [graph](./graphs/Roulette.svg) | [Quillhash](https://github.com/Quillhash/QuillAudit_Reports/blob/master/BetSwirlSmart%20Contract%20Audit%20Report%20-%20QuillAudits.pdf) | 13 | | Russian Roulette v1 | [source](./contracts/games/RussianRoulette.sol) | [doc](./docs/games/RussianRoulette.md) | [graph](./graphs/RussianRoulette.svg) | | 14 | | PvP Games Store v1 | [source](./contracts/games/PvPGamesStore.sol) | [doc](./docs/games/PvPGamesStore.md) | [graph](./graphs/PvPGamesStore.svg) | | 15 | 16 | ## Deployments 17 | 18 | [Listed on the documentation](https://documentation.betswirl.com/ecosystem/contracts) 19 | 20 | ## Build 21 | 22 | 1) `npm install` 23 | 24 | 2) `npm run compile` 25 | -------------------------------------------------------------------------------- /contracts/games/IPvPGamesStore.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | interface IPvPGamesStore { 6 | 7 | /// @notice Token's house edge allocations struct. 8 | /// The games house edge is split into several allocations. 9 | /// The allocated amounts stays in the controct until authorized parties withdraw. They are subtracted from the balance. 10 | /// @param dividend Rate to be allocated as staking rewards, on bet payout. 11 | /// @param treasury Rate to be allocated to the treasury, on bet payout. 12 | /// @param team Rate to be allocated to the team, on bet payout. 13 | /// @param dividendAmount The number of tokens to be sent as staking rewards. 14 | /// @param treasuryAmount The number of tokens to be sent to the treasury. 15 | /// @param teamAmount The number of tokens to be sent to the team. 16 | struct HouseEdgeSplit { 17 | uint16 dividend; 18 | uint16 treasury; 19 | uint16 team; 20 | uint16 initiator; 21 | } 22 | 23 | /// @notice Token struct. 24 | /// @param houseEdge House edge rate. 25 | /// @param pendingCount Number of pending bets. 26 | /// @param VRFFees Chainlink's VRF collected fees amount. 27 | struct Token { 28 | uint64 vrfSubId; 29 | HouseEdgeSplit houseEdgeSplit; 30 | } 31 | 32 | /// @notice Token's metadata struct. It contains additional information from the ERC20 token. 33 | /// @dev Only used on the `getTokens` getter for the front-end. 34 | /// @param decimals Number of token's decimals. 35 | /// @param tokenAddress Contract address of the token. 36 | /// @param name Name of the token. 37 | /// @param symbol Symbol of the token. 38 | /// @param token Token data. 39 | struct TokenMetadata { 40 | uint8 decimals; 41 | address tokenAddress; 42 | string name; 43 | string symbol; 44 | Token token; 45 | } 46 | 47 | function setHouseEdgeSplit( 48 | address token, 49 | uint16 dividend, 50 | uint16 treasury, 51 | uint16 team, 52 | uint16 initiator 53 | ) external; 54 | 55 | function addToken(address token) external; 56 | function setVRFSubId(address token, uint64 vrfSubId) external; 57 | function setTeamWallet(address teamWallet) external; 58 | function getTokenConfig(address token) external view returns (Token memory config); 59 | function getTreasuryAndTeamAddresses() external view returns (address, address); 60 | function getTokensAddresses() external view returns (address[] memory); 61 | } -------------------------------------------------------------------------------- /docs/games/IPvPGamesStore.md: -------------------------------------------------------------------------------- 1 | # IPvPGamesStore 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### addToken 14 | 15 | ```solidity 16 | function addToken(address token) external nonpayable 17 | ``` 18 | 19 | 20 | 21 | 22 | 23 | #### Parameters 24 | 25 | | Name | Type | Description | 26 | |---|---|---| 27 | | token | address | undefined | 28 | 29 | ### getTokenConfig 30 | 31 | ```solidity 32 | function getTokenConfig(address token) external view returns (struct IPvPGamesStore.Token config) 33 | ``` 34 | 35 | 36 | 37 | 38 | 39 | #### Parameters 40 | 41 | | Name | Type | Description | 42 | |---|---|---| 43 | | token | address | undefined | 44 | 45 | #### Returns 46 | 47 | | Name | Type | Description | 48 | |---|---|---| 49 | | config | IPvPGamesStore.Token | undefined | 50 | 51 | ### getTokensAddresses 52 | 53 | ```solidity 54 | function getTokensAddresses() external view returns (address[]) 55 | ``` 56 | 57 | 58 | 59 | 60 | 61 | 62 | #### Returns 63 | 64 | | Name | Type | Description | 65 | |---|---|---| 66 | | _0 | address[] | undefined | 67 | 68 | ### getTreasuryAndTeamAddresses 69 | 70 | ```solidity 71 | function getTreasuryAndTeamAddresses() external view returns (address, address) 72 | ``` 73 | 74 | 75 | 76 | 77 | 78 | 79 | #### Returns 80 | 81 | | Name | Type | Description | 82 | |---|---|---| 83 | | _0 | address | undefined | 84 | | _1 | address | undefined | 85 | 86 | ### setHouseEdgeSplit 87 | 88 | ```solidity 89 | function setHouseEdgeSplit(address token, uint16 dividend, uint16 treasury, uint16 team, uint16 initiator) external nonpayable 90 | ``` 91 | 92 | 93 | 94 | 95 | 96 | #### Parameters 97 | 98 | | Name | Type | Description | 99 | |---|---|---| 100 | | token | address | undefined | 101 | | dividend | uint16 | undefined | 102 | | treasury | uint16 | undefined | 103 | | team | uint16 | undefined | 104 | | initiator | uint16 | undefined | 105 | 106 | ### setTeamWallet 107 | 108 | ```solidity 109 | function setTeamWallet(address teamWallet) external nonpayable 110 | ``` 111 | 112 | 113 | 114 | 115 | 116 | #### Parameters 117 | 118 | | Name | Type | Description | 119 | |---|---|---| 120 | | teamWallet | address | undefined | 121 | 122 | ### setVRFSubId 123 | 124 | ```solidity 125 | function setVRFSubId(address token, uint64 vrfSubId) external nonpayable 126 | ``` 127 | 128 | 129 | 130 | 131 | 132 | #### Parameters 133 | 134 | | Name | Type | Description | 135 | |---|---|---| 136 | | token | address | undefined | 137 | | vrfSubId | uint64 | undefined | 138 | 139 | 140 | 141 | 142 | -------------------------------------------------------------------------------- /docs/bank/IBank.md: -------------------------------------------------------------------------------- 1 | # IBank 2 | 3 | *Romuald Hog.* 4 | 5 | 6 | 7 | Minimal interface for Bank. 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### cashIn 14 | 15 | ```solidity 16 | function cashIn(address tokenAddress, uint256 amount, uint256 fees) external payable 17 | ``` 18 | 19 | Accounts a loss bet. 20 | 21 | *In case of an ERC20, the bet amount should be transfered prior to this tx.In case of the gas token, the bet amount is sent along with this tx.* 22 | 23 | #### Parameters 24 | 25 | | Name | Type | Description | 26 | |---|---|---| 27 | | tokenAddress | address | Address of the token. | 28 | | amount | uint256 | Loss bet amount. | 29 | | fees | uint256 | Bet amount and bet profit fees amount. | 30 | 31 | ### getMaxBetAmount 32 | 33 | ```solidity 34 | function getMaxBetAmount(address token, uint256 multiplier) external view returns (uint256) 35 | ``` 36 | 37 | Calculates the max bet amount based on the token balance, the balance risk, and the game multiplier. 38 | 39 | *The multiplier should be at least 10000.* 40 | 41 | #### Parameters 42 | 43 | | Name | Type | Description | 44 | |---|---|---| 45 | | token | address | Address of the token. | 46 | | multiplier | uint256 | The bet amount leverage determines the user's profit amount. 10000 = 100% = no profit. | 47 | 48 | #### Returns 49 | 50 | | Name | Type | Description | 51 | |---|---|---| 52 | | _0 | uint256 | Maximum bet amount for the token. | 53 | 54 | ### getMinBetAmount 55 | 56 | ```solidity 57 | function getMinBetAmount(address token) external view returns (uint256) 58 | ``` 59 | 60 | 61 | 62 | 63 | 64 | #### Parameters 65 | 66 | | Name | Type | Description | 67 | |---|---|---| 68 | | token | address | undefined | 69 | 70 | #### Returns 71 | 72 | | Name | Type | Description | 73 | |---|---|---| 74 | | _0 | uint256 | undefined | 75 | 76 | ### getTokenOwner 77 | 78 | ```solidity 79 | function getTokenOwner(address token) external view returns (address) 80 | ``` 81 | 82 | 83 | 84 | 85 | 86 | #### Parameters 87 | 88 | | Name | Type | Description | 89 | |---|---|---| 90 | | token | address | undefined | 91 | 92 | #### Returns 93 | 94 | | Name | Type | Description | 95 | |---|---|---| 96 | | _0 | address | undefined | 97 | 98 | ### getVRFSubId 99 | 100 | ```solidity 101 | function getVRFSubId(address token) external view returns (uint64) 102 | ``` 103 | 104 | 105 | 106 | 107 | 108 | #### Parameters 109 | 110 | | Name | Type | Description | 111 | |---|---|---| 112 | | token | address | undefined | 113 | 114 | #### Returns 115 | 116 | | Name | Type | Description | 117 | |---|---|---| 118 | | _0 | uint64 | undefined | 119 | 120 | ### isAllowedToken 121 | 122 | ```solidity 123 | function isAllowedToken(address token) external view returns (bool) 124 | ``` 125 | 126 | Gets the token's allow status used on the games smart contracts. 127 | 128 | 129 | 130 | #### Parameters 131 | 132 | | Name | Type | Description | 133 | |---|---|---| 134 | | token | address | Address of the token. | 135 | 136 | #### Returns 137 | 138 | | Name | Type | Description | 139 | |---|---|---| 140 | | _0 | bool | Whether the token is enabled for bets. | 141 | 142 | ### payout 143 | 144 | ```solidity 145 | function payout(address user, address token, uint256 profit, uint256 fees) external payable 146 | ``` 147 | 148 | Payouts a winning bet, and allocate the house edge fee. 149 | 150 | 151 | 152 | #### Parameters 153 | 154 | | Name | Type | Description | 155 | |---|---|---| 156 | | user | address | Address of the gamer. | 157 | | token | address | Address of the token. | 158 | | profit | uint256 | Number of tokens to be sent to the gamer. | 159 | | fees | uint256 | Bet amount and bet profit fees amount. | 160 | 161 | 162 | 163 | 164 | -------------------------------------------------------------------------------- /graphs/BetsToken.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | BetsToken 10 | 11 | 12 | 13 | 14 | Legend 15 | 16 | 17 | 18 | 19 | 20 | <Constructor> 21 | 22 | 23 | 24 | 25 | 26 | _mint 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | getOwner 39 | 40 | 41 | 42 | 43 | 44 | owner 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | Internal Call 57 | External Call 58 | Defined Contract 59 | Undefined Contract 60 | 61 | 62 | 63 | 64 | 65 |     66 |     67 | 68 |     69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | -------------------------------------------------------------------------------- /contracts/games/CoinToss.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | import {Game} from "./Game.sol"; 6 | 7 | /// @title BetSwirl's Coin Toss game 8 | /// @notice The game is played with a two-sided coin. The game's goal is to guess whether the lucky coin face will be Heads or Tails. 9 | /// @author Romuald Hog (based on Yakitori's Coin Toss) 10 | contract CoinToss is Game { 11 | /// @notice Full coin toss bet information struct. 12 | /// @param bet The Bet struct information. 13 | /// @param diceBet The Coin Toss bet struct information. 14 | /// @dev Used to package bet information for the front-end. 15 | struct FullCoinTossBet { 16 | Bet bet; 17 | CoinTossBet coinTossBet; 18 | } 19 | 20 | /// @notice Coin Toss bet information struct. 21 | /// @param face The chosen coin face. 22 | /// @param rolled The rolled coin face. 23 | struct CoinTossBet { 24 | bool face; 25 | bool rolled; 26 | } 27 | 28 | /// @notice Maps bets IDs to chosen and rolled coin faces. 29 | /// @dev Coin faces: true = Tails, false = Heads. 30 | mapping(uint256 => CoinTossBet) public coinTossBets; 31 | 32 | /// @notice Emitted after a bet is placed. 33 | /// @param id The bet ID. 34 | /// @param user Address of the gamer. 35 | /// @param token Address of the token. 36 | /// @param amount The bet amount. 37 | /// @param vrfCost The Chainlink VRF cost paid by player. 38 | /// @param face The chosen coin face. 39 | event PlaceBet( 40 | uint256 id, 41 | address indexed user, 42 | address indexed token, 43 | uint256 amount, 44 | uint256 vrfCost, 45 | bool face 46 | ); 47 | 48 | /// @notice Emitted after a bet is rolled. 49 | /// @param id The bet ID. 50 | /// @param user Address of the gamer. 51 | /// @param token Address of the token. 52 | /// @param amount The bet amount. 53 | /// @param face The chosen coin face. 54 | /// @param rolled The rolled coin face. 55 | /// @param payout The payout amount. 56 | event Roll( 57 | uint256 id, 58 | address indexed user, 59 | address indexed token, 60 | uint256 amount, 61 | bool face, 62 | bool rolled, 63 | uint256 payout 64 | ); 65 | 66 | /// @notice Initialize the game base contract. 67 | /// @param bankAddress The address of the bank. 68 | /// @param chainlinkCoordinatorAddress Address of the Chainlink VRF Coordinator. 69 | /// @param LINK_ETH_feedAddress Address of the Chainlink LINK/ETH price feed. 70 | constructor( 71 | address bankAddress, 72 | address chainlinkCoordinatorAddress, 73 | address LINK_ETH_feedAddress 74 | ) Game(bankAddress, chainlinkCoordinatorAddress, 1, LINK_ETH_feedAddress) {} 75 | 76 | /// @notice Calculates the target payout amount. 77 | /// @param betAmount Bet amount. 78 | /// @return The target payout amount. 79 | function _getPayout(uint256 betAmount) private pure returns (uint256) { 80 | return betAmount * 2; 81 | } 82 | 83 | /// @notice Creates a new bet and stores the chosen coin face. 84 | /// @param face The chosen coin face. 85 | /// @param token Address of the token. 86 | /// @param tokenAmount The number of tokens bet. 87 | function wager( 88 | bool face, 89 | address token, 90 | uint256 tokenAmount 91 | ) external payable whenNotPaused { 92 | Bet memory bet = _newBet(token, tokenAmount, _getPayout(10000)); 93 | 94 | coinTossBets[bet.id].face = face; 95 | 96 | emit PlaceBet( 97 | bet.id, 98 | bet.user, 99 | bet.token, 100 | bet.amount, 101 | bet.vrfCost, 102 | face 103 | ); 104 | } 105 | 106 | /// @notice Resolves the bet using the Chainlink randomness. 107 | /// @param id The bet ID. 108 | /// @param randomWords Random words list. Contains only one for this game. 109 | // solhint-disable-next-line private-vars-leading-underscore 110 | function fulfillRandomWords(uint256 id, uint256[] memory randomWords) 111 | internal 112 | override 113 | { 114 | uint256 startGas = gasleft(); 115 | 116 | CoinTossBet storage coinTossBet = coinTossBets[id]; 117 | Bet storage bet = bets[id]; 118 | 119 | uint256 rolled = randomWords[0] % 2; 120 | 121 | bool[2] memory coinSides = [false, true]; 122 | bool rolledCoinSide = coinSides[rolled]; 123 | coinTossBet.rolled = rolledCoinSide; 124 | uint256 payout = _resolveBet( 125 | bet, 126 | rolledCoinSide == coinTossBet.face ? 127 | _getPayout(bet.amount) : 0 128 | ); 129 | 130 | emit Roll( 131 | bet.id, 132 | bet.user, 133 | bet.token, 134 | bet.amount, 135 | coinTossBet.face, 136 | rolledCoinSide, 137 | payout 138 | ); 139 | 140 | _accountVRFCost(bet, startGas); 141 | } 142 | 143 | /// @notice Gets the list of the last user bets. 144 | /// @param user Address of the gamer. 145 | /// @param dataLength The amount of bets to return. 146 | /// @return A list of Coin Toss bet. 147 | function getLastUserBets(address user, uint256 dataLength) 148 | external 149 | view 150 | returns (FullCoinTossBet[] memory) 151 | { 152 | Bet[] memory lastBets = _getLastUserBets(user, dataLength); 153 | FullCoinTossBet[] memory lastCoinTossBets = new FullCoinTossBet[]( 154 | lastBets.length 155 | ); 156 | for (uint256 i; i < lastBets.length; i++) { 157 | lastCoinTossBets[i] = FullCoinTossBet( 158 | lastBets[i], 159 | coinTossBets[lastBets[i].id] 160 | ); 161 | } 162 | return lastCoinTossBets; 163 | } 164 | } -------------------------------------------------------------------------------- /contracts/games/Dice.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | import {Game} from "./Game.sol"; 6 | 7 | /// @title BetSwirl's Dice game 8 | /// @notice The game is played with a 100 sided dice. The game's goal is to guess whether the lucky number will be above your chosen number. 9 | /// @author Romuald Hog (based on Yakitori's Dice) 10 | contract Dice is Game { 11 | /// @notice Full dice bet information struct. 12 | /// @param bet The Bet struct information. 13 | /// @param diceBet The Dice bet struct information. 14 | /// @dev Used to package bet information for the front-end. 15 | struct FullDiceBet { 16 | Bet bet; 17 | DiceBet diceBet; 18 | } 19 | 20 | /// @notice Dice bet information struct. 21 | /// @param cap The chosen dice number. 22 | /// @param rolled The rolled dice number. 23 | struct DiceBet { 24 | uint8 cap; 25 | uint8 rolled; 26 | } 27 | 28 | /// @notice Maps bets IDs to chosen and rolled dice numbers. 29 | mapping(uint256 => DiceBet) public diceBets; 30 | 31 | /// @notice Emitted after a bet is placed. 32 | /// @param id The bet ID. 33 | /// @param user Address of the gamer. 34 | /// @param token Address of the token. 35 | /// @param amount The bet amount. 36 | /// @param vrfCost The Chainlink VRF cost paid by player. 37 | /// @param cap The chosen dice number. 38 | event PlaceBet( 39 | uint256 id, 40 | address indexed user, 41 | address indexed token, 42 | uint256 amount, 43 | uint256 vrfCost, 44 | uint8 cap 45 | ); 46 | 47 | /// @notice Emitted after a bet is rolled. 48 | /// @param id The bet ID. 49 | /// @param user Address of the gamer. 50 | /// @param token Address of the token. 51 | /// @param amount The bet amount. 52 | /// @param cap The chosen dice number. 53 | /// @param rolled The rolled dice number. 54 | /// @param payout The payout amount. 55 | event Roll( 56 | uint256 id, 57 | address indexed user, 58 | address indexed token, 59 | uint256 amount, 60 | uint8 cap, 61 | uint8 rolled, 62 | uint256 payout 63 | ); 64 | 65 | /// @notice Provided cap is not within 1 and 99 included. 66 | /// @param minCap The minimum cap. 67 | /// @param maxCap The maximum cap. 68 | error CapNotInRange(uint8 minCap, uint8 maxCap); 69 | 70 | /// @notice Initialize the game base contract. 71 | /// @param bankAddress The address of the bank. 72 | /// @param chainlinkCoordinatorAddress Address of the Chainlink VRF Coordinator. 73 | /// @param LINK_ETH_feedAddress Address of the Chainlink LINK/ETH price feed. 74 | constructor( 75 | address bankAddress, 76 | address chainlinkCoordinatorAddress, 77 | address LINK_ETH_feedAddress 78 | ) Game(bankAddress, chainlinkCoordinatorAddress, 1, LINK_ETH_feedAddress) {} 79 | 80 | /// @notice Calculates the target payout amount. 81 | /// @param betAmount Bet amount. 82 | /// @param cap The chosen dice number. 83 | /// @return The target payout amount. 84 | function _getPayout(uint256 betAmount, uint8 cap) 85 | private 86 | pure 87 | returns (uint256) 88 | { 89 | return (betAmount * 100) / (100 - cap); 90 | } 91 | 92 | /// @notice Creates a new bet and stores the chosen dice number. 93 | /// @param cap The chosen dice number. 94 | /// @param token Address of the token. 95 | /// @param tokenAmount The number of tokens bet. 96 | function wager( 97 | uint8 cap, 98 | address token, 99 | uint256 tokenAmount 100 | ) external payable whenNotPaused { 101 | /// Dice cap 1 gives 99% chance. 102 | /// Dice cap 99 gives 1% chance. 103 | if (cap == 0 || cap > 99) { 104 | revert CapNotInRange(1, 99); 105 | } 106 | 107 | Bet memory bet = _newBet(token, tokenAmount, _getPayout(10000, cap)); 108 | diceBets[bet.id].cap = cap; 109 | 110 | emit PlaceBet( 111 | bet.id, 112 | bet.user, 113 | bet.token, 114 | bet.amount, 115 | bet.vrfCost, 116 | cap 117 | ); 118 | } 119 | 120 | /// @notice Resolves the bet using the Chainlink randomness. 121 | /// @param id The bet ID. 122 | /// @param randomWords Random words list. Contains only one for this game. 123 | // solhint-disable-next-line private-vars-leading-underscore 124 | function fulfillRandomWords(uint256 id, uint256[] memory randomWords) 125 | internal 126 | override 127 | { 128 | uint256 startGas = gasleft(); 129 | 130 | DiceBet storage diceBet = diceBets[id]; 131 | Bet storage bet = bets[id]; 132 | 133 | uint8 rolled = uint8((randomWords[0] % 100) + 1); 134 | diceBet.rolled = rolled; 135 | uint256 payout = _resolveBet( 136 | bet, 137 | rolled > diceBet.cap ? 138 | _getPayout(bet.amount, diceBet.cap) : 0 139 | ); 140 | 141 | emit Roll( 142 | bet.id, 143 | bet.user, 144 | bet.token, 145 | bet.amount, 146 | diceBet.cap, 147 | rolled, 148 | payout 149 | ); 150 | 151 | _accountVRFCost(bet, startGas); 152 | } 153 | 154 | /// @notice Gets the list of the last user bets. 155 | /// @param user Address of the gamer. 156 | /// @param dataLength The amount of bets to return. 157 | /// @return A list of Dice bet. 158 | function getLastUserBets(address user, uint256 dataLength) 159 | external 160 | view 161 | returns (FullDiceBet[] memory) 162 | { 163 | Bet[] memory lastBets = _getLastUserBets(user, dataLength); 164 | FullDiceBet[] memory lastDiceBets = new FullDiceBet[](lastBets.length); 165 | for (uint256 i; i < lastBets.length; i++) { 166 | lastDiceBets[i] = FullDiceBet( 167 | lastBets[i], 168 | diceBets[lastBets[i].id] 169 | ); 170 | } 171 | return lastDiceBets; 172 | } 173 | } -------------------------------------------------------------------------------- /contracts/games/Roulette.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | import {Game} from "./Game.sol"; 6 | 7 | /// @title BetSwirl's Roulette game 8 | /// @notice 9 | /// @author Romuald Hog 10 | contract Roulette is Game { 11 | /// @notice Full roulette bet information struct. 12 | /// @param bet The Bet struct information. 13 | /// @param rouletteBet The Roulette bet struct information. 14 | /// @dev Used to package bet information for the front-end. 15 | struct FullRouletteBet { 16 | Bet bet; 17 | RouletteBet rouletteBet; 18 | } 19 | 20 | /// @notice Roulette bet information struct. 21 | /// @param bet The Bet struct information. 22 | /// @param numbers The chosen numbers. 23 | struct RouletteBet { 24 | uint40 numbers; 25 | uint8 rolled; 26 | } 27 | 28 | uint8 private constant MODULO = 37; 29 | uint256 private constant POPCNT_MULT = 30 | 0x0000000000002000000000100000000008000000000400000000020000000001; 31 | uint256 private constant POPCNT_MASK = 32 | 0x0001041041041041041041041041041041041041041041041041041041041041; 33 | uint256 private constant POPCNT_MODULO = 0x3F; 34 | 35 | /// @notice Maps bets IDs to chosen numbers. 36 | mapping(uint256 => RouletteBet) public rouletteBets; 37 | 38 | /// @notice Emitted after a bet is placed. 39 | /// @param id The bet ID. 40 | /// @param user Address of the gamer. 41 | /// @param token Address of the token. 42 | /// @param amount The bet amount. 43 | /// @param vrfCost The Chainlink VRF cost paid by player. 44 | /// @param numbers The chosen numbers. 45 | event PlaceBet( 46 | uint256 id, 47 | address indexed user, 48 | address indexed token, 49 | uint256 amount, 50 | uint256 vrfCost, 51 | uint40 numbers 52 | ); 53 | 54 | /// @notice Emitted after a bet is rolled. 55 | /// @param id The bet ID. 56 | /// @param user Address of the gamer. 57 | /// @param token Address of the token. 58 | /// @param amount The bet amount. 59 | /// @param numbers The chosen numbers. 60 | /// @param rolled The rolled number. 61 | /// @param payout The payout amount. 62 | event Roll( 63 | uint256 id, 64 | address indexed user, 65 | address indexed token, 66 | uint256 amount, 67 | uint40 numbers, 68 | uint8 rolled, 69 | uint256 payout 70 | ); 71 | 72 | /// @notice Provided cap is under the minimum. 73 | error NumbersNotInRange(); 74 | 75 | /// @notice Initialize the game base contract. 76 | /// @param bankAddress The address of the bank. 77 | /// @param chainlinkCoordinatorAddress Address of the Chainlink VRF Coordinator. 78 | /// @param LINK_ETH_feedAddress Address of the Chainlink LINK/ETH price feed. 79 | constructor( 80 | address bankAddress, 81 | address chainlinkCoordinatorAddress, 82 | address LINK_ETH_feedAddress 83 | ) Game(bankAddress, chainlinkCoordinatorAddress, 1, LINK_ETH_feedAddress) {} 84 | 85 | /// @notice Calculates the target payout amount. 86 | /// @param betAmount Bet amount. 87 | /// @param numbers The chosen numbers. 88 | /// @return The target payout amount. 89 | function _getPayout(uint256 betAmount, uint40 numbers) 90 | private 91 | pure 92 | returns (uint256) 93 | { 94 | return 95 | (betAmount * MODULO) / 96 | (((numbers * POPCNT_MULT) & POPCNT_MASK) % POPCNT_MODULO); 97 | } 98 | 99 | /// @notice Creates a new bet and stores the chosen bet mask. 100 | /// @param numbers The chosen numbers. 101 | /// @param token Address of the token. 102 | /// @param tokenAmount The number of tokens bet. 103 | function wager( 104 | uint40 numbers, 105 | address token, 106 | uint256 tokenAmount 107 | ) external payable whenNotPaused { 108 | if (numbers == 0 || numbers >= 2**MODULO - 1) { 109 | revert NumbersNotInRange(); 110 | } 111 | 112 | Bet memory bet = _newBet( 113 | token, 114 | tokenAmount, 115 | _getPayout(10000, numbers) 116 | ); 117 | 118 | rouletteBets[bet.id].numbers = numbers; 119 | 120 | emit PlaceBet( 121 | bet.id, 122 | bet.user, 123 | bet.token, 124 | bet.amount, 125 | bet.vrfCost, 126 | numbers 127 | ); 128 | } 129 | 130 | /// @notice Resolves the bet using the Chainlink randomness. 131 | /// @param id The bet ID. 132 | /// @param randomWords Random words list. Contains only one for this game. 133 | // solhint-disable-next-line private-vars-leading-underscore 134 | function fulfillRandomWords(uint256 id, uint256[] memory randomWords) 135 | internal 136 | override 137 | { 138 | uint256 startGas = gasleft(); 139 | 140 | RouletteBet storage rouletteBet = rouletteBets[id]; 141 | Bet storage bet = bets[id]; 142 | 143 | uint8 rolled = uint8(randomWords[0] % MODULO); 144 | rouletteBet.rolled = rolled; 145 | uint256 payout = _resolveBet( 146 | bet, 147 | (2**rolled) & rouletteBet.numbers != 0 ? 148 | _getPayout(bet.amount, rouletteBet.numbers) : 0 149 | ); 150 | 151 | emit Roll( 152 | bet.id, 153 | bet.user, 154 | bet.token, 155 | bet.amount, 156 | rouletteBet.numbers, 157 | rolled, 158 | payout 159 | ); 160 | 161 | _accountVRFCost(bet, startGas); 162 | } 163 | 164 | /// @notice Gets the list of the last user bets. 165 | /// @param user Address of the gamer. 166 | /// @param dataLength The amount of bets to return. 167 | /// @return A list of Roulette bet. 168 | function getLastUserBets(address user, uint256 dataLength) 169 | external 170 | view 171 | returns (FullRouletteBet[] memory) 172 | { 173 | Bet[] memory lastBets = _getLastUserBets(user, dataLength); 174 | FullRouletteBet[] memory lastRouletteBets = new FullRouletteBet[]( 175 | lastBets.length 176 | ); 177 | for (uint256 i; i < lastBets.length; i++) { 178 | lastRouletteBets[i] = FullRouletteBet( 179 | lastBets[i], 180 | rouletteBets[lastBets[i].id] 181 | ); 182 | } 183 | return lastRouletteBets; 184 | } 185 | } -------------------------------------------------------------------------------- /contracts/games/PvPGamesStore.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | import {Ownable} from "@openzeppelin/contracts/access/Ownable.sol"; 5 | import {IERC20Metadata} from "@openzeppelin/contracts/token/ERC20/extensions/IERC20Metadata.sol"; 6 | import {IPvPGamesStore} from "./IPvPGamesStore.sol"; 7 | 8 | contract PvPGamesStore is Ownable, IPvPGamesStore { 9 | 10 | /// @notice Maps tokens addresses to token configuration. 11 | mapping(address => Token) public tokens; 12 | 13 | /// @notice Number of tokens added. 14 | uint256 private _tokensCount; 15 | 16 | /// @notice Maps tokens indexes to token address. 17 | mapping(uint256 => address) private _tokensList; 18 | 19 | address public immutable treasuryWallet; 20 | address public teamWallet; 21 | event SetTeamWallet(address teamWallet); 22 | 23 | /// @notice Emitted after the Chainlink callback subId is set for a token. 24 | /// @param token Address of the token. 25 | /// @param vrfSubId New vrfSubId. 26 | event SetVRFSubId( 27 | address indexed token, 28 | uint64 vrfSubId 29 | ); 30 | 31 | /// @notice Emitted after the token's house edge allocations for bet payout is set. 32 | /// @param token Address of the token. 33 | /// @param dividend Rate to be allocated as staking rewards, on bet payout. 34 | /// @param treasury Rate to be allocated to the treasury, on bet payout. 35 | /// @param team Rate to be allocated to the team, on bet payout. 36 | event SetTokenHouseEdgeSplit( 37 | address indexed token, 38 | uint16 dividend, 39 | uint16 treasury, 40 | uint16 team, 41 | uint16 initiator 42 | ); 43 | 44 | /// @notice Emitted after a token is added. 45 | /// @param token Address of the token. 46 | event AddToken(address token); 47 | 48 | /// @notice Emitted after a token is paused. 49 | /// @param token Address of the token. 50 | /// @param paused Whether the token is paused for betting. 51 | event SetPausedToken(address indexed token, bool paused); 52 | 53 | /// @notice Reverting error when trying to add an existing token. 54 | error TokenExists(); 55 | 56 | /// @notice Reverting error when setting the house edge allocations, but the sum isn't 100%. 57 | /// @param sum of the house edge allocations rates. 58 | error WrongHouseEdgeSplit(uint256 sum); 59 | 60 | /// @notice Reverting error when provided address isn't valid. 61 | error InvalidAddress(); 62 | 63 | /// @param treasuryWalletAddress Treasury multi-sig wallet. 64 | /// @param teamWalletAddress Team wallet. 65 | constructor (address treasuryWalletAddress, 66 | address teamWalletAddress 67 | ) { 68 | if ( 69 | treasuryWalletAddress == address(0) 70 | ) { 71 | revert InvalidAddress(); 72 | } 73 | treasuryWallet = treasuryWalletAddress; 74 | setTeamWallet(teamWalletAddress); 75 | } 76 | 77 | /// @notice Sets the token's house edge allocations for bet payout. 78 | /// @param token Address of the token. 79 | /// @param dividend Rate to be allocated as staking rewards, on bet payout. 80 | /// @param treasury Rate to be allocated to the treasuryWallet, on bet payout. 81 | /// @param team Rate to be allocated to the team, on bet payout. 82 | /// @param initiator Rate to be allocated to the initiator of the bet, on bet payout. 83 | /// @dev `dividend`, `_treasuryWallet` and `team` rates sum must equals 10000. 84 | function setHouseEdgeSplit( 85 | address token, 86 | uint16 dividend, 87 | uint16 treasury, 88 | uint16 team, 89 | uint16 initiator 90 | ) external onlyOwner { 91 | uint16 splitSum = dividend + team + treasury + initiator; 92 | if (splitSum != 10000) { 93 | revert WrongHouseEdgeSplit(splitSum); 94 | } 95 | 96 | HouseEdgeSplit storage tokenHouseEdge = tokens[token].houseEdgeSplit; 97 | tokenHouseEdge.dividend = dividend; 98 | tokenHouseEdge.treasury = treasury; 99 | tokenHouseEdge.team = team; 100 | tokenHouseEdge.initiator = initiator; 101 | 102 | emit SetTokenHouseEdgeSplit( 103 | token, 104 | dividend, 105 | treasury, 106 | team, 107 | initiator 108 | ); 109 | } 110 | 111 | /// @notice Adds a new token that'll be enabled for the games' betting. 112 | /// Token shouldn't exist yet. 113 | /// @param token Address of the token. 114 | function addToken(address token) external onlyOwner { 115 | if (_tokensCount != 0) { 116 | for (uint8 i; i < _tokensCount; i++) { 117 | if (_tokensList[i] == token) { 118 | revert TokenExists(); 119 | } 120 | } 121 | } 122 | _tokensList[_tokensCount] = token; 123 | _tokensCount += 1; 124 | emit AddToken(token); 125 | } 126 | 127 | /// @notice Sets the Chainlink VRF subId. 128 | /// @param vrfSubId New subId. 129 | function setVRFSubId(address token, uint64 vrfSubId) 130 | public 131 | onlyOwner 132 | { 133 | tokens[token].vrfSubId = vrfSubId; 134 | emit SetVRFSubId(token, vrfSubId); 135 | } 136 | 137 | /// @notice Sets the new team wallet. 138 | /// @param _teamWallet The team wallet address. 139 | function setTeamWallet(address _teamWallet) 140 | public 141 | onlyOwner() 142 | { 143 | if (_teamWallet == address(0)) { 144 | revert InvalidAddress(); 145 | } 146 | teamWallet = _teamWallet; 147 | emit SetTeamWallet(teamWallet); 148 | } 149 | 150 | /// @dev For the front-end 151 | function getTokens() external view returns (TokenMetadata[] memory) { 152 | TokenMetadata[] memory _tokens = new TokenMetadata[](_tokensCount); 153 | for (uint8 i; i < _tokensCount; i++) { 154 | address tokenAddress = _tokensList[i]; 155 | Token memory token = tokens[tokenAddress]; 156 | if (tokenAddress == address(0)) { 157 | _tokens[i] = TokenMetadata({ 158 | decimals: 18, 159 | tokenAddress: tokenAddress, 160 | name: "ETH", 161 | symbol: "ETH", 162 | token: token 163 | }); 164 | } else { 165 | IERC20Metadata erc20Metadata = IERC20Metadata(tokenAddress); 166 | _tokens[i] = TokenMetadata({ 167 | decimals: erc20Metadata.decimals(), 168 | tokenAddress: tokenAddress, 169 | name: erc20Metadata.name(), 170 | symbol: erc20Metadata.symbol(), 171 | token: token 172 | }); 173 | } 174 | } 175 | return _tokens; 176 | } 177 | 178 | function getTokensAddresses() external view returns (address[] memory) { 179 | address[] memory _tokens = new address[](_tokensCount); 180 | for (uint8 i; i < _tokensCount; i++) { 181 | _tokens[i] = _tokensList[i]; 182 | } 183 | return _tokens; 184 | } 185 | 186 | function getTokenConfig(address token) public view returns (Token memory config) { 187 | config = tokens[token]; 188 | } 189 | 190 | function getTreasuryAndTeamAddresses() public view returns (address, address) { 191 | return (treasuryWallet, teamWallet); 192 | } 193 | } -------------------------------------------------------------------------------- /contracts/games/RussianRoulette.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | import {PvPGame} from "./PvPGame.sol"; 6 | import {IERC20, SafeERC20} from "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol"; 7 | 8 | // import "hardhat/console.sol"; 9 | contract RussianRoulette is PvPGame { 10 | /// @notice Stores the Russian Roulette params 11 | struct RussianRouletteBet { 12 | uint16 maxSeats; 13 | uint32 startsAt; 14 | uint8 deathRatio; 15 | uint256 randomWord; 16 | } 17 | 18 | /// @notice Maps bets id with Russian Roulette data 19 | mapping(uint24 => RussianRouletteBet) private russianRouletteBets; 20 | 21 | /// @notice Maximum number of seats per game. 22 | uint16 public maxSeats; 23 | 24 | /// @notice Emitted after the max seats is set. 25 | event SetMaxSeats(uint16 maxSeats); 26 | 27 | // / @notice Emitted after a bet is placed. 28 | // / @param id The bet ID. 29 | // / @param player Address of the gamer. 30 | // / @param opponents Address of the opponents. 31 | // / @param token Address of the token. 32 | // / @param amount The bet amount. 33 | // / @param maxSeats Maximum of seats allowed. 34 | // / @param startsAt When the game can start even if not all seats has been filled. 35 | // / @param deathRatio Percentage of seats to kill. 36 | // / @param pot The prize pool. 37 | event PlaceBet( 38 | uint24 id, 39 | address indexed player, 40 | address[] opponents, 41 | address indexed token, 42 | uint256 amount, 43 | uint16 maxSeats, 44 | uint32 startsAt, 45 | uint8 deathRatio, 46 | uint256 pot 47 | ); 48 | 49 | /// @notice Emitted after a bet is rolled. 50 | /// @param id The bet ID. 51 | /// @param seats Players addresses of seats. 52 | /// @param winners who won. 53 | /// @param killedSeats the bets won. 54 | /// @param token The token used. 55 | /// @param betAmount The bet amount. 56 | /// @param payout The payout amount. 57 | event Roll( 58 | uint24 indexed id, 59 | address[] seats, 60 | address[] winners, 61 | address[] killedSeats, 62 | address indexed token, 63 | uint256 betAmount, 64 | uint256 payout 65 | ); 66 | 67 | /// @notice Emitted when chainlink's resolution appens 68 | /// @param id The bet ID. 69 | /// @param killedSeatsNumber Killed seats. 70 | event GameResolved(uint24 indexed id, uint256 killedSeatsNumber); 71 | 72 | error InvalidDeathRatio(); 73 | error InvalidDate(); 74 | 75 | constructor( 76 | address chainlinkCoordinatorAddress, 77 | address pvpGamesStoreAddress 78 | ) PvPGame(chainlinkCoordinatorAddress, pvpGamesStoreAddress) {} 79 | 80 | function setMaxSeats(uint16 _maxSeats) external onlyOwner { 81 | maxSeats = _maxSeats; 82 | emit SetMaxSeats(_maxSeats); 83 | } 84 | 85 | /// @notice Creates a new bet and stores the chosen coin face. 86 | /// @param token Address of the token. 87 | /// @param tokenAmount The number of tokens bet. 88 | /// @param opponents Selected players to play with. 89 | /// @param _maxSeats Maximum number of seats. The game will start when its reached. 90 | /// @param startsAt Timestamp when the game can start. 91 | /// @param deathRatio Players kill rate. 92 | function wager( 93 | address token, 94 | uint256 tokenAmount, 95 | address[] calldata opponents, 96 | uint16 _maxSeats, 97 | uint32 startsAt, 98 | uint8 deathRatio, 99 | bytes calldata nfts 100 | ) external payable whenNotPaused { 101 | if (_maxSeats < 2 || _maxSeats > maxSeats) revert WrongSeatsNumber(); 102 | if (deathRatio == 0 || deathRatio > 99) revert InvalidDeathRatio(); 103 | if (startsAt < block.timestamp) revert InvalidDate(); 104 | 105 | Bet memory bet = _newBet(token, tokenAmount, opponents, nfts); 106 | russianRouletteBets[bet.id].maxSeats = _maxSeats; 107 | russianRouletteBets[bet.id].startsAt = startsAt; 108 | russianRouletteBets[bet.id].deathRatio = deathRatio; 109 | 110 | emit PlaceBet( 111 | bet.id, 112 | msg.sender, 113 | opponents, 114 | token, 115 | bet.amount, 116 | _maxSeats, 117 | startsAt, 118 | deathRatio, 119 | bet.pot 120 | ); 121 | } 122 | 123 | function joinGame(uint24 id, uint16 seatsNumber) external payable { 124 | _joinGame(id, seatsNumber); 125 | } 126 | 127 | /// @notice Fullfills the chainlink request 128 | /// @param requestId id of the bet 129 | /// @param randomWords result 130 | function fulfillRandomWords( 131 | uint256 requestId, 132 | uint256[] memory randomWords 133 | ) internal override { 134 | uint24 id = _betsByVrfRequestId[requestId]; 135 | Bet storage bet = bets[id]; 136 | 137 | // Check the bet state in case it has been refunded or canceled 138 | if (bet.resolved) { 139 | revert NotPendingBet(); 140 | } 141 | 142 | uint256 killedSeatsNumber = (bet.seats.length * 143 | russianRouletteBets[bet.id].deathRatio) / 100; 144 | if (killedSeatsNumber == 0) killedSeatsNumber = 1; 145 | 146 | russianRouletteBets[bet.id].randomWord = randomWords[0]; 147 | 148 | emit GameResolved(id, killedSeatsNumber); 149 | } 150 | 151 | /// @notice Pull the triggers killing seats. 152 | /// @param id id of the bet 153 | function pullTriggers(uint24 id) external { 154 | // Check if random result has arrived 155 | uint256 randomWord = russianRouletteBets[id].randomWord; 156 | if (randomWord == 0) revert NotPendingBet(); 157 | 158 | Bet storage bet = bets[id]; 159 | uint256 seatsLength = bet.seats.length; 160 | uint256 killedSeatsNumber = (seatsLength * 161 | russianRouletteBets[bet.id].deathRatio) / 100; 162 | if (killedSeatsNumber == 0) killedSeatsNumber = 1; 163 | 164 | // Copy the list of players' seats 165 | address[] memory killedSeats = new address[](killedSeatsNumber); 166 | address[] memory winners = bet.seats; 167 | 168 | // Kill the seats 169 | for (uint i = 0; i < killedSeatsNumber; i++) { 170 | // Pickup a new random index 171 | uint256 deadIndex = uint256(keccak256(abi.encode(randomWord, i))) % 172 | (seatsLength - i); 173 | killedSeats[i] = winners[deadIndex]; 174 | winners[deadIndex] = winners[seatsLength - i - 1]; 175 | delete winners[seatsLength - i - 1]; 176 | } 177 | 178 | uint256 remainingSeats = seatsLength - killedSeatsNumber; 179 | assembly { 180 | mstore(winners, remainingSeats) 181 | } 182 | 183 | uint256 payOut = _resolveBet(bet, winners, randomWord); 184 | 185 | emit Roll( 186 | id, 187 | bet.seats, 188 | winners, 189 | killedSeats, 190 | bet.token, 191 | bet.amount, 192 | payOut 193 | ); 194 | } 195 | 196 | function betMaxSeats(uint24 id) public view override returns (uint256) { 197 | return russianRouletteBets[id].maxSeats; 198 | } 199 | 200 | function betMinSeats(uint24) public pure override returns (uint256) { 201 | return 2; 202 | } 203 | 204 | function gameCanStart(uint24 id) public view override returns (bool) { 205 | return russianRouletteBets[id].startsAt <= block.timestamp; 206 | } 207 | 208 | function getRussianRouletteBet( 209 | uint24 id 210 | ) 211 | external 212 | view 213 | returns (RussianRouletteBet memory russianRouletteBet, Bet memory bet) 214 | { 215 | return (russianRouletteBets[id], bets[id]); 216 | } 217 | } -------------------------------------------------------------------------------- /docs/games/PvPGamesStore.md: -------------------------------------------------------------------------------- 1 | # PvPGamesStore 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### addToken 14 | 15 | ```solidity 16 | function addToken(address token) external nonpayable 17 | ``` 18 | 19 | Adds a new token that'll be enabled for the games' betting. Token shouldn't exist yet. 20 | 21 | 22 | 23 | #### Parameters 24 | 25 | | Name | Type | Description | 26 | |---|---|---| 27 | | token | address | Address of the token. | 28 | 29 | ### getTokenConfig 30 | 31 | ```solidity 32 | function getTokenConfig(address token) external view returns (struct IPvPGamesStore.Token config) 33 | ``` 34 | 35 | 36 | 37 | 38 | 39 | #### Parameters 40 | 41 | | Name | Type | Description | 42 | |---|---|---| 43 | | token | address | undefined | 44 | 45 | #### Returns 46 | 47 | | Name | Type | Description | 48 | |---|---|---| 49 | | config | IPvPGamesStore.Token | undefined | 50 | 51 | ### getTokens 52 | 53 | ```solidity 54 | function getTokens() external view returns (struct IPvPGamesStore.TokenMetadata[]) 55 | ``` 56 | 57 | 58 | 59 | *For the front-end* 60 | 61 | 62 | #### Returns 63 | 64 | | Name | Type | Description | 65 | |---|---|---| 66 | | _0 | IPvPGamesStore.TokenMetadata[] | undefined | 67 | 68 | ### getTokensAddresses 69 | 70 | ```solidity 71 | function getTokensAddresses() external view returns (address[]) 72 | ``` 73 | 74 | 75 | 76 | 77 | 78 | 79 | #### Returns 80 | 81 | | Name | Type | Description | 82 | |---|---|---| 83 | | _0 | address[] | undefined | 84 | 85 | ### getTreasuryAndTeamAddresses 86 | 87 | ```solidity 88 | function getTreasuryAndTeamAddresses() external view returns (address, address) 89 | ``` 90 | 91 | 92 | 93 | 94 | 95 | 96 | #### Returns 97 | 98 | | Name | Type | Description | 99 | |---|---|---| 100 | | _0 | address | undefined | 101 | | _1 | address | undefined | 102 | 103 | ### owner 104 | 105 | ```solidity 106 | function owner() external view returns (address) 107 | ``` 108 | 109 | 110 | 111 | *Returns the address of the current owner.* 112 | 113 | 114 | #### Returns 115 | 116 | | Name | Type | Description | 117 | |---|---|---| 118 | | _0 | address | undefined | 119 | 120 | ### renounceOwnership 121 | 122 | ```solidity 123 | function renounceOwnership() external nonpayable 124 | ``` 125 | 126 | 127 | 128 | *Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.* 129 | 130 | 131 | ### setHouseEdgeSplit 132 | 133 | ```solidity 134 | function setHouseEdgeSplit(address token, uint16 dividend, uint16 treasury, uint16 team, uint16 initiator) external nonpayable 135 | ``` 136 | 137 | Sets the token's house edge allocations for bet payout. 138 | 139 | *`dividend`, `_treasuryWallet` and `team` rates sum must equals 10000.* 140 | 141 | #### Parameters 142 | 143 | | Name | Type | Description | 144 | |---|---|---| 145 | | token | address | Address of the token. | 146 | | dividend | uint16 | Rate to be allocated as staking rewards, on bet payout. | 147 | | treasury | uint16 | Rate to be allocated to the treasuryWallet, on bet payout. | 148 | | team | uint16 | Rate to be allocated to the team, on bet payout. | 149 | | initiator | uint16 | Rate to be allocated to the initiator of the bet, on bet payout. | 150 | 151 | ### setTeamWallet 152 | 153 | ```solidity 154 | function setTeamWallet(address _teamWallet) external nonpayable 155 | ``` 156 | 157 | Sets the new team wallet. 158 | 159 | 160 | 161 | #### Parameters 162 | 163 | | Name | Type | Description | 164 | |---|---|---| 165 | | _teamWallet | address | The team wallet address. | 166 | 167 | ### setVRFSubId 168 | 169 | ```solidity 170 | function setVRFSubId(address token, uint64 vrfSubId) external nonpayable 171 | ``` 172 | 173 | Sets the Chainlink VRF subId. 174 | 175 | 176 | 177 | #### Parameters 178 | 179 | | Name | Type | Description | 180 | |---|---|---| 181 | | token | address | undefined | 182 | | vrfSubId | uint64 | New subId. | 183 | 184 | ### teamWallet 185 | 186 | ```solidity 187 | function teamWallet() external view returns (address) 188 | ``` 189 | 190 | 191 | 192 | 193 | 194 | 195 | #### Returns 196 | 197 | | Name | Type | Description | 198 | |---|---|---| 199 | | _0 | address | undefined | 200 | 201 | ### tokens 202 | 203 | ```solidity 204 | function tokens(address) external view returns (uint64 vrfSubId, struct IPvPGamesStore.HouseEdgeSplit houseEdgeSplit) 205 | ``` 206 | 207 | Maps tokens addresses to token configuration. 208 | 209 | 210 | 211 | #### Parameters 212 | 213 | | Name | Type | Description | 214 | |---|---|---| 215 | | _0 | address | undefined | 216 | 217 | #### Returns 218 | 219 | | Name | Type | Description | 220 | |---|---|---| 221 | | vrfSubId | uint64 | undefined | 222 | | houseEdgeSplit | IPvPGamesStore.HouseEdgeSplit | undefined | 223 | 224 | ### transferOwnership 225 | 226 | ```solidity 227 | function transferOwnership(address newOwner) external nonpayable 228 | ``` 229 | 230 | 231 | 232 | *Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.* 233 | 234 | #### Parameters 235 | 236 | | Name | Type | Description | 237 | |---|---|---| 238 | | newOwner | address | undefined | 239 | 240 | ### treasuryWallet 241 | 242 | ```solidity 243 | function treasuryWallet() external view returns (address) 244 | ``` 245 | 246 | 247 | 248 | 249 | 250 | 251 | #### Returns 252 | 253 | | Name | Type | Description | 254 | |---|---|---| 255 | | _0 | address | undefined | 256 | 257 | 258 | 259 | ## Events 260 | 261 | ### AddToken 262 | 263 | ```solidity 264 | event AddToken(address token) 265 | ``` 266 | 267 | Emitted after a token is added. 268 | 269 | 270 | 271 | #### Parameters 272 | 273 | | Name | Type | Description | 274 | |---|---|---| 275 | | token | address | Address of the token. | 276 | 277 | ### OwnershipTransferred 278 | 279 | ```solidity 280 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 281 | ``` 282 | 283 | 284 | 285 | 286 | 287 | #### Parameters 288 | 289 | | Name | Type | Description | 290 | |---|---|---| 291 | | previousOwner `indexed` | address | undefined | 292 | | newOwner `indexed` | address | undefined | 293 | 294 | ### SetPausedToken 295 | 296 | ```solidity 297 | event SetPausedToken(address indexed token, bool paused) 298 | ``` 299 | 300 | Emitted after a token is paused. 301 | 302 | 303 | 304 | #### Parameters 305 | 306 | | Name | Type | Description | 307 | |---|---|---| 308 | | token `indexed` | address | Address of the token. | 309 | | paused | bool | Whether the token is paused for betting. | 310 | 311 | ### SetTeamWallet 312 | 313 | ```solidity 314 | event SetTeamWallet(address teamWallet) 315 | ``` 316 | 317 | 318 | 319 | 320 | 321 | #### Parameters 322 | 323 | | Name | Type | Description | 324 | |---|---|---| 325 | | teamWallet | address | undefined | 326 | 327 | ### SetTokenHouseEdgeSplit 328 | 329 | ```solidity 330 | event SetTokenHouseEdgeSplit(address indexed token, uint16 dividend, uint16 treasury, uint16 team, uint16 initiator) 331 | ``` 332 | 333 | Emitted after the token's house edge allocations for bet payout is set. 334 | 335 | 336 | 337 | #### Parameters 338 | 339 | | Name | Type | Description | 340 | |---|---|---| 341 | | token `indexed` | address | Address of the token. | 342 | | dividend | uint16 | Rate to be allocated as staking rewards, on bet payout. | 343 | | treasury | uint16 | Rate to be allocated to the treasury, on bet payout. | 344 | | team | uint16 | Rate to be allocated to the team, on bet payout. | 345 | | initiator | uint16 | undefined | 346 | 347 | ### SetVRFSubId 348 | 349 | ```solidity 350 | event SetVRFSubId(address indexed token, uint64 vrfSubId) 351 | ``` 352 | 353 | Emitted after the Chainlink callback subId is set for a token. 354 | 355 | 356 | 357 | #### Parameters 358 | 359 | | Name | Type | Description | 360 | |---|---|---| 361 | | token `indexed` | address | Address of the token. | 362 | | vrfSubId | uint64 | New vrfSubId. | 363 | 364 | 365 | 366 | ## Errors 367 | 368 | ### InvalidAddress 369 | 370 | ```solidity 371 | error InvalidAddress() 372 | ``` 373 | 374 | Reverting error when provided address isn't valid. 375 | 376 | 377 | 378 | 379 | ### TokenExists 380 | 381 | ```solidity 382 | error TokenExists() 383 | ``` 384 | 385 | Reverting error when trying to add an existing token. 386 | 387 | 388 | 389 | 390 | ### WrongHouseEdgeSplit 391 | 392 | ```solidity 393 | error WrongHouseEdgeSplit(uint256 sum) 394 | ``` 395 | 396 | Reverting error when setting the house edge allocations, but the sum isn't 100%. 397 | 398 | 399 | 400 | #### Parameters 401 | 402 | | Name | Type | Description | 403 | |---|---|---| 404 | | sum | uint256 | of the house edge allocations rates. | 405 | 406 | 407 | -------------------------------------------------------------------------------- /graphs/CoinToss.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | CoinToss 10 | 11 | 12 | 13 | 14 | Legend 15 | 16 | 17 | 18 | 19 | 20 | <Constructor> 21 | 22 | 23 | 24 | 25 | 26 | _getPayout 27 | 28 | 29 | 30 | 31 | 32 | wager 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | _newBet 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | fulfillRandomWords 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | _resolveBet 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | _accountVRFCost 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | getLastUserBets 93 | 94 | 95 | 96 | 97 | 98 | _getLastUserBets 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | Internal Call 111 | External Call 112 | Defined Contract 113 | Undefined Contract 114 | 115 | 116 | 117 | 118 | 119 |     120 |     121 | 122 |     123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | -------------------------------------------------------------------------------- /docs/BetsToken.md: -------------------------------------------------------------------------------- 1 | # BetsToken 2 | 3 | *Romuald Hog* 4 | 5 | > BetSwirl's ERC20 token 6 | 7 | 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### allowance 14 | 15 | ```solidity 16 | function allowance(address owner, address spender) external view returns (uint256) 17 | ``` 18 | 19 | 20 | 21 | *See {IERC20-allowance}.* 22 | 23 | #### Parameters 24 | 25 | | Name | Type | Description | 26 | |---|---|---| 27 | | owner | address | undefined | 28 | | spender | address | undefined | 29 | 30 | #### Returns 31 | 32 | | Name | Type | Description | 33 | |---|---|---| 34 | | _0 | uint256 | undefined | 35 | 36 | ### approve 37 | 38 | ```solidity 39 | function approve(address spender, uint256 amount) external nonpayable returns (bool) 40 | ``` 41 | 42 | 43 | 44 | *See {IERC20-approve}. NOTE: If `amount` is the maximum `uint256`, the allowance is not updated on `transferFrom`. This is semantically equivalent to an infinite approval. Requirements: - `spender` cannot be the zero address.* 45 | 46 | #### Parameters 47 | 48 | | Name | Type | Description | 49 | |---|---|---| 50 | | spender | address | undefined | 51 | | amount | uint256 | undefined | 52 | 53 | #### Returns 54 | 55 | | Name | Type | Description | 56 | |---|---|---| 57 | | _0 | bool | undefined | 58 | 59 | ### balanceOf 60 | 61 | ```solidity 62 | function balanceOf(address account) external view returns (uint256) 63 | ``` 64 | 65 | 66 | 67 | *See {IERC20-balanceOf}.* 68 | 69 | #### Parameters 70 | 71 | | Name | Type | Description | 72 | |---|---|---| 73 | | account | address | undefined | 74 | 75 | #### Returns 76 | 77 | | Name | Type | Description | 78 | |---|---|---| 79 | | _0 | uint256 | undefined | 80 | 81 | ### decimals 82 | 83 | ```solidity 84 | function decimals() external view returns (uint8) 85 | ``` 86 | 87 | 88 | 89 | *Returns the number of decimals used to get its user representation. For example, if `decimals` equals `2`, a balance of `505` tokens should be displayed to a user as `5.05` (`505 / 10 ** 2`). Tokens usually opt for a value of 18, imitating the relationship between Ether and Wei. This is the value {ERC20} uses, unless this function is overridden; NOTE: This information is only used for _display_ purposes: it in no way affects any of the arithmetic of the contract, including {IERC20-balanceOf} and {IERC20-transfer}.* 90 | 91 | 92 | #### Returns 93 | 94 | | Name | Type | Description | 95 | |---|---|---| 96 | | _0 | uint8 | undefined | 97 | 98 | ### decreaseAllowance 99 | 100 | ```solidity 101 | function decreaseAllowance(address spender, uint256 subtractedValue) external nonpayable returns (bool) 102 | ``` 103 | 104 | 105 | 106 | *Atomically decreases the allowance granted to `spender` by the caller. This is an alternative to {approve} that can be used as a mitigation for problems described in {IERC20-approve}. Emits an {Approval} event indicating the updated allowance. Requirements: - `spender` cannot be the zero address. - `spender` must have allowance for the caller of at least `subtractedValue`.* 107 | 108 | #### Parameters 109 | 110 | | Name | Type | Description | 111 | |---|---|---| 112 | | spender | address | undefined | 113 | | subtractedValue | uint256 | undefined | 114 | 115 | #### Returns 116 | 117 | | Name | Type | Description | 118 | |---|---|---| 119 | | _0 | bool | undefined | 120 | 121 | ### getOwner 122 | 123 | ```solidity 124 | function getOwner() external view returns (address) 125 | ``` 126 | 127 | 128 | 129 | *This function is here to ensure BEP-20 compatibility* 130 | 131 | 132 | #### Returns 133 | 134 | | Name | Type | Description | 135 | |---|---|---| 136 | | _0 | address | undefined | 137 | 138 | ### increaseAllowance 139 | 140 | ```solidity 141 | function increaseAllowance(address spender, uint256 addedValue) external nonpayable returns (bool) 142 | ``` 143 | 144 | 145 | 146 | *Atomically increases the allowance granted to `spender` by the caller. This is an alternative to {approve} that can be used as a mitigation for problems described in {IERC20-approve}. Emits an {Approval} event indicating the updated allowance. Requirements: - `spender` cannot be the zero address.* 147 | 148 | #### Parameters 149 | 150 | | Name | Type | Description | 151 | |---|---|---| 152 | | spender | address | undefined | 153 | | addedValue | uint256 | undefined | 154 | 155 | #### Returns 156 | 157 | | Name | Type | Description | 158 | |---|---|---| 159 | | _0 | bool | undefined | 160 | 161 | ### multicall 162 | 163 | ```solidity 164 | function multicall(bytes[] data) external nonpayable returns (bytes[] results) 165 | ``` 166 | 167 | 168 | 169 | *Receives and executes a batch of function calls on this contract.* 170 | 171 | #### Parameters 172 | 173 | | Name | Type | Description | 174 | |---|---|---| 175 | | data | bytes[] | undefined | 176 | 177 | #### Returns 178 | 179 | | Name | Type | Description | 180 | |---|---|---| 181 | | results | bytes[] | undefined | 182 | 183 | ### name 184 | 185 | ```solidity 186 | function name() external view returns (string) 187 | ``` 188 | 189 | 190 | 191 | *Returns the name of the token.* 192 | 193 | 194 | #### Returns 195 | 196 | | Name | Type | Description | 197 | |---|---|---| 198 | | _0 | string | undefined | 199 | 200 | ### owner 201 | 202 | ```solidity 203 | function owner() external view returns (address) 204 | ``` 205 | 206 | 207 | 208 | *Returns the address of the current owner.* 209 | 210 | 211 | #### Returns 212 | 213 | | Name | Type | Description | 214 | |---|---|---| 215 | | _0 | address | undefined | 216 | 217 | ### renounceOwnership 218 | 219 | ```solidity 220 | function renounceOwnership() external nonpayable 221 | ``` 222 | 223 | 224 | 225 | *Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.* 226 | 227 | 228 | ### symbol 229 | 230 | ```solidity 231 | function symbol() external view returns (string) 232 | ``` 233 | 234 | 235 | 236 | *Returns the symbol of the token, usually a shorter version of the name.* 237 | 238 | 239 | #### Returns 240 | 241 | | Name | Type | Description | 242 | |---|---|---| 243 | | _0 | string | undefined | 244 | 245 | ### totalSupply 246 | 247 | ```solidity 248 | function totalSupply() external view returns (uint256) 249 | ``` 250 | 251 | 252 | 253 | *See {IERC20-totalSupply}.* 254 | 255 | 256 | #### Returns 257 | 258 | | Name | Type | Description | 259 | |---|---|---| 260 | | _0 | uint256 | undefined | 261 | 262 | ### transfer 263 | 264 | ```solidity 265 | function transfer(address to, uint256 amount) external nonpayable returns (bool) 266 | ``` 267 | 268 | 269 | 270 | *See {IERC20-transfer}. Requirements: - `to` cannot be the zero address. - the caller must have a balance of at least `amount`.* 271 | 272 | #### Parameters 273 | 274 | | Name | Type | Description | 275 | |---|---|---| 276 | | to | address | undefined | 277 | | amount | uint256 | undefined | 278 | 279 | #### Returns 280 | 281 | | Name | Type | Description | 282 | |---|---|---| 283 | | _0 | bool | undefined | 284 | 285 | ### transferFrom 286 | 287 | ```solidity 288 | function transferFrom(address from, address to, uint256 amount) external nonpayable returns (bool) 289 | ``` 290 | 291 | 292 | 293 | *See {IERC20-transferFrom}. Emits an {Approval} event indicating the updated allowance. This is not required by the EIP. See the note at the beginning of {ERC20}. NOTE: Does not update the allowance if the current allowance is the maximum `uint256`. Requirements: - `from` and `to` cannot be the zero address. - `from` must have a balance of at least `amount`. - the caller must have allowance for ``from``'s tokens of at least `amount`.* 294 | 295 | #### Parameters 296 | 297 | | Name | Type | Description | 298 | |---|---|---| 299 | | from | address | undefined | 300 | | to | address | undefined | 301 | | amount | uint256 | undefined | 302 | 303 | #### Returns 304 | 305 | | Name | Type | Description | 306 | |---|---|---| 307 | | _0 | bool | undefined | 308 | 309 | ### transferOwnership 310 | 311 | ```solidity 312 | function transferOwnership(address newOwner) external nonpayable 313 | ``` 314 | 315 | 316 | 317 | *Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.* 318 | 319 | #### Parameters 320 | 321 | | Name | Type | Description | 322 | |---|---|---| 323 | | newOwner | address | undefined | 324 | 325 | 326 | 327 | ## Events 328 | 329 | ### Approval 330 | 331 | ```solidity 332 | event Approval(address indexed owner, address indexed spender, uint256 value) 333 | ``` 334 | 335 | 336 | 337 | 338 | 339 | #### Parameters 340 | 341 | | Name | Type | Description | 342 | |---|---|---| 343 | | owner `indexed` | address | undefined | 344 | | spender `indexed` | address | undefined | 345 | | value | uint256 | undefined | 346 | 347 | ### OwnershipTransferred 348 | 349 | ```solidity 350 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 351 | ``` 352 | 353 | 354 | 355 | 356 | 357 | #### Parameters 358 | 359 | | Name | Type | Description | 360 | |---|---|---| 361 | | previousOwner `indexed` | address | undefined | 362 | | newOwner `indexed` | address | undefined | 363 | 364 | ### Transfer 365 | 366 | ```solidity 367 | event Transfer(address indexed from, address indexed to, uint256 value) 368 | ``` 369 | 370 | 371 | 372 | 373 | 374 | #### Parameters 375 | 376 | | Name | Type | Description | 377 | |---|---|---| 378 | | from `indexed` | address | undefined | 379 | | to `indexed` | address | undefined | 380 | | value | uint256 | undefined | 381 | 382 | 383 | 384 | -------------------------------------------------------------------------------- /graphs/Dice.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Dice 10 | 11 | 12 | 13 | 14 | Legend 15 | 16 | 17 | 18 | 19 | 20 | <Constructor> 21 | 22 | 23 | 24 | 25 | 26 | _getPayout 27 | 28 | 29 | 30 | 31 | 32 | wager 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | CapNotInRange 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | _newBet 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | fulfillRandomWords 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | _resolveBet 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | _accountVRFCost 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | getLastUserBets 105 | 106 | 107 | 108 | 109 | 110 | _getLastUserBets 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | Internal Call 123 | External Call 124 | Defined Contract 125 | Undefined Contract 126 | 127 | 128 | 129 | 130 | 131 |     132 |     133 | 134 |     135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | -------------------------------------------------------------------------------- /graphs/Roulette.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Roulette 10 | 11 | 12 | 13 | 14 | Legend 15 | 16 | 17 | 18 | 19 | 20 | <Constructor> 21 | 22 | 23 | 24 | 25 | 26 | _getPayout 27 | 28 | 29 | 30 | 31 | 32 | wager 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | NumbersNotInRange 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | _newBet 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | fulfillRandomWords 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | _resolveBet 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | _accountVRFCost 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | getLastUserBets 105 | 106 | 107 | 108 | 109 | 110 | _getLastUserBets 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | Internal Call 123 | External Call 124 | Defined Contract 125 | Undefined Contract 126 | 127 | 128 | 129 | 130 | 131 |     132 |     133 | 134 |     135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | -------------------------------------------------------------------------------- /graphs/RussianRoulette.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | RussianRoulette 10 | 11 | 12 | 13 | 14 | Legend 15 | 16 | 17 | 18 | 19 | 20 | <Constructor> 21 | 22 | 23 | 24 | 25 | 26 | setMaxSeats 27 | 28 | 29 | 30 | 31 | 32 | wager 33 | 34 | 35 | 36 | 37 | 38 | WrongSeatsNumber 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | InvalidDeathRatio 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | InvalidDate 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | _newBet 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | joinGame 87 | 88 | 89 | 90 | 91 | 92 | _joinGame 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | fulfillRandomWords 105 | 106 | 107 | 108 | 109 | 110 | NotPendingBet 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | pullTriggers 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | _resolveBet 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | betMaxSeats 147 | 148 | 149 | 150 | 151 | 152 | betMinSeats 153 | 154 | 155 | 156 | 157 | 158 | gameCanStart 159 | 160 | 161 | 162 | 163 | 164 | getRussianRouletteBet 165 | 166 | 167 | 168 | 169 | 170 | Internal Call 171 | External Call 172 | Defined Contract 173 | Undefined Contract 174 | 175 | 176 | 177 | 178 | 179 |     180 |     181 | 182 |     183 | 184 | 185 | 186 | 187 | 188 | 189 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | 197 | 198 | -------------------------------------------------------------------------------- /contracts/games/Keno.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | 3 | pragma solidity 0.8.17; 4 | 5 | import {Game} from "./Game.sol"; 6 | 7 | /// @title BetSwirl's Keno game 8 | /// @notice 9 | 10 | contract Keno is Game { 11 | /// @notice Full keno bet information struct. 12 | /// @param bet The Bet struct information. 13 | /// @param kenoBet The Keno bet struct information. 14 | /// @dev Used to package bet information for the front-end. 15 | struct FullKenoBet { 16 | Bet bet; 17 | KenoBet kenoBet; 18 | } 19 | 20 | /// @notice Keno bet information struct. 21 | /// @param bet The Bet struct information. 22 | /// @param numbers The chosen numbers. 23 | struct KenoBet { 24 | uint40 numbers; 25 | uint40 rolled; 26 | } 27 | 28 | /// @notice stores the settings for a specific token 29 | /// @param biggestNumber Sets the biggest number that can be played 30 | /// @param maxNumbersPlayed Sets the maximum numbers that can be picked 31 | struct TokenConfig { 32 | uint128 biggestNumber; 33 | uint128 maxNumbersPlayed; 34 | } 35 | 36 | /// @notice Maps bets IDs to chosen numbers. 37 | mapping(uint256 => KenoBet) public kenoBets; 38 | 39 | /// @notice Maps all possible factors. 40 | mapping(uint256 => mapping(uint256 => mapping(uint256 => uint256[]))) 41 | private gainsFactor; 42 | 43 | /// @notice Maps all token configs 44 | mapping(address => TokenConfig) public tokenConfigurations; 45 | 46 | uint256 private constant FACTORPRECISION = 10000; 47 | 48 | /// @notice Emitted after a bet is placed. 49 | /// @param id The bet ID. 50 | /// @param user Address of the gamer. 51 | /// @param token Address of the token. 52 | /// @param amount The bet amount. 53 | /// @param vrfCost The Chainlink VRF cost paid by player. 54 | /// @param numbers The chosen numbers. 55 | event PlaceBet( 56 | uint256 id, 57 | address indexed user, 58 | address indexed token, 59 | uint256 amount, 60 | uint256 vrfCost, 61 | uint40 numbers 62 | ); 63 | 64 | /// @notice Emitted after a bet is rolled. 65 | /// @param id The bet ID. 66 | /// @param user Address of the gamer. 67 | /// @param token Address of the token. 68 | /// @param amount The bet amount. 69 | /// @param numbers The chosen numbers. 70 | /// @param rolled The rolled number. 71 | /// @param payout The payout amount. 72 | event Roll( 73 | uint256 id, 74 | address indexed user, 75 | address indexed token, 76 | uint256 amount, 77 | uint40 numbers, 78 | uint40 rolled, 79 | uint256 payout 80 | ); 81 | 82 | /// @notice Emitted when the settings are updated for a specific token 83 | /// @param newBiggestNumber The new biggest number 84 | /// @param newMaxNumbers The new maximum of pick 85 | event TokenConfigUpdated( 86 | address token, 87 | uint128 newBiggestNumber, 88 | uint128 newMaxNumbers 89 | ); 90 | 91 | /// @notice Numbers provided is not in the allowed range 92 | error NumbersNotInRange(); 93 | 94 | /// @notice Too many numbers are submitted. 95 | error TooManyNumbersPlayed(); 96 | 97 | /// @notice Thrown when settings could block the contract. 98 | error InvalidSettings(); 99 | 100 | /// @notice Initialize the game base contract. 101 | /// @param bankAddress The address of the bank. 102 | /// @param chainlinkCoordinatorAddress Address of the Chainlink VRF Coordinator. 103 | /// @param LINK_ETH_feedAddress Address of the Chainlink LINK/ETH price feed. 104 | constructor( 105 | address bankAddress, 106 | address chainlinkCoordinatorAddress, 107 | address LINK_ETH_feedAddress, 108 | address wrappedGasToken 109 | ) Game(bankAddress, chainlinkCoordinatorAddress, 1, LINK_ETH_feedAddress) {} 110 | 111 | /// @notice Calculate all gain factors 112 | /// @param token used 113 | function _calculateFactors(address token) private { 114 | TokenConfig memory config = tokenConfigurations[token]; 115 | for (uint256 played = 1; played <= config.maxNumbersPlayed; played++) { 116 | uint256[] storage factors = gainsFactor[config.biggestNumber][ 117 | config.maxNumbersPlayed 118 | ][played]; 119 | if (factors.length == 0) { 120 | for ( 121 | uint256 matchCount = 0; 122 | matchCount <= played; 123 | matchCount++ 124 | ) { 125 | factors.push(gain(token, played, matchCount)); 126 | } 127 | } 128 | } 129 | } 130 | 131 | /// @notice Updates the settings for a specific token 132 | /// @param newBiggestNumber The new biggest number 133 | /// @param newMaxNumbers The new maximum of pick 134 | function updateTokenConfig( 135 | address token, 136 | uint128 newBiggestNumber, 137 | uint128 newMaxNumbers 138 | ) external onlyOwner { 139 | if (hasPendingBets(token)) { 140 | revert TokenHasPendingBets(); 141 | } 142 | if ( 143 | newMaxNumbers > newBiggestNumber || 144 | newBiggestNumber > 40 || 145 | newMaxNumbers > 10 146 | ) revert InvalidSettings(); 147 | 148 | TokenConfig storage config = tokenConfigurations[token]; 149 | config.biggestNumber = newBiggestNumber; 150 | config.maxNumbersPlayed = newMaxNumbers; 151 | 152 | _calculateFactors(token); 153 | emit TokenConfigUpdated(token, newBiggestNumber, newMaxNumbers); 154 | } 155 | 156 | /// @notice Calculates the target payout amount. 157 | /// @param betAmount Bet amount. 158 | /// @param played the count of numbers played 159 | /// @param matchCount the count of matching numbers 160 | /// @return factor The target payout amount. 161 | function _getPayout( 162 | address token, 163 | uint256 betAmount, 164 | uint256 played, 165 | uint256 matchCount 166 | ) private view returns (uint256 factor) { 167 | TokenConfig memory config = tokenConfigurations[token]; 168 | factor = 169 | (betAmount * 170 | gainsFactor[config.biggestNumber][config.maxNumbersPlayed][ 171 | played 172 | ][matchCount]) / 173 | FACTORPRECISION; 174 | } 175 | 176 | /// @notice Creates a new bet and stores the chosen bet mask. 177 | /// @param numbers The chosen numbers. 178 | /// @param token Address of the token. 179 | /// @param tokenAmount The number of tokens bet. 180 | function wager( 181 | uint40 numbers, 182 | address token, 183 | uint256 tokenAmount 184 | ) external payable whenNotPaused { 185 | TokenConfig memory config = tokenConfigurations[token]; 186 | if (numbers == 0 || numbers >= 2 ** config.biggestNumber - 1) { 187 | revert NumbersNotInRange(); 188 | } 189 | 190 | uint256 _count = _countNumbers(numbers); 191 | if (_count > config.maxNumbersPlayed) { 192 | revert TooManyNumbersPlayed(); 193 | } 194 | 195 | Bet memory bet = _newBet( 196 | token, 197 | tokenAmount, 198 | _getPayout(token, 10000, _count, _count) 199 | ); 200 | 201 | kenoBets[bet.id].numbers = numbers; 202 | 203 | emit PlaceBet( 204 | bet.id, 205 | bet.user, 206 | bet.token, 207 | bet.amount, 208 | bet.vrfCost, 209 | numbers 210 | ); 211 | } 212 | 213 | /// @notice Count how many numbers are encoded 214 | /// @param numbers The binary encoded list of numbers 215 | /// @return count The total of numbers encoded 216 | function _countNumbers( 217 | uint40 numbers 218 | ) private pure returns (uint256 count) { 219 | if (numbers & 0x1 > 0) count++; 220 | if (numbers & 0x2 > 0) count++; 221 | if (numbers & 0x4 > 0) count++; 222 | if (numbers & 0x8 > 0) count++; 223 | 224 | if (numbers & 0x10 > 0) count++; 225 | if (numbers & 0x20 > 0) count++; 226 | if (numbers & 0x40 > 0) count++; 227 | if (numbers & 0x80 > 0) count++; 228 | 229 | if (numbers & 0x100 > 0) count++; 230 | if (numbers & 0x200 > 0) count++; 231 | if (numbers & 0x400 > 0) count++; 232 | if (numbers & 0x800 > 0) count++; 233 | 234 | if (numbers & 0x1000 > 0) count++; 235 | if (numbers & 0x2000 > 0) count++; 236 | if (numbers & 0x4000 > 0) count++; 237 | if (numbers & 0x8000 > 0) count++; 238 | 239 | if (numbers & 0x10000 > 0) count++; 240 | if (numbers & 0x20000 > 0) count++; 241 | if (numbers & 0x40000 > 0) count++; 242 | if (numbers & 0x80000 > 0) count++; 243 | 244 | if (numbers & 0x100000 > 0) count++; 245 | if (numbers & 0x200000 > 0) count++; 246 | if (numbers & 0x400000 > 0) count++; 247 | if (numbers & 0x800000 > 0) count++; 248 | 249 | if (numbers & 0x1000000 > 0) count++; 250 | if (numbers & 0x2000000 > 0) count++; 251 | if (numbers & 0x4000000 > 0) count++; 252 | if (numbers & 0x8000000 > 0) count++; 253 | 254 | if (numbers & 0x10000000 > 0) count++; 255 | if (numbers & 0x20000000 > 0) count++; 256 | if (numbers & 0x40000000 > 0) count++; 257 | if (numbers & 0x80000000 > 0) count++; 258 | 259 | if (numbers & 0x100000000 > 0) count++; 260 | if (numbers & 0x200000000 > 0) count++; 261 | if (numbers & 0x400000000 > 0) count++; 262 | if (numbers & 0x800000000 > 0) count++; 263 | 264 | if (numbers & 0x1000000000 > 0) count++; 265 | if (numbers & 0x2000000000 > 0) count++; 266 | if (numbers & 0x4000000000 > 0) count++; 267 | if (numbers & 0x8000000000 > 0) count++; 268 | } 269 | 270 | /// @notice Resolves the bet using the Chainlink randomness. 271 | /// @param id The bet ID. 272 | /// @param randomWords Random words list. Contains only one for this game. 273 | // solhint-disable-next-line private-vars-leading-underscore 274 | function fulfillRandomWords( 275 | uint256 id, 276 | uint256[] memory randomWords 277 | ) internal override { 278 | uint256 startGas = gasleft(); 279 | 280 | KenoBet storage kenoBet = kenoBets[id]; 281 | Bet storage bet = bets[id]; 282 | uint40 rolled = getNumbersOutOfRandomWord(bet.token, randomWords[0]); 283 | 284 | kenoBet.rolled = rolled; 285 | uint256 _gain = _getPayout( 286 | bet.token, 287 | bet.amount, 288 | _countNumbers(kenoBet.numbers), 289 | _countNumbers(kenoBet.numbers & rolled) 290 | ); 291 | 292 | uint256 payout = _resolveBet(bet, _gain); 293 | 294 | emit Roll( 295 | bet.id, 296 | bet.user, 297 | bet.token, 298 | bet.amount, 299 | kenoBet.numbers, 300 | rolled, 301 | payout 302 | ); 303 | 304 | _accountVRFCost(bet, startGas); 305 | } 306 | 307 | /// @notice Calculate the _factorial of a number 308 | /// @param n Param for the calculation 309 | /// @return result The _factorial result 310 | function _fact(uint256 n) private pure returns (uint256 result) { 311 | if (n == 0) return 1; 312 | result = n; 313 | for (uint i = n - 1; i > 1; i--) { 314 | result = result * i; 315 | } 316 | } 317 | 318 | /// @notice Calculate the proability to draw x items out of n 319 | /// @param n Total number 320 | /// @param x Number of Trials 321 | /// @return The mathematical result 322 | function _outof(uint n, uint x) private pure returns (uint256) { 323 | return _fact(n) / (_fact(x) * _fact(n - x)); 324 | } 325 | 326 | /// @notice Calculate the gain ratio based on Hypergeometric formula 327 | /// @param played Number of numbers chosen 328 | /// @param matchCount Number of winning numbers 329 | /// @return _factor The gain _factor 330 | function gain( 331 | address token, 332 | uint256 played, 333 | uint256 matchCount 334 | ) public view returns (uint256 _factor) { 335 | TokenConfig memory config = tokenConfigurations[token]; 336 | 337 | uint256 hypergeometricNumerator = _outof(played, matchCount) * 338 | _outof( 339 | config.biggestNumber - played, 340 | config.maxNumbersPlayed - matchCount 341 | ); 342 | uint256 hypergeometricDenominator = _outof( 343 | config.biggestNumber, 344 | config.maxNumbersPlayed 345 | ); 346 | 347 | // Calculate the inverse of the hypergeometric function 348 | _factor = 349 | (FACTORPRECISION * hypergeometricDenominator) / 350 | (hypergeometricNumerator * (played + 1)); 351 | } 352 | 353 | /// @notice returns all gains table for one token 354 | /// @param token used 355 | function gains( 356 | address token 357 | ) 358 | external 359 | view 360 | returns ( 361 | uint biggestNumber, 362 | uint maxNumbersPlayed, 363 | uint256[] memory _gains 364 | ) 365 | { 366 | TokenConfig memory config = tokenConfigurations[token]; 367 | _gains = new uint256[](config.maxNumbersPlayed + 1); 368 | biggestNumber = config.biggestNumber; 369 | maxNumbersPlayed = config.maxNumbersPlayed; 370 | for ( 371 | uint256 matchCount = 0; 372 | matchCount <= config.maxNumbersPlayed; 373 | matchCount++ 374 | ) { 375 | _gains[matchCount] = gainsFactor[config.biggestNumber][ 376 | config.maxNumbersPlayed 377 | ][config.maxNumbersPlayed][matchCount]; 378 | } 379 | } 380 | 381 | /// @notice Transforms a random word into a suite of number encoded in binary 382 | /// @param randomWord The source of randomness 383 | /// @return result The encoded numbers list 384 | function getNumbersOutOfRandomWord( 385 | address token, 386 | uint256 randomWord 387 | ) public view returns (uint40) { 388 | uint256 result = 0; 389 | TokenConfig memory config = tokenConfigurations[token]; 390 | for (uint256 i = 0; i < config.maxNumbersPlayed; i++) { 391 | // Draw a number 392 | uint256 current = ((randomWord & 0xFF) % config.biggestNumber) + 1; 393 | 394 | // Check if number does not already exist 395 | uint256 bitmask = 2 ** (current - 1); 396 | while ((result & bitmask) != 0) { 397 | // Draw the next number is it does already exist 398 | current += 1; 399 | 400 | // Loop back to the first number if biggest number is reached 401 | if (current > config.biggestNumber) current = 1; 402 | bitmask = 2 ** (current - 1); 403 | } 404 | 405 | // Add the number to the result 406 | result = result | bitmask; 407 | 408 | // Offset to draw the next one 409 | randomWord = randomWord >> 8; 410 | } 411 | return uint40(result); 412 | } 413 | 414 | /// @notice Gets the list of the last user bets. 415 | /// @param user Address of the gamer. 416 | /// @param dataLength The amount of bets to return. 417 | /// @return A list of Keno bet. 418 | function getLastUserBets( 419 | address user, 420 | uint256 dataLength 421 | ) external view returns (FullKenoBet[] memory) { 422 | Bet[] memory lastBets = _getLastUserBets(user, dataLength); 423 | FullKenoBet[] memory lastKenoBets = new FullKenoBet[](lastBets.length); 424 | for (uint256 i; i < lastBets.length; i++) { 425 | lastKenoBets[i] = FullKenoBet( 426 | lastBets[i], 427 | kenoBets[lastBets[i].id] 428 | ); 429 | } 430 | return lastKenoBets; 431 | } 432 | } 433 | -------------------------------------------------------------------------------- /graphs/PvPGamesStore.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | PvPGamesStore 10 | 11 | 12 | 13 | 14 | IERC20Metadata 15 | 16 | 17 | 18 | 19 | Legend 20 | 21 | 22 | 23 | 24 | 25 | <Constructor> 26 | 27 | 28 | 29 | 30 | 31 | setTeamWallet 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | address 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | InvalidAddress 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | setHouseEdgeSplit 68 | 69 | 70 | 71 | 72 | 73 | WrongHouseEdgeSplit 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | addToken 86 | 87 | 88 | 89 | 90 | 91 | TokenExists 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | setVRFSubId 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | getTokens 122 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | TokenMetadata 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | 151 | IERC20Metadata 152 | 153 | 154 | 155 | 156 | 157 | 158 | 159 | 160 | 161 | 162 | 163 | decimals 164 | 165 | 166 | 167 | 168 | 169 | 170 | 171 | 172 | 173 | 174 | 175 | name 176 | 177 | 178 | 179 | 180 | 181 | 182 | 183 | 184 | 185 | 186 | 187 | symbol 188 | 189 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | 197 | 198 | 199 | getTokensAddresses 200 | 201 | 202 | 203 | 204 | 205 | getTokenConfig 206 | 207 | 208 | 209 | 210 | 211 | getTreasuryAndTeamAddresses 212 | 213 | 214 | 215 | 216 | 217 | Internal Call 218 | External Call 219 | Defined Contract 220 | Undefined Contract 221 | 222 | 223 | 224 | 225 | 226 |     227 |     228 | 229 |     230 | 231 | 232 | 233 | 234 | 235 | 236 | 237 | 238 | 239 | 240 | 241 | 242 | 243 | 244 | 245 | -------------------------------------------------------------------------------- /docs/games/Roulette.md: -------------------------------------------------------------------------------- 1 | # Roulette 2 | 3 | 4 | 5 | > BetSwirl's Roulette game 6 | 7 | @author Romuald Hog 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### bank 14 | 15 | ```solidity 16 | function bank() external view returns (contract IBank) 17 | ``` 18 | 19 | The bank that manage to payout a won bet and collect a loss bet. 20 | 21 | 22 | 23 | 24 | #### Returns 25 | 26 | | Name | Type | Description | 27 | |---|---|---| 28 | | _0 | contract IBank | undefined | 29 | 30 | ### bets 31 | 32 | ```solidity 33 | function bets(uint256) external view returns (bool resolved, address user, address token, uint256 id, uint256 amount, uint256 blockNumber, uint256 payout, uint256 vrfCost) 34 | ``` 35 | 36 | Maps bets IDs to Bet information. 37 | 38 | 39 | 40 | #### Parameters 41 | 42 | | Name | Type | Description | 43 | |---|---|---| 44 | | _0 | uint256 | undefined | 45 | 46 | #### Returns 47 | 48 | | Name | Type | Description | 49 | |---|---|---| 50 | | resolved | bool | undefined | 51 | | user | address | undefined | 52 | | token | address | undefined | 53 | | id | uint256 | undefined | 54 | | amount | uint256 | undefined | 55 | | blockNumber | uint256 | undefined | 56 | | payout | uint256 | undefined | 57 | | vrfCost | uint256 | undefined | 58 | 59 | ### getChainlinkConfig 60 | 61 | ```solidity 62 | function getChainlinkConfig() external view returns (uint16 requestConfirmations, bytes32 keyHash, contract IVRFCoordinatorV2 chainlinkCoordinator, uint256 gasAfterCalculation) 63 | ``` 64 | 65 | Returns the Chainlink VRF config. 66 | 67 | 68 | 69 | 70 | #### Returns 71 | 72 | | Name | Type | Description | 73 | |---|---|---| 74 | | requestConfirmations | uint16 | undefined | 75 | | keyHash | bytes32 | undefined | 76 | | chainlinkCoordinator | contract IVRFCoordinatorV2 | undefined | 77 | | gasAfterCalculation | uint256 | undefined | 78 | 79 | ### getChainlinkVRFCost 80 | 81 | ```solidity 82 | function getChainlinkVRFCost(address token) external view returns (uint256) 83 | ``` 84 | 85 | Returns the amount of ETH that should be passed to the wager transaction. to cover Chainlink VRF fee. 86 | 87 | 88 | 89 | #### Parameters 90 | 91 | | Name | Type | Description | 92 | |---|---|---| 93 | | token | address | undefined | 94 | 95 | #### Returns 96 | 97 | | Name | Type | Description | 98 | |---|---|---| 99 | | _0 | uint256 | The bet resolution cost amount. | 100 | 101 | ### getLastUserBets 102 | 103 | ```solidity 104 | function getLastUserBets(address user, uint256 dataLength) external view returns (struct Roulette.FullRouletteBet[]) 105 | ``` 106 | 107 | Gets the list of the last user bets. 108 | 109 | 110 | 111 | #### Parameters 112 | 113 | | Name | Type | Description | 114 | |---|---|---| 115 | | user | address | Address of the gamer. | 116 | | dataLength | uint256 | The amount of bets to return. | 117 | 118 | #### Returns 119 | 120 | | Name | Type | Description | 121 | |---|---|---| 122 | | _0 | Roulette.FullRouletteBet[] | A list of Roulette bet. | 123 | 124 | ### hasPendingBets 125 | 126 | ```solidity 127 | function hasPendingBets(address token) external view returns (bool) 128 | ``` 129 | 130 | Returns whether the token has pending bets. 131 | 132 | 133 | 134 | #### Parameters 135 | 136 | | Name | Type | Description | 137 | |---|---|---| 138 | | token | address | undefined | 139 | 140 | #### Returns 141 | 142 | | Name | Type | Description | 143 | |---|---|---| 144 | | _0 | bool | Whether the token has pending bets. | 145 | 146 | ### multicall 147 | 148 | ```solidity 149 | function multicall(bytes[] data) external nonpayable returns (bytes[] results) 150 | ``` 151 | 152 | 153 | 154 | *Receives and executes a batch of function calls on this contract.* 155 | 156 | #### Parameters 157 | 158 | | Name | Type | Description | 159 | |---|---|---| 160 | | data | bytes[] | undefined | 161 | 162 | #### Returns 163 | 164 | | Name | Type | Description | 165 | |---|---|---| 166 | | results | bytes[] | undefined | 167 | 168 | ### owner 169 | 170 | ```solidity 171 | function owner() external view returns (address) 172 | ``` 173 | 174 | 175 | 176 | *Returns the address of the current owner.* 177 | 178 | 179 | #### Returns 180 | 181 | | Name | Type | Description | 182 | |---|---|---| 183 | | _0 | address | undefined | 184 | 185 | ### pause 186 | 187 | ```solidity 188 | function pause() external nonpayable 189 | ``` 190 | 191 | Pauses the contract to disable new bets. 192 | 193 | 194 | 195 | 196 | ### paused 197 | 198 | ```solidity 199 | function paused() external view returns (bool) 200 | ``` 201 | 202 | 203 | 204 | *Returns true if the contract is paused, and false otherwise.* 205 | 206 | 207 | #### Returns 208 | 209 | | Name | Type | Description | 210 | |---|---|---| 211 | | _0 | bool | undefined | 212 | 213 | ### rawFulfillRandomWords 214 | 215 | ```solidity 216 | function rawFulfillRandomWords(uint256 requestId, uint256[] randomWords) external nonpayable 217 | ``` 218 | 219 | 220 | 221 | 222 | 223 | #### Parameters 224 | 225 | | Name | Type | Description | 226 | |---|---|---| 227 | | requestId | uint256 | undefined | 228 | | randomWords | uint256[] | undefined | 229 | 230 | ### refundBet 231 | 232 | ```solidity 233 | function refundBet(uint256 id) external nonpayable 234 | ``` 235 | 236 | Refunds the bet to the user if the Chainlink VRF callback failed. 237 | 238 | 239 | 240 | #### Parameters 241 | 242 | | Name | Type | Description | 243 | |---|---|---| 244 | | id | uint256 | The Bet ID. | 245 | 246 | ### renounceOwnership 247 | 248 | ```solidity 249 | function renounceOwnership() external nonpayable 250 | ``` 251 | 252 | 253 | 254 | *Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.* 255 | 256 | 257 | ### rouletteBets 258 | 259 | ```solidity 260 | function rouletteBets(uint256) external view returns (uint40 numbers, uint8 rolled) 261 | ``` 262 | 263 | Maps bets IDs to chosen numbers. 264 | 265 | 266 | 267 | #### Parameters 268 | 269 | | Name | Type | Description | 270 | |---|---|---| 271 | | _0 | uint256 | undefined | 272 | 273 | #### Returns 274 | 275 | | Name | Type | Description | 276 | |---|---|---| 277 | | numbers | uint40 | undefined | 278 | | rolled | uint8 | undefined | 279 | 280 | ### setChainlinkConfig 281 | 282 | ```solidity 283 | function setChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) external nonpayable 284 | ``` 285 | 286 | Sets the Chainlink VRF V2 configuration. 287 | 288 | 289 | 290 | #### Parameters 291 | 292 | | Name | Type | Description | 293 | |---|---|---| 294 | | requestConfirmations | uint16 | How many confirmations the Chainlink node should wait before responding. | 295 | | keyHash | bytes32 | Hash of the public key used to verify the VRF proof. | 296 | | gasAfterCalculation | uint256 | Gas to be added for VRF cost refund. | 297 | 298 | ### setHouseEdge 299 | 300 | ```solidity 301 | function setHouseEdge(address token, uint16 houseEdge) external nonpayable 302 | ``` 303 | 304 | Sets the game house edge rate for a specific token. 305 | 306 | *The house edge rate couldn't exceed 4%.* 307 | 308 | #### Parameters 309 | 310 | | Name | Type | Description | 311 | |---|---|---| 312 | | token | address | Address of the token. | 313 | | houseEdge | uint16 | House edge rate. | 314 | 315 | ### setVRFCallbackGasLimit 316 | 317 | ```solidity 318 | function setVRFCallbackGasLimit(address token, uint32 callbackGasLimit) external nonpayable 319 | ``` 320 | 321 | Sets the Chainlink VRF V2 configuration. 322 | 323 | 324 | 325 | #### Parameters 326 | 327 | | Name | Type | Description | 328 | |---|---|---| 329 | | token | address | undefined | 330 | | callbackGasLimit | uint32 | How much gas is needed in the Chainlink VRF callback. | 331 | 332 | ### tokens 333 | 334 | ```solidity 335 | function tokens(address) external view returns (uint16 houseEdge, uint64 pendingCount, uint32 VRFCallbackGasLimit, uint256 VRFFees) 336 | ``` 337 | 338 | Maps tokens addresses to token configuration. 339 | 340 | 341 | 342 | #### Parameters 343 | 344 | | Name | Type | Description | 345 | |---|---|---| 346 | | _0 | address | undefined | 347 | 348 | #### Returns 349 | 350 | | Name | Type | Description | 351 | |---|---|---| 352 | | houseEdge | uint16 | undefined | 353 | | pendingCount | uint64 | undefined | 354 | | VRFCallbackGasLimit | uint32 | undefined | 355 | | VRFFees | uint256 | undefined | 356 | 357 | ### transferOwnership 358 | 359 | ```solidity 360 | function transferOwnership(address newOwner) external nonpayable 361 | ``` 362 | 363 | 364 | 365 | *Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.* 366 | 367 | #### Parameters 368 | 369 | | Name | Type | Description | 370 | |---|---|---| 371 | | newOwner | address | undefined | 372 | 373 | ### userOverchargedVRFCost 374 | 375 | ```solidity 376 | function userOverchargedVRFCost(address) external view returns (uint256) 377 | ``` 378 | 379 | Maps user addresses to VRF overcharged cost. 380 | 381 | 382 | 383 | #### Parameters 384 | 385 | | Name | Type | Description | 386 | |---|---|---| 387 | | _0 | address | undefined | 388 | 389 | #### Returns 390 | 391 | | Name | Type | Description | 392 | |---|---|---| 393 | | _0 | uint256 | undefined | 394 | 395 | ### wager 396 | 397 | ```solidity 398 | function wager(uint40 numbers, address token, uint256 tokenAmount) external payable 399 | ``` 400 | 401 | Creates a new bet and stores the chosen bet mask. 402 | 403 | 404 | 405 | #### Parameters 406 | 407 | | Name | Type | Description | 408 | |---|---|---| 409 | | numbers | uint40 | The chosen numbers. | 410 | | token | address | Address of the token. | 411 | | tokenAmount | uint256 | The number of tokens bet. | 412 | 413 | ### withdrawOverchargedVRFCost 414 | 415 | ```solidity 416 | function withdrawOverchargedVRFCost(address user) external nonpayable 417 | ``` 418 | 419 | Withdraw user's overcharged Chainlink fees. 420 | 421 | 422 | 423 | #### Parameters 424 | 425 | | Name | Type | Description | 426 | |---|---|---| 427 | | user | address | undefined | 428 | 429 | ### withdrawTokensVRFFees 430 | 431 | ```solidity 432 | function withdrawTokensVRFFees(address token) external nonpayable 433 | ``` 434 | 435 | Distributes the token's collected Chainlink fees. 436 | 437 | 438 | 439 | #### Parameters 440 | 441 | | Name | Type | Description | 442 | |---|---|---| 443 | | token | address | Address of the token. | 444 | 445 | 446 | 447 | ## Events 448 | 449 | ### AccountOverchargedVRFCost 450 | 451 | ```solidity 452 | event AccountOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 453 | ``` 454 | 455 | Emitted after the overcharged VRF cost amount is accounted. 456 | 457 | 458 | 459 | #### Parameters 460 | 461 | | Name | Type | Description | 462 | |---|---|---| 463 | | user `indexed` | address | undefined | 464 | | overchargedVRFCost | uint256 | undefined | 465 | 466 | ### BetRefunded 467 | 468 | ```solidity 469 | event BetRefunded(uint256 id, address user, uint256 amount, uint256 chainlinkVRFCost) 470 | ``` 471 | 472 | Emitted after the bet amount is transfered to the user. 473 | 474 | 475 | 476 | #### Parameters 477 | 478 | | Name | Type | Description | 479 | |---|---|---| 480 | | id | uint256 | undefined | 481 | | user | address | undefined | 482 | | amount | uint256 | undefined | 483 | | chainlinkVRFCost | uint256 | undefined | 484 | 485 | ### DistributeOverchargedVRFCost 486 | 487 | ```solidity 488 | event DistributeOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 489 | ``` 490 | 491 | Emitted after the user's overcharged VRF cost amount is transfered. 492 | 493 | 494 | 495 | #### Parameters 496 | 497 | | Name | Type | Description | 498 | |---|---|---| 499 | | user `indexed` | address | undefined | 500 | | overchargedVRFCost | uint256 | undefined | 501 | 502 | ### DistributeTokenVRFFees 503 | 504 | ```solidity 505 | event DistributeTokenVRFFees(address indexed token, uint256 amount) 506 | ``` 507 | 508 | Emitted after the token's VRF fees amount is transfered to the user. 509 | 510 | 511 | 512 | #### Parameters 513 | 514 | | Name | Type | Description | 515 | |---|---|---| 516 | | token `indexed` | address | undefined | 517 | | amount | uint256 | undefined | 518 | 519 | ### OwnershipTransferred 520 | 521 | ```solidity 522 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 523 | ``` 524 | 525 | 526 | 527 | 528 | 529 | #### Parameters 530 | 531 | | Name | Type | Description | 532 | |---|---|---| 533 | | previousOwner `indexed` | address | undefined | 534 | | newOwner `indexed` | address | undefined | 535 | 536 | ### Paused 537 | 538 | ```solidity 539 | event Paused(address account) 540 | ``` 541 | 542 | 543 | 544 | 545 | 546 | #### Parameters 547 | 548 | | Name | Type | Description | 549 | |---|---|---| 550 | | account | address | undefined | 551 | 552 | ### PlaceBet 553 | 554 | ```solidity 555 | event PlaceBet(uint256 id, address indexed user, address indexed token, uint256 amount, uint256 vrfCost, uint40 numbers) 556 | ``` 557 | 558 | Emitted after a bet is placed. 559 | 560 | 561 | 562 | #### Parameters 563 | 564 | | Name | Type | Description | 565 | |---|---|---| 566 | | id | uint256 | The bet ID. | 567 | | user `indexed` | address | Address of the gamer. | 568 | | token `indexed` | address | Address of the token. | 569 | | amount | uint256 | The bet amount. | 570 | | vrfCost | uint256 | The Chainlink VRF cost paid by player. | 571 | | numbers | uint40 | The chosen numbers. | 572 | 573 | ### Roll 574 | 575 | ```solidity 576 | event Roll(uint256 id, address indexed user, address indexed token, uint256 amount, uint40 numbers, uint8 rolled, uint256 payout) 577 | ``` 578 | 579 | Emitted after a bet is rolled. 580 | 581 | 582 | 583 | #### Parameters 584 | 585 | | Name | Type | Description | 586 | |---|---|---| 587 | | id | uint256 | The bet ID. | 588 | | user `indexed` | address | Address of the gamer. | 589 | | token `indexed` | address | Address of the token. | 590 | | amount | uint256 | The bet amount. | 591 | | numbers | uint40 | The chosen numbers. | 592 | | rolled | uint8 | The rolled number. | 593 | | payout | uint256 | The payout amount. | 594 | 595 | ### SetChainlinkConfig 596 | 597 | ```solidity 598 | event SetChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) 599 | ``` 600 | 601 | Emitted after the Chainlink config is set. 602 | 603 | 604 | 605 | #### Parameters 606 | 607 | | Name | Type | Description | 608 | |---|---|---| 609 | | requestConfirmations | uint16 | undefined | 610 | | keyHash | bytes32 | undefined | 611 | | gasAfterCalculation | uint256 | undefined | 612 | 613 | ### SetHouseEdge 614 | 615 | ```solidity 616 | event SetHouseEdge(address indexed token, uint16 houseEdge) 617 | ``` 618 | 619 | Emitted after the house edge is set for a token. 620 | 621 | 622 | 623 | #### Parameters 624 | 625 | | Name | Type | Description | 626 | |---|---|---| 627 | | token `indexed` | address | undefined | 628 | | houseEdge | uint16 | undefined | 629 | 630 | ### SetVRFCallbackGasLimit 631 | 632 | ```solidity 633 | event SetVRFCallbackGasLimit(address indexed token, uint32 callbackGasLimit) 634 | ``` 635 | 636 | Emitted after the Chainlink callback gas limit is set for a token. 637 | 638 | 639 | 640 | #### Parameters 641 | 642 | | Name | Type | Description | 643 | |---|---|---| 644 | | token `indexed` | address | undefined | 645 | | callbackGasLimit | uint32 | undefined | 646 | 647 | ### Unpaused 648 | 649 | ```solidity 650 | event Unpaused(address account) 651 | ``` 652 | 653 | 654 | 655 | 656 | 657 | #### Parameters 658 | 659 | | Name | Type | Description | 660 | |---|---|---| 661 | | account | address | undefined | 662 | 663 | 664 | 665 | ## Errors 666 | 667 | ### AccessDenied 668 | 669 | ```solidity 670 | error AccessDenied() 671 | ``` 672 | 673 | Reverting error when sender isn't allowed. 674 | 675 | 676 | 677 | 678 | ### ExcessiveHouseEdge 679 | 680 | ```solidity 681 | error ExcessiveHouseEdge() 682 | ``` 683 | 684 | House edge is capped at 4%. 685 | 686 | 687 | 688 | 689 | ### ForbiddenToken 690 | 691 | ```solidity 692 | error ForbiddenToken() 693 | ``` 694 | 695 | Token is not allowed. 696 | 697 | 698 | 699 | 700 | ### InvalidAddress 701 | 702 | ```solidity 703 | error InvalidAddress() 704 | ``` 705 | 706 | Reverting error when provided address isn't valid. 707 | 708 | 709 | 710 | 711 | ### InvalidLinkWeiPrice 712 | 713 | ```solidity 714 | error InvalidLinkWeiPrice(int256 linkWei) 715 | ``` 716 | 717 | Chainlink price feed not working 718 | 719 | 720 | 721 | #### Parameters 722 | 723 | | Name | Type | Description | 724 | |---|---|---| 725 | | linkWei | int256 | LINK/ETH price returned. | 726 | 727 | ### NoOverchargedVRFCost 728 | 729 | ```solidity 730 | error NoOverchargedVRFCost() 731 | ``` 732 | 733 | No user's overcharged Chainlink fee. 734 | 735 | 736 | 737 | 738 | ### NotFulfilled 739 | 740 | ```solidity 741 | error NotFulfilled() 742 | ``` 743 | 744 | Bet isn't resolved yet. 745 | 746 | 747 | 748 | 749 | ### NotPendingBet 750 | 751 | ```solidity 752 | error NotPendingBet() 753 | ``` 754 | 755 | Bet provided doesn't exist or was already resolved. 756 | 757 | 758 | 759 | 760 | ### NumbersNotInRange 761 | 762 | ```solidity 763 | error NumbersNotInRange() 764 | ``` 765 | 766 | Provided cap is under the minimum. 767 | 768 | 769 | 770 | 771 | ### OnlyCoordinatorCanFulfill 772 | 773 | ```solidity 774 | error OnlyCoordinatorCanFulfill(address have, address want) 775 | ``` 776 | 777 | 778 | 779 | 780 | 781 | #### Parameters 782 | 783 | | Name | Type | Description | 784 | |---|---|---| 785 | | have | address | undefined | 786 | | want | address | undefined | 787 | 788 | ### TokenHasPendingBets 789 | 790 | ```solidity 791 | error TokenHasPendingBets() 792 | ``` 793 | 794 | Reverting error when token has pending bets. 795 | 796 | 797 | 798 | 799 | ### UnderMinBetAmount 800 | 801 | ```solidity 802 | error UnderMinBetAmount(uint256 minBetAmount) 803 | ``` 804 | 805 | Insufficient bet amount. 806 | 807 | 808 | 809 | #### Parameters 810 | 811 | | Name | Type | Description | 812 | |---|---|---| 813 | | minBetAmount | uint256 | Bet amount. | 814 | 815 | ### WrongGasValueToCoverFee 816 | 817 | ```solidity 818 | error WrongGasValueToCoverFee() 819 | ``` 820 | 821 | The msg.value is not enough to cover Chainlink's fee. 822 | 823 | 824 | 825 | 826 | 827 | -------------------------------------------------------------------------------- /docs/games/CoinToss.md: -------------------------------------------------------------------------------- 1 | # CoinToss 2 | 3 | *Romuald Hog (based on Yakitori's Coin Toss)* 4 | 5 | > BetSwirl's Coin Toss game 6 | 7 | The game is played with a two-sided coin. The game's goal is to guess whether the lucky coin face will be Heads or Tails. 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### bank 14 | 15 | ```solidity 16 | function bank() external view returns (contract IBank) 17 | ``` 18 | 19 | The bank that manage to payout a won bet and collect a loss bet. 20 | 21 | 22 | 23 | 24 | #### Returns 25 | 26 | | Name | Type | Description | 27 | |---|---|---| 28 | | _0 | contract IBank | undefined | 29 | 30 | ### bets 31 | 32 | ```solidity 33 | function bets(uint256) external view returns (bool resolved, address user, address token, uint256 id, uint256 amount, uint256 blockNumber, uint256 payout, uint256 vrfCost) 34 | ``` 35 | 36 | Maps bets IDs to Bet information. 37 | 38 | 39 | 40 | #### Parameters 41 | 42 | | Name | Type | Description | 43 | |---|---|---| 44 | | _0 | uint256 | undefined | 45 | 46 | #### Returns 47 | 48 | | Name | Type | Description | 49 | |---|---|---| 50 | | resolved | bool | undefined | 51 | | user | address | undefined | 52 | | token | address | undefined | 53 | | id | uint256 | undefined | 54 | | amount | uint256 | undefined | 55 | | blockNumber | uint256 | undefined | 56 | | payout | uint256 | undefined | 57 | | vrfCost | uint256 | undefined | 58 | 59 | ### coinTossBets 60 | 61 | ```solidity 62 | function coinTossBets(uint256) external view returns (bool face, bool rolled) 63 | ``` 64 | 65 | Maps bets IDs to chosen and rolled coin faces. 66 | 67 | *Coin faces: true = Tails, false = Heads.* 68 | 69 | #### Parameters 70 | 71 | | Name | Type | Description | 72 | |---|---|---| 73 | | _0 | uint256 | undefined | 74 | 75 | #### Returns 76 | 77 | | Name | Type | Description | 78 | |---|---|---| 79 | | face | bool | undefined | 80 | | rolled | bool | undefined | 81 | 82 | ### getChainlinkConfig 83 | 84 | ```solidity 85 | function getChainlinkConfig() external view returns (uint16 requestConfirmations, bytes32 keyHash, contract IVRFCoordinatorV2 chainlinkCoordinator, uint256 gasAfterCalculation) 86 | ``` 87 | 88 | Returns the Chainlink VRF config. 89 | 90 | 91 | 92 | 93 | #### Returns 94 | 95 | | Name | Type | Description | 96 | |---|---|---| 97 | | requestConfirmations | uint16 | undefined | 98 | | keyHash | bytes32 | undefined | 99 | | chainlinkCoordinator | contract IVRFCoordinatorV2 | undefined | 100 | | gasAfterCalculation | uint256 | undefined | 101 | 102 | ### getChainlinkVRFCost 103 | 104 | ```solidity 105 | function getChainlinkVRFCost(address token) external view returns (uint256) 106 | ``` 107 | 108 | Returns the amount of ETH that should be passed to the wager transaction. to cover Chainlink VRF fee. 109 | 110 | 111 | 112 | #### Parameters 113 | 114 | | Name | Type | Description | 115 | |---|---|---| 116 | | token | address | undefined | 117 | 118 | #### Returns 119 | 120 | | Name | Type | Description | 121 | |---|---|---| 122 | | _0 | uint256 | The bet resolution cost amount. | 123 | 124 | ### getLastUserBets 125 | 126 | ```solidity 127 | function getLastUserBets(address user, uint256 dataLength) external view returns (struct CoinToss.FullCoinTossBet[]) 128 | ``` 129 | 130 | Gets the list of the last user bets. 131 | 132 | 133 | 134 | #### Parameters 135 | 136 | | Name | Type | Description | 137 | |---|---|---| 138 | | user | address | Address of the gamer. | 139 | | dataLength | uint256 | The amount of bets to return. | 140 | 141 | #### Returns 142 | 143 | | Name | Type | Description | 144 | |---|---|---| 145 | | _0 | CoinToss.FullCoinTossBet[] | A list of Coin Toss bet. | 146 | 147 | ### hasPendingBets 148 | 149 | ```solidity 150 | function hasPendingBets(address token) external view returns (bool) 151 | ``` 152 | 153 | Returns whether the token has pending bets. 154 | 155 | 156 | 157 | #### Parameters 158 | 159 | | Name | Type | Description | 160 | |---|---|---| 161 | | token | address | undefined | 162 | 163 | #### Returns 164 | 165 | | Name | Type | Description | 166 | |---|---|---| 167 | | _0 | bool | Whether the token has pending bets. | 168 | 169 | ### multicall 170 | 171 | ```solidity 172 | function multicall(bytes[] data) external nonpayable returns (bytes[] results) 173 | ``` 174 | 175 | 176 | 177 | *Receives and executes a batch of function calls on this contract.* 178 | 179 | #### Parameters 180 | 181 | | Name | Type | Description | 182 | |---|---|---| 183 | | data | bytes[] | undefined | 184 | 185 | #### Returns 186 | 187 | | Name | Type | Description | 188 | |---|---|---| 189 | | results | bytes[] | undefined | 190 | 191 | ### owner 192 | 193 | ```solidity 194 | function owner() external view returns (address) 195 | ``` 196 | 197 | 198 | 199 | *Returns the address of the current owner.* 200 | 201 | 202 | #### Returns 203 | 204 | | Name | Type | Description | 205 | |---|---|---| 206 | | _0 | address | undefined | 207 | 208 | ### pause 209 | 210 | ```solidity 211 | function pause() external nonpayable 212 | ``` 213 | 214 | Pauses the contract to disable new bets. 215 | 216 | 217 | 218 | 219 | ### paused 220 | 221 | ```solidity 222 | function paused() external view returns (bool) 223 | ``` 224 | 225 | 226 | 227 | *Returns true if the contract is paused, and false otherwise.* 228 | 229 | 230 | #### Returns 231 | 232 | | Name | Type | Description | 233 | |---|---|---| 234 | | _0 | bool | undefined | 235 | 236 | ### rawFulfillRandomWords 237 | 238 | ```solidity 239 | function rawFulfillRandomWords(uint256 requestId, uint256[] randomWords) external nonpayable 240 | ``` 241 | 242 | 243 | 244 | 245 | 246 | #### Parameters 247 | 248 | | Name | Type | Description | 249 | |---|---|---| 250 | | requestId | uint256 | undefined | 251 | | randomWords | uint256[] | undefined | 252 | 253 | ### refundBet 254 | 255 | ```solidity 256 | function refundBet(uint256 id) external nonpayable 257 | ``` 258 | 259 | Refunds the bet to the user if the Chainlink VRF callback failed. 260 | 261 | 262 | 263 | #### Parameters 264 | 265 | | Name | Type | Description | 266 | |---|---|---| 267 | | id | uint256 | The Bet ID. | 268 | 269 | ### renounceOwnership 270 | 271 | ```solidity 272 | function renounceOwnership() external nonpayable 273 | ``` 274 | 275 | 276 | 277 | *Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.* 278 | 279 | 280 | ### setChainlinkConfig 281 | 282 | ```solidity 283 | function setChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) external nonpayable 284 | ``` 285 | 286 | Sets the Chainlink VRF V2 configuration. 287 | 288 | 289 | 290 | #### Parameters 291 | 292 | | Name | Type | Description | 293 | |---|---|---| 294 | | requestConfirmations | uint16 | How many confirmations the Chainlink node should wait before responding. | 295 | | keyHash | bytes32 | Hash of the public key used to verify the VRF proof. | 296 | | gasAfterCalculation | uint256 | Gas to be added for VRF cost refund. | 297 | 298 | ### setHouseEdge 299 | 300 | ```solidity 301 | function setHouseEdge(address token, uint16 houseEdge) external nonpayable 302 | ``` 303 | 304 | Sets the game house edge rate for a specific token. 305 | 306 | *The house edge rate couldn't exceed 4%.* 307 | 308 | #### Parameters 309 | 310 | | Name | Type | Description | 311 | |---|---|---| 312 | | token | address | Address of the token. | 313 | | houseEdge | uint16 | House edge rate. | 314 | 315 | ### setVRFCallbackGasLimit 316 | 317 | ```solidity 318 | function setVRFCallbackGasLimit(address token, uint32 callbackGasLimit) external nonpayable 319 | ``` 320 | 321 | Sets the Chainlink VRF V2 configuration. 322 | 323 | 324 | 325 | #### Parameters 326 | 327 | | Name | Type | Description | 328 | |---|---|---| 329 | | token | address | undefined | 330 | | callbackGasLimit | uint32 | How much gas is needed in the Chainlink VRF callback. | 331 | 332 | ### tokens 333 | 334 | ```solidity 335 | function tokens(address) external view returns (uint16 houseEdge, uint64 pendingCount, uint32 VRFCallbackGasLimit, uint256 VRFFees) 336 | ``` 337 | 338 | Maps tokens addresses to token configuration. 339 | 340 | 341 | 342 | #### Parameters 343 | 344 | | Name | Type | Description | 345 | |---|---|---| 346 | | _0 | address | undefined | 347 | 348 | #### Returns 349 | 350 | | Name | Type | Description | 351 | |---|---|---| 352 | | houseEdge | uint16 | undefined | 353 | | pendingCount | uint64 | undefined | 354 | | VRFCallbackGasLimit | uint32 | undefined | 355 | | VRFFees | uint256 | undefined | 356 | 357 | ### transferOwnership 358 | 359 | ```solidity 360 | function transferOwnership(address newOwner) external nonpayable 361 | ``` 362 | 363 | 364 | 365 | *Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.* 366 | 367 | #### Parameters 368 | 369 | | Name | Type | Description | 370 | |---|---|---| 371 | | newOwner | address | undefined | 372 | 373 | ### userOverchargedVRFCost 374 | 375 | ```solidity 376 | function userOverchargedVRFCost(address) external view returns (uint256) 377 | ``` 378 | 379 | Maps user addresses to VRF overcharged cost. 380 | 381 | 382 | 383 | #### Parameters 384 | 385 | | Name | Type | Description | 386 | |---|---|---| 387 | | _0 | address | undefined | 388 | 389 | #### Returns 390 | 391 | | Name | Type | Description | 392 | |---|---|---| 393 | | _0 | uint256 | undefined | 394 | 395 | ### wager 396 | 397 | ```solidity 398 | function wager(bool face, address token, uint256 tokenAmount) external payable 399 | ``` 400 | 401 | Creates a new bet and stores the chosen coin face. 402 | 403 | 404 | 405 | #### Parameters 406 | 407 | | Name | Type | Description | 408 | |---|---|---| 409 | | face | bool | The chosen coin face. | 410 | | token | address | Address of the token. | 411 | | tokenAmount | uint256 | The number of tokens bet. | 412 | 413 | ### withdrawOverchargedVRFCost 414 | 415 | ```solidity 416 | function withdrawOverchargedVRFCost(address user) external nonpayable 417 | ``` 418 | 419 | Withdraw user's overcharged Chainlink fees. 420 | 421 | 422 | 423 | #### Parameters 424 | 425 | | Name | Type | Description | 426 | |---|---|---| 427 | | user | address | undefined | 428 | 429 | ### withdrawTokensVRFFees 430 | 431 | ```solidity 432 | function withdrawTokensVRFFees(address token) external nonpayable 433 | ``` 434 | 435 | Distributes the token's collected Chainlink fees. 436 | 437 | 438 | 439 | #### Parameters 440 | 441 | | Name | Type | Description | 442 | |---|---|---| 443 | | token | address | Address of the token. | 444 | 445 | 446 | 447 | ## Events 448 | 449 | ### AccountOverchargedVRFCost 450 | 451 | ```solidity 452 | event AccountOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 453 | ``` 454 | 455 | Emitted after the overcharged VRF cost amount is accounted. 456 | 457 | 458 | 459 | #### Parameters 460 | 461 | | Name | Type | Description | 462 | |---|---|---| 463 | | user `indexed` | address | undefined | 464 | | overchargedVRFCost | uint256 | undefined | 465 | 466 | ### BetRefunded 467 | 468 | ```solidity 469 | event BetRefunded(uint256 id, address user, uint256 amount, uint256 chainlinkVRFCost) 470 | ``` 471 | 472 | Emitted after the bet amount is transfered to the user. 473 | 474 | 475 | 476 | #### Parameters 477 | 478 | | Name | Type | Description | 479 | |---|---|---| 480 | | id | uint256 | undefined | 481 | | user | address | undefined | 482 | | amount | uint256 | undefined | 483 | | chainlinkVRFCost | uint256 | undefined | 484 | 485 | ### DistributeOverchargedVRFCost 486 | 487 | ```solidity 488 | event DistributeOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 489 | ``` 490 | 491 | Emitted after the user's overcharged VRF cost amount is transfered. 492 | 493 | 494 | 495 | #### Parameters 496 | 497 | | Name | Type | Description | 498 | |---|---|---| 499 | | user `indexed` | address | undefined | 500 | | overchargedVRFCost | uint256 | undefined | 501 | 502 | ### DistributeTokenVRFFees 503 | 504 | ```solidity 505 | event DistributeTokenVRFFees(address indexed token, uint256 amount) 506 | ``` 507 | 508 | Emitted after the token's VRF fees amount is transfered to the user. 509 | 510 | 511 | 512 | #### Parameters 513 | 514 | | Name | Type | Description | 515 | |---|---|---| 516 | | token `indexed` | address | undefined | 517 | | amount | uint256 | undefined | 518 | 519 | ### OwnershipTransferred 520 | 521 | ```solidity 522 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 523 | ``` 524 | 525 | 526 | 527 | 528 | 529 | #### Parameters 530 | 531 | | Name | Type | Description | 532 | |---|---|---| 533 | | previousOwner `indexed` | address | undefined | 534 | | newOwner `indexed` | address | undefined | 535 | 536 | ### Paused 537 | 538 | ```solidity 539 | event Paused(address account) 540 | ``` 541 | 542 | 543 | 544 | 545 | 546 | #### Parameters 547 | 548 | | Name | Type | Description | 549 | |---|---|---| 550 | | account | address | undefined | 551 | 552 | ### PlaceBet 553 | 554 | ```solidity 555 | event PlaceBet(uint256 id, address indexed user, address indexed token, uint256 amount, uint256 vrfCost, bool face) 556 | ``` 557 | 558 | Emitted after a bet is placed. 559 | 560 | 561 | 562 | #### Parameters 563 | 564 | | Name | Type | Description | 565 | |---|---|---| 566 | | id | uint256 | The bet ID. | 567 | | user `indexed` | address | Address of the gamer. | 568 | | token `indexed` | address | Address of the token. | 569 | | amount | uint256 | The bet amount. | 570 | | vrfCost | uint256 | The Chainlink VRF cost paid by player. | 571 | | face | bool | The chosen coin face. | 572 | 573 | ### Roll 574 | 575 | ```solidity 576 | event Roll(uint256 id, address indexed user, address indexed token, uint256 amount, bool face, bool rolled, uint256 payout) 577 | ``` 578 | 579 | Emitted after a bet is rolled. 580 | 581 | 582 | 583 | #### Parameters 584 | 585 | | Name | Type | Description | 586 | |---|---|---| 587 | | id | uint256 | The bet ID. | 588 | | user `indexed` | address | Address of the gamer. | 589 | | token `indexed` | address | Address of the token. | 590 | | amount | uint256 | The bet amount. | 591 | | face | bool | The chosen coin face. | 592 | | rolled | bool | The rolled coin face. | 593 | | payout | uint256 | The payout amount. | 594 | 595 | ### SetChainlinkConfig 596 | 597 | ```solidity 598 | event SetChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) 599 | ``` 600 | 601 | Emitted after the Chainlink config is set. 602 | 603 | 604 | 605 | #### Parameters 606 | 607 | | Name | Type | Description | 608 | |---|---|---| 609 | | requestConfirmations | uint16 | undefined | 610 | | keyHash | bytes32 | undefined | 611 | | gasAfterCalculation | uint256 | undefined | 612 | 613 | ### SetHouseEdge 614 | 615 | ```solidity 616 | event SetHouseEdge(address indexed token, uint16 houseEdge) 617 | ``` 618 | 619 | Emitted after the house edge is set for a token. 620 | 621 | 622 | 623 | #### Parameters 624 | 625 | | Name | Type | Description | 626 | |---|---|---| 627 | | token `indexed` | address | undefined | 628 | | houseEdge | uint16 | undefined | 629 | 630 | ### SetVRFCallbackGasLimit 631 | 632 | ```solidity 633 | event SetVRFCallbackGasLimit(address indexed token, uint32 callbackGasLimit) 634 | ``` 635 | 636 | Emitted after the Chainlink callback gas limit is set for a token. 637 | 638 | 639 | 640 | #### Parameters 641 | 642 | | Name | Type | Description | 643 | |---|---|---| 644 | | token `indexed` | address | undefined | 645 | | callbackGasLimit | uint32 | undefined | 646 | 647 | ### Unpaused 648 | 649 | ```solidity 650 | event Unpaused(address account) 651 | ``` 652 | 653 | 654 | 655 | 656 | 657 | #### Parameters 658 | 659 | | Name | Type | Description | 660 | |---|---|---| 661 | | account | address | undefined | 662 | 663 | 664 | 665 | ## Errors 666 | 667 | ### AccessDenied 668 | 669 | ```solidity 670 | error AccessDenied() 671 | ``` 672 | 673 | Reverting error when sender isn't allowed. 674 | 675 | 676 | 677 | 678 | ### ExcessiveHouseEdge 679 | 680 | ```solidity 681 | error ExcessiveHouseEdge() 682 | ``` 683 | 684 | House edge is capped at 4%. 685 | 686 | 687 | 688 | 689 | ### ForbiddenToken 690 | 691 | ```solidity 692 | error ForbiddenToken() 693 | ``` 694 | 695 | Token is not allowed. 696 | 697 | 698 | 699 | 700 | ### InvalidAddress 701 | 702 | ```solidity 703 | error InvalidAddress() 704 | ``` 705 | 706 | Reverting error when provided address isn't valid. 707 | 708 | 709 | 710 | 711 | ### InvalidLinkWeiPrice 712 | 713 | ```solidity 714 | error InvalidLinkWeiPrice(int256 linkWei) 715 | ``` 716 | 717 | Chainlink price feed not working 718 | 719 | 720 | 721 | #### Parameters 722 | 723 | | Name | Type | Description | 724 | |---|---|---| 725 | | linkWei | int256 | LINK/ETH price returned. | 726 | 727 | ### NoOverchargedVRFCost 728 | 729 | ```solidity 730 | error NoOverchargedVRFCost() 731 | ``` 732 | 733 | No user's overcharged Chainlink fee. 734 | 735 | 736 | 737 | 738 | ### NotFulfilled 739 | 740 | ```solidity 741 | error NotFulfilled() 742 | ``` 743 | 744 | Bet isn't resolved yet. 745 | 746 | 747 | 748 | 749 | ### NotPendingBet 750 | 751 | ```solidity 752 | error NotPendingBet() 753 | ``` 754 | 755 | Bet provided doesn't exist or was already resolved. 756 | 757 | 758 | 759 | 760 | ### OnlyCoordinatorCanFulfill 761 | 762 | ```solidity 763 | error OnlyCoordinatorCanFulfill(address have, address want) 764 | ``` 765 | 766 | 767 | 768 | 769 | 770 | #### Parameters 771 | 772 | | Name | Type | Description | 773 | |---|---|---| 774 | | have | address | undefined | 775 | | want | address | undefined | 776 | 777 | ### TokenHasPendingBets 778 | 779 | ```solidity 780 | error TokenHasPendingBets() 781 | ``` 782 | 783 | Reverting error when token has pending bets. 784 | 785 | 786 | 787 | 788 | ### UnderMinBetAmount 789 | 790 | ```solidity 791 | error UnderMinBetAmount(uint256 minBetAmount) 792 | ``` 793 | 794 | Insufficient bet amount. 795 | 796 | 797 | 798 | #### Parameters 799 | 800 | | Name | Type | Description | 801 | |---|---|---| 802 | | minBetAmount | uint256 | Bet amount. | 803 | 804 | ### WrongGasValueToCoverFee 805 | 806 | ```solidity 807 | error WrongGasValueToCoverFee() 808 | ``` 809 | 810 | The msg.value is not enough to cover Chainlink's fee. 811 | 812 | 813 | 814 | 815 | 816 | -------------------------------------------------------------------------------- /docs/games/Dice.md: -------------------------------------------------------------------------------- 1 | # Dice 2 | 3 | *Romuald Hog (based on Yakitori's Dice)* 4 | 5 | > BetSwirl's Dice game 6 | 7 | The game is played with a 100 sided dice. The game's goal is to guess whether the lucky number will be above your chosen number. 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### bank 14 | 15 | ```solidity 16 | function bank() external view returns (contract IBank) 17 | ``` 18 | 19 | The bank that manage to payout a won bet and collect a loss bet. 20 | 21 | 22 | 23 | 24 | #### Returns 25 | 26 | | Name | Type | Description | 27 | |---|---|---| 28 | | _0 | contract IBank | undefined | 29 | 30 | ### bets 31 | 32 | ```solidity 33 | function bets(uint256) external view returns (bool resolved, address user, address token, uint256 id, uint256 amount, uint256 blockNumber, uint256 payout, uint256 vrfCost) 34 | ``` 35 | 36 | Maps bets IDs to Bet information. 37 | 38 | 39 | 40 | #### Parameters 41 | 42 | | Name | Type | Description | 43 | |---|---|---| 44 | | _0 | uint256 | undefined | 45 | 46 | #### Returns 47 | 48 | | Name | Type | Description | 49 | |---|---|---| 50 | | resolved | bool | undefined | 51 | | user | address | undefined | 52 | | token | address | undefined | 53 | | id | uint256 | undefined | 54 | | amount | uint256 | undefined | 55 | | blockNumber | uint256 | undefined | 56 | | payout | uint256 | undefined | 57 | | vrfCost | uint256 | undefined | 58 | 59 | ### diceBets 60 | 61 | ```solidity 62 | function diceBets(uint256) external view returns (uint8 cap, uint8 rolled) 63 | ``` 64 | 65 | Maps bets IDs to chosen and rolled dice numbers. 66 | 67 | 68 | 69 | #### Parameters 70 | 71 | | Name | Type | Description | 72 | |---|---|---| 73 | | _0 | uint256 | undefined | 74 | 75 | #### Returns 76 | 77 | | Name | Type | Description | 78 | |---|---|---| 79 | | cap | uint8 | undefined | 80 | | rolled | uint8 | undefined | 81 | 82 | ### getChainlinkConfig 83 | 84 | ```solidity 85 | function getChainlinkConfig() external view returns (uint16 requestConfirmations, bytes32 keyHash, contract IVRFCoordinatorV2 chainlinkCoordinator, uint256 gasAfterCalculation) 86 | ``` 87 | 88 | Returns the Chainlink VRF config. 89 | 90 | 91 | 92 | 93 | #### Returns 94 | 95 | | Name | Type | Description | 96 | |---|---|---| 97 | | requestConfirmations | uint16 | undefined | 98 | | keyHash | bytes32 | undefined | 99 | | chainlinkCoordinator | contract IVRFCoordinatorV2 | undefined | 100 | | gasAfterCalculation | uint256 | undefined | 101 | 102 | ### getChainlinkVRFCost 103 | 104 | ```solidity 105 | function getChainlinkVRFCost(address token) external view returns (uint256) 106 | ``` 107 | 108 | Returns the amount of ETH that should be passed to the wager transaction. to cover Chainlink VRF fee. 109 | 110 | 111 | 112 | #### Parameters 113 | 114 | | Name | Type | Description | 115 | |---|---|---| 116 | | token | address | undefined | 117 | 118 | #### Returns 119 | 120 | | Name | Type | Description | 121 | |---|---|---| 122 | | _0 | uint256 | The bet resolution cost amount. | 123 | 124 | ### getLastUserBets 125 | 126 | ```solidity 127 | function getLastUserBets(address user, uint256 dataLength) external view returns (struct Dice.FullDiceBet[]) 128 | ``` 129 | 130 | Gets the list of the last user bets. 131 | 132 | 133 | 134 | #### Parameters 135 | 136 | | Name | Type | Description | 137 | |---|---|---| 138 | | user | address | Address of the gamer. | 139 | | dataLength | uint256 | The amount of bets to return. | 140 | 141 | #### Returns 142 | 143 | | Name | Type | Description | 144 | |---|---|---| 145 | | _0 | Dice.FullDiceBet[] | A list of Dice bet. | 146 | 147 | ### hasPendingBets 148 | 149 | ```solidity 150 | function hasPendingBets(address token) external view returns (bool) 151 | ``` 152 | 153 | Returns whether the token has pending bets. 154 | 155 | 156 | 157 | #### Parameters 158 | 159 | | Name | Type | Description | 160 | |---|---|---| 161 | | token | address | undefined | 162 | 163 | #### Returns 164 | 165 | | Name | Type | Description | 166 | |---|---|---| 167 | | _0 | bool | Whether the token has pending bets. | 168 | 169 | ### multicall 170 | 171 | ```solidity 172 | function multicall(bytes[] data) external nonpayable returns (bytes[] results) 173 | ``` 174 | 175 | 176 | 177 | *Receives and executes a batch of function calls on this contract.* 178 | 179 | #### Parameters 180 | 181 | | Name | Type | Description | 182 | |---|---|---| 183 | | data | bytes[] | undefined | 184 | 185 | #### Returns 186 | 187 | | Name | Type | Description | 188 | |---|---|---| 189 | | results | bytes[] | undefined | 190 | 191 | ### owner 192 | 193 | ```solidity 194 | function owner() external view returns (address) 195 | ``` 196 | 197 | 198 | 199 | *Returns the address of the current owner.* 200 | 201 | 202 | #### Returns 203 | 204 | | Name | Type | Description | 205 | |---|---|---| 206 | | _0 | address | undefined | 207 | 208 | ### pause 209 | 210 | ```solidity 211 | function pause() external nonpayable 212 | ``` 213 | 214 | Pauses the contract to disable new bets. 215 | 216 | 217 | 218 | 219 | ### paused 220 | 221 | ```solidity 222 | function paused() external view returns (bool) 223 | ``` 224 | 225 | 226 | 227 | *Returns true if the contract is paused, and false otherwise.* 228 | 229 | 230 | #### Returns 231 | 232 | | Name | Type | Description | 233 | |---|---|---| 234 | | _0 | bool | undefined | 235 | 236 | ### rawFulfillRandomWords 237 | 238 | ```solidity 239 | function rawFulfillRandomWords(uint256 requestId, uint256[] randomWords) external nonpayable 240 | ``` 241 | 242 | 243 | 244 | 245 | 246 | #### Parameters 247 | 248 | | Name | Type | Description | 249 | |---|---|---| 250 | | requestId | uint256 | undefined | 251 | | randomWords | uint256[] | undefined | 252 | 253 | ### refundBet 254 | 255 | ```solidity 256 | function refundBet(uint256 id) external nonpayable 257 | ``` 258 | 259 | Refunds the bet to the user if the Chainlink VRF callback failed. 260 | 261 | 262 | 263 | #### Parameters 264 | 265 | | Name | Type | Description | 266 | |---|---|---| 267 | | id | uint256 | The Bet ID. | 268 | 269 | ### renounceOwnership 270 | 271 | ```solidity 272 | function renounceOwnership() external nonpayable 273 | ``` 274 | 275 | 276 | 277 | *Leaves the contract without owner. It will not be possible to call `onlyOwner` functions anymore. Can only be called by the current owner. NOTE: Renouncing ownership will leave the contract without an owner, thereby removing any functionality that is only available to the owner.* 278 | 279 | 280 | ### setChainlinkConfig 281 | 282 | ```solidity 283 | function setChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) external nonpayable 284 | ``` 285 | 286 | Sets the Chainlink VRF V2 configuration. 287 | 288 | 289 | 290 | #### Parameters 291 | 292 | | Name | Type | Description | 293 | |---|---|---| 294 | | requestConfirmations | uint16 | How many confirmations the Chainlink node should wait before responding. | 295 | | keyHash | bytes32 | Hash of the public key used to verify the VRF proof. | 296 | | gasAfterCalculation | uint256 | Gas to be added for VRF cost refund. | 297 | 298 | ### setHouseEdge 299 | 300 | ```solidity 301 | function setHouseEdge(address token, uint16 houseEdge) external nonpayable 302 | ``` 303 | 304 | Sets the game house edge rate for a specific token. 305 | 306 | *The house edge rate couldn't exceed 4%.* 307 | 308 | #### Parameters 309 | 310 | | Name | Type | Description | 311 | |---|---|---| 312 | | token | address | Address of the token. | 313 | | houseEdge | uint16 | House edge rate. | 314 | 315 | ### setVRFCallbackGasLimit 316 | 317 | ```solidity 318 | function setVRFCallbackGasLimit(address token, uint32 callbackGasLimit) external nonpayable 319 | ``` 320 | 321 | Sets the Chainlink VRF V2 configuration. 322 | 323 | 324 | 325 | #### Parameters 326 | 327 | | Name | Type | Description | 328 | |---|---|---| 329 | | token | address | undefined | 330 | | callbackGasLimit | uint32 | How much gas is needed in the Chainlink VRF callback. | 331 | 332 | ### tokens 333 | 334 | ```solidity 335 | function tokens(address) external view returns (uint16 houseEdge, uint64 pendingCount, uint32 VRFCallbackGasLimit, uint256 VRFFees) 336 | ``` 337 | 338 | Maps tokens addresses to token configuration. 339 | 340 | 341 | 342 | #### Parameters 343 | 344 | | Name | Type | Description | 345 | |---|---|---| 346 | | _0 | address | undefined | 347 | 348 | #### Returns 349 | 350 | | Name | Type | Description | 351 | |---|---|---| 352 | | houseEdge | uint16 | undefined | 353 | | pendingCount | uint64 | undefined | 354 | | VRFCallbackGasLimit | uint32 | undefined | 355 | | VRFFees | uint256 | undefined | 356 | 357 | ### transferOwnership 358 | 359 | ```solidity 360 | function transferOwnership(address newOwner) external nonpayable 361 | ``` 362 | 363 | 364 | 365 | *Transfers ownership of the contract to a new account (`newOwner`). Can only be called by the current owner.* 366 | 367 | #### Parameters 368 | 369 | | Name | Type | Description | 370 | |---|---|---| 371 | | newOwner | address | undefined | 372 | 373 | ### userOverchargedVRFCost 374 | 375 | ```solidity 376 | function userOverchargedVRFCost(address) external view returns (uint256) 377 | ``` 378 | 379 | Maps user addresses to VRF overcharged cost. 380 | 381 | 382 | 383 | #### Parameters 384 | 385 | | Name | Type | Description | 386 | |---|---|---| 387 | | _0 | address | undefined | 388 | 389 | #### Returns 390 | 391 | | Name | Type | Description | 392 | |---|---|---| 393 | | _0 | uint256 | undefined | 394 | 395 | ### wager 396 | 397 | ```solidity 398 | function wager(uint8 cap, address token, uint256 tokenAmount) external payable 399 | ``` 400 | 401 | Creates a new bet and stores the chosen dice number. 402 | 403 | 404 | 405 | #### Parameters 406 | 407 | | Name | Type | Description | 408 | |---|---|---| 409 | | cap | uint8 | The chosen dice number. | 410 | | token | address | Address of the token. | 411 | | tokenAmount | uint256 | The number of tokens bet. | 412 | 413 | ### withdrawOverchargedVRFCost 414 | 415 | ```solidity 416 | function withdrawOverchargedVRFCost(address user) external nonpayable 417 | ``` 418 | 419 | Withdraw user's overcharged Chainlink fees. 420 | 421 | 422 | 423 | #### Parameters 424 | 425 | | Name | Type | Description | 426 | |---|---|---| 427 | | user | address | undefined | 428 | 429 | ### withdrawTokensVRFFees 430 | 431 | ```solidity 432 | function withdrawTokensVRFFees(address token) external nonpayable 433 | ``` 434 | 435 | Distributes the token's collected Chainlink fees. 436 | 437 | 438 | 439 | #### Parameters 440 | 441 | | Name | Type | Description | 442 | |---|---|---| 443 | | token | address | Address of the token. | 444 | 445 | 446 | 447 | ## Events 448 | 449 | ### AccountOverchargedVRFCost 450 | 451 | ```solidity 452 | event AccountOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 453 | ``` 454 | 455 | Emitted after the overcharged VRF cost amount is accounted. 456 | 457 | 458 | 459 | #### Parameters 460 | 461 | | Name | Type | Description | 462 | |---|---|---| 463 | | user `indexed` | address | undefined | 464 | | overchargedVRFCost | uint256 | undefined | 465 | 466 | ### BetRefunded 467 | 468 | ```solidity 469 | event BetRefunded(uint256 id, address user, uint256 amount, uint256 chainlinkVRFCost) 470 | ``` 471 | 472 | Emitted after the bet amount is transfered to the user. 473 | 474 | 475 | 476 | #### Parameters 477 | 478 | | Name | Type | Description | 479 | |---|---|---| 480 | | id | uint256 | undefined | 481 | | user | address | undefined | 482 | | amount | uint256 | undefined | 483 | | chainlinkVRFCost | uint256 | undefined | 484 | 485 | ### DistributeOverchargedVRFCost 486 | 487 | ```solidity 488 | event DistributeOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 489 | ``` 490 | 491 | Emitted after the user's overcharged VRF cost amount is transfered. 492 | 493 | 494 | 495 | #### Parameters 496 | 497 | | Name | Type | Description | 498 | |---|---|---| 499 | | user `indexed` | address | undefined | 500 | | overchargedVRFCost | uint256 | undefined | 501 | 502 | ### DistributeTokenVRFFees 503 | 504 | ```solidity 505 | event DistributeTokenVRFFees(address indexed token, uint256 amount) 506 | ``` 507 | 508 | Emitted after the token's VRF fees amount is transfered to the user. 509 | 510 | 511 | 512 | #### Parameters 513 | 514 | | Name | Type | Description | 515 | |---|---|---| 516 | | token `indexed` | address | undefined | 517 | | amount | uint256 | undefined | 518 | 519 | ### OwnershipTransferred 520 | 521 | ```solidity 522 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 523 | ``` 524 | 525 | 526 | 527 | 528 | 529 | #### Parameters 530 | 531 | | Name | Type | Description | 532 | |---|---|---| 533 | | previousOwner `indexed` | address | undefined | 534 | | newOwner `indexed` | address | undefined | 535 | 536 | ### Paused 537 | 538 | ```solidity 539 | event Paused(address account) 540 | ``` 541 | 542 | 543 | 544 | 545 | 546 | #### Parameters 547 | 548 | | Name | Type | Description | 549 | |---|---|---| 550 | | account | address | undefined | 551 | 552 | ### PlaceBet 553 | 554 | ```solidity 555 | event PlaceBet(uint256 id, address indexed user, address indexed token, uint256 amount, uint256 vrfCost, uint8 cap) 556 | ``` 557 | 558 | Emitted after a bet is placed. 559 | 560 | 561 | 562 | #### Parameters 563 | 564 | | Name | Type | Description | 565 | |---|---|---| 566 | | id | uint256 | The bet ID. | 567 | | user `indexed` | address | Address of the gamer. | 568 | | token `indexed` | address | Address of the token. | 569 | | amount | uint256 | The bet amount. | 570 | | vrfCost | uint256 | The Chainlink VRF cost paid by player. | 571 | | cap | uint8 | The chosen dice number. | 572 | 573 | ### Roll 574 | 575 | ```solidity 576 | event Roll(uint256 id, address indexed user, address indexed token, uint256 amount, uint8 cap, uint8 rolled, uint256 payout) 577 | ``` 578 | 579 | Emitted after a bet is rolled. 580 | 581 | 582 | 583 | #### Parameters 584 | 585 | | Name | Type | Description | 586 | |---|---|---| 587 | | id | uint256 | The bet ID. | 588 | | user `indexed` | address | Address of the gamer. | 589 | | token `indexed` | address | Address of the token. | 590 | | amount | uint256 | The bet amount. | 591 | | cap | uint8 | The chosen dice number. | 592 | | rolled | uint8 | The rolled dice number. | 593 | | payout | uint256 | The payout amount. | 594 | 595 | ### SetChainlinkConfig 596 | 597 | ```solidity 598 | event SetChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) 599 | ``` 600 | 601 | Emitted after the Chainlink config is set. 602 | 603 | 604 | 605 | #### Parameters 606 | 607 | | Name | Type | Description | 608 | |---|---|---| 609 | | requestConfirmations | uint16 | undefined | 610 | | keyHash | bytes32 | undefined | 611 | | gasAfterCalculation | uint256 | undefined | 612 | 613 | ### SetHouseEdge 614 | 615 | ```solidity 616 | event SetHouseEdge(address indexed token, uint16 houseEdge) 617 | ``` 618 | 619 | Emitted after the house edge is set for a token. 620 | 621 | 622 | 623 | #### Parameters 624 | 625 | | Name | Type | Description | 626 | |---|---|---| 627 | | token `indexed` | address | undefined | 628 | | houseEdge | uint16 | undefined | 629 | 630 | ### SetVRFCallbackGasLimit 631 | 632 | ```solidity 633 | event SetVRFCallbackGasLimit(address indexed token, uint32 callbackGasLimit) 634 | ``` 635 | 636 | Emitted after the Chainlink callback gas limit is set for a token. 637 | 638 | 639 | 640 | #### Parameters 641 | 642 | | Name | Type | Description | 643 | |---|---|---| 644 | | token `indexed` | address | undefined | 645 | | callbackGasLimit | uint32 | undefined | 646 | 647 | ### Unpaused 648 | 649 | ```solidity 650 | event Unpaused(address account) 651 | ``` 652 | 653 | 654 | 655 | 656 | 657 | #### Parameters 658 | 659 | | Name | Type | Description | 660 | |---|---|---| 661 | | account | address | undefined | 662 | 663 | 664 | 665 | ## Errors 666 | 667 | ### AccessDenied 668 | 669 | ```solidity 670 | error AccessDenied() 671 | ``` 672 | 673 | Reverting error when sender isn't allowed. 674 | 675 | 676 | 677 | 678 | ### CapNotInRange 679 | 680 | ```solidity 681 | error CapNotInRange(uint8 minCap, uint8 maxCap) 682 | ``` 683 | 684 | Provided cap is not within 1 and 99 included. 685 | 686 | 687 | 688 | #### Parameters 689 | 690 | | Name | Type | Description | 691 | |---|---|---| 692 | | minCap | uint8 | The minimum cap. | 693 | | maxCap | uint8 | The maximum cap. | 694 | 695 | ### ExcessiveHouseEdge 696 | 697 | ```solidity 698 | error ExcessiveHouseEdge() 699 | ``` 700 | 701 | House edge is capped at 4%. 702 | 703 | 704 | 705 | 706 | ### ForbiddenToken 707 | 708 | ```solidity 709 | error ForbiddenToken() 710 | ``` 711 | 712 | Token is not allowed. 713 | 714 | 715 | 716 | 717 | ### InvalidAddress 718 | 719 | ```solidity 720 | error InvalidAddress() 721 | ``` 722 | 723 | Reverting error when provided address isn't valid. 724 | 725 | 726 | 727 | 728 | ### InvalidLinkWeiPrice 729 | 730 | ```solidity 731 | error InvalidLinkWeiPrice(int256 linkWei) 732 | ``` 733 | 734 | Chainlink price feed not working 735 | 736 | 737 | 738 | #### Parameters 739 | 740 | | Name | Type | Description | 741 | |---|---|---| 742 | | linkWei | int256 | LINK/ETH price returned. | 743 | 744 | ### NoOverchargedVRFCost 745 | 746 | ```solidity 747 | error NoOverchargedVRFCost() 748 | ``` 749 | 750 | No user's overcharged Chainlink fee. 751 | 752 | 753 | 754 | 755 | ### NotFulfilled 756 | 757 | ```solidity 758 | error NotFulfilled() 759 | ``` 760 | 761 | Bet isn't resolved yet. 762 | 763 | 764 | 765 | 766 | ### NotPendingBet 767 | 768 | ```solidity 769 | error NotPendingBet() 770 | ``` 771 | 772 | Bet provided doesn't exist or was already resolved. 773 | 774 | 775 | 776 | 777 | ### OnlyCoordinatorCanFulfill 778 | 779 | ```solidity 780 | error OnlyCoordinatorCanFulfill(address have, address want) 781 | ``` 782 | 783 | 784 | 785 | 786 | 787 | #### Parameters 788 | 789 | | Name | Type | Description | 790 | |---|---|---| 791 | | have | address | undefined | 792 | | want | address | undefined | 793 | 794 | ### TokenHasPendingBets 795 | 796 | ```solidity 797 | error TokenHasPendingBets() 798 | ``` 799 | 800 | Reverting error when token has pending bets. 801 | 802 | 803 | 804 | 805 | ### UnderMinBetAmount 806 | 807 | ```solidity 808 | error UnderMinBetAmount(uint256 minBetAmount) 809 | ``` 810 | 811 | Insufficient bet amount. 812 | 813 | 814 | 815 | #### Parameters 816 | 817 | | Name | Type | Description | 818 | |---|---|---| 819 | | minBetAmount | uint256 | Bet amount. | 820 | 821 | ### WrongGasValueToCoverFee 822 | 823 | ```solidity 824 | error WrongGasValueToCoverFee() 825 | ``` 826 | 827 | The msg.value is not enough to cover Chainlink's fee. 828 | 829 | 830 | 831 | 832 | 833 | -------------------------------------------------------------------------------- /docs/games/Keno.md: -------------------------------------------------------------------------------- 1 | # Keno 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | ## Methods 12 | 13 | ### bank 14 | 15 | ```solidity 16 | function bank() external view returns (contract IBank) 17 | ``` 18 | 19 | 20 | 21 | 22 | 23 | 24 | #### Returns 25 | 26 | | Name | Type | Description | 27 | |---|---|---| 28 | | _0 | contract IBank | undefined | 29 | 30 | ### bets 31 | 32 | ```solidity 33 | function bets(uint256) external view returns (bool resolved, address user, address token, uint256 id, uint256 amount, uint256 blockNumber, uint256 payout, uint256 vrfCost) 34 | ``` 35 | 36 | 37 | 38 | 39 | 40 | #### Parameters 41 | 42 | | Name | Type | Description | 43 | |---|---|---| 44 | | _0 | uint256 | undefined | 45 | 46 | #### Returns 47 | 48 | | Name | Type | Description | 49 | |---|---|---| 50 | | resolved | bool | undefined | 51 | | user | address | undefined | 52 | | token | address | undefined | 53 | | id | uint256 | undefined | 54 | | amount | uint256 | undefined | 55 | | blockNumber | uint256 | undefined | 56 | | payout | uint256 | undefined | 57 | | vrfCost | uint256 | undefined | 58 | 59 | ### gain 60 | 61 | ```solidity 62 | function gain(address token, uint256 played, uint256 matchCount) external view returns (uint256 _factor) 63 | ``` 64 | 65 | 66 | 67 | 68 | 69 | #### Parameters 70 | 71 | | Name | Type | Description | 72 | |---|---|---| 73 | | token | address | undefined | 74 | | played | uint256 | undefined | 75 | | matchCount | uint256 | undefined | 76 | 77 | #### Returns 78 | 79 | | Name | Type | Description | 80 | |---|---|---| 81 | | _factor | uint256 | undefined | 82 | 83 | ### gains 84 | 85 | ```solidity 86 | function gains(address token) external view returns (uint256 biggestNumber, uint256 maxNumbersPlayed, uint256[] _gains) 87 | ``` 88 | 89 | 90 | 91 | 92 | 93 | #### Parameters 94 | 95 | | Name | Type | Description | 96 | |---|---|---| 97 | | token | address | undefined | 98 | 99 | #### Returns 100 | 101 | | Name | Type | Description | 102 | |---|---|---| 103 | | biggestNumber | uint256 | undefined | 104 | | maxNumbersPlayed | uint256 | undefined | 105 | | _gains | uint256[] | undefined | 106 | 107 | ### getChainlinkConfig 108 | 109 | ```solidity 110 | function getChainlinkConfig() external view returns (uint16 requestConfirmations, bytes32 keyHash, contract IVRFCoordinatorV2 chainlinkCoordinator, uint256 gasAfterCalculation) 111 | ``` 112 | 113 | 114 | 115 | 116 | 117 | 118 | #### Returns 119 | 120 | | Name | Type | Description | 121 | |---|---|---| 122 | | requestConfirmations | uint16 | undefined | 123 | | keyHash | bytes32 | undefined | 124 | | chainlinkCoordinator | contract IVRFCoordinatorV2 | undefined | 125 | | gasAfterCalculation | uint256 | undefined | 126 | 127 | ### getChainlinkVRFCost 128 | 129 | ```solidity 130 | function getChainlinkVRFCost(address token) external view returns (uint256) 131 | ``` 132 | 133 | 134 | 135 | 136 | 137 | #### Parameters 138 | 139 | | Name | Type | Description | 140 | |---|---|---| 141 | | token | address | undefined | 142 | 143 | #### Returns 144 | 145 | | Name | Type | Description | 146 | |---|---|---| 147 | | _0 | uint256 | undefined | 148 | 149 | ### getLastUserBets 150 | 151 | ```solidity 152 | function getLastUserBets(address user, uint256 dataLength) external view returns (struct Keno.FullKenoBet[]) 153 | ``` 154 | 155 | 156 | 157 | 158 | 159 | #### Parameters 160 | 161 | | Name | Type | Description | 162 | |---|---|---| 163 | | user | address | undefined | 164 | | dataLength | uint256 | undefined | 165 | 166 | #### Returns 167 | 168 | | Name | Type | Description | 169 | |---|---|---| 170 | | _0 | Keno.FullKenoBet[] | undefined | 171 | 172 | ### getNumbersOutOfRandomWord 173 | 174 | ```solidity 175 | function getNumbersOutOfRandomWord(address token, uint256 randomWord) external view returns (uint40) 176 | ``` 177 | 178 | 179 | 180 | 181 | 182 | #### Parameters 183 | 184 | | Name | Type | Description | 185 | |---|---|---| 186 | | token | address | undefined | 187 | | randomWord | uint256 | undefined | 188 | 189 | #### Returns 190 | 191 | | Name | Type | Description | 192 | |---|---|---| 193 | | _0 | uint40 | undefined | 194 | 195 | ### hasPendingBets 196 | 197 | ```solidity 198 | function hasPendingBets(address token) external view returns (bool) 199 | ``` 200 | 201 | 202 | 203 | 204 | 205 | #### Parameters 206 | 207 | | Name | Type | Description | 208 | |---|---|---| 209 | | token | address | undefined | 210 | 211 | #### Returns 212 | 213 | | Name | Type | Description | 214 | |---|---|---| 215 | | _0 | bool | undefined | 216 | 217 | ### kenoBets 218 | 219 | ```solidity 220 | function kenoBets(uint256) external view returns (uint40 numbers, uint40 rolled) 221 | ``` 222 | 223 | 224 | 225 | 226 | 227 | #### Parameters 228 | 229 | | Name | Type | Description | 230 | |---|---|---| 231 | | _0 | uint256 | undefined | 232 | 233 | #### Returns 234 | 235 | | Name | Type | Description | 236 | |---|---|---| 237 | | numbers | uint40 | undefined | 238 | | rolled | uint40 | undefined | 239 | 240 | ### multicall 241 | 242 | ```solidity 243 | function multicall(bytes[] data) external nonpayable returns (bytes[] results) 244 | ``` 245 | 246 | 247 | 248 | 249 | 250 | #### Parameters 251 | 252 | | Name | Type | Description | 253 | |---|---|---| 254 | | data | bytes[] | undefined | 255 | 256 | #### Returns 257 | 258 | | Name | Type | Description | 259 | |---|---|---| 260 | | results | bytes[] | undefined | 261 | 262 | ### owner 263 | 264 | ```solidity 265 | function owner() external view returns (address) 266 | ``` 267 | 268 | 269 | 270 | 271 | 272 | 273 | #### Returns 274 | 275 | | Name | Type | Description | 276 | |---|---|---| 277 | | _0 | address | undefined | 278 | 279 | ### pause 280 | 281 | ```solidity 282 | function pause() external nonpayable 283 | ``` 284 | 285 | 286 | 287 | 288 | 289 | 290 | ### paused 291 | 292 | ```solidity 293 | function paused() external view returns (bool) 294 | ``` 295 | 296 | 297 | 298 | 299 | 300 | 301 | #### Returns 302 | 303 | | Name | Type | Description | 304 | |---|---|---| 305 | | _0 | bool | undefined | 306 | 307 | ### rawFulfillRandomWords 308 | 309 | ```solidity 310 | function rawFulfillRandomWords(uint256 requestId, uint256[] randomWords) external nonpayable 311 | ``` 312 | 313 | 314 | 315 | 316 | 317 | #### Parameters 318 | 319 | | Name | Type | Description | 320 | |---|---|---| 321 | | requestId | uint256 | undefined | 322 | | randomWords | uint256[] | undefined | 323 | 324 | ### refundBet 325 | 326 | ```solidity 327 | function refundBet(uint256 id) external nonpayable 328 | ``` 329 | 330 | 331 | 332 | 333 | 334 | #### Parameters 335 | 336 | | Name | Type | Description | 337 | |---|---|---| 338 | | id | uint256 | undefined | 339 | 340 | ### renounceOwnership 341 | 342 | ```solidity 343 | function renounceOwnership() external nonpayable 344 | ``` 345 | 346 | 347 | 348 | 349 | 350 | 351 | ### setChainlinkConfig 352 | 353 | ```solidity 354 | function setChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) external nonpayable 355 | ``` 356 | 357 | 358 | 359 | 360 | 361 | #### Parameters 362 | 363 | | Name | Type | Description | 364 | |---|---|---| 365 | | requestConfirmations | uint16 | undefined | 366 | | keyHash | bytes32 | undefined | 367 | | gasAfterCalculation | uint256 | undefined | 368 | 369 | ### setHouseEdge 370 | 371 | ```solidity 372 | function setHouseEdge(address token, uint16 houseEdge) external nonpayable 373 | ``` 374 | 375 | 376 | 377 | 378 | 379 | #### Parameters 380 | 381 | | Name | Type | Description | 382 | |---|---|---| 383 | | token | address | undefined | 384 | | houseEdge | uint16 | undefined | 385 | 386 | ### setVRFCallbackGasLimit 387 | 388 | ```solidity 389 | function setVRFCallbackGasLimit(address token, uint32 callbackGasLimit) external nonpayable 390 | ``` 391 | 392 | 393 | 394 | 395 | 396 | #### Parameters 397 | 398 | | Name | Type | Description | 399 | |---|---|---| 400 | | token | address | undefined | 401 | | callbackGasLimit | uint32 | undefined | 402 | 403 | ### tokenConfigurations 404 | 405 | ```solidity 406 | function tokenConfigurations(address) external view returns (uint128 biggestNumber, uint128 maxNumbersPlayed) 407 | ``` 408 | 409 | 410 | 411 | 412 | 413 | #### Parameters 414 | 415 | | Name | Type | Description | 416 | |---|---|---| 417 | | _0 | address | undefined | 418 | 419 | #### Returns 420 | 421 | | Name | Type | Description | 422 | |---|---|---| 423 | | biggestNumber | uint128 | undefined | 424 | | maxNumbersPlayed | uint128 | undefined | 425 | 426 | ### tokens 427 | 428 | ```solidity 429 | function tokens(address) external view returns (uint16 houseEdge, uint64 pendingCount, uint32 VRFCallbackGasLimit, uint256 VRFFees) 430 | ``` 431 | 432 | 433 | 434 | 435 | 436 | #### Parameters 437 | 438 | | Name | Type | Description | 439 | |---|---|---| 440 | | _0 | address | undefined | 441 | 442 | #### Returns 443 | 444 | | Name | Type | Description | 445 | |---|---|---| 446 | | houseEdge | uint16 | undefined | 447 | | pendingCount | uint64 | undefined | 448 | | VRFCallbackGasLimit | uint32 | undefined | 449 | | VRFFees | uint256 | undefined | 450 | 451 | ### transferOwnership 452 | 453 | ```solidity 454 | function transferOwnership(address newOwner) external nonpayable 455 | ``` 456 | 457 | 458 | 459 | 460 | 461 | #### Parameters 462 | 463 | | Name | Type | Description | 464 | |---|---|---| 465 | | newOwner | address | undefined | 466 | 467 | ### updateTokenConfig 468 | 469 | ```solidity 470 | function updateTokenConfig(address token, uint128 newBiggestNumber, uint128 newMaxNumbers) external nonpayable 471 | ``` 472 | 473 | 474 | 475 | 476 | 477 | #### Parameters 478 | 479 | | Name | Type | Description | 480 | |---|---|---| 481 | | token | address | undefined | 482 | | newBiggestNumber | uint128 | undefined | 483 | | newMaxNumbers | uint128 | undefined | 484 | 485 | ### userOverchargedVRFCost 486 | 487 | ```solidity 488 | function userOverchargedVRFCost(address) external view returns (uint256) 489 | ``` 490 | 491 | 492 | 493 | 494 | 495 | #### Parameters 496 | 497 | | Name | Type | Description | 498 | |---|---|---| 499 | | _0 | address | undefined | 500 | 501 | #### Returns 502 | 503 | | Name | Type | Description | 504 | |---|---|---| 505 | | _0 | uint256 | undefined | 506 | 507 | ### wager 508 | 509 | ```solidity 510 | function wager(uint40 numbers, address token, uint256 tokenAmount) external payable 511 | ``` 512 | 513 | 514 | 515 | 516 | 517 | #### Parameters 518 | 519 | | Name | Type | Description | 520 | |---|---|---| 521 | | numbers | uint40 | undefined | 522 | | token | address | undefined | 523 | | tokenAmount | uint256 | undefined | 524 | 525 | ### withdrawOverchargedVRFCost 526 | 527 | ```solidity 528 | function withdrawOverchargedVRFCost(address user) external nonpayable 529 | ``` 530 | 531 | 532 | 533 | 534 | 535 | #### Parameters 536 | 537 | | Name | Type | Description | 538 | |---|---|---| 539 | | user | address | undefined | 540 | 541 | ### withdrawTokensVRFFees 542 | 543 | ```solidity 544 | function withdrawTokensVRFFees(address token) external nonpayable 545 | ``` 546 | 547 | 548 | 549 | 550 | 551 | #### Parameters 552 | 553 | | Name | Type | Description | 554 | |---|---|---| 555 | | token | address | undefined | 556 | 557 | 558 | 559 | ## Events 560 | 561 | ### AccountOverchargedVRFCost 562 | 563 | ```solidity 564 | event AccountOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 565 | ``` 566 | 567 | 568 | 569 | 570 | 571 | #### Parameters 572 | 573 | | Name | Type | Description | 574 | |---|---|---| 575 | | user `indexed` | address | undefined | 576 | | overchargedVRFCost | uint256 | undefined | 577 | 578 | ### BetRefunded 579 | 580 | ```solidity 581 | event BetRefunded(uint256 id, address user, uint256 amount, uint256 chainlinkVRFCost) 582 | ``` 583 | 584 | 585 | 586 | 587 | 588 | #### Parameters 589 | 590 | | Name | Type | Description | 591 | |---|---|---| 592 | | id | uint256 | undefined | 593 | | user | address | undefined | 594 | | amount | uint256 | undefined | 595 | | chainlinkVRFCost | uint256 | undefined | 596 | 597 | ### DistributeOverchargedVRFCost 598 | 599 | ```solidity 600 | event DistributeOverchargedVRFCost(address indexed user, uint256 overchargedVRFCost) 601 | ``` 602 | 603 | 604 | 605 | 606 | 607 | #### Parameters 608 | 609 | | Name | Type | Description | 610 | |---|---|---| 611 | | user `indexed` | address | undefined | 612 | | overchargedVRFCost | uint256 | undefined | 613 | 614 | ### DistributeTokenVRFFees 615 | 616 | ```solidity 617 | event DistributeTokenVRFFees(address indexed token, uint256 amount) 618 | ``` 619 | 620 | 621 | 622 | 623 | 624 | #### Parameters 625 | 626 | | Name | Type | Description | 627 | |---|---|---| 628 | | token `indexed` | address | undefined | 629 | | amount | uint256 | undefined | 630 | 631 | ### OwnershipTransferred 632 | 633 | ```solidity 634 | event OwnershipTransferred(address indexed previousOwner, address indexed newOwner) 635 | ``` 636 | 637 | 638 | 639 | 640 | 641 | #### Parameters 642 | 643 | | Name | Type | Description | 644 | |---|---|---| 645 | | previousOwner `indexed` | address | undefined | 646 | | newOwner `indexed` | address | undefined | 647 | 648 | ### Paused 649 | 650 | ```solidity 651 | event Paused(address account) 652 | ``` 653 | 654 | 655 | 656 | 657 | 658 | #### Parameters 659 | 660 | | Name | Type | Description | 661 | |---|---|---| 662 | | account | address | undefined | 663 | 664 | ### PlaceBet 665 | 666 | ```solidity 667 | event PlaceBet(uint256 id, address indexed user, address indexed token, uint256 amount, uint256 vrfCost, uint40 numbers) 668 | ``` 669 | 670 | 671 | 672 | 673 | 674 | #### Parameters 675 | 676 | | Name | Type | Description | 677 | |---|---|---| 678 | | id | uint256 | undefined | 679 | | user `indexed` | address | undefined | 680 | | token `indexed` | address | undefined | 681 | | amount | uint256 | undefined | 682 | | vrfCost | uint256 | undefined | 683 | | numbers | uint40 | undefined | 684 | 685 | ### Roll 686 | 687 | ```solidity 688 | event Roll(uint256 id, address indexed user, address indexed token, uint256 amount, uint40 numbers, uint40 rolled, uint256 payout) 689 | ``` 690 | 691 | 692 | 693 | 694 | 695 | #### Parameters 696 | 697 | | Name | Type | Description | 698 | |---|---|---| 699 | | id | uint256 | undefined | 700 | | user `indexed` | address | undefined | 701 | | token `indexed` | address | undefined | 702 | | amount | uint256 | undefined | 703 | | numbers | uint40 | undefined | 704 | | rolled | uint40 | undefined | 705 | | payout | uint256 | undefined | 706 | 707 | ### SetChainlinkConfig 708 | 709 | ```solidity 710 | event SetChainlinkConfig(uint16 requestConfirmations, bytes32 keyHash, uint256 gasAfterCalculation) 711 | ``` 712 | 713 | 714 | 715 | 716 | 717 | #### Parameters 718 | 719 | | Name | Type | Description | 720 | |---|---|---| 721 | | requestConfirmations | uint16 | undefined | 722 | | keyHash | bytes32 | undefined | 723 | | gasAfterCalculation | uint256 | undefined | 724 | 725 | ### SetHouseEdge 726 | 727 | ```solidity 728 | event SetHouseEdge(address indexed token, uint16 houseEdge) 729 | ``` 730 | 731 | 732 | 733 | 734 | 735 | #### Parameters 736 | 737 | | Name | Type | Description | 738 | |---|---|---| 739 | | token `indexed` | address | undefined | 740 | | houseEdge | uint16 | undefined | 741 | 742 | ### SetVRFCallbackGasLimit 743 | 744 | ```solidity 745 | event SetVRFCallbackGasLimit(address indexed token, uint32 callbackGasLimit) 746 | ``` 747 | 748 | 749 | 750 | 751 | 752 | #### Parameters 753 | 754 | | Name | Type | Description | 755 | |---|---|---| 756 | | token `indexed` | address | undefined | 757 | | callbackGasLimit | uint32 | undefined | 758 | 759 | ### TokenConfigUpdated 760 | 761 | ```solidity 762 | event TokenConfigUpdated(address token, uint128 newBiggestNumber, uint128 newMaxNumbers) 763 | ``` 764 | 765 | 766 | 767 | 768 | 769 | #### Parameters 770 | 771 | | Name | Type | Description | 772 | |---|---|---| 773 | | token | address | undefined | 774 | | newBiggestNumber | uint128 | undefined | 775 | | newMaxNumbers | uint128 | undefined | 776 | 777 | ### Unpaused 778 | 779 | ```solidity 780 | event Unpaused(address account) 781 | ``` 782 | 783 | 784 | 785 | 786 | 787 | #### Parameters 788 | 789 | | Name | Type | Description | 790 | |---|---|---| 791 | | account | address | undefined | 792 | 793 | 794 | 795 | ## Errors 796 | 797 | ### AccessDenied 798 | 799 | ```solidity 800 | error AccessDenied() 801 | ``` 802 | 803 | 804 | 805 | 806 | 807 | 808 | ### ExcessiveHouseEdge 809 | 810 | ```solidity 811 | error ExcessiveHouseEdge() 812 | ``` 813 | 814 | 815 | 816 | 817 | 818 | 819 | ### ForbiddenToken 820 | 821 | ```solidity 822 | error ForbiddenToken() 823 | ``` 824 | 825 | 826 | 827 | 828 | 829 | 830 | ### InvalidAddress 831 | 832 | ```solidity 833 | error InvalidAddress() 834 | ``` 835 | 836 | 837 | 838 | 839 | 840 | 841 | ### InvalidLinkWeiPrice 842 | 843 | ```solidity 844 | error InvalidLinkWeiPrice(int256 linkWei) 845 | ``` 846 | 847 | 848 | 849 | 850 | 851 | #### Parameters 852 | 853 | | Name | Type | Description | 854 | |---|---|---| 855 | | linkWei | int256 | undefined | 856 | 857 | ### InvalidSettings 858 | 859 | ```solidity 860 | error InvalidSettings() 861 | ``` 862 | 863 | 864 | 865 | 866 | 867 | 868 | ### NoOverchargedVRFCost 869 | 870 | ```solidity 871 | error NoOverchargedVRFCost() 872 | ``` 873 | 874 | 875 | 876 | 877 | 878 | 879 | ### NotFulfilled 880 | 881 | ```solidity 882 | error NotFulfilled() 883 | ``` 884 | 885 | 886 | 887 | 888 | 889 | 890 | ### NotPendingBet 891 | 892 | ```solidity 893 | error NotPendingBet() 894 | ``` 895 | 896 | 897 | 898 | 899 | 900 | 901 | ### NumbersNotInRange 902 | 903 | ```solidity 904 | error NumbersNotInRange() 905 | ``` 906 | 907 | 908 | 909 | 910 | 911 | 912 | ### OnlyCoordinatorCanFulfill 913 | 914 | ```solidity 915 | error OnlyCoordinatorCanFulfill(address have, address want) 916 | ``` 917 | 918 | 919 | 920 | 921 | 922 | #### Parameters 923 | 924 | | Name | Type | Description | 925 | |---|---|---| 926 | | have | address | undefined | 927 | | want | address | undefined | 928 | 929 | ### TokenHasPendingBets 930 | 931 | ```solidity 932 | error TokenHasPendingBets() 933 | ``` 934 | 935 | 936 | 937 | 938 | 939 | 940 | ### TooManyNumbersPlayed 941 | 942 | ```solidity 943 | error TooManyNumbersPlayed() 944 | ``` 945 | 946 | 947 | 948 | 949 | 950 | 951 | ### UnderMinBetAmount 952 | 953 | ```solidity 954 | error UnderMinBetAmount(uint256 minBetAmount) 955 | ``` 956 | 957 | 958 | 959 | 960 | 961 | #### Parameters 962 | 963 | | Name | Type | Description | 964 | |---|---|---| 965 | | minBetAmount | uint256 | undefined | 966 | 967 | ### WrongGasValueToCoverFee 968 | 969 | ```solidity 970 | error WrongGasValueToCoverFee() 971 | ``` 972 | 973 | 974 | 975 | 976 | 977 | 978 | 979 | --------------------------------------------------------------------------------