I'm on small Windows phone project.
In this project, I use a WebBrowser component (like WebView in Android) to show the mobile website of my company as an application.
I need to show a progress bar/dialog/indicator whatever you say, after every link click.
How can I handle that? For example, I will click the news link and something will be shown to the user like loading etc.
UPDATE :
public partial class MainPage : PhoneApplicationPage
{
// Constructor
public MainPage()
{
InitializeComponent();
Browser.Navigated += new EventHandler<System.Windows.Navigation.NavigationEventArgs>(Browser_Navigated);
Browser.Navigating += new EventHandler<NavigatingEventArgs>(Browser_Navigating);
Browser.ScriptNotify += new EventHandler<NotifyEventArgs>(Browser_ScriptNotify);
}
void Browser_ScriptNotify(object sender, NotifyEventArgs e)
{
Browser.Navigate(new Uri(e.Value, UriKind.Absolute));
}
void Browser_Navigating(object sender, NavigatingEventArgs e)
{
ProgBar.Visibility = Visibility.Visible;
}
void Browser_Navigated(object sender, System.Windows.Navigation.NavigationEventArgs e)
{
ProgBar.Visibility = Visibility.Collapsed;
}
}
i wrote this code but it doesnt show anything about progress.
You should use intercept the Navigating event of the WebBrowser control to start your progress bar.
You can just change the Visibility property of a loading overlay, say consisting of a semi-transparent Rectangle and a ProgressBar.
Then you should intercept the LoadComplete or NavigationFailed events and use these to remove your overlay.
Beware that some URLs (such as tel: links) don't fire the Navigated event, so you may need special handling for these.
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
}
}
I have a popup window in my windows phone 8.1 runtime application.
While back button pressed and popup is opened in a page, the app should stay in the page itself, else it should go back. This is my concept. So, I coded like below:
void HardwareButtons_BackPressed(object sender, BackPressedEventArgs e)
{
if (PopupWindow.IsOpen)
{
PopupWindow.IsOpen = false;
e.Handled = true;
}
}
Even if the popup windows is open in the page, the app goes to the previous page. I used the same logic in windows phone silverlight application and that worked.
NOTE: I'm using Basic Page.
What mistake actually I'm doing ?
Check two things:
by default in NavigationHelper, HardwareButtons_BackPressed lacks checking if the event was already handeled, try to improve it:
private void HardwareButtons_BackPressed(object sender, Windows.Phone.UI.Input.BackPressedEventArgs e)
{
// if (this.GoBackCommand.CanExecute(null)) // this is as a default
if (this.GoBackCommand.CanExecute(null) && !e.Handled) // add a check-up
// ... rest of the code
look at your App.xaml.cs file, and in App() there is HardwareButtons_BackPressed subscribed (check if subscribed method also navigates back):
public App()
{
this.InitializeComponent();
this.Suspending += OnSuspending;
// HardwareButtons.BackPressed += HardwareButtons_BackPressed; // this line also could fire Frame.GoBack() (as default project template)
// of course check what is in the above method
}
Also remeber that events are fired in the order you have subscribed them and for example Navigation helper subscribes in Loaded event. If you subscribe after then the navigation will be first. You may subscribe before or maybe use a flag.
I resolve in thi way
protected override void OnNavigatedTo(NavigationEventArgs e)
{
Windows.Phone.UI.Input.HardwareButtons.BackPressed += HardwareButtons_BackPressed;
}
protected virtual void HardwareButtons_BackPressed(object sender, Windows.Phone.UI.Input.BackPressedEventArgs e)
{
e.Handled = true;
}
I have tried to set up a click event for a button that opens another window,but the error I'm getting at NavigationService is that the project doesn't contain a definition for it.
This is how I'm trying to call the page at present:
private void conditioningBtn_Click(object sender, RoutedEventArgs e)
{
this.NavigationService.Navigate(new Uri("TrainingFrm.xaml", UriKind.RelativeOrAbsolute));
}
Can someone point me in the right direction with this or show alternatives to this method for window navigation?
NavigationService is for browser navigation within WPF. What you are trying to do is change to a different window TrainingFrm.
To go to a different window, you should do this:
private void conditioningBtn_Click(object sender, RoutedEventArgs e)
{
var newForm = new TrainingFrm(); //create your new form.
newForm.Show(); //show the new form.
this.Close(); //only if you want to close the current form.
}
If, on the other hand, you want your WPF application to behave like a browser, then you would need to create Pages instead of Forms, and then use a Frame in your application to do the navigation. See this example.
If you want to navigate from Window to Window:
private void conditioningBtn_Click(object sender, RoutedEventArgs e)
{
Window1 window1 = new Window1();
// window1.Show(); // Win10 tablet in tablet mode, use this, when sub Window is closed, the main window will be covered by the Start menu.
window.ShowDialog();
}
If you want to navigate from Window to Page:
private void conditioningBtn_Click(object sender, RoutedEventArgs e)
{
NavigationWindow window = new NavigationWindow();
window.Source = new Uri("Page1.xaml", UriKind.Relative);
window.Show();
}
In order to use NavigationService you should use the Page and not the Window class
I'm working on a Windows Forms app and I'm wanting to remove the close button from the top. I'm aware of the ControlBox option, but I'm wanting to provide a help button. Is there a way to have the Close button not visible while maintaining the help button?
Your best bet may be to subcribe to the FormClosing event of the form like so and cancel the closing action:
// In your code somewhere subscribe to this event
Form1.FormClosing += Form1_FormClosing;
void Form1_FormClosing(object sender, FormClosingEventArgs e)
{
e.Cancel = true;
}
The benefit of doing this is that it prevents the user from closing the application from the close button and the taskbar.
Obviously you don't want to ALWAYS cancel the form from closing. So you will want to set some type of boolean flag that you will check in the event listener as to whether you want the form to be allowed to close or not. Example:
void Form1_FormClosing(object sender, FormClosingEventArgs e)
{
if (BlockClosing)
e.Cancel = true;
}
EDIT: If you don't want to approach the problem that way, and you really do intend to completely remove the close button, then your best bet is to create your own custom title bar. In that case, you set the form's FormBorderStyle property to None. And you then dock your custom title bar to the top of the form. Here is some sample code from one I made a while back:
using System;
using System.ComponentModel;
using System.Windows.Forms;
namespace Spectrum.UI
{
public partial class TitleBar : UserControl
{
public delegate void EventHandler(object sender, EventArgs e);
public event EventHandler MinButtonClick;
public event EventHandler MaxButtonClick;
public event EventHandler CloseButtonClick;
#region Properties
[Category("Appearance")]
public string Title
{
get { return TitleLabel.Text; }
set { TitleLabel.Text = value; }
}
[Category("Appearance")]
public bool MinimizeEnabled
{
get
{
return minButton.Visible;
}
set
{
minButton.Visible = value;
}
}
[Category("Appearance")]
public bool MaximizeEnabled
{
get
{
return maxButton.Visible;
}
set
{
maxButton.Visible = value;
}
}
#endregion
public TitleBar()
{
InitializeComponent();
ShowTitleBarImage = false;
}
#region Mouse Events
private void TitleBar_MouseDown(object sender, MouseEventArgs e)
{
this.OnMouseDown(e);
}
private void TitleBar_MouseUp(object sender, MouseEventArgs e)
{
this.OnMouseUp(e);
}
private void TitleBar_MouseMove(object sender, MouseEventArgs e)
{
this.OnMouseMove(e);
}
#endregion
#region Button Click Events
private void minButton_Click(object sender, EventArgs e)
{
if (MinButtonClick != null)
this.MinButtonClick.Invoke(this, e);
}
private void maxButton_Click(object sender, EventArgs e)
{
if (MaxButtonClick != null)
this.MaxButtonClick.Invoke(this, e);
}
private void closeButton_Click(object sender, EventArgs e)
{
if (CloseButtonClick != null)
this.CloseButtonClick.Invoke(this, e);
}
#endregion
}
}
As you can see from the image, I also added a background image to the control. Depending on your patience and your requirements, you can use images and PictureBox controls to make this look as much like a standard title bar as you need.
In the above example I placed three buttons on the control with images I found online to represent minimize, maximize, and close. in your case you would simply exclude a close button. I also placed a string on the control with an appropriate font to serve as the title of the window.
Adding the custom title bar to your form is easy.
public TitleBar titleBar = new TitleBar();
titleBar.Dock = DockStyle.Top;
titleBar.MaximizeEnabled = true;
titleBar.MinimizeEnabled = true;
titleBar.Size = new System.Drawing.Size(10, 40); // Width doesn't matter - I wanted it 40 pixels tall
titleBar.Title = "Title Example";
titleBar.MinButtonClick += titleBar_MinButtonClick;
titleBar.Max ButtonClick += titleBar_MaxButtonClick;
this.Controls.Add(this.TitleBar);
And then last step is to set up your event listeners for the min and max button clicks:
private void titleBar_MinButtonClick(object sender, EventArgs e)
{
WindowState = FormWindowState.Minimized;
}
private void titleBar_MaxButtonClick(object sender, EventArgs e)
{
WindowState = FormWindowState.Maximized;
}
You may also note that I included events for mouse down, up and move in my title bar. This was so that I could create listeners in my form to move the form when the user clicked and dragged the title bar. This is optional and depends on if you need the user to be able to move your application window.
The added benefit of doing this is that can use the title bar for additional controls. For example, my application was custom written for use on a toughbook style tablet computer with a small touchscreen display. In my application, utilization of the limited space was extremely important. I was able to further modify what I've described here to also include menu bar style control directly on the title bar. In addition, I added more buttons to the left of the stand minimize, maximize, and close buttons. Really helped me utilize every square inch of the screen in my application. Couldn't have done it with the standard title bar.
Can you simply use Form.ControlBox = false (or via the designer as you point out rather negatively in your comment) and then add a custom help button on the form?
EDIT: A colleague of mine wrote an Excel add in and had a requirement to remove the X from certain forms (e.g. a Progress Bar that shouldn't be closed). He found a function written by Stephen Bullen that did just that. I've only seen this function used in VB, but perhaps you can get some ideas or direction out of his approach of using Windows API to solve your issue.
This code will disable the Close button. I am not sure if you can actually make it invisible. http://www.codeproject.com/Articles/20379/Disabling-Close-Button-on-Forms
//
// source code
// Code Snippet
private const int CP_NOCLOSE_BUTTON = 0x200;
protected override CreateParams CreateParams
{
get
{
CreateParams myCp = base.CreateParams;
myCp.ClassStyle = myCp.ClassStyle | CP_NOCLOSE_BUTTON ;
return myCp;
}
}
Good luck!
Please try this.ControlBox = false.
I have a Winforms application, which hosts two PDF Viewers (Unmanaged C++) in its panels.
I want to have application wide hotkeys for project handling (Open,Save,Close,...) which would work even when users focus is on the hosted PDF Viewer.
I managed to achieve that via Winapi and RegisterHotKey, but client doesnt like that those are system wide (e.g. they disable the same MS Word hotkeys)
I did try to disable and enable global hotkeys on Form's Activate/Deactivate events, however those events appear even when i dont leave my own app, for example on top-menu entry or on a dialog-box.
Are there other solutions for application-wide hotkeys, that would work even if the focus is on the hosted application?
SOLUTION:
In the main Form, I handle Activated and Deactivate events like this :
public void PDFPicker_Activated(object sender, EventArgs e)
{
var foregroundHwnd = GUI.winapiwrap.GetForegroundWindow();
if (foregroundHwnd==this.Handle || this.OwnedForms.Any(form => form.Handle==foregroundHwnd))
{
if (!this.hotkeys.Any())
{
registerHotkeys();
this.Text = "Hotkeys just registered";
}
}
}
public void PDFPicker_Deactivate(object sender, EventArgs e)
{
var foregroundHwnd = GUI.winapiwrap.GetForegroundWindow();
if (foregroundHwnd == this.Handle || this.OwnedForms.Any(form => form.Handle == foregroundHwnd))
{
}
else
{
unregisterHotkeys();
this.Text = "Hotkeys off";
}
}
Then in the dialog, which is in the OwnedForms array, i call just this:
private void QuestionPostingPanel_Activated(object sender, EventArgs e)
{
parent.PDFPicker_Activated(sender, e);
}
private void QuestionPostingPanel_Deactivate(object sender, EventArgs e)
{
parent.PDFPicker_Deactivate(sender, e);
}
In case of more such dialogs, I would inherit AbstractDialog : Form, add those 2 event functions and a reference to parent, and then inherit all of them from this AbstractDialog.
While registering/unregistering GlobalHotkeys, it was a problem for me when I tried doing that in parallel - global hot keys were bound to a thread.
So then check on Form Activate/Deactivate events whether the form is a foreground window or not (::GetForegroundWindow()) and then disable/enable hotkeys appropriately.