Tic Tac Toe game, trying to use more than 9 choices.

Ah, @nick_sherman and @roaminggamer, I now see the missing post that was deleted. Mail notifications are a good thing :slight_smile:

Just to clarify, we have over 500,000 developers. Most people come to the forums, learn how to use the product and don’t hang out here after they learn. But we have an active forum and there are quite a few very helpful developers who do hang out here offering help at no expense to the community (and the Staff at Corona Labs is eternally grateful for this). 

Corona staff actively monitors the forums, but as to avoid dominating all the conversations, we have to pick and choose which topics we respond to. As such, if it’s a product-specific question, I feel we are the best to answer. If it’s a “How do I use the product” question, those are best for the community to answer. If I’m going about this in the wrong way, let me know. Our community developers build and deploy way more games than our staff does and therefore has more experience on what can be done with the product. This thread is a great example. I worked on a BINGO game back in the 1990’s on the server side in C. Not very practical on building a BINGO game in Corona, but @roaming_gamer has. He’s a much better resource to answer that “How do I” question…

We (Corona Labs) and I believe the community developers all want everyone to be successful and use Corona for years. As for lack of information, I’m pretty sure all of this is explained in our Getting Started Guide. http://docs.coronalabs.com/guide/programming/index.html

But all that said, tutorials have to be generic where possible, but there are times where they get very specific and that specificity is very unlikely going to directly translate to copy and paste code. Tutorials are there to teach you concepts that you will adapt to your own use.

Rob

I had received from Rob the code for a bingo game (Thank you so much)  I have styled this around your tutorial on the Tic-Tac-Toe game where you have a reset button.  The reset is has code of

local function resetGame() for i = 1, #spots do spots[i].moveText.text = " " spots[i].moveType = nil end display.remove( winningLine ) winningLine = nil display.remove( winningRec ) winningRec = nil display.remove( winningImage ) display.remove( resetButton ) resetButton = onPress player = "X" allowMoves = true end

This works well.  Is there a way to add code to shuffle the numbers.  I have tried virtually every combination that I could think of. The section of code to shuffle the bingo card is

local B = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } local I = { 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30 } local N = { 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45 } local G = { 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58 ,59, 60 } local O = { 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75 } math.randomseed( os.time() ) -- Seed the pseudo-random number generator local function shuffleTable( t ) if ( type(t) ~= "table" ) then print( "WARNING: shuffleTable() function expects a table" ) return false end local j for i = #t, 2, -1 do j = math.random( i ) t[i], t[j] = t[j], t[i] end return t end shuffleTable( B ) shuffleTable( I ) shuffleTable( N ) shuffleTable( G ) shuffleTable( O )

Thanks again for your help. 

Create a table with the valid numbers in it:

local bingoBalls = {} for i = 1, 75 do     bingoBalls[i] = i end shuffleTable( bingoBalls )

Then just take the balls in order out of the shuffled list.

Rob

I put this into my code and made a button at the bottom of the code 

local button3 = widget.newButton( { width = 60, height = 35, defaultFile = "btn green.png", overFile = "btn yellow.png", label = "", onPress = bingoBalls } ) -- Center the button button3.x = display.contentCenterX button3.y = display.contentCenterY -90 -- Change the button's label text button1:setLabel( "" )

Trying to reference it to shuffle the table.  It doesn’t shuffle the numbers.

bingoBalls is not a function, it is a table containing a series of numbers.

You need to point onPress at a function that calls shuffleTable(bingoBalls).

How do I do that?  I thought that was what I was doing.

You have written onPress = bingoBalls. This tells the button to call the function bingoBalls when it is pressed. As bingoBalls is not a function, nothing happens.

You need to write a function that contains the shuffleTable(bingoBalls) call. Then change bingoBalls to the name of the new function. Ensure this function is above the code that creates the button so it is in scope.

I have a function called "shuffleTable (t)

local function shuffleTable( t ) if ( type(t) ~= "table" ) then print( "WARNING: shuffleTable() function expects a table" ) return false end local j for i = #t, 2, -1 do j = math.random( i ) t[i], t[j] = t[j], t[i] end return t end shuffleTable( B ) shuffleTable( I ) shuffleTable( N ) shuffleTable( G ) shuffleTable( O ) local B\_spots = {} local I\_spots = {} local N\_spots = {} local G\_spots = {} local O\_spots = {} for i = 1, 5 do B\_spots[i] = display.newText( B[i], 45, i \* 105, native.systemFontBold, 28 ) B\_spots[i] : setFillColor(1, 1, 1 ) I\_spots[i] = display.newText( I[i], 100, i \* 105, native.systemFontBold, 28 ) B\_spots[i] : setFillColor(1, 1, 1 ) N\_spots[i] = display.newText( N[i], 160, i \* 105, native.systemFontBold, 28 ) B\_spots[i] : setFillColor(1, 1, 1 ) G\_spots[i] = display.newText( G[i], 220, i \* 105, native.systemFontBold, 28 ) B\_spots[i] : setFillColor(1, 1, 1 ) O\_spots[i] = display.newText( O[i], 280, i \* 105, native.systemFontBold, 28 ) B\_spots[i] : setFillColor(1, 1, 1 ) B\_spots[i].y = math.floor( ( i - 1 ) / 1 ) \* 60 + 205 I\_spots[i].y = math.floor( ( i - 1 ) / 1 ) \* 60 + 205 N\_spots[i].y = math.floor( ( i - 1 ) / 1 ) \* 60 + 205 G\_spots[i].y = math.floor( ( i - 1 ) / 1 ) \* 60 + 205 O\_spots[i].y = math.floor( ( i - 1 ) / 1 ) \* 60 + 205 B\_spots[i].moveType = nil I\_spots[i].moveType = nil N\_spots[i].moveType = nil G\_spots[i].moveType = nil O\_spots[i].moveType = nil spots[i]:addEventListener( "touch", handleMove ) end N\_spots[3].text = " " for k = 1, 1 do spots[k] = display.newRect( 0, 0, 55, 55) spots[k]:setFillColor( 0.2,0.2,0.2,0 ) spots[k].x = ( k - 1 ) % 5 \* 60 + 40 spots[k].y = math.floor( ( k - 1 ) / 5 ) \* 60 + 205 spots[k].moveText = display.newText( " ", spots[k].x, spots[k].y, native.systemFontBold, 60) spots[k].moveType = nil spots[k]:addEventListener( "touch", handleMove ) end

I also have the “Reset” of the game that resets everything but the shuffle

local function resetGame() for i = 1, #spots do spots[i].moveText.text = " " spots[i].moveType = nil end display.remove( winningLine ) winningLine = nil display.remove( winningRec ) winningRec = nil display.remove( winningImage ) display.remove( resetButton ) resetButton = onPress player = "X" allowMoves = true end 

Is there a way I could add code to this that would allow me to shuffle the numbers from table t when reset is pressed.  I am truely trying to figure this out but I am stuck. 

No, I mean put the CALL to the shuffleTable function inside another one. When you run a function, that is called ‘calling’ the function.

[lua]

local function shuffleBingoBalls()

  tableShuffle(bingoBalls)

end

[/lua]

Then edit button:

[lua]

local button3 = widget.newButton(

{
width = 60,
height = 35,
defaultFile = “btn green.png”,
overFile = “btn yellow.png”,
label = “”,
onPress = shuffleBingoBalls
}
)

[/lua]

We need to ‘wrap’ the call to tableShuffle because the button listener cannot be passed custom parameters. 

We could not do for example: onPress = tableShuffle(bingoBalls)

So we must call an intermediary function that does this step for us.

The table I am trying to shuffle is labeled “t”.  I put the first part of the code up higher in my code as the first function.  I put the button at the bottom of the code. I get the error,

"main.lua35:attempt to call global’tableShuffle’ (a nil value) stack traceback: 

main.lua:35: in function ‘_onPress’

?:in function ‘?’

?:in function ‘?’

?:in function <?:190>"

If I change the 

tableShuffle(bingoBalls)

to

tableShuffle(t)

I get the same error.

Mark,

I am coming into this late… and know nothing of all the issues or the initial question…  but to the last error message posted…   if you look closely at the error messages, there are clues.

your note list error as  :

attempt to call global’tableShuffle’ (a nil value)

I think you have, in your sample code,  just above nick_sherman’s last post the function called ‘shuffleTable’ …

so tableShuffle is wrong … it should be shuffleTable

I hope this helps, and again I have not read any of this post except your last two posts to this issue.  But I think that is the cause of the error you posted.

Good luck

Bob

it gives the same error, except with shuffleTable instead of tableShuffle

My guess is that the function you are calling is not visible in the scope you are calling it.

i.e. If you did this, you’d get a similar error:

https://github.com/roaminggamer/RG_FreeStuff/raw/master/AskEd/2018/10/scopeAndVisibility.zip

local function test2() print("\n\nGets an error...") doit() end local function doit() print("YO I'm visible to test1(), but not test2()") end local function test1() print("\n\nWorks fine...") doit() end test1() test2()

Produces this log:

15:28:06.036 Works fine... 15:28:06.036 YO I'm visible to test1(), but not test2() 15:28:06.036 15:28:06.036 15:28:06.036 Gets an error... 15:28:06.036 ERROR: Runtime error 15:28:06.036 X:\Work\00\_CurentProjects\Corona\RG\_FreeStuff\AskEd\2018\10\scopeAndVisibility\main.lua:8: attempt to call global 'doit' (a nil value) 15:28:06.036 stack traceback: 15:28:06.036 X:\Work\00\_CurentProjects\Corona\RG\_FreeStuff\AskEd\2018\10\scopeAndVisibility\main.lua:8: in function 'test2' 15:28:06.036 X:\Work\00\_CurentProjects\Corona\RG\_FreeStuff\AskEd\2018\10\scopeAndVisibility\main.lua:22: in main chunk

I have tried everything I can think of, everything that I can guess, everything I can research.  I know it isn’t working.  I really need help with a solution rather than posts that what I am doing isn’t working.  I do know that. Is there anyone out there that can help Please?

Sorry Mark, but that’s how it works.  We respond the best we can to the posts you write.  

Sometimes folks feel generous enough to really dig in and help re-write a project, but often times we’re too busy so we post back help and hints instead.

What it really sounds like you need is  a partner, mentor, or contractor.  

Would it be of any value to you at all if someone posted code that could do this?:

  • Draw a bingo card with these attributes
    • 5x5 alternating color grid separated by lines
    • Free spot filled with circle
    • Other grid spots filled with numbers that you can define in code as a table.
    • each grid is a button that can be toggled to show it is selected
  • Includes logic to detect a BINGO and if so, to highlight the line and show a message. “BINGO”.
  • Includes a reset button to clear all selections and essentially restart the game.

Thank you so much for all of your help.  I really do appreciate it.  I can’t waste any more time on this.  I really truly do appreciate your help. 

First, you can’t do:

tableShuffle( t )

because you don’t have a table named “t”. Second of all, when people are helping you here, they are hand typing in examples that **should** work, but sometimes typos get in the way. It’s really important for you to learn how to debug your code. There is a typo in some provided code, but the answer is in your error message.

"main.lua35:attempt to call global 'tableShuffle' (a nil value) stack traceback:&nbsp;main.lua:35: in function '\_onPress' ?:in function '?' ?:in function '?' ?:in function \<?:190\>"

 

Look at your main.lua.

Go to line 35

You are calling a function named “tableShuffle”. 

Corona says it can’t find it (a nil value)

 

You need to ask yourself a question? Why is “tableShuffle” nil or non-existent? 

Then you need to look through your code and see why it can’t find a function named “tableShuffle”

 

If you do that, the answer is clear. You don’t have one named tableShuffle, but you do have one named shuffleTable. In this case, 

 

This code:

 

local function shuffleBingoBalls() tableShuffle(bingoBalls) end

probably should be

local function shuffleBingoBalls() shuffleTable(bingoBalls) end

Now order of code matters in Lua. This function must exist before you create your button. This code calls shuffleTable and references the table “bingoBalls”, so it has to exist **after** both of those items in your code.

 

Rob
 

Mark,

If you truly want to code and make games, don’t give up.  It will make you pull your hair out alot of times.  Take a break for a day and give it another go.

If you don’t mind me saying, learning from scratch as you apparently are doing, is the way I did it - and it took a lot of time and a lot of frustration… and I am still not at the level of Roaming Gamer and Nick_Sherman and Rob Miracle to just name a few… but for me it was worth it.

If I can add; I had to take apart sample code over and over and over… and go thru countless tutorials - changing code in those tutorials to get a feel of what was actually happening…  it is time consuming and aggravating; especially when you are anxious to get to making something real.  I also started with the simplest of sample code.  Simple tic tac toe type game. And moved up from there.

Just a few last points:

  1. As Roaming Gamer mentioned ‘scope’ is the likely issue to the last error… very common for someone new to coding.  Look at as many tutorials as you can find that strictly talk about ‘scope’.

  2. It is not an easy; and one of the most common mistakes I made and I see others make, is not reading the error message completely and misspelling the name of the variable or functions and not matching ‘case’.

I hope you give it another try after a short break… that is if you truly want to code games.  Corona is a great tool for doing that.

Best of luck

Bob

As advised before Mark, you cannot code without learning to code. Countless hours of frustration you have experienced would have been avoided by learning the basics. And probably saved you hours of trial and error.

For example, the whole table named ‘t’ mix up.

When an object is used in a function, it is often given a different name than that of the object provided. We can pass any table to shuffleTable and all these could have different names.

While it is being processed in that function, it will be called ‘t’. It’s kind of a nickname, a handle. ‘t’ is used because it’s easy to type over and over and short for table.

A more accurate name might be ‘tableThatIsToBeShuffled’. However, in this small function, an abbreviation is fine. If we had a global variable called ‘t’ however, we’d come back to it 6 months later and have no idea what it stood for.

Once that shuffleTable function is over, the table must still be referred to by its original name. The nickname, or reference, ‘t’ no longer exists.

https://www.youtube.com/watch?v=ZugCYGLF12Q&feature=youtu.be

https://github.com/roaminggamer/RG_FreeStuff/raw/master/gamesIn250/002_bingoCard.zip