Android Question Button click in B4A WebView

chaurcey

Member
Hi I have a webview that loads a page with a print button on it. But a click does not load the default print functionality as in a browser.
I have the override url but B4A does not go there as when a URL is clicked. It goes to the page_finished but there is no way to tell that it is a button click as the URL field is what is in the browser it seems.

I also loaded a file chooser test page and the file chooser button click does not seem to do anything either.

Any ideas?
 

ilan

Expert
Licensed User
Longtime User
i am not sure i have understood you question. do you load a website to the webview and the buttons it that website are not working?
or are you trying to run a button click event in your b4a app that should be trigger from a button click inside the webview?
 
Upvote 0

Ivica Golubovic

Active Member
Licensed User
Native WebView does not support active buttons because it does not have the required event. You must use a library or insert java code for the required event. I suggest you try UltimateWebView. Pay attention to the following events:
  • FileChooserInitialized (FilePathCallback As Object, FileChooserParams1 As FileChooserParams)
  • OverrideUrlWithExternalAppIntent (WebResourceRequest1 As WebResourceRequest, ExternalAppIntent As Intent) As Boolean
You can find library, instructions and documentation here:
 
Upvote 0

chaurcey

Member
Use UltimateWebview or WebviewExtra... They would solve most of your issues..

i am not sure i have understood you question. do you load a website to the webview and the buttons it that website are not working?
or are you trying to run a button click event in your b4a app that should be trigger from a button click inside the webview?
It is the button in the website loaded into webview that is not working as I expect when clicked. Code is:
WebView1.LoadUrl("https://www.occ.treas.gov/about/who-we-are/history/1866-1913/Index-occ-history-1866-1913.html")

The social media buttons on the site work but not the print button yet it works if I use the OpenBrowser intent.

A couple of members have recommended UltimateWebView which I will take a look at. Also will look at WebviewExtra.

Appreciate everyone's replies as I am fairly new to B4A and not familiar with all the libraries and functionality.
 
Upvote 0

chaurcey

Member
Hi I have a webview that loads a page with a print button on it. But a click does not load the default print functionality as in a browser.
I have the override url but B4A does not go there as when a URL is clicked. It goes to the page_finished but there is no way to tell that it is a button click as the URL field is what is in the browser it seems.

I also loaded a file chooser test page and the file chooser button click does not seem to do anything either.

Any ideas?
The webpage I was loading into webview is https://www.occ.treas.gov/about/who-we-are/history/1866-1913/Index-occ-history-1866-1913.html

Looking at the page source, it has a print button defined by the following code fragment:
<a href="#" role="button" onclick="printFriendly('.occ-grid1-1')">

Was looking at B4A Webview to provide more of an inapp look/feel but for now sticking with providing a button to open page in browser since I am handling arbitrary pages with arbitrary links and arbitrary buttons.

WebView including UltimateWebView does not seem to generate an event when the inputtype/role is "button" with an onclick javascript. it does if it is type "submit with onclick which of course produces the form action.

Looks like it is a limitation of android webview rather than b4a as android webview does not seem to have an onclick event. Also android webview does not seem to support javascript as part of the printmanager per https://developer.android.com/training/printing/html-docs which says "You cannot use JavaScript in a HTML document to trigger printing." in android Webview.

Look like android webview is designed for known custom pages not arbitrary pages but I am not an expert on webview.

UltimateView ShouldInterceptRequest event does receive the above print button click but no way to tell it was that button except searching on the word print but of course the word may not be print for arbitray pages especially when page is in non-English.

UltimateView certainly offer more functionality especially events than Webview so I will incorporate it in future code.

Again, opening page in browser is safest route as I see it for now unless I am missing something.

Again, thanks everyone for the great help.
 
Upvote 0

Ivica Golubovic

Active Member
Licensed User
The webpage I was loading into webview is https://www.occ.treas.gov/about/who-we-are/history/1866-1913/Index-occ-history-1866-1913.html

Looking at the page source, it has a print button defined by the following code fragment:
<a href="#" role="button" onclick="printFriendly('.occ-grid1-1')">

Was looking at B4A Webview to provide more of an inapp look/feel but for now sticking with providing a button to open page in browser since I am handling arbitrary pages with arbitrary links and arbitrary buttons.

WebView including UltimateWebView does not seem to generate an event when the inputtype/role is "button" with an onclick javascript. it does if it is type "submit with onclick which of course produces the form action.

