Jump to content

[TOPIC: topicViewTemplate]
[GLOBAL: userSmallPhoto]
Photo

Lowering a string from a user input
Started by hayful59 Feb 21 2019 11:28 PM

11 replies to this topic
string input user lower event
[TOPIC CONTROLS]
[/TOPIC CONTROLS]
[modOptionsDropdown]
[/modOptionsDropdown]
[reputationFilter]
[TOPIC: post.html]
#1

hayful59

[GLOBAL: userInfoPane.html]
hayful59
  • Enthusiast

  • 40 posts
  • Corona SDK

Hello, Im trying to convert the users input from a text field to all lowercase, Ive read how to do it so im confused on why its not working, am I missing a step?

if cluthaButtonTrigger then
            if cluthaTable[event.target.text] then
                print(string.lower(event.target.text)) ----------
                print(cluthaTable[event.target.text])

what the above code is suppose to do is when the clutha button is selected it takes the input from the text field then lowers it and prints both a lowered and a normal version

 

Thanks

   

 

 



[TOPIC: post.html]
#2

nick_sherman

[GLOBAL: userInfoPane.html]
nick_sherman
  • Corona Geek

  • 1,807 posts
  • Corona SDK

What does it do?



[TOPIC: post.html]
#3

hayful59

[GLOBAL: userInfoPane.html]
hayful59
  • Enthusiast

  • 40 posts
  • Corona SDK

What does it do?

literally nothing,

nothing to the console, it doesnt crash, it just doesnt do anthing



[TOPIC: post.html]
#4

nick_sherman

[GLOBAL: userInfoPane.html]
nick_sherman
  • Corona Geek

  • 1,807 posts
  • Corona SDK

I suspect then that cluthaTable[event.target.text] is nil. You are looking in that table for a key that exactly matched what the user has input - seems unlikely. If you remove that if statement, the code should work, with 'nil' output for the second print statement.



[TOPIC: post.html]
#5

XeduR @Spyric

[GLOBAL: userInfoPane.html]
XeduR @Spyric
  • Contributor

  • 773 posts
  • Corona SDK

I'm pretty sure that nick is right on the money here.

Lua is case sensitive, so if you've turned the string to lowercase as you discussed in your previous thread and used that to create a new entry in your table, then you must refer to the entry by its lowercase form.

If you are uncertain as to what entries you have in your table, you can run the following code to find out all key-value pairs:
 

for i, j in pairs( cluthaTable ) do
	print( i, j )
end


[TOPIC: post.html]
#6

hayful59

[GLOBAL: userInfoPane.html]
hayful59
  • Enthusiast

  • 40 posts
  • Corona SDK

 

I'm pretty sure that nick is right on the money here.

Lua is case sensitive, so if you've turned the string to lowercase as you discussed in your previous thread and used that to create a new entry in your table, then you must refer to the entry by its lowercase form.

If you are uncertain as to what entries you have in your table, you can run the following code to find out all key-value pairs:
 

for i, j in pairs( cluthaTable ) do
	print( i, j )
end

 

Ive taken a few days to really work on it, ive renamed my table to lowercase, which now works (I had to do it for other reasons) but I still need to take what the users typed and lower it and search the lowered version I can print a lowered version find, do I need to store the Uppercase input somewhere and covert it, then use it?

 

Thanks for all the help thus far



[TOPIC: post.html]
#7

nick_sherman

[GLOBAL: userInfoPane.html]
nick_sherman
  • Corona Geek

  • 1,807 posts
  • Corona SDK

It would help to know what the overall goal is. What sort of thing are users inputting? What is in cluthaTable? How and when is it populated? Why do you need to look for matches between what the user entered and what's in the table?

[TOPIC: post.html]
#8

hayful59

[GLOBAL: userInfoPane.html]
hayful59
  • Enthusiast

  • 40 posts
  • Corona SDK

It would help to know what the overall goal is. What sort of thing are users inputting? What is in cluthaTable? How and when is it populated? Why do you need to look for matches between what the user entered and what's in the table?

 

