Roku Developer Program

Developers and content creators—a complete solution for growing an audience directly.
cancel
Showing results for 
Search instead for 
Did you mean: 
Komag
Level 9

Why does this code crash? Just a string variable

	gS = 1 ' Base "Game Speed"
di = CreateObject("roDeviceInfo")
model = di.GetModel()
? model
? Type(model)
fastRokus = ["2400X", "2450X", "3000X", "3050X", "3100X", "4200X", "2700X", "2710X", "2720X"]
slowRokus = ["N1050", "N1000", "N1100", "2050X", "2050N", "N1101", "2100X", "2100N", "2000C"]
FOR EACH roku IN slowRokus
IF model = roku THEN gS = 2
END FOR
? model " is the model"
? "Game Speed set to " gS
? "Roku model " model


It correctly prints:
2050X
String
2050X is the model
Game Speed set to 2

Then it crashes with message: "Use of uninitialized variable" on line ? "Roku model " model

What the heck? I've already used that variable four times before that line, what gives? Does it have something to do with it being a String and not a roString? I believe I've printed strings that way before, but maybe I'm remembering wrong. Why would it work to use "model" first in the print ("2050X is the model"), but not second ("Roku model 2050X")?
0 Kudos
11 Replies
EnTerr
Level 8

Re: Why does this code crash? Just a string variable

That's really weird, yeah. My guess would be that either the error is coming from another line or that "model" on said line is misspelt somehow (e.g. having cyrillic "о" instead of latin "o", "е" instead of "e" - or an invisible non-space char). Try re-typing the line, let us know?

On a side note, checking for exact model id like that seem unreliable. Is likely to miss some models. I think a better ideas are:
  • use GetVersion() - specifically the major version# (3rd char). All slower models are on 3.x. Yes, it's a hack but it works.

  • You can test the performance instead of making assumptions by model. Like so:
    BrightScript Debugger> ti = createObject("roTimeSpan"): for _ = 1 to 1e5: end for: ? ti.TotalMilliseconds()
    74 '2xxx model, fw3

    BrightScript Debugger> ti = createObject("roTimeSpan"): for _ = 1 to 1e5: end for: ? ti.TotalMilliseconds()
    18 '3xxx model

    Later models are at least 4x faster in B/S than the fw3 ones. Given the particular loop example, i'll recommend using 36ms (geometric mean, sqr(74*18)) as cut-off margin in determining if it's slow (>36) or fast (<=36) model.
0 Kudos
NewManLiving
Level 7

Re: Why does this code crash? Just a string variable

Just off the cuff - You can experiment with functionality already built into the string object instead of mapping
They both have drawbacks ( the pattern may change ) but one is much shorter, although they both would have to be adjusted if the standard
should change:


Device = CreateObject( "roDeviceInfo" )
RokuModel = Device.GetModel()
RokuVersion = Device.GetVersion()

IsFast = ( RokuModel.Tokenize( "N,C,X" )[0].ToInt() >= 2400 and RokuVersion.Mid(2, 1).ToInt() > 3 )



Substituting whatever you consider to be fast based upon EnTerr's calculations
My Channels: 2D API Framework Presentation: https://owner.roku.com/add/2M9LCVC
Updated: 11-11-2015 - Completed Keyboard interface
The Joel Channel ( Final Beta )
0 Kudos
EnTerr
Level 8

Re: Why does this code crash? Just a string variable

"NewManLiving" wrote:
Substituting whatever you consider to be fast based upon EnTerr's calculations

But why check model#, that's round-about? Can simply do

function isSlowModel():
ti = createObject("roTimeSpan")
for _ = 1 to 1e5: end for
return (ti.TotalMilliseconds() > 36)
end function
0 Kudos
Komag
Level 9

Re: Why does this code crash? Just a string variable

So far I've only had a chance to test my game on two Rokus, my own Roku 2 XS 3100X and my friend's old Roku XD 2050X. I'm using a lot of sprites and some alpha blending, so I'd be curious if that FOR loop test correlates closely with actual game performance across different Roku models. If so, it's a nice solution, thank you EnTerr.

And yeah, NewManLiving, if I do end up still checking models, I should use a pattern so it will work with new Rokus, assuming they keep the pattern. Since that's a big unknown, plus I have no idea about thinks like the streaming stick or the Roku smart TVs, maybe just a quick performance check would be the best way to go. I'll know more after more actual game performance testing with different models
0 Kudos
Komag
Level 9