Looks like it is a limitation of android webview rather than b4a as android webview does not seem to have an onclick event. Also android webview does not seem to support javascript as part of the printmanager per https://developer.android.com/training/printing/html-docs which says "You cannot use JavaScript in a HTML document to trigger printing." in android Webview.

Look like android webview is designed for known custom pages not arbitrary pages but I am not an expert on webview.

UltimateView ShouldInterceptRequest event does receive the above print button click but no way to tell it was that button except searching on the word print but of course the word may not be print for arbitray pages especially when page is in non-English.

UltimateView certainly offer more functionality especially events than Webview so I will incorporate it in future code.

Again, opening page in browser is safest route as I see it for now unless I am missing something.

Again, thanks everyone for the great help.
Yes, you are right, webview does not support the javascript command window.print(). Printing could be done via getPrintAdapter but the problem is how to catch the click of a button and whether that button is intended for printing content. In either case, on UltimateWebView, when you click the print button, a ConsoleMessage event is triggered that reports a javascript error. Here you can find some way to recognize if it is a content print button and insert java code to print webview content. Cheers.
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
The webpage I was loading into webview is https://www.occ.treas.gov/about/who-we-are/history/1866-1913/Index-occ-history-1866-1913.html

Looking at the page source, it has a print button defined by the following code fragment:
<a href="#" role="button" onclick="printFriendly('.occ-grid1-1')">

Was looking at B4A Webview to provide more of an inapp look/feel but for now sticking with providing a button to open page in browser since I am handling arbitrary pages with arbitrary links and arbitrary buttons.

WebView including UltimateWebView does not seem to generate an event when the inputtype/role is "button" with an onclick javascript. it does if it is type "submit with onclick which of course produces the form action.

Looks like it is a limitation of android webview rather than b4a as android webview does not seem to have an onclick event. Also android webview does not seem to support javascript as part of the printmanager per https://developer.android.com/training/printing/html-docs which says "You cannot use JavaScript in a HTML document to trigger printing." in android Webview.

Look like android webview is designed for known custom pages not arbitrary pages but I am not an expert on webview.

UltimateView ShouldInterceptRequest event does receive the above print button click but no way to tell it was that button except searching on the word print but of course the word may not be print for arbitray pages especially when page is in non-English.

UltimateView certainly offer more functionality especially events than Webview so I will incorporate it in future code.

Again, opening page in browser is safest route as I see it for now unless I am missing something.

Again, thanks everyone for the great help.

you are mistaken in some of your conclusions. in any case, it was not difficult to print the url you refer to from within a webview (no browsers were harmed) on my local network-attached printer. see attached. we can talk about it unless you've moved on.
 

Attachments

  • print.jpg
    print.jpg
    163 KB · Views: 184
Upvote 0

chaurcey

Member
you are mistaken in some of your conclusions. in any case, it was not difficult to print the url you refer to from within a webview (no browsers were harmed) on my local network-attached printer. see attached. we can talk about it unless you've moved on.
Thanks for the response.

I am an old Visual BASIC developer but new to B4A and Android so I certainly do not know as much as some. That is why I used the word seems in my write up earlier as I realize I may be missing some techniques available in B4A/Java.

I know how to print the page. I just don't know how to trap the print button with certainity. So if you could please share what event in WebView or UlitimateWebView or Webview extras or non-event process you used that would definitely be appreciated or whether you used native java and how you determined it was the print button that was clicked, etc.

Again, thanks.
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
what works in this particular case will not necessarily work in others.
you don't necessarily need the libraries you refer to, although in a
different case, you might.

you need a few lines of inline java, an event sub in the app, and
familiarity with webview and b4a that you do not have yet.

we were expecting an error to be thrown when javascript's window.print()
is called. we do not actually get that far; two different errors are thrown
both are reported back to b4a. one holds the key. window.print() might
have held the key too, but you'll have to wait for another day and a
different webpage to find out (or generate it yourself in a dummy webpage.)

the "key" is a reference (in the literal sense, not the programming one) to
the .js file in which it occurred. that tells you the print button has been
clicked on. once you know that, you can print the page.

