Jump to content

[TOPIC: topicViewTemplate]
[GLOBAL: userSmallPhoto]
Photo

Why am I getting this error?
Started by tokyodan Jul 04 2010 02:20 PM

- - - - -
9 replies to this topic
[TOPIC CONTROLS]
This topic has been archived. This means that you cannot reply to this topic.
[/TOPIC CONTROLS]
[modOptionsDropdown]
[/modOptionsDropdown]
[reputationFilter]
[TOPIC: post.html]
#1

tokyodan

[GLOBAL: userInfoPane.html]
tokyodan
  • Contributor

  • 260 posts
  • Guests

Why am I getting this runtime error before the function is even called?

Runtime error
...er/Data1/iDev/Corona Projs/TOT/TOTbuttonHandlers.lua:2: attempt to concatenate global 'buttonRotation' (a nil value)

--------------------------------------------------------------------------------------------
local setSelectedPiece = function()
    local selectedPiece=display.newImage("Player1-Piece".. buttonRotation ..".png")
    return selectedPiece
end

local buttonRotation = 0 

local currentPiece = setSelectedPiece()
--------------------------------------------------------------------------------------------
The 'setSelectedPiece' function isn't called till line 8, after 'buttonRotation" has a value.
If I move the variable declarations above the function then I don't get an error.
uid: 295 topic_id: 1356 reply_id: 301356


[TOPIC: post.html]
#2

MikeHart

[GLOBAL: userInfoPane.html]
MikeHart
  • Corona Geek

  • 1,278 posts
  • Corona SDK

Yip, welcome to the world of LUA's scoping and definition rules.

Even that you did not have called the function, it is already parsed. And because it is parsed before buttonRotation was defined, you will get that error as LUA doesn't know at that point, which kind of content the variable will have later on. You can't concatenate content that is undefined.

IF you can not define the button before, how about this. I hope it works:

local setSelectedPiece = function(btn)    local selectedPiece=display.newImage("Player1-Piece".. btn ..".png")    return selectedPieceend local buttonRotation = 0  local currentPiece = setSelectedPiece(buttonRotation)
uid: 5712 topic_id: 1356 reply_id: 3694


[TOPIC: post.html]
#3

tokyodan

[GLOBAL: userInfoPane.html]
tokyodan
  • Contributor

  • 260 posts
  • Guests

Thanks. That'll help.

I also noticed that if I make buttonRotation a global the error will go away.
uid: 295 topic_id: 1356 reply_id: 3695


[TOPIC: post.html]
#4

OderWat

[GLOBAL: userInfoPane.html]
OderWat
  • Contributor

  • 347 posts
  • Corona SDK

Yes.. Mike explained it not in enough detail. From his explanation it sounds like it is a side effect of the position of the declaration.

The "local" part introduces the variable for the remaining code. This is not a side effect where the definition happens but the very nature of how "local" is supposed to work.

Most (seniors) programmers may expect "locals" in the global scope to be hidden inside functions. But in Lua every new "block" gets all the parent data as "global" information. And a function is such a block too.

Try this and get confused :)

test=3

do

local test=4

function func()
	print(test)
end

test=6

end

-- may do also: collectgarbage('collect')

func()
print(test)

It prints 6 and 3 ..

I think it is because the function gets it's local scope variables as "globals" which still exist after the "end" of the block it encapsulates. The local version of test still exists!

I have to admit that this confuses me too :)
uid: 6928 topic_id: 1356 reply_id: 3700


[TOPIC: post.html]
#5

tokyodan

[GLOBAL: userInfoPane.html]
tokyodan
  • Contributor

  • 260 posts
  • Guests

Thanks for the explanation. But I've never seen such a fu*ked up thing!

It makes no logical sense at all. Just that alone is almost enough to make me give up on Corona/Lua and ask for my money back and go back to Objective-C/Cocoa Touch.
uid: 295 topic_id: 1356 reply_id: 3701


[TOPIC: post.html]
#6

OderWat

[GLOBAL: userInfoPane.html]
OderWat
  • Contributor

  • 347 posts
  • Corona SDK

Well... actually I believe this is a very powerful concept...

Keyword for what I demonstrated is: Closure. It is also used by other languages... for example java-script.

While still working on my current app (which already consists of more than 10.000 lines of Lua code) I can say that I enjoy this language and the overall concept very much.

See:

- http://www.lua.org/pil/4.2.html
- http://www.lua.org/pil/6.1.html

And... to be honest... When I write Objective C code... I often think as you do about Lua :)
uid: 6928 topic_id: 1356 reply_id: 3703


[TOPIC: post.html]
#7

tokyodan

[GLOBAL: userInfoPane.html]
tokyodan
  • Contributor

  • 260 posts
  • Guests

Well actually I like Lua more than Obj-C. Or I did till I saw your example which scared the heck out of me. I'll go back and read your PIL suggestions again but I'll pay more attention this time. This is important. Thanks again for your help.
uid: 295 topic_id: 1356 reply_id: 3705


[TOPIC: post.html]
#8

OderWat

[GLOBAL: userInfoPane.html]
OderWat
  • Contributor

  • 347 posts
  • Corona SDK

Just read the links I provided...

Lua bases on this concept for modules, oo, interators, generators... well everything :)

If you "blend out" your knowledge of other languages and read that code.. it makes perfect sense.

Because.. if the lifetime of "local test" would end with the "end"... it would be not clear what "test" inside of the function is meant...

You had to limit it so that it always means the global one (as traditional languages do).. or to introduce something like "static" inside of the function. But that would need to explicitly know what is "static" there.

Anyway.. It is possible to write quite elegant code in Lua ... In the end... I code with what is available :)
uid: 6928 topic_id: 1356 reply_id: 3706


[TOPIC: post.html]
#9

tokyodan

[GLOBAL: userInfoPane.html]
tokyodan
  • Contributor

  • 260 posts
  • Guests

Hot damn! Now I see it. Woke up this morning and took another look and It's like black clouds moved away and the sun came out:

Although the function 'func()' is defined within the do-end block after the local variable 'test' is set to 4, 'func()' ISN'T CALLED until after the local variable 'test' has been set to 6. It would be the same if the local variable 'test' were set to 6 right after setting it to 4:

test=3

do
	local test=4
	test=6                        -- Setting 'test' here or
	function func()
		print(test)
	end
	
	-- test=6                     -- setting it here has the same meaning to 'funct()'
end
 
-- may do also: collectgarbage('collect')
 
func()
print(test)

It does make perfect sense!

(Is my short explanationI correct?)
uid: 295 topic_id: 1356 reply_id: 3723


[TOPIC: post.html]
#10

OderWat

[GLOBAL: userInfoPane.html]
OderWat
  • Contributor

  • 347 posts
  • Corona SDK

It is... For "func" the world looks like it does in the little do end block. But at the time when we call fun() which is after this code block has executed. Hence test is 6 in any case. And func sees only this local test and does not know about the existens of another one... Philosophic... :)
uid: 6928 topic_id: 1356 reply_id: 3725



[topic_controls]
[/topic_controls]