This app is to be used at work, Its designed to select the area (via a button on screen) where a product is being delivered (in this case clutha) then you type in the name of the business (in a text field) and it outputs to the display the id number of the business something like:

cluthaTable["jack jack"] = ["Jack Jack = 24"];   --Jack Jack = 24 being the final output 

Im trying to convert all entries that get typed in to the text field to lowercase so it matches the table better and I dont have to add as many table entries, then it outputs the final id how ive entered it into the table "Jack Jack = 24"

 

Hope this helps



[TOPIC: post.html]
#9

nick_sherman

[GLOBAL: userInfoPane.html]
nick_sherman
  • Corona Geek

  • 1,807 posts
  • Corona SDK

Ok, well as long as users aren't likely to make spelling mistakes, I guess that works. Won't it be a bit annoying if a business name is really long? If the number of entries in the tables is relatively small, you could just loop through all of them and look for the user's text string, and give them a list of possible results.

 

Anyway, to convert to lower case and lookup at the same time just do:

 

 
if (cluthaTable[string.lower(event.target.text)] ~= nil) then
 
 print ("ID for "..event.target.text.." is "..cluthaTable[string.lower(event.target.text)])
 
end
 



[TOPIC: post.html]
#10

XeduR @Spyric

[GLOBAL: userInfoPane.html]
XeduR @Spyric
  • Contributor

  • 773 posts
  • Corona SDK

It sounds like you want to store both normal and lowercase versions of the string, i.e. something like

 

local sLower = string.lower( event.target.text )

-- see if the entry exists
if cluthaTable[sLower] then
	print( cluthaTable[sLower].name.." = "..cluthaTable[sLower].id )
-- if it doesn't exist, then create it
else
	cluthaTable[sLower] = { name = event.target.text, id = 24 }
end

Still, you'd need to determine how you give out those id's, and as nick already said, you may run into issues if people mistype those entries.

Having worked on things like this in the past, I must advice against your current approach. That is, if I've understood your approach correctly. The safest way is to create a dedicated function for creating new table entries (and only allowing specific people access to it). This should be completely separate from where you search for information.

Then, you should create a predictive (but not really) search function, case and point:
 

local t = {}
t["electric dance llc"] = { name = "Electric Dance LLC", id = 1 }
t["electrics supreme"] = { name = "Electrics Supreme", id = 2 }
t["electronics n' stuff"] = { name = "Electronics n' Stuff", id = 3 }
t["elections for all"] = { name = "Elections for All", id = 4 }

local defaultField, lowerS, match
local lower = string.lower
local len = string.len

local function textListener( event )
    if ( event.phase == "editing" ) then
		lowerS = lower( event.text )
		match = false
		print( "\n----------------\npossible matches:" )
		for i, j in pairs( t ) do
			if i:sub( 1, len(lowerS) ) == lowerS then
				print( j.name )
				if not match then
					match = true
				end
			end
		end
		if not match then
			print( "0 matches found" )
		end
    end
end

defaultField = native.newTextField( 150, 150, 180, 30 )
defaultField:addEventListener( "userInput", textListener )

The textListener function will go through table t after every keystroke and see if the initial characters of the inputted string matches with one or more of the entries. Then it prints out those possible matches.

Now, this is just an example and you'd want to create display objects of the top 3-5 matches that the user can then tap to directly select a company (or they can just keep on writing and hope that they don't mistype it, because any and all mistyped entries need to be ignored). This makes it faster, safer and more convenient for the users. You could additionally have a list of "the most commonly searched companies" available for the users to directly tap as well without typing anything in.


The truth of the matter is that people make mistakes. Tired, hungry or inattentive people make even more mistakes. Offices are full of people like these, and when people in offices make mistakes, they cost money. So, best to try to prevent as many and as serious mistakes as possible.



[TOPIC: post.html]
#11

hayful59