Re: Why does this code crash? Just a string variable

HA! The original post problem is somehow due to legacy Roku!

The code works fine on my Roku 2 XS 3100X, it's only on my friend's Roku XD 2050X that I get the "unitialized variable" crash!

If I add a semicolon it works without crashing:
? "Roku model "; model

But testing same sort of thing (not using semicolons) in other parts of my code it works fine, so something I don't understand is going on.
Example, later in the game code, this runs fine:
? "Intrct " objct.name ", trig " trig ", dist " dist ", y" y ", x" x ", sl1" sl1 ", sl2" sl2 ", rm" rm
0 Kudos
RokuMarkn
Level 7

Re: Why does this code crash? Just a string variable

Oh, I remember this bug. The problem is the 3.x parser misinterprets the "mod" at the beginning of "model" as the MOD operator. It shouldn't fail if you use a different name that doesn't start with "mod".

--Mark
0 Kudos
EnTerr
Level 8

Re: Why does this code crash? Just a string variable

"Komag" wrote:
So far I've only had a chance to test my game on two Rokus, my own Roku 2 XS 3100X and my friend's old Roku XD 2050X. I'm using a lot of sprites and some alpha blending, so I'd be curious if that FOR loop test correlates closely with actual game performance across different Roku models. If so, it's a nice solution, thank you EnTerr.

Let me put it this way: assuming you are dividing players in discrete groups ("slow" vs "fast"), the last fn i proposed will do no worse than checking model# and/or fw# (but potentially better). There is a big B/S performance gap between 1st gen and the later ones, of at least 4x. And then Roku-3 is roughly 4x faster than that, per experiments here viewtopic.php?f=34&t=66062&p=422729 .

The graphics engine is a whole another thing from the CPU, that's true - so timing empty loops won't give you exact idea on drawing speed - but as practical matter it is the same ballpark, magnitudinally/logarithmically there. Notice the fn has a wide safety margin of 2x, i placed the cut-off in the middle, so below #2050 and up to 2x faster will be "slow", where above #3100 and down to 2x slower will be "fast". It should give true result even if VM goes through evolutionary optimizations and pessimizations.

Now if you want to get a continuous-value measure of the drawing performance, presumably for the game to have more than 2 modes of drawing - the right way would be to do a mini-benchmark by drawing some sprites on screen and timing that. I don't think it is likely you'll need that, because of the way video hardware works - it outputs at 60Hz and because of VSYNC i believe we can only output with speed that is a factor of 60 frames/sec. In other words in practice you'll only get 60fps, 30fps, 15fps, 7.5fps and so on. So you end up with only two or three discrete buckets of animation speed, the rest of performance is "wasted" in SwapBuffers() waiting for VSYNC. I experienced my "2048" game prototype geting 30fps on 1st gen platforms and 60fps on the rest. TheEndless can probably say a word on this from his experience.

PS. acting on a hunch, i just switched to using single-buffered roScreen and #3100 rate jumped to 143fps (with minimal blinking), where #2050 went to 62fps (with awful screen tearing) but only for an empty board, then quickly drops down to ~30fps. Which confirms the VSYNC-ronization of double-buffering causing the "bucketing" from above.
0 Kudos
EnTerr
Level 8

Re: Why does this code crash? Just a string variable

"RokuMarkn" wrote:
Oh, I remember this bug. The problem is the 3.x parser misinterprets the "mod" at the beginning of "model" as the MOD operator. It shouldn't fail if you use a different name that doesn't start with "mod".

Nice. Really interesting bug!
Before anyone freaks out, i'll go ahead and speculate this problem probably can only happen in a PRINT statement that does not use ";" or "," as separators, because of the ambiguity in determining where expression ends. In normal expressions (1+model, 1*model, 1/model, 1^model) there is no trouble.

Use ";" between elements in PRINT, people! 8-)
0 Kudos
Komag
Level 9

Re: Why does this code crash? Just a string variable

"RokuMarkn" wrote:
Oh, I remember this bug. The problem is the 3.x parser misinterprets the "mod" at the beginning of "model" as the MOD operator. It shouldn't fail if you use a different name that doesn't start with "mod".

--Mark


Yup, I changed it to rModel and it works fine. Odd bug that. Thanks.

EnTerr, I'll probably do the fn test as you suggest, sounds like it's as good as anything Smiley Happy
0 Kudos