Please Help -> Problem with json and tableview

Hey

I have a json file with data that I plan to have on a server or dropbox but for now I just have it locally on the computer when testing on simulator.

When I open the file, I can’t get it to add the entries to the tableview row, they return empty everytime. The json is valid, what am I doing wrong?

json file:

{  
 "data": [  
  
 {  
 "weekDays": [  
 {  
  
 "day":{  
 "name":"Monday",  
  
 "data": [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "day":{  
 "name":"Tuesday",  
  
 "data": [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "day":{  
 "name":"Wednesday",  
  
 "data": [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 }  
 ]  
 }  
 ]  
}  

When I try to get the value for something like the name of the day I do:

local storyboard = require( "storyboard" )  
local scene = storyboard.newScene()  
local widget = require("widget")  
local json = require("json")  
  
function scene:createScene( event )  
 local group = self.view  
 local myFile  
 local data  
-- Above here I got the jsonFile (fileName, fileDir) function.  
  
 myFile = json.decode( jsonFile( "activities.json", system.DocumentsDirectory ) )  
  
 for i = 1, #myFile.data do  
 local function onRowRender( event )  
 local row = event.target  
 local rowGroup = event.view  
  
 if row.isCategory then  
 row.dayText = display.newRetinaText(rowGroup, myFile.data[i].weekDays.day.name, 0, 0, "Helvetica-Bold", 16)  
 row.dayText(display.TopLeftReferencePoint)  
 row.dayText.x = 10;  
 row.dayText.y = 5;  
 row.dayText:setTextColor(123, 123, 123, 255)  
 else  
 row.dayActivity = display.newRetinaText(rowGroup, myFile.data[i].weekDays.day.data.name, 0, 0, "Helvetica-Bold", 12)  
 row.dayActivity(display.TopLeftReferencePoint)  
 row.dayActivity.x = 10;  
 row.dayActivity.y = 10;  
 row.dayActivity:setTextColor(123, 123, 123, 255)  
 end  
  
 end  
  
 local isCategory  
 local rowColor  
 local rowHeight  
 local lineColor  
  
  
 if i == 1 or i == 6 or i == 11 then   
 isCategory = true  
 rowHeight = 24  
 lineColor = {0,0,0,255}  
 else  
 isCategory = false  
 rowHeight = 64  
 lineColor = {0,0,0,255}  
 end  
  
 myTableView:insertRow{  
 height = rowHeight,  
 rowColor = rowColor,  
 lineColor = lineColor,  
 isCategory = isCategory,  
 --onEvent=onRowTouch,  
 onRender = onRowRender  
 --listener = listener  
 }  
 end  
end  

Nothing shows up on the simulator, why is that?
Is it also possible to make so the Categories cell number is based on how many entries in the non category?

Thanks Cindy [import]uid: 65840 topic_id: 21631 reply_id: 321631[/import]

I still can’t figure out where it goes wrong, I’ve tried so many ways now and none of them works.
If this;

 for i = 1, #myFile.data do  
myFile.data[i].weekDays.day.name  
myFile.data[i].weekDays.day.data.name  
  
 for i = 1, #myFile do  
myFile.data.weekDays.day.name  
myFile.data.weekDays.day.data.name  
  
 for i = 1, #myFile do  
myFile[i].data.weekDays.day.name  
myFile[i].data.weekDays.day.data.name  
  
 for i = 1, #myFile.data.weekDays do  
myFile.data.weekDays[i].day.name  
myFile.data.weekDays[i].day.data.name  

Sometimes it give an error, sometimes it don’t and returns one empty cell.
I have removed the isCategory stuff and just try to get at least one field correct but nothing seems to work.

 for i = 1, #myFile.data do  
myFile.data[i].weekDays.day.data.name  
  
 for i = 1, #myFile do  
myFile.data.weekDays.day.data.name  
  
 for i = 1, #myFile do  
myFile[i].data.weekDays.day.data.name  
  
 for i = 1, #myFile.data.weekDays do  
myFile.data.weekDays[i].day.data.name  

Can someone fill in the blanks what I am doing wrong?
Thanks. [import]uid: 65840 topic_id: 21631 reply_id: 85882[/import]

Did you find your problem?

I created a project, put ‘activities.json’ file in the project directory and the following code worked fine.

local json = require("json")  
  
 local jsonFile = function( theFile, base )  
   
 if not base then   
 base = system.ResourceDirectory;   
 end  
   
 local path = system.pathForFile( theFile, base )  
   
 local contents  
   
 local file = io.open( path, "r" )  
 if file then  
  
 contents = file:read( "\*a" )  
 io.close( file )   
 end  
   
 return contents  
 end  
   
 myFile = json.decode( jsonFile( "activities.json", system.ResourceDirectory ) )  
for i = 1, #myFile.data do  
print (myFile.data[i].weekDays.name)  
end  

console output:

Monday
Tuesday
Wednesday
Thursday
Friday

[import]uid: 14119 topic_id: 21631 reply_id: 87314[/import]

After reading your post again, I’m not sure where you were placing the ‘activities.json’ file. In your code you use ‘system.DocumentsDirectory’ so I assume you placed the json file in the ‘Documents’ directory. I placed the json file in the project directory so I used ‘system.ResourceDirectory’ in the json.decode statement.

Could that be the problem?

Jeff
[import]uid: 14119 topic_id: 21631 reply_id: 87317[/import]

Thanks for the reply, the json is downloaded to documents dir from a server. I do that in my main.lua right on startup of the app.

I have figured out how to get the jsondata into my tableview but when I build for device the app crashes when I start it. I have read in other post and searched stackoverflow for answers but I can’t get the crash to go away on device.

I don’t have any errors in my code, it builds fine.

This is the xcode error i get…

Lua Runtime Error: lua_pcall failed with status: 2, error message is: bad argument #1 to ‘?’ (string expected, got nil)

So what is causing this?

I have looked at other post and everyone seems to do it this way and get it to work…
[import]uid: 65840 topic_id: 21631 reply_id: 88075[/import]

I compared my json file to the facebook json response in another thread and changed my file accordingly to make it work but it still doesn’t populate the tableview rows.

Can someone PLEASE help me with this, the json is validated…

activities.json

{  
 "data": [  
 {  
 "weekDays":   
 {  
 "name": "Monday"  
 },  
 "activity":   
 {  
 "data":   
 [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "time":"12.20",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "time":"12.20",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "weekDays":   
 {  
 "name": "Tuesday"  
 },  
 "activity":   
 {  
 "data":   
 [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "time":"12.20",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "time":"12.20",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "weekDays":   
 {  
 "name": "Wednesday"  
 },  
 "activity":   
 {  
 "data":  
 [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "time":"12.20",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "time":"12.20",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "weekDays":   
 {  
 "name": "Thursday"  
 },  
 "activity":   
 {  
 "data":  
 [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "time":"12.20",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "time":"12.20",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 },  
 {  
 "weekDays":   
 {  
 "name": "Friday"  
 },  
 "activity":  
 {  
 "data":   
 [  
 {  
 "name": "Dancing",  
 "price": "$13.95",  
 "time":"12.20",  
 "description": "Latin dance for all ages."  
 },  
 {  
 "name": "Bodypump",  
 "price": "Free",  
 "time":"12.20",  
 "description": "Get toned for the summer!"  
 }  
 ]  
 }  
 }  
 ]  
}  

And here’s my tableview code from my tabbar application.

[code]
local storyboard = require( “storyboard” )
local scene = storyboard.newScene()
local widget = require(“widget”)
local json = require(“json”)

function scene:createScene( event )
local row = event.row
local group = self.view
local myFile
local data

local jsonFile = function( theFile, base )

if not base then
base = system.ResourceDirectory;
end

local path = system.pathForFile( theFile, base )

local contents

local file = io.open( path, “r” )
if file then

contents = file:read( “*a” )
io.close( file )
end

return contents
end

myFile = json.decode( jsonFile( “activities.json”, system.DocumentsDirectory ) )

for i = 1, #myFile.data do
local function onRowRender( event )
local row = event.target
local rowGroup = event.view
local dayTxt
local nameTxt
local priceTxt
local descTxt

if row.isCategory then
row.dayTxt = display.newRetinaText(rowGroup, myFile.data[i].weekDays.name, 0, 0, “Helvetica-Bold”, 16)
row.dayTxt(display.TopLeftReferencePoint)
row.dayTxt.x = 10;
row.dayTxt.y = 5;
row.dayTxt:setTextColor(123, 123, 123, 255)

else

row.nameTxt = display.newRetinaText(rowGroup, myFile.data[i].activity.data.name, 0, 0, “Helvetica-Bold”, 12)
row.nameTxt(display.TopLeftReferencePoint)
row.nameTxt.x = 10;
row.nameTxt.y = 10;
row.nameTxt:setTextColor(123, 123, 123, 255)

row.priceTxt = display.newRetinaText(rowGroup, myFile.data[i].activity.data.price, 0, 0, “Helvetica-Bold”, 12)
row.priceTxt(display.TopRightReferencePoint)
row.priceTxt.x = 290;
row.priceTxt.y = 10;
row.priceTxt:setTextColor(123, 123, 123, 255)

row.timeTxt = display.newRetinaText(rowGroup, myFile.data[i].activity.data.time, 0, 0, “Helvetica”, 10)
row.timeTxt(display.TopLeftReferencePoint)
row.timeTxt.x = 10;
row.timeTxt.y = 25;
row.timeTxt:setTextColor(123, 123, 123, 255)

row.descTxt= display.newRetinaText(rowGroup, myFile.data[i].activity.data.description, 0, 0, 300, 0 “Helvetica”, 10)
row.descTxt(display.TopLeftReferencePoint)
row.descTxt.x = 10;
row.descTxt.y = 35;
row.descTxt:setTextColor(123, 123, 123, 255)

end

end

local isCategory
local rowColor
local rowHeight
local lineColor

if i == 1 or i == 6 or i == 11 then
isCategory = true
rowHeight = 24
lineColor = {0,0,0,255}
else
isCategory = false
rowHeight = 80
lineColor = {0,0,0,255}
end

myTableView:insertRow{
height = rowHeight,
rowColor = rowColor,
lineColor = lineColor,
isCategory = isCategory,
–onEvent=onRowTouch,
onRender = onRowRender
–listener = listener
}
end
end

– Called immediately after scene has moved onscreen:
function scene:enterScene( event )
local group = self.view

– Do nothing
end

– Called when scene is about to move offscreen:
function scene:exitScene( event )
local group = self.view

– INSERT code here (e.g. stop timers, remove listenets, unload sounds, etc.)

end

– If scene’s view is removed, scene:destroyScene() will be called just prior to:
function scene:destroyScene( event )
local group = self.view

– INSERT code here (e.g. remove listeners, remove widgets, save state variables, etc.)

end


– END OF YOUR IMPLEMENTATION

– “createScene” event is dispatched if scene’s view does not exist
scene:addEventListener( “createScene”, scene )

– “enterScene” event is dispatched whenever scene transition has finished
scene:addEventListener( “enterScene”, scene )

– “exitScene” event is dispatched whenever before next scene’s transition begins
scene:addEventListener( “exitScene”, scene )

– “destroyScene” event is dispatched before view is unloaded, which can be
– automatically unloaded in low memory situations, or explicitly via a call to
– storyboard.purgeScene() or storyboard.removeScene().
scene:addEventListener( “destroyScene”, scene )


return scene
[/code] [import]uid: 65840 topic_id: 21631 reply_id: 86170[/import]