[GLOBAL: userInfoPane.html]
hayful59
  • Enthusiast

  • 40 posts
  • Corona SDK

It sounds like you want to store both normal and lowercase versions of the string, i.e. something like

 

local sLower = string.lower( event.target.text )

-- see if the entry exists
if cluthaTable[sLower] then
	print( cluthaTable[sLower].name.." = "..cluthaTable[sLower].id )
-- if it doesn't exist, then create it
else
	cluthaTable[sLower] = { name = event.target.text, id = 24 }
end

Still, you'd need to determine how you give out those id's, and as nick already said, you may run into issues if people mistype those entries.

Having worked on things like this in the past, I must advice against your current approach. That is, if I've understood your approach correctly. The safest way is to create a dedicated function for creating new table entries (and only allowing specific people access to it). This should be completely separate from where you search for information.

Then, you should create a predictive (but not really) search function, case and point:
 

local t = {}
t["electric dance llc"] = { name = "Electric Dance LLC", id = 1 }
t["electrics supreme"] = { name = "Electrics Supreme", id = 2 }
t["electronics n' stuff"] = { name = "Electronics n' Stuff", id = 3 }
t["elections for all"] = { name = "Elections for All", id = 4 }

local defaultField, lowerS, match
local lower = string.lower
local len = string.len

local function textListener( event )
    if ( event.phase == "editing" ) then
		lowerS = lower( event.text )
		match = false
		print( "\n----------------\npossible matches:" )
		for i, j in pairs( t ) do
			if i:sub( 1, len(lowerS) ) == lowerS then
				print( j.name )
				if not match then
					match = true
				end
			end
		end
		if not match then
			print( "0 matches found" )
		end
    end
end

defaultField = native.newTextField( 150, 150, 180, 30 )
defaultField:addEventListener( "userInput", textListener )

The textListener function will go through table t after every keystroke and see if the initial characters of the inputted string matches with one or more of the entries. Then it prints out those possible matches.

Now, this is just an example and you'd want to create display objects of the top 3-5 matches that the user can then tap to directly select a company (or they can just keep on writing and hope that they don't mistype it, because any and all mistyped entries need to be ignored). This makes it faster, safer and more convenient for the users. You could additionally have a list of "the most commonly searched companies" available for the users to directly tap as well without typing anything in.


The truth of the matter is that people make mistakes. Tired, hungry or inattentive people make even more mistakes. Offices are full of people like these, and when people in offices make mistakes, they cost money. So, best to try to prevent as many and as serious mistakes as possible.

 

Hi, thanks for the help so far, its been very useful. Ive taken what you said into account and will carry on with the way that you said would work better (its also alot faster to type :P), Ive been trying for the last few day to figure out how to stop your code from spitting out every entry in the table if the text box had something in it then it was deleted, any ideas?

 

I was thinking something like

i:sub( 1, len(lowerS) ) == lowerS and lowerS == ""

Thanks



[TOPIC: post.html]
#12

XeduR @Spyric

[GLOBAL: userInfoPane.html]
XeduR @Spyric
  • Contributor

  • 773 posts
  • Corona SDK

That would work, but you'd need to use ~= "".

 

One simple way that also improves the function's overall performance is to determine the string's length once at the start of the function and then use that (instead of checking the length in every loop as I originally had done).

 

This way, you can also check if the string's length is more than 0, i.e. if the user has actually inputted something, before you run the loop.

 

local function textListener( event )
    if ( event.phase == "editing" ) then
	lowerS = lower( event.text )
	lengthS = len(lowerS)
	match = false
	print( "\n----------------\npossible matches:" )
	if lengthS > 0 then
		for i, j in pairs( t ) do
			if i:sub( 1, lengthS ) == lowerS then
				print( j.name )
				if not match then
					match = true
				end
			end
		end
	end
	if not match then
		print( "0 matches found" )
	end
    end
end



[topic_controls]
[/topic_controls]

Also tagged with one or more of these keywords: string, input, user, lower, event