I have created a simple windows application that uses a webview2 to shows a Website in a winform. I need to close this windows application after submit button click on the website.
Is it possible?
I am new to Windows Development.
The solution really depends to the content and how the page works. In most cases you should not close the app immediately after clicking on submit button and you need to wait until you receive the response of the submit and if the submit is successful, then you can close the window.
Here I share two examples:
Handle submit event and call a C# method from WebView2
Detect success of a submitted survey form based on URL
Please keep in mind, both examples are here for learning purpose to give you some idea on handling js events in C#. You need to tweak them to make them working on your specific case.
Example 1 - Handle submit event and call a C# method from WebView2
In the following example you can learn:
How to handle submit event of the form
How to call a C# method from JavaScript code and pass js object to .NET
Here is the code:
WebView2Host host;
private async void TestForm_Load(object sender, EventArgs e)
{
await webView21.EnsureCoreWebView2Async();
host = new WebView2Host(this);
webView21.NavigateToString(
"<html>" +
"<head><title>Test from</title></head>" +
"<body>" +
"<form id='form1' action='/' method='post'>" +
"<input type='text' name='someProperty' value ='something'/>" +
"<input type='submit' value='Click me'/>" +
"</form>" +
"</body>");
webView21.CoreWebView2.AddHostObjectToScript("host", host);
webView21.CoreWebView2.DOMContentLoaded += CoreWebView2_DOMContentLoaded;
}
private async void CoreWebView2_DOMContentLoaded(object sender,
CoreWebView2DOMContentLoadedEventArgs e)
{
await webView21.ExecuteScriptAsync(
"var form = document.getElementById('form1');" +
"form.addEventListener('submit', function(e){" +
"var data = JSON.stringify(Object.fromEntries(new FormData(form)));" +
"window.chrome.webview.hostObjects.sync.host.OnSubmit(data);" +
"});");
}
public class WebView2Host
{
TestForm hostForm;
public WebView2Host(TestForm hostForm)
{
this.hostForm = hostForm;
}
public void OnSubmit(string data)
{
//data is in json format
MessageBox.Show($"data: {data}", "C# OnSubmit!");
//You can close form like this: hostForm.Close();
}
}
Exmaple 2 - Detect success of a submitted survey form based on URL
You can rely on any of the navigation events and check the URL of the page, to see whether the submit has been successful. In this example I show how you can do it with a google survey form:
private async void TestForm_Load(object sender, EventArgs e)
{
await webView21.EnsureCoreWebView2Async();
webView21.Source = new Uri("https://forms.gle/pspLBJFZW5z8J1K37");
webView21.CoreWebView2.SourceChanged += CoreWebView2_SourceChanged;
}
private void CoreWebView2_SourceChanged(object? sender,
CoreWebView2SourceChangedEventArgs e)
{
if (webView21.Source.ToString().EndsWith("/formResponse"))
{
MessageBox.Show("Submitted successfully.");
}
}
Related
I have a xaml page in which I have used a webbrowser control.I need to scroll down to the web page and once the bottom is reached,I have to enable a button.
Thanks in advance!
There's two part to this. The first is to detect, in Javascript, the moment when the browser reaches the bottom of the page. The second is to forward the event to the C# code.
Say you ask your WebBrowser control to navigate to a given page. First, in the C# code, subscribe to the Navigated event to inject the proper Javascript code:
private void WebBrowser_Navigated(object sender, NavigationEventArgs e)
{
const string Script = #"window.onscroll = function() {
if ((window.innerHeight + document.documentElement.scrollTop) >= document.body.offsetHeight) {
window.external.notify('bottom');
}
};";
this.WebBrowser.InvokeScript("eval", Script);
}
This Javascript code uses the window.external.notify method to notify the C# code. To receive the notification, you need to subscribe to the ScriptNotify event of the WebBrowser:
private void WebBrowser_ScriptNotify(object sender, NotifyEventArgs e)
{
if (e.Value == "bottom")
{
// Reached the bottom of the page
}
}
With the click event of a link button calling a server side method from Form1
Form1 aspx.cs page code:-
protected void lnkTakeAction_OnCommand(object sender, CommandEventArgs e)
{
if (e.CommandName == "duplicate")
{
//Some operations conditional
//If condition true
//call javascript method to call a javascript function to open a rad window
ScriptManager.RegisterStartupScript(this, typeof(System.Web.UI.Page), "ABC "ABCPopUp" + ID + "','Tag');", true);
}
}
Form1 aspx javascript code:-
function ABCPopUp(ID, Tag) {
var oWindow = window.radopen('XYZPage.aspx?ID=' + scoreMethodId + '&Tag=' + mode, 'rdWindowMapping');
oWindow.SetSize(600, 500);
oWindow.Center();
var titleBar = oWindow.GetTitlebar();
$telerik.$(titleBar).parent().hide();
return false;
}
Issue facing - The XYZPage is not opening.The same functionality works if I call the function ABCPopUp from javascript.But when I call from server side the form is not opening.Please give expert advice
Most likely, the script runs too early. You have two options:
use AJAX for the grid and do not include the RadWindow in the response
OR, use the Sys.Application.Load event to call your function: http://www.telerik.com/help/aspnet-ajax/window-troubleshooting-opening-from-server.html.
Okay, this one will be a fun one. I am building an authentication flow in my application. My application will open a modal window with a webbrowser element and browse to the auth URL. Then it wil monitor the URL changes of the webbrowser element for a specific string. When it finds the string, it does it's work to retrieve the access code, closes the window and then returns the code to the parent. My code is as follows:
The modal window:
public partial class Browser : Window
{
private string code = "";
private Uri navi;
public TwitchBrowser(Uri url)
{
InitializeComponent();
this.navi = url;
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
webBrowser.Navigate(this.navi);
webBrowser.Navigating += webBrowser_Navigating;
}
void webBrowser_Navigating(object sender, NavigatingCancelEventArgs e)
{
if (e.Uri.ToString().Contains("?code="))
{
this.code = e.Uri.ToString().Split('?')[1].Split('&')[0].Replace("code=", "");
this.DialogResult = true;
}
}
public string result
{
get { return code; }
}
}
The call from the parent:
string url = ...
Browser browser = new Browser(new Uri(url));
browser.Owner = parent;
if (browser.ShowDialog() == true)
{
password.Password = browser.result;
...
}
And of course, the error I get:
DialogResult can be set only after Window is created and shown as dialog.
The interesting thing is, the app WORKS! It gets the code and stores it in the password field as it's supposed to. So whats the point of the error? I mean, I know I can suppress it with a Try-Catch; but I'm afraid its the root of a larger problem.
You original code had a race condition in there. You were navigating in the creation of browser. The navigation complete could be fired before you called ShowDialog().
Instead stash away the url in a private variable and setup the WebBrowser in your Loaded event.
Now that you have fixed that, I am guessing that you want the Nagivated event instead of the Navigating event to check the returned URI.
It is still interesting that the Navigating event gives that error. I was able to reproduce it with a button click on the form, so I know the form is completely shown at that point.
I have created a web browser in c#
this was what i get when i opened my web browser and typed google. Then i searched google for something
the result was like this
But the url wasn't updated in address bar. How to update the address bar when user click on a link on any website in my web browser
In the first image the url was google.com
In the second image url was https://www.google.co.in/#hl=en&output=search&sclient=psy-ab like that some thing but it wasn't updated
You must update the textbox on top with the URL of the WebBrowserControl, using the webBrowser1_Navigating event.
private void webBrowser1_Navigating(object sender, WebBrowserNavigatingEventArgs e)
{
textbox1.text = webBrowser1.Url.ToString();
}
Check http://msdn.microsoft.com/en-us/library/system.windows.forms.webbrowser_events.
I think you can use Navigating event to detect when user starts search or navigates to another page.
The Form_Load must contain this:
private void Form1_Load(object sender, EventArgs e)
{
web = new WebBrowser();
web.Navigated += web_Navigated;
}
and this function:
private void web_Navigated(object sender, WebBrowserNavigatedEventArgs e)
{
textBox1.Text = web.Url.ToString();
}
I am creating the same button twice: once on Page_Load, and another on: Page_PreRender.
I expected to see the same behavior, however, the buttons created on Page_PreRender doesn't work the way intended. (i.e. property "causeValidation" remains true).
"I want to disable "causeValidation" for the button in page_preRender, and i want it there in PreRender. Also, I want the Button_Click function to execute for both buttons, currently it does only for button created on "Page_load" ".
I am looking for a solution or an explanation for this behavior.
Thank You.
Take a look at the code:
protected void Page_Load(object sender, EventArgs e)
{
form1.Controls.Add(GetButton("Button1", "Click"));
}
protected void page_PreRender(object sender, EventArgs e)
{
form1.Controls.Add(GetButton("Button3", "Click"));
}
private Button GetButton(string id, string name)
{
Button b = new Button();
b.Text = name;
b.ID = id;
b.CausesValidation = false;
b.Click += new EventHandler(Button_Click);
b.OnClientClick = "ButtonClick('" + b.ClientID + "')";
return b;
}
protected void Button_Click(object sender, EventArgs e)
{
ClientScript.RegisterClientScriptBlock(this.GetType(), ((Button)sender).ID, "<script>alert('Button_Click');</script>");
Response.Write(DateTime.Now.ToString() + ": " + ((Button)sender).ID + " was clicked");
}
and here is the javascript:
<script type="text/javascript">
function ButtonClick(buttonId) {
alert("Button " + buttonId + " clicked from javascript");
}
</script>
Update:
let me add this: Both buttons execute the client's script. This means that buttons are created. "see function GetButton() ".
Also, the reason why i have the button created "on preRender" instead of "on Page_Load" is that: if i have a form used to enter data into a table dynamically, and i add the data on button click, the the page will PostBack first, then execute the event handler, (i.e the data is added to the table but will show on NEXT postBack). So, PreRender is used to show the table AFTER it is updated by the button_click event.
I hope this addition is useful
As you see from this image, that represents asp.net page life cycle (copied from MSDN), Event Handling precedes PreRender. So, in order to fire Button_Click the button itself has to be created before the Event Handling. Page PreInit is a preferred place to add dynamic controls.
you can see it yourself, just add breakpoints at Page_Load, Page_PreRender, Button_Click. notice the order there are triggered?
Check asp.net page lifecycle: events are handled after page load and before PreRender.
ASP.NET cannot handle an event involving a control that does not yet exists.