if you add a chromeclient (via a library), you will see errors seen by the
webview and sent to the console. you see them in the b4a log, but
they are not helpful, except in a post mortem. under normal circumstances,
you can't do anything that affects how the app behaves. however, if you
create your own chromeclient and override its onconsole() method, you
can raise an event in b4a (exactly like the pagefinished or overrideurl
events raised by webview and webviewextras, etc). so now, instead of
seeing errors in the log, you'll see them in the new event sub. now
you can control your destiny. if a console message refers to a
printing error, you launch your own page print. the user thinks he's
printing the page.

attached is the project. it should work out of the box. i tried it twice
before archiving. when you say you know how to print the page, i
assume you're referring to the Printing library. if not, you'll either
need to find it somewhere in the bowels of b4x or you need to
remove the few references to it and replace them with your own
print function. when i was initially trying to solve your problem,
i used my own webpage printing library, having forgotten b4a
already had one. so i used the Printing library in my example to
keep things simple. if you don't have the library, you'll get an
error as soon as you load the project. otherwise, all you need
is the javaobject library
 

Attachments

  • webprint.zip
    9.4 KB · Views: 206
Last edited:
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
for whatever reason, if you edit a reply (as i did above), as opposed to adding a new reply, the system does not alter the date of the edited reply. as a result, if a thread is found on page 6, it will remain on page six even though the last reply may have been edited a few minutes ago. it is what it is; i'm not here to judge.

i am therefore "touching" the thread to move it up in the event queue, should anyone have been following its denouement and grown tired of paging through the posts looking for it. if you weren't following it, please move along. nothing to see here.
 
Upvote 0

Ivica Golubovic

Active Member
Licensed User
what works in this particular case will not necessarily work in others.
you don't necessarily need the libraries you refer to, although in a
different case, you might.

you need a few lines of inline java, an event sub in the app, and
familiarity with webview and b4a that you do not have yet.

we were expecting an error to be thrown when javascript's window.print()
is called. we do not actually get that far; two different errors are thrown
both are reported back to b4a. one holds the key. window.print() might
have held the key too, but you'll have to wait for another day and a
different webpage to find out (or generate it yourself in a dummy webpage.)

the "key" is a reference (in the literal sense, not the programming one) to
the .js file in which it occurred. that tells you the print button has been
clicked on. once you know that, you can print the page.

if you add a chromeclient (via a library), you will see errors seen by the
webview and sent to the console. you see them in the b4a log, but
they are not helpful, except in a post mortem. under normal circumstances,
you can't do anything that affects how the app behaves. however, if you
create your own chromeclient and override its onconsole() method, you
can raise an event in b4a (exactly like the pagefinished or overrideurl
events raised by webview and webviewextras, etc). so now, instead of
seeing errors in the log, you'll see them in the new event sub. now
you can control your destiny. if a console message refers to a
printing error, you launch your own page print. the user thinks he's
printing the page.

attached is the project. it should work out of the box. i tried it twice
before archiving. when you say you know how to print the page, i
assume you're referring to the Printing library. if not, you'll either
need to find it somewhere in the bowels of b4x or you need to
remove the few references to it and replace them with your own
print function. when i was initially trying to solve your problem,
i used my own webpage printing library, having forgotten b4a
already had one. so i used the Printing library in my example to
keep things simple. if you don't have the library, you'll get an
error as soon as you load the project. otherwise, all you need
is the javaobject library
Your example works for that particular webpage, but not every webpage will contain printer-frendly in its URL. If you read my answer above, you will see that it indicates exactly what you did in your example. I repeat, your solution will only work for websites that contain printer-friendly text in their URL. In any other case, your solution will not start printing. Cheers.
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
Your example works for that particular webpage, but not every webpage will contain printer-frendly in its URL. If you read my answer above, you will see that it indicates exactly what you did in your example. I repeat, your solution will only work for websites that contain printer-friendly text in their URL. In any other case, your solution will not start printing. Cheers.
i stated quite clearly that my solution works in this particular case. thank you for repeating that. twice. but let's repeat it again: my solution works in this case. this case is, after all, what we are talking about. i was hoping to engage the OP in a discussion of why a solution to his problem would be unique.

solutions to given problems are sometimes discovered by various people independently of one other. if you had wanted to help the OP, you could have presented a solution. next time, provide the solution so as to avoid the perception that others are taking your ideas.

when it was clear the OP did not know how to follow your answer, i provided a my solution. by the way, did i mention that my solution is for this particular case?

