Skip to content

Instantly share code, notes, and snippets.

@Usamahafiz8
Created December 12, 2023 08:51
Show Gist options
  • Save Usamahafiz8/ef5a0456ae2bb105d810dac2acae9e4f to your computer and use it in GitHub Desktop.
Save Usamahafiz8/ef5a0456ae2bb105d810dac2acae9e4f to your computer and use it in GitHub Desktop.
Created using remix-ide: Realtime Ethereum Contract Compiler and Runtime. Load this file by pasting this gists URL or ID at https://remix.ethereum.org/#version=soljson-v0.8.22+commit.4fc1097e.js&optimize=false&runs=200&gist=
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BaccaratMultiTable {
address public admin;
struct Table {
uint256 NoOfGamers;
uint256 lossLimitPercentage;
bool tableClosed;
uint256 investmentSeats;
uint256 investmentCostPerSeat;
uint256 winnersReturnMultiplier;
HouseDetails house;
Gamer[] gamersList;
mapping(address => Gamer) gamerDetails;
Banker banker;
}
struct HouseDetails {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
}
struct Gamer {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
bool hasPlayed;
uint256 winMultiplier;
uint256 bet;
}
struct Banker {
uint256 totalBets;
uint256 totalInvestments;
}
Gamer[] gamersListMemory;
mapping(uint256 => Table) public tables;
uint256 public tableCount;
event TableCreated(
address indexed admin,
uint256 tableId,
uint256 NoOfGamers,
uint256 lossLimitPercentage
);
event TableClosed(uint256 tableId, bool tableClosed);
event HouseInvested(
uint256 tableId,
address indexed houseAccount,
uint256 houseInvestmentAmount
);
event SeatTaken(uint256 tableId, address indexed gamer, uint256 investment);
event GamerDetails(
uint256 tableId,
address indexed gamer,
uint256 investment,
uint256 profit,
uint256 loss
);
event SeatPurchased(
uint256 tableId,
address indexed investor,
uint256 seatsPurchased,
uint256 totalCost
);
event BetPlaced(uint256 tableId, address indexed gamer, uint256 betAmount);
event Payout(uint256 tableId, address indexed gamer, uint256 payout);
modifier onlyAdmin() {
require(msg.sender == admin, "Not authorized");
_;
}
constructor() {
admin = msg.sender;
}
function createTable(
uint256 _NoOfGamers,
uint256 _lossLimitPercentage,
uint256 _investmentSeats,
uint256 _investmentCostPerSeat,
uint256 _winnersReturnMultiplier
) external onlyAdmin {
Table storage newTable = tables[tableCount];
newTable.NoOfGamers = _NoOfGamers;
newTable.lossLimitPercentage = _lossLimitPercentage;
newTable.tableClosed = false;
newTable.investmentSeats = _investmentSeats;
newTable.investmentCostPerSeat = _investmentCostPerSeat;
newTable.winnersReturnMultiplier = _winnersReturnMultiplier;
newTable.house = HouseDetails({
account: address(0),
investment: 0,
profit: 0,
loss: 0
});
// Initialize gamersList by pushing elements from the memory array to the storage array
for (uint256 i = 0; i < gamersListMemory.length; i++) {
newTable.gamersList.push(gamersListMemory[i]);
}
// Note: You don't need to initialize gamerDetails mapping separately; it's created automatically
newTable.banker = Banker({totalBets: 0, totalInvestments: 0});
emit TableCreated(admin, tableCount, _NoOfGamers, _lossLimitPercentage);
tableCount++;
}
function closeTable(uint256 tableId) external onlyAdmin {
Table storage table = tables[tableId];
require(!table.tableClosed, "Table already closed");
table.tableClosed = true;
emit TableClosed(tableId, true);
}
function manageHouseInvestment(
uint256 tableId,
address investor,
uint256 seatsToPurchase
) external onlyAdmin {
Table storage table = tables[tableId];
require(!table.tableClosed, "Table is closed");
require(
seatsToPurchase > 0,
"Number of seats to purchase must be greater than zero"
);
uint256 totalCost = seatsToPurchase * table.investmentCostPerSeat;
require(
totalCost <= table.NoOfGamers,
"Insufficient funds to purchase seats"
);
table.NoOfGamers -= totalCost;
emit SeatPurchased(tableId, investor, seatsToPurchase, totalCost);
}
function joinTable(
uint256 tableId,
address gamerAddress,
uint256 bet
) external {
Table storage table = tables[tableId];
require(!table.tableClosed, "Table is closed");
require(
table.gamersList.length < table.NoOfGamers,
"All seats are taken"
);
require(
table.gamerDetails[gamerAddress].account == address(0),
"Gamer already has a seat"
);
uint256 minInvestmentPerSeat = table.NoOfGamers / table.investmentSeats;
require(minInvestmentPerSeat > 0, "Invalid total funds or seats");
uint256 finalInvestment = bet > minInvestmentPerSeat
? bet
: minInvestmentPerSeat;
require(
finalInvestment > minInvestmentPerSeat,
"Custom investment must be higher than the minimum preset"
);
Gamer memory newGamer = Gamer({
account: gamerAddress,
investment: finalInvestment,
profit: 0,
loss: 0,
hasPlayed: false,
winMultiplier: 0,
bet: finalInvestment
});
table.gamerDetails[gamerAddress] = newGamer;
table.gamersList.push(newGamer);
table.banker.totalBets += finalInvestment;
emit SeatTaken(tableId, gamerAddress, finalInvestment);
emit BetPlaced(tableId, gamerAddress, finalInvestment);
}
function manageGamerAction(
uint256 tableId,
address gamerAddress,
bool win
) external {
Table storage table = tables[tableId];
require(!table.tableClosed, "Table is closed");
require(
table.gamerDetails[gamerAddress].account != address(0),
"Gamer not found"
);
require(
!table.gamerDetails[gamerAddress].hasPlayed,
"Gamer has already played"
);
Gamer storage gamer = table.gamerDetails[gamerAddress];
gamer.hasPlayed = true;
if (win) {
gamer.profit = gamer.investment;
gamer.loss = 0;
} else {
gamer.profit = 0;
gamer.loss = gamer.investment;
}
if (win) {
table.house.loss += gamer.investment;
} else {
table.house.profit += gamer.investment;
}
emit GamerDetails(
tableId,
gamerAddress,
gamer.investment,
gamer.profit,
gamer.loss
);
if (!win && gamer.loss >= calculateLossLimit(tableId)) {
uint256 houseWinAmount = calculateLossLimit(tableId);
table.house.loss += houseWinAmount;
table.NoOfGamers -= houseWinAmount;
emit GamerDetails(
tableId,
table.house.account,
table.house.investment,
table.house.profit,
table.house.loss
);
}
if (table.tableClosed || (win && shouldGamerWin(tableId))) {
gamer.winMultiplier = table.winnersReturnMultiplier;
uint256 payout = gamer.bet * gamer.winMultiplier;
table.banker.totalBets -= gamer.bet;
table.banker.totalInvestments += payout;
emit Payout(tableId, gamerAddress, payout);
}
}
function shouldGamerWin(uint256 tableId) public view returns (bool) {
Table storage table = tables[tableId];
return table.tableClosed;
}
function getTableDetails(uint256 tableId)
external
view
returns (
uint256,
uint256,
uint256,
uint256,
bool,
uint256,
uint256,
uint256,
uint256,
uint256,
uint256,
uint256
)
{
Table storage table = tables[tableId];
return (
table.NoOfGamers,
table.lossLimitPercentage,
table.investmentSeats,
table.investmentCostPerSeat,
table.tableClosed,
table.house.investment,
table.house.profit,
table.house.loss,
table.gamersList.length,
table.winnersReturnMultiplier,
table.banker.totalBets,
table.banker.totalInvestments
);
}
function calculateLossLimit(uint256 tableId) public view returns (uint256) {
Table storage table = tables[tableId];
return (table.NoOfGamers * table.lossLimitPercentage) / 100;
}
}
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BaccaratPoolManager {
address public admin;
// Details for houseRoll
struct HouseDetails {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
}
// Details for gamers
struct Gamer {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
}
// Details for each table
struct TableDetails {
uint256 totalFunds;
uint256 seats;
uint256 lossLimitPercentage;
bool tableClosed;
HouseDetails house;
mapping(address => Gamer) gamers;
Gamer[] gamersArray;
}
// Mapping to store table details by table ID
mapping(uint256 => TableDetails) public tables;
uint256 public tableCount;
event TableCreated(
uint256 indexed tableId,
address indexed admin,
uint256 totalFunds,
uint256 seats,
uint256 lossLimitPercentage
);
event TableClosed(uint256 indexed tableId, bool tableClosed);
event HouseInvested(
uint256 indexed tableId,
address indexed houseAccount,
uint256 houseInvestmentAmount
);
event SeatTaken(uint256 indexed tableId, address indexed gamer, uint256 investment);
event GamerDetails(
uint256 indexed tableId,
address indexed gamer,
uint256 investment,
uint256 profit,
uint256 loss
);
modifier onlyAdmin() {
require(msg.sender == admin, "Not authorized");
_;
}
constructor() {
admin = msg.sender;
}
function createTable(
uint256 _totalFunds,
uint256 _seats,
uint256 _lossLimitPercentage
) external onlyAdmin {
tableCount++;
TableDetails storage newTable = tables[tableCount];
newTable.totalFunds = _totalFunds;
newTable.seats = _seats;
newTable.lossLimitPercentage = _lossLimitPercentage;
newTable.tableClosed = false;
newTable.house = HouseDetails({
account: address(0),
investment: 0,
profit: 0,
loss: 0
});
emit TableCreated(tableCount, admin, _totalFunds, _seats, _lossLimitPercentage);
}
function closeTable(uint256 tableId) external onlyAdmin {
TableDetails storage table = tables[tableId];
require(!table.tableClosed, "Table already closed");
table.tableClosed = true;
emit TableClosed(tableId, table.tableClosed);
}
function manageHouseInvestment(
uint256 tableId,
address houseAccount,
uint256 investment
) external onlyAdmin {
TableDetails storage table = tables[tableId];
require(!table.tableClosed, "Table is closed");
require(investment > 0, "Investment must be greater than zero");
if (houseAccount == admin) {
table.house = HouseDetails({
account: houseAccount,
investment: investment,
profit: 0,
loss: 0
});
emit HouseInvested(tableId, houseAccount, investment);
} else {
revert("Invalid house account");
}
}
function manageGamerAction(
uint256 tableId,
address gamerAddress,
uint256 investment,
bool win
) external {
TableDetails storage table = tables[tableId];
require(!table.tableClosed, "Table is closed");
require(investment > 0, "Investment must be greater than zero");
require(table.gamersArray.length < table.seats, "All seats are taken");
require(table.gamers[gamerAddress].account == address(0), "Gamer already has a seat");
// Store gamer details
Gamer memory newGamer = Gamer({
account: gamerAddress,
investment: investment,
profit: win ? investment : 0,
loss: win ? 0 : investment
});
// Store gamer details by address
table.gamers[gamerAddress] = newGamer;
table.gamersArray.push(newGamer);
// Store gamer address and investment together
emit SeatTaken(tableId, gamerAddress, investment);
emit GamerDetails(tableId, gamerAddress, investment, newGamer.profit, newGamer.loss);
// Update house roll
if (win) {
table.house.loss += investment;
} else {
table.house.profit += investment;
}
}
function getTableDetails(uint256 tableId)
external
view
returns (
uint256,
uint256,
uint256,
bool,
uint256,
uint256,
uint256,
uint256
)
{
TableDetails storage table = tables[tableId];
return (
table.totalFunds,
table.seats,
table.lossLimitPercentage,
table.tableClosed,
table.house.investment,
table.house.profit,
table.house.loss,
table.gamersArray.length
);
}
function calculateLossLimit(uint256 tableId) public view returns (uint256) {
TableDetails storage table = tables[tableId];
return (table.totalFunds * table.lossLimitPercentage) / 100;
}
}
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BaccaratPoolTable {
address public admin;
uint256 public NoOfGamers;
uint256 public lossLimitPercentage;
bool public tableClosed;
uint256 public investmentSeats;
uint256 public investmentCostPerSeat;
uint256 public winnersReturnMultiplier;
// Details for houseRoll
struct HouseDetails {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
}
HouseDetails public house;
// Details for gamers
struct Gamer {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
bool hasPlayed; // Flag to track whether the gamer has played or not
uint256 winMultiplier; // Multiplier for the gamer's win
uint256 bet; // Gamer's bet on the table
}
Gamer[] public gamersList;
mapping(address => Gamer) public gamerDetails; // Mapping to store gamer details by address
// Banker to manage bets and payouts
struct Banker {
uint256 totalBets;
uint256 totalInvestments;
}
Banker public banker;
event TableCreated(
address indexed admin,
uint256 NoOfGamers,
uint256 lossLimitPercentage
);
event TableClosed(bool tableClosed);
event HouseInvested(
address indexed houseAccount,
uint256 houseInvestmentAmount
);
event SeatTaken(address indexed gamer, uint256 investment);
event GamerDetails(
address indexed gamer,
uint256 investment,
uint256 profit,
uint256 loss
);
event SeatPurchased(address indexed investor, uint256 seatsPurchased, uint256 totalCost);
event BetPlaced(address indexed gamer, uint256 betAmount);
event Payout(address indexed gamer, uint256 payout);
modifier onlyAdmin() {
require(msg.sender == admin, "Not authorized");
_;
}
constructor(
uint256 _NoOfGamers,
uint256 _lossLimitPercentage,
uint256 _investmentSeats,
uint256 _investmentCostPerSeat,
uint256 _winnersReturnMultiplier
) {
admin = msg.sender;
NoOfGamers = _NoOfGamers;
lossLimitPercentage = _lossLimitPercentage;
tableClosed = false;
investmentSeats = _investmentSeats;
investmentCostPerSeat = _investmentCostPerSeat;
winnersReturnMultiplier = _winnersReturnMultiplier;
emit TableCreated(admin, _NoOfGamers, _lossLimitPercentage);
}
function closeTable() external onlyAdmin {
require(!tableClosed, "Table already closed");
tableClosed = true;
emit TableClosed(tableClosed);
}
function manageHouseInvestment(address investor, uint256 seatsToPurchase) external onlyAdmin {
require(!tableClosed, "Table is closed");
require(seatsToPurchase > 0, "Number of seats to purchase must be greater than zero");
// Calculate the total cost for the investor to purchase seats
uint256 totalCost = seatsToPurchase * investmentCostPerSeat;
// Ensure the investor has enough funds
require(totalCost <= NoOfGamers, "Insufficient funds to purchase seats");
// Update total funds
NoOfGamers -= totalCost;
// Emit event for seat purchase
emit SeatPurchased(investor, seatsToPurchase, totalCost);
}
function joinTable(address gamerAddress, uint256 bet) external {
require(!tableClosed, "Table is closed");
require(gamersList.length < NoOfGamers, "All seats are taken");
require(gamerDetails[gamerAddress].account == address(0), "Gamer already has a seat");
// Calculate minimum investment per seat
uint256 minInvestmentPerSeat = NoOfGamers / investmentSeats;
require(minInvestmentPerSeat > 0, "Invalid total funds or seats");
// Set the gamer's investment to the higher of the preset minimum or the custom investment
uint256 finalInvestment = bet > minInvestmentPerSeat ? bet : minInvestmentPerSeat;
// Ensure the custom investment is higher than the minimum preset
require(finalInvestment > minInvestmentPerSeat, "Custom investment must be higher than the minimum preset");
// Store gamer details
Gamer memory newGamer = Gamer({
account: gamerAddress,
investment: finalInvestment,
profit: 0,
loss: 0,
hasPlayed: false,
winMultiplier: 0,
bet: finalInvestment // Initialize the gamer's bet on the table
});
// Store gamer details by address
gamerDetails[gamerAddress] = newGamer;
gamersList.push(newGamer);
// Update banker's total bets
banker.totalBets += finalInvestment;
// Store gamer address and investment together
emit SeatTaken(gamerAddress, finalInvestment);
emit BetPlaced(gamerAddress, finalInvestment);
}
function manageGamerAction(address gamerAddress, bool win) external {
require(!tableClosed, "Table is closed");
require(gamerDetails[gamerAddress].account != address(0), "Gamer not found");
require(!gamerDetails[gamerAddress].hasPlayed, "Gamer has already played");
// Update gamer details
Gamer storage gamer = gamerDetails[gamerAddress];
gamer.hasPlayed = true;
// Set win and loss based on the provided parameter
if (win) {
gamer.profit = gamer.investment;
gamer.loss = 0;
} else {
gamer.profit = 0;
gamer.loss = gamer.investment;
}
// Update house roll
if (win) {
house.loss += gamer.investment;
} else {
house.profit += gamer.investment;
}
emit GamerDetails(gamerAddress, gamer.investment, gamer.profit, gamer.loss);
// Check if the gamer's loss triggers the house investor win
if (!win && gamer.loss >= calculateLossLimit()) {
uint256 houseWinAmount = calculateLossLimit();
house.loss += houseWinAmount;
NoOfGamers -= houseWinAmount;
emit GamerDetails(house.account, house.investment, house.profit, house.loss);
}
// Check if the table is closed or the gamer wins
if (tableClosed || (win && shouldGamerWin())) {
// If the table is closed or the gamer wins, update the win boolean
gamer.winMultiplier = winnersReturnMultiplier;
// Calculate payout for the gamer
uint256 payout = gamer.bet * gamer.winMultiplier;
// Update gamer's profit and banker's total investments
gamer.profit += payout;
banker.totalInvestments += payout;
// Emit payout event
emit Payout(gamerAddress, payout);
}
}
function shouldGamerWin() public view returns (bool) {
// Implement your logic to determine if the gamer should win based on your game rules
// For now, let's assume the gamer always wins if the table is closed
return tableClosed;
}
function getTableDetails() external view returns (
uint256, // NoOfGamers
uint256, // lossLimitPercentage
uint256, // investmentSeats
uint256, // investmentCostPerSeat
bool, // tableClosed
uint256, // house.investment
uint256, // house.profit
uint256, // house.loss
uint256, // gamersList.length
uint256, // winnersReturnMultiplier
uint256, // banker.totalBets
uint256 // banker.totalInvestments
) {
return (
NoOfGamers,
lossLimitPercentage,
investmentSeats,
investmentCostPerSeat,
tableClosed,
house.investment,
house.profit,
house.loss,
gamersList.length,
winnersReturnMultiplier,
banker.totalBets,
banker.totalInvestments
);
}
function calculateLossLimit() public view returns (uint256) {
return (NoOfGamers * lossLimitPercentage) / 100;
}
}
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BaccaratPoolTable {
address public admin;
uint256 public totalFunds;
uint256 public maxGamers;
uint256 public lossLimitPercentage;
bool public tableClosed;
uint256 public winnersReturnMultiplier;
// Details for houseRoll
struct HouseDetails {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
}
HouseDetails public house;
// Details for gamers
struct Gamer {
address account;
uint256 investment;
uint256 profit;
uint256 loss;
bool hasPlayed; // Flag to track whether the gamer has played or not
uint256 winningNumber; // Number associated with the win
}
mapping(address => Gamer) public gamerDetails; // Mapping to store gamer details by address
Gamer[] public gamers;
event TableCreated(
address indexed admin,
uint256 totalFunds,
uint256 maxGamers,
uint256 lossLimitPercentage,
uint256 winnersReturnMultiplier
);
event TableClosed(bool tableClosed);
event HouseInvested(
address indexed houseAccount,
uint256 houseInvestmentAmount
);
event SeatTaken(address indexed gamer, uint256 investment);
event GamerDetails(
address indexed gamer,
uint256 investment,
uint256 profit,
uint256 loss
);
event WinnersReturnMultiplierSet(uint256 winnersReturnMultiplier);
modifier onlyAdmin() {
require(msg.sender == admin, "Not authorized");
_;
}
constructor(
uint256 _totalFunds,
uint256 _maxGamers,
uint256 _lossLimitPercentage,
uint256 _winnersReturnMultiplier
) {
admin = msg.sender;
totalFunds = _totalFunds;
maxGamers = _maxGamers;
lossLimitPercentage = _lossLimitPercentage;
tableClosed = false;
winnersReturnMultiplier = _winnersReturnMultiplier;
emit TableCreated(admin, _totalFunds, _maxGamers, _lossLimitPercentage, _winnersReturnMultiplier);
}
function closeTable() external onlyAdmin {
require(!tableClosed, "Table already closed");
tableClosed = true;
emit TableClosed(tableClosed);
}
function setWinnersReturnMultiplier(uint256 multiplier) external onlyAdmin {
require(multiplier > 0, "Multiplier must be greater than zero");
winnersReturnMultiplier = multiplier;
emit WinnersReturnMultiplierSet(multiplier);
}
function manageHouseInvestment(address houseAccount, uint256 investment) external onlyAdmin {
require(!tableClosed, "Table is closed");
require(investment > 0, "Investment must be greater than zero");
if (houseAccount == admin) {
house = HouseDetails({
account: houseAccount,
investment: investment,
profit: 0,
loss: 0
});
emit HouseInvested(houseAccount, investment);
} else {
revert("Invalid house account");
}
}
function joinTable(address gamerAddress, uint256 bet) external {
require(!tableClosed, "Table is closed");
require(gamers.length < maxGamers, "All gamers' seats are taken");
require(gamerDetails[gamerAddress].account == address(0), "Gamer already has a seat");
// Calculate minimum investment per gamer's seat
uint256 minInvestmentPerGamer = totalFunds / maxGamers;
require(minInvestmentPerGamer > 0, "Invalid total funds or maxGamers");
// Set the gamer's investment to the higher of the preset minimum or the custom bet
uint256 finalInvestment = bet > minInvestmentPerGamer ? bet : minInvestmentPerGamer;
// Ensure the custom bet is higher than the minimum preset
require(finalInvestment > minInvestmentPerGamer, "Custom bet must be higher than the minimum preset");
// Store gamer details
Gamer memory newGamer = Gamer({
account: gamerAddress,
investment: finalInvestment,
profit: 0,
loss: 0,
hasPlayed: false,
winningNumber: 0
});
// Store gamer details by address
gamerDetails[gamerAddress] = newGamer;
gamers.push(newGamer);
// Store gamer address and investment together
emit SeatTaken(gamerAddress, finalInvestment);
}
function manageGamerAction(address gamerAddress, uint256 winningNumber) external {
require(!tableClosed, "Table is closed");
require(gamerDetails[gamerAddress].account != address(0), "Gamer not found");
require(!gamerDetails[gamerAddress].hasPlayed, "Gamer has already played");
// Update gamer details
Gamer storage gamer = gamerDetails[gamerAddress];
gamer.hasPlayed = true;
gamer.winningNumber = winningNumber;
gamer.profit = winningNumber > 0 ? gamer.investment * winnersReturnMultiplier : 0;
gamer.loss = winningNumber > 0 ? 0 : gamer.investment;
// Update house roll
if (winningNumber > 0) {
house.loss += gamer.investment;
} else {
house.profit += gamer.investment;
}
emit GamerDetails(gamerAddress, gamer.investment, gamer.profit, gamer.loss);
}
function getTableDetails() external view returns (uint256, uint256, uint256, bool, uint256, uint256, uint256, uint256, uint256) {
return (totalFunds, maxGamers, lossLimitPercentage, tableClosed, house.investment, house.profit, house.loss, gamers.length, winnersReturnMultiplier);
}
function calculateLossLimit() public view returns (uint256) {
return (totalFunds * lossLimitPercentage) / 100;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment