Programming Project - Phase 1

Hey @Spartak

I was checking the code you wrote above, can you also post your contract "./Random.sol"; so that I can fully test it?

Thanks
Dani

1 Like

After so many days of coding! I’m too scared to stylize the radio buttons, I might mess up my code again :grimacing: :laughing:
Here’s an actual video:
https://www.youtube.com/watch?v=5NrhVVdgqNw

Some screenshots:


Great thanks to everyone in the academy for letting us create our own project. It really hits different when you code on your own instead of just following the stuff you see on Filip’s videos. Ready for Phase 2!

1 Like
pragma solidity ^0.5.12;


contract Random{

  function flipHead() public returns( bool ){
    uint flip = now % 2;
    if( flip == 0 ){
      return false;
    }
    else{
      return true;
    }
  }

}

omg this is so cool. Feels amazing so finally get my first dapp to work!!

1 Like

Hi @Spartak

There are some things in your contracts which I would like you to think about :slight_smile:

You have declared a struct but you don’t have any mapping pointing to it.
You are also not using your struct at all in this smart contract.

Although a struct is not necessary at this stage of the project, you can surely use it as long as it is implemented correctly.

Also, as suggested to other students, I would make sure that the contract has enough balance to pay the user in case of a victory.

What happens if your contract balance is 1 eth, but the customer payout is 2 eth?

Happy coding,
Dani

1 Like

Happy to hear that you liked the project, now it’s time for phase two !

Thanks Dani! I still have a few finishing touches for it before I move on.
But I have a question.
I’ve set my initial contract balance by just

uint balance = 1 ether.

How would you set it up in the real world, where I would actually need to deposit initial eth into the balance.

I remember it was something to do with an initializing file which Philip explained but I can’t find the vid.

Hey @Atheal

What you have done here uint balance = 1 ether. is just initialise a variable called balance to 10 ** 18 (1 Ether).
That does not mean that you contract balance is one ether.

In order to send Ether to the contract you have to make a transaction where you effectively send ethers, you can do it in your migration file or create a payable function in your smart contract.

Happy learning,
Dani

2 Likes

I’m not sure why the Dapp doesnt send ether back to owner when they win. Is there anything wrong with my code Dani?
The winnings does actually get saved to the ‘toReward’ variable but it just doesnt pay out on Metamask the matamask account balance never increases.



What are your thoughts on this new code @dan-i ? Any suggestions?

Hey @Atheal

In the screenshot you’ve posted I do not see where the function winOrLose is called.
Can you please push your project to Github and send me the link?

Thanks,
Dani

1 Like

Sure, here it is : https://github.com/Atheal9k/coinFlip/tree/master

I may have a few useless functions and variables in there as tests :sweat_smile:

1 Like

@Atheal

The issue is here :slight_smile:

function winOrLose() internal returns (uint){
        if (result == 1){
            //pay player
            uint toReward = betAmount*2;

            msg.sender.transfer(betAmount);

Look at your function above:

uint toReward = betAmount*2;

Look at what you are transferring.

 msg.sender.transfer(betAmount);

Anything strange?

Let me know !
Dani

2 Likes

I’m happy and shocked at the same time.
Spent the whole night trying to fix that…

Thanks Dani that worked, you’re awesome!

1 Like

Hello,

thank you very much for your help. I was able to run it but unfortunately only once.

  1. After the first time I got this error:
MetaMask - RPC Error: Error: [ethjs-rpc] rpc error with payload {"id":4343814116127,"jsonrpc":"2.0","params":["0xf8ac018504a817c8008302d2b3946623444594c3555f9652ad1ed273f8317a55b35f80b84454965b8500000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001822d45a06e39bdc2af545d1645ad9d79a8018fd4911602b4cf07e1a3a2f17be6b06b4492a013176a958e68671885ab0ad5377763f4641d74f50e891893858670bd25aafdb5"],"method":"eth_sendRawTransaction"} [object Object] {code: -32603, message: "Error: [ethjs-rpc] rpc error with payload {"id":43…method":"eth_sendRawTransaction"} [object Object]", stack: "Error: Error: [ethjs-rpc] rpc error with payload {…method":"eth_sendRawTransaction"} [object Object]"}

and

Uncaught (in promise) {code: -32603, message: "Error: [ethjs-rpc] rpc error with payload {"id":43…method":"eth_sendRawTransaction"} [object Object]", stack: "Error: Error: [ethjs-rpc] rpc error with payload {…method":"eth_sendRawTransaction"} [object Object]"}
(anonymous) @ web3.min.js:1
setTimeout (async)
_fireError @ web3.min.js:1
u @ web3.min.js:1
(anonymous) @ web3.min.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
i @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
c @ inpage.js:1
(anonymous) @ inpage.js:1
Bt @ inpage.js:1
(anonymous) @ inpage.js:1
_runReturnHandlersUp @ inpage.js:1
(anonymous) @ inpage.js:1
n @ inpage.js:1
i @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
n @ inpage.js:1
i @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
c @ inpage.js:1
u @ inpage.js:1
(anonymous) @ inpage.js:1
(anonymous) @ inpage.js:1
a @ inpage.js:1
setTimeout (async)
(anonymous) @ inpage.js:15
write @ inpage.js:15
b @ inpage.js:15
(anonymous) @ inpage.js:15
v.write @ inpage.js:15
y @ inpage.js:15
h @ inpage.js:8
s.emit @ inpage.js:8
_ @ inpage.js:15
w @ inpage.js:15
b.push @ inpage.js:15
_write @ inpage.js:15
b @ inpage.js:15
(anonymous) @ inpage.js:15
v.write @ inpage.js:15
y @ inpage.js:15
h @ inpage.js:8
s.emit @ inpage.js:8
_ @ inpage.js:15
w @ inpage.js:15
b.push @ inpage.js:15
o._onMessage @ inpage.js:15
postMessage (async)
o._write @ contentscript.js:15
b @ contentscript.js:15
(anonymous) @ contentscript.js:15
v.write @ contentscript.js:15
y @ contentscript.js:15
h @ contentscript.js:8
s.emit @ contentscript.js:8
_ @ contentscript.js:15
w @ contentscript.js:15
b.push @ contentscript.js:15
_write @ contentscript.js:15
b @ contentscript.js:15
(anonymous) @ contentscript.js:15
v.write @ contentscript.js:15
y @ contentscript.js:15
h @ contentscript.js:8
s.emit @ contentscript.js:8
_ @ contentscript.js:15
w @ contentscript.js:15
b.push @ contentscript.js:15
_write @ contentscript.js:15
b @ contentscript.js:15
(anonymous) @ contentscript.js:15
v.write @ contentscript.js:15
y @ contentscript.js:8
h @ contentscript.js:8
s.emit @ contentscript.js:8
_ @ contentscript.js:8
w @ contentscript.js:8
b.push @ contentscript.js:8
o._onMessage @ contentscript.js:8

I tried to restart the browser, metamask and ganache but it gives always the same problem. Do you know what it means?

  1. I tried to add a button in the html file in order to display the contract balance.
    I added the link in main.js file $("#get_balance_button").click(gBalance) and I added the function gBalance
  function gBalance(){    
  contractInstance.methods.getBalance().call().then(function(res){
$("#balance_output").text(res.Balance);
})
  }

I’m not sure what should I set after contractInstance.methods. I tried getBalance, Balance but it doesn’t work.

In other word How can I call and display a variable of the contract?

thanks a lot!

1 Like

Can anyone direct me on what I should be doing next? Is this code alright?

Thanks

1 Like

Please help I am unable to withdraw the ether that was deposited. I am able to coinflip and distribute the amount to players with etherBalance[msg.sender] = etherBalance[msg.sender].sub(_amount); I am able to check balances of players as well But unable to withdraw amount sent in. Im getting an Error “value should be less that your current balance.” Not sure how to get past this. Any suggestions would help. Thanks!

    mapping(address => uint) public etherBalance;
    event Deposit(address indexed player, uint amount, uint balance);
    event Withdraw(address indexed player, uint amount, uint balance);

    function depositEther(uint _amount) payable public {
        etherBalance[msg.sender] = etherBalance[msg.sender].add(_amount);
        emit Deposit(msg.sender, _amount, etherBalance[msg.sender]);
    }
    function withdrawEther(uint _amount) public {
        require(etherBalance[msg.sender] >= _amount);
        msg.sender.transfer(_amount);
        etherBalance[msg.sender] = etherBalance[msg.sender].sub(_amount);
        emit Withdraw(msg.sender, _amount, etherBalance[msg.sender]);
    }

For some reason I’m getting a SyntaxError: Unexpected end of input at line 220. It’s the tag at the bottom. Any idea why?

<!DOCTYPE html>
<html lang="en" dir="ltr">
  <head>
    <meta charset="utf-8">

    <script src="https://code.jquery.com/jquery-3.4.1.min.js"
      integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
      crossorigin="anonymous"></script>
    <script src="main.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css"></script>
    <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <link rel="stylesheet" href="main.css"></script>
    <script type="text/javascript" src="./web3.min.js"></script>
    <title>Cash Flip</title>
  </head>
    <body>
      <br>
        <div class="flexbox-container">
          <div class="flexbox-item flexbox-item-1">
              <h1>cash flip</h1>
              <p>Double your bet by correctly guessing the results of a coin flip</p>
              <br>
              <img src="img/mainImage.gif" alt="" style="width: 500px;">
          </div>
        </div>
        <br>
        <div class="flexbox-container">
          <div class="flexbox-item flexbox-item-2">
            <form id="newBetForm" class="playerBet">
              <ul class="betAmount">
                <li>
                  <input type="radio" id="1" value= "1" name="betAmount" checked="checked"/>
                  <label for="1">$1</label>
                </li>
                <li>
                  <input type="radio" id="5" value= "5" name="betAmount"/>
                  <label for="5">$5</label>
                </li>
                <li>
                  <input type="radio" id="10" value= "10" name="betAmount"/>
                  <label for="10">$10</label>
                </li>
                <li>
                  <input type="radio" id="25" value= "25" name="betAmount"/>
                  <label for="25">$25</label>
                </li>
              </ul>
              <ul class="headsOrTails">
                <li>
                  <input type="radio" id="heads" value= "1" name="selection" checked="checked"/>
                  <label for="heads">heads</label>
                </li>
                <li>
                  <input type="radio" id="tails" value= "0" name="selection"/>
                  <label for="tails">tails</label>
                </li>
              </ul>
              <button type="submit" name="submitButton" id="submitButton">place bet</button>
            </form>
          </div>
        </div>
      </div>

      <script>

      var web3 = new Web3(Web3.givenProvider);
var address = "0xDfD21969F0Cb0EC79326F8C254800B443Dd65F17";
var CashFlip;

var alert = `<div class="alert alert-dismissible fade show" role="alert">
                <button type="button" class="close" data-dismiss="alert" aria-label="Close">
                    <span aria-hidden="true">&times;</span>
                </button>
            </div>`

$(document).ready(function() {
    window.ethereum.enable().then(async function(accounts) {
        CashFlip = new web3.eth.Contract([
          {
            "inputs": [],
            "payable": true,
            "stateMutability": "payable",
            "type": "constructor"
          },
          {
            "anonymous": false,
            "inputs": [
              {
                "indexed": false,
                "internalType": "bool",
                "name": "",
                "type": "bool"
              }
            ],
            "name": "result",
            "type": "event"
          },
          {
            "constant": true,
            "inputs": [],
            "name": "owner",
            "outputs": [
              {
                "internalType": "address payable",
                "name": "",
                "type": "address"
              }
            ],
            "payable": false,
            "stateMutability": "view",
            "type": "function"
          },
          {
            "constant": true,
            "inputs": [],
            "name": "player",
            "outputs": [
              {
                "internalType": "address payable",
                "name": "",
                "type": "address"
              }
            ],
            "payable": false,
            "stateMutability": "view",
            "type": "function"
          },
          {
            "constant": true,
            "inputs": [],
            "name": "playerBalance",
            "outputs": [
              {
                "internalType": "uint256",
                "name": "",
                "type": "uint256"
              }
            ],
            "payable": false,
            "stateMutability": "view",
            "type": "function"
          },
          {
            "constant": true,
            "inputs": [],
            "name": "getBalance",
            "outputs": [
              {
                "internalType": "uint256",
                "name": "",
                "type": "uint256"
              }
            ],
            "payable": false,
            "stateMutability": "view",
            "type": "function"
          },
          {
            "constant": false,
            "inputs": [],
            "name": "depositETH",
            "outputs": [],
            "payable": true,
            "stateMutability": "payable",
            "type": "function"
          },
          {
            "constant": false,
            "inputs": [
              {
                "internalType": "uint256",
                "name": "_amount",
                "type": "uint256"
              }
            ],
            "name": "withdrawETH",
            "outputs": [],
            "payable": false,
            "stateMutability": "nonpayable",
            "type": "function"
          },
          {
            "constant": false,
            "inputs": [
              {
                "internalType": "uint256",
                "name": "_playerGuess",
                "type": "uint256"
              }
            ],
            "name": "randomFlip",
            "outputs": [],
            "payable": true,
            "stateMutability": "payable",
            "type": "function"
          }
        ], address, {from: accounts[0]});

        console.log(CashFlip);


      let allBets = [];
      let EXR = 2535000000000000;

      const newBetForm = document.getElementById("newBetForm");

    newBetForm.addEventListener("submit", (e) => {
        e.preventDefault();
        let playerBet = {
          betAmount: document.querySelector('input[name="betAmount"]:checked').value * EXR,
          guessHeads: document.querySelector('input[name="selection"]:checked').value
        }
        allBets.push(playerBet);
        document.forms[0].reset();
        console.log('added' , {allBets} );
      });


      </script>
    </body>
</html>

ezgif.com-gif-maker

Not sure why this is happening. A little Googling made it seem like it could be an issue with the gas limit but I’m not sure. I am seeing the TX count go up in Ganache every time I try to send a transaction in the browser. Here’s the error I’m getting:

RPC Error: Error: [ethjs-rpc] rpc error with payload {“id”:2536352364799,“jsonrpc”:“2.0”,“params”:[“0xf892548504a817c800836170d494dfd21969f0cb0ec79326f8c254800b443dd65f17875a0fb0d10e6000a4705265c10000000000000000000000000000000000000000000000000000000000000000822d45a0c2de3a5036bd2d080cfde9fedc0a7130f530cc9bf14bb4ff7e543867eca4421ea041d1d64e889a719adeac3fe79adcf52d402ff9a87621209dcaf28fc3267ac789”],“method”:“eth_sendRawTransaction”} [object Object] {code: -32603, message: “Error: [ethjs-rpc] rpc error with payload {“id”:25…method”:“eth_sendRawTransaction”} [object Object]", stack: “Error: Error: [ethjs-rpc] rpc error with payload {…method”:“eth_sendRawTransaction”} [object Object]"}

And the Second one:

Uncaught (in promise) {code: -32603, message: “Error: [ethjs-rpc] rpc error with payload {“id”:25…method”:“eth_sendRawTransaction”} [object Object]", stack: “Error: Error: [ethjs-rpc] rpc error with payload {…method”:“eth_sendRawTransaction”} [object Object]"}

UPDATE: NVM I figure it out. I forgot to load my smart contract with ETH so calling my function was reverted.

I fixed the depositEther() function below but can someone explain why passing (uint _amount) as a parameter when depositing eth doesnt read the value when withdrawing? I am able to withdraw ether out of the contract now and My whole flipcoin contract works now. Thanks

function depositEther() payable public {
        etherBalance[msg.sender] = etherBalance[msg.sender].add(msg.value);
        emit Deposit(msg.sender, msg.value, etherBalance[msg.sender]);
    }
1 Like