Get JavaScript variables back from HTMLViewer without changing the title.

I posted this by mistake in WebSDK. Sorry.

While looking into getting cookies back from the HTMLViewer, I just found a new way to return the JavaScript variable to Xojo without messing up the page title, which appears in Chrome or Internet explorer.

Instead of using the Titlechange event, i use the CancelLoad one.

Here is an example :

In a button, the code that gets cookies :

Sub Action() HTMLViewer1.ExecuteJavaScript("window.location='jsreturn'+document.cookie;") End Sub
Note the “jsreturn” token at the beginning, which will be used to distinguish between regular URLs and a JavaScript variable.

In the CancelLoad event, we look if the token is present. If so, the URL is decoded, its encoding defined, then split with “jsreturn”, and finally available in the array jsreturn(1). Used here in a MsgBox.

Function CancelLoad(URL as String) As Boolean if instr(URL,"jsreturn") > 0 then dim theURLString as string theURLString = DefineEncoding(DecodeURLComponent(URL), Encodings.UTF8 ) dim jsreturn() as string = split(theURLString,"jsreturn") MsgBox Replaceall(jsreturn(1),";",EndOfLine) return true end if End Function

I find it easier to just use StatusChanged. That way it doesn’t mess with the title, doesn’t show up anywhere, and doesn’t require you to interject page loads.

HTMLViewer1.ExecuteJavaScript("window.status= /* the result of whatever js you're running */;")

Sub StatusChanged(newStatus as String) System.DebugLog("The status is now: " + newStatus) End Sub

If you are Mac only you can use a declare…

Function EvaluateJavaScript(Extends viewer As HTMLViewer, script As String) As String #if TargetCocoa Declare Function stringByEvaluatingJavaScriptFromString Lib "Cocoa" Selector "stringByEvaluatingJavaScriptFromString:" (id As Integer, script As CFStringRef) As CFStringRef Return stringByEvaluatingJavaScriptFromString(viewer.Handle, script) #else #Pragma unused script #endif End Function

[quote=188698:@Tim Parnell]I find it easier to just use StatusChanged. That way it doesn’t mess with the title, doesn’t show up anywhere, and doesn’t require you to interject page loads.

HTMLViewer1.ExecuteJavaScript("window.status= /* the result of whatever js you're running */;")

Sub StatusChanged(newStatus as String) System.DebugLog("The status is now: " + newStatus) End Sub [/quote]

I just tried to use that, but it appears that property is not supported anymore in all major browsers. See http://www.w3schools.com/jsref/prop_win_status.asp

[quote]Note: The status property does not work in the default configuration of IE, Firefox, Chrome, Safari or Opera 15 and newer. To allow scripts to change the text of the status, the user must set the dom.disable_window_status_change preference to false in the about:config screen. (or in Firefox: “Tools - Options - Content -Enable JavaScript / Advanced - Allow scripts to change status bar text”).
[/quote]

I seems it was possible in the past, but window.status has been removed because it was used to fake links.

I found no way to change the dom.disable_window_status_change preference in HTMLViewer, so this method is unavailable.

The browsers may be blocking out that functionality, but it does not mean that it was removed from the actually rendering engine (or whatever part of the puzzle takes care of it)

Indeed, the functionality may still be there. However, I could not find any easy way to change that setting. The Mozilla site that documentation constantly refers to offers no technical information beyond using the FireFox settings, which is of course inadequate for HTMLViewer.

I am content with the CancelLoad method I posted initially, but I though I would test the Status method, as it is way simpler. I reported my finding to spare other readers from trying it and not getting any result.

Your declare is ideal on Mac. Cross platform can use other methods.

I will look at doing declares for the other two platforms…

Super. Thank you in advance.

Michel, I haven’t had any issues with window.status within Xojo, has an issue presented itself in a newer version? The last version I have tested with is 2015r1

OK. Just tested with 2015R1 and 2015R2.2 on Mac.

It appears it still works on Mac with Native renderer.

Not with WebKit. Not under Windows no matter the renderer.

I would not trust that to work forever. It has been removed from all major browsers, and according to W3C, that includes Safari.

Apple has been aware of the dangers of window.status for some time.
See https://lists.apple.com/archives/security-announce/2007/Nov/msg00003.html

Isn’t the native renderer for Mac WebKit?
Which version of Windows?

[quote=202925:@Tim Parnell]Isn’t the native renderer for Mac WebKit?
Which version of Windows?[/quote]

Yes everything is WebKit on Mac, but fact remains window.status does not work if one sets renderer to Webkit.

I tested under Windows 8.1 and Windows 10 alike.

You can test yourself.

OK. I just tried to change the status in Safari 9. Does not work.

Okay, I’m not concerned about browsers at all.
Actual in-xojo html viewer status changes is what I’m concerned with.

I only have Windows 7. If you have some spare time and could test HTML Edit on Windows 8 and 10 I would really appreciate it. This thread has me concerned so I’m going to switch it over to titlechanged later today.

[quote=203245:@Tim Parnell]Okay, I’m not concerned about browsers at all.
Actual in-xojo html viewer status changes is what I’m concerned with.

I only have Windows 7. If you have some spare time and could test HTML Edit on Windows 8 and 10 I would really appreciate it. This thread has me concerned so I’m going to switch it over to titlechanged later today.[/quote]

It lets me enter text change attributes and fonts, add pictures. Is there anything I should do besides that in the demo ?

[quote=188810:@shao sean]If you are Mac only you can use a declare…

Function EvaluateJavaScript(Extends viewer As HTMLViewer, script As String) As String #if TargetCocoa Declare Function stringByEvaluatingJavaScriptFromString Lib "Cocoa" Selector "stringByEvaluatingJavaScriptFromString:" (id As Integer, script As CFStringRef) As CFStringRef Return stringByEvaluatingJavaScriptFromString(viewer.Handle, script) #else #Pragma unused script #endif End Function[/quote]

OK. Today I need to return a value so I tried that, and it simply does not work for complex scripts.

It seems to work only for elementary scripts such as

return 'hello' 

Even assigning a variable and it no longer works :

var myvar = 'hello' ; return myvar

Unless I completely missed something important, I rather go back to statuschanged…

Stumbled on this comment on stackoverflow

Sure enough this script works

var myvar = 'hello' ;  myvar

[quote=240234:@Will Shank]Stumbled on this comment on stackoverflow

Sure enough this script works

var myvar = 'hello' ;  myvar

Thank you Will :slight_smile:

I can’t find a more recent thread than this for getting variables from Javascript in an HTMLVIewer back to xojo.

Is there a better and less-hacky cross-platform method for obtaining the value of a variable in JavaScript than using the TitleChanged event?

Trouble with titlechanged is you are limited in the length returned. Statuschanged still works with default renderer in 2018r2 macOS, but the question is for how much longer.