cheers.
 
Upvote 0

Ivica Golubovic

Active Member
Licensed User
i stated quite clearly that my solution works in this particular case. thank you for repeating that. twice. but let's repeat it again: my solution works in this case. this case is, after all, what we are talking about. i was hoping to engage the OP in a discussion of why a solution to his problem would be unique.

solutions to given problems are sometimes discovered by various people independently of one other. if you had wanted to help the OP, you could have presented a solution. next time, provide the solution so as to avoid the perception that others are taking your ideas.

when it was clear the OP did not know how to follow your answer, i provided a my solution. by the way, did i mention that my solution is for this particular case?

cheers.
I didn't even think to say you stole my idea at any point. I’m just saying that the question was how to capture an event when a print button is clicked, and that same event indicates that it’s just for print content. It seems to me that I understood the point of the question well.
 
Upvote 0

chaurcey

Member
what works in this particular case will not necessarily work in others.
you don't necessarily need the libraries you refer to, although in a
different case, you might.

you need a few lines of inline java, an event sub in the app, and
familiarity with webview and b4a that you do not have yet.

we were expecting an error to be thrown when javascript's window.print()
is called. we do not actually get that far; two different errors are thrown
both are reported back to b4a. one holds the key. window.print() might
have held the key too, but you'll have to wait for another day and a
different webpage to find out (or generate it yourself in a dummy webpage.)

the "key" is a reference (in the literal sense, not the programming one) to
the .js file in which it occurred. that tells you the print button has been
clicked on. once you know that, you can print the page.

if you add a chromeclient (via a library), you will see errors seen by the
webview and sent to the console. you see them in the b4a log, but
they are not helpful, except in a post mortem. under normal circumstances,
you can't do anything that affects how the app behaves. however, if you
create your own chromeclient and override its onconsole() method, you
can raise an event in b4a (exactly like the pagefinished or overrideurl
events raised by webview and webviewextras, etc). so now, instead of
seeing errors in the log, you'll see them in the new event sub. now
you can control your destiny. if a console message refers to a
printing error, you launch your own page print. the user thinks he's
printing the page.

attached is the project. it should work out of the box. i tried it twice
before archiving. when you say you know how to print the page, i
assume you're referring to the Printing library. if not, you'll either
need to find it somewhere in the bowels of b4x or you need to
remove the few references to it and replace them with your own
print function. when i was initially trying to solve your problem,
i used my own webpage printing library, having forgotten b4a
already had one. so i used the Printing library in my example to
keep things simple. if you don't have the library, you'll get an
error as soon as you load the project. otherwise, all you need
is the javaobject library
Greetings,

I been busy on other things so just got back around to looking at my post and the responses.

Thanks for the work you and everyone put into answering my post.

I understand your approach but as you and Ivica said it is not general enough to handle every webpage as my webpages of interest are arbitrary not pre-determined. So I think providing browser access to the page is the simplest thing for me to do right now. The way I handle it is I still use webview but provide a button to bring the page up in the browser if a webpage button does not give a response. I note that in a Help function. Not optimally user friendly but is functional. I am in the prototype stage so don't won't to spend a lot of time right now on those seemingly rare button circumstances.

I was looking for a B4A only solution without going into java.

It seems like webview and its variants do not invoke the javascript code as a regular browser does. That seems to be by design as the native android webview does not seem to do so either per the article I referenced earlier at https://developer.android.com/training/printing/html-docs.

Again thanks to you and everyone for their input. Hopefully we all fine tuned our understanding of B4A.

I am new to B4A and chose it because I am familiar with Visual BASIC syntax. I find B4A to be a powerful platform so five stars to Erel and any others involved in B4X development/maintenance.

I began programming a long time ago and one thing I have learned is that humility is an important virtue in programming as it is in every area of life.

Looking forward to continued interaction in this forum on whatever question I can offer assistance as time permits.

Again, thanks to everyone for your responses.
 
Upvote 0

chaurcey

Member
Your example works for that particular webpage, but not every webpage will contain printer-frendly in its URL. If you read my answer above, you will see that it indicates exactly what you did in your example. I repeat, your solution will only work for websites that contain printer-friendly text in their URL. In any other case, your solution will not start printing. Cheers.
Greetings,

Thanks for your time and help. Please see my comment to drgottjr I posted just prior to this one.
 
Upvote 0
Top