Customizing Text Input - What am I doing wrong?

Hey all, I’m fairly new to Solar2d and Lua. I can’t for the life of me figure out what I’m doing wrong. I’m following the example of customizing text input, but I just get error after error. Also why in this tutorial is there a function with no end statement? Any help with how to implement this properly is very appreciated.

The error:
ERROR: Syntax error
main.lua:122: ‘’ expected near ‘local’

My code which is mostly just copied and pasted:


– main.lua


local myTextField = widget.newTextField(
{
top = 10,
left = 20,
width = 200,
height = 30,
cornerRadius = 8,
strokeWidth = 3,
backgroundColor = { 1, 1, 1 },
strokeColor = { 0, 0, 0 },
font = “Helvetica”,
fontSize = 24,
listener = textFieldHandler
}
)

local function textFieldHandler( event )

– “event.text” only exists during the editing phase to show what’s being edited;
– it is NOT the field’s “.text” attribute (that is “event.target.text”).

if ( event.phase == “began” ) then
– user begins editing textField
print( “Begin editing”, event.target.text )
elseif ( event.phase == “ended” or event.phase == “submitted” ) then
– do something with defaulField’s text
print( "Final Text: ", event.target.text )
native.setKeyboardFocus( nil )
elseif ( event.phase == “editing” ) then
print( event.newCharacters )
print( event.oldText )
print( event.startPosition )
print( event.text )
end
end

local widget = require(“widget”)
function widget.newTextField( options )

end

function widget.newTextField( options )
local customOptions = options or {}
local opt = {}
opt.left = customOptions.left or 0
opt.top = customOptions.top or 0
opt.x = customOptions.x or 0
opt.y = customOptions.y or 0
opt.width = customOptions.width or (display.contentWidth * 0.75)
opt.height = customOptions.height or 20
opt.id = customOptions.id
opt.listener = customOptions.listener or nil
opt.text = customOptions.text or “”
opt.inputType = customOptions.inputType or “default”
opt.font = customOptions.font or native.systemFont
opt.fontSize = customOptions.fontSize or opt.height * 0.67

– Vector options
opt.strokeWidth = customOptions.strokeWidth or 2
opt.cornerRadius = customOptions.cornerRadius or opt.height * 0.33 or 10
opt.strokeColor = customOptions.strokeColor or { 0, 0, 0 }
opt.backgroundColor = customOptions.backgroundColor or { 1, 1, 1 }
end

local field = display.newGroup()

local background = display.newRoundedRect( 0, 0, opt.width, opt.height, opt.cornerRadius )
background:setFillColor( unpack(opt.backgroundColor) )
background.strokeWidth = opt.strokeWidth
background.stroke = opt.strokeColor
field:insert( background )

if ( opt.x ) then
field.x = opt.x
elseif ( opt.left ) then
field.x = opt.left + opt.width * 0.5
end
if ( opt.y ) then
field.y = opt.y
elseif ( opt.top ) then
field.y = opt.top + opt.height * 0.5
end

– Native UI element
local tHeight = opt.height - opt.strokeWidth * 2
if “Android” == system.getInfo(“platformName”) then

– Older Android devices have extra “chrome” that needs to be compesnated for.

tHeight = tHeight + 10
end

field.textField = native.newTextField( 0, 0, opt.width - opt.cornerRadius, tHeight )
field.textField.x = field.x
field.textField.y = field.y
field.textField.hasBackground = false
field.textField.inputType = opt.inputType
field.textField.text = opt.text
print( opt.listener, type(opt.listener) )
if ( opt.listener and type(opt.listener) == “function” ) then
field.textField:addEventListener( “userInput”, opt.listener )
end

local deviceScale = ( display.pixelWidth / display.contentWidth ) * 0.5

field.textField.font = native.newFont( opt.font )
field.textField.size = opt.fontSize * deviceScale

function field:finalize( event )
event.target.textField:removeSelf()
end
field:addEventListener( “finalize” )

return field

local myTextField = widget.newTextField(
{
width = 250,
height = 30,
text = “Hello World!”,
fontSize = 18,
font = “HelveticaNeue-Light”,
listener = textFieldHandler
}
)

myTextField.x = display.contentCenterX
myTextField.y = 100

local myText = myTextField.textField.text
myTextField.textField.text = “Edited Value”

You can’t have a return statement in the middle of a function like this:

return field

local myTextField = widget.newTextField(

The Lua interpreter will expect the function to end after the return statement.

For future posts, please format your code properly to make it readable. Also, when you have an error message giving you a specific line number, you can help us help you by clearly pointing out that line in your code.

1 Like

Hey I appreciate it and will do in the future. I guess I’m still not following. To me that doesn’t appear to be in the middle of a function. The function above it has an end statement, is that not correct? I took that out altogether and now get in line 7 - main.lua:7: attempt to index global ‘widget’ (a nil value). I really don’t get what I’m doing wrong. I was basically just copying the code exactly as the tutorial shows but that seems to not work at all. Any chance there is a working example of this somewhere I could look at? Thanks again.

A return statement can only be used within a function, and if you don’t have an end immediately after the return it means that it’s “in the middle of a function” which is not valid. An exception to that is that you can also return as the last statement within if/else blocks. Simply put, you can’t have any code directly after a return statement because it will never get executed.

Because of the code formatting it is really hard to follow, but when I look at it a little closer it seems like the return statement is not within any function at all, which is certainly not valid. I think you should read up on how functions and return values work for a better understanding.

Now to this:

line 7 - main.lua:7: attempt to index global ‘widget’ (a nil value)

Have you required widget?

local widget = require("widget")

Thanks for the explanation, I should have realized that. But unfortunately my problems still exists. I do have:

local widget = require(“widget”)

I moved it in my code to the top. I still get the same error. It’s like it’s not seeing the widget library or I’m still just doing something wrong, which I’m sure that I am.

Hey I got it working now. Thanks for the help. Although I’m having another issue, but I’m sure I’ll figure it out.