SettingsFlyout Class For C#/XAML Windows 8 Apps

One of the interesting things about Windows 8 Modern UI app development is the amount of boilerplate code that the project wizard adds to your project. Why some of the classes are not part of the WinRT base class library is not clear and not hugely important. It is more puzzling to think of the things that are not provided such as a settings flyout wrapper. If you're new to all this, the settings flyout1 is that thing that appears to the right when you use the Settings charm2. Windows has its own implementation for the system level Settings but your app must implement this for its own settings.

I discovered the hard way that to get certified in the Windows Store you must support the settings contract so you can provide "about" information. Adding this isn't particularly difficult, but there is a lot of boilerplate that can be abstracted away. Not only that, but if you're using the WebView, you need to know when the settings come and go to ensure the WebView is properly hidden as it would otherwise draw all over your beautiful settings (I'll perhaps talk about XAML apps and the WebView another time, when I've calmed down a bit).

To simplify this I wrote SettingsFlyout, a simple wrapper that handles the boilerplate activity of showing a UserControl as your settings while providing some handy events to track any settings flyout being shown or hidden. You may notice that other than the dimensions of this flyout, it could easily be adapted to support any of your flyout needs. However, I'm not sure that there are many valid reasons for flyout usage in Modern UI apps other than the standard system implementations and settings. Therefore, I'll leave that up to you, I'd hate to lead you into bad habits.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;

namespace SomewhatAbstract
{
    /// <summary>
    /// Provides a wrapper for showing settings with events to track any settings flyout coming or going.
    /// </summary>
    public class SettingsFlyout
    {
        private const int FlyoutWidth = 346;
        private Popup popup;

        /// <summary>
        /// Shows the given control in the flyout.
        /// </summary>
        public void ShowFlyout(UserControl control)
        {
            this.popup = new Popup();
            this.popup.Opened += OnPopupOpened;
            this.popup.Closed += OnPopupClosed;
            Window.Current.Activated += OnWindowActivated;
            this.popup.IsLightDismissEnabled = true;
            this.popup.Width = FlyoutWidth;
            this.popup.Height = Window.Current.Bounds.Height;

            control.Width = FlyoutWidth;
            control.Height = Window.Current.Bounds.Height;

            this.popup.Child = control;
            this.popup.SetValue(Canvas.LeftProperty, Window.Current.Bounds.Width - FlyoutWidth);
            this.popup.SetValue(Canvas.TopProperty, 0);
            this.popup.IsOpen = true;
        }


        private void OnWindowActivated(object sender, Windows.UI.Core.WindowActivatedEventArgs e)
        {
            if (e.WindowActivationState == Windows.UI.Core.CoreWindowActivationState.Deactivated)
            {
                this.popup.IsOpen = false;
            }
        }

        private void OnPopupClosed(object sender, object e)
        {
            Window.Current.Activated -= OnWindowActivated;
            OnSettingsClosed(EventArgs.Empty);
        }

        private void OnPopupOpened(object sender, object e)
        {
            OnSettingsOpened(EventArgs.Empty);
        }

        /// <summary>
        /// Raised to indicate settings flyout has been opened.
        /// </summary>
        public static event EventHandler SettingsOpened;
        private static void OnSettingsOpened(EventArgs args)
        {
            var handler = SettingsFlyout.SettingsOpened;
            if (handler != null)
            {
                handler(null, args);
            }
        }

        /// <summary>
        /// Raised to indicate settings flyout has been closed.
        /// </summary>
        public static event EventHandler SettingsClosed;
        private static void OnSettingsClosed(EventArgs args)
        {
            var handler = SettingsFlyout.SettingsClosed;
            if (handler != null)
            {
                handler(null, args);
            }
        }
    }
}

Using the SettingsFlyout class is as simple as this:

// Add an About command
var about = new SettingsCommand("about", "About", (handler) =>
{
    var settings = new SettingsFlyout();
    settings.ShowFlyout(new MyAboutSettingsControl());
});

If you find this useful or you did something similar yourself, I would love to hear about it. Is there something you feel is missing that should be there either in WinRT or the project template? Have you created any useful utility classes like this that could be used in almost every app?

  1. A flyout is the new Windows 8 modern UI term for what we might've called a popup, dialog or tooltip in the past. It's anything that appears over your application and you use a Popup control to show them as you would in Silverlight or WPF. []
  2. The Settings charm is the cog-like button that appears when you swipe from the right or hover your mouse in the lower right (or press Windows+C). It looks a lot like an icon, except it's not. It's a charm. []

Mouse without Borders and a VPN

When I'm working from home, I like to make use of the keyboard and mouse I normally use for my home super computer with my work laptop. Rather than unplug them from one machine to plug into the other, I use Mouse Without Borders.

Mouse Without Borders is awesome. It seamlessly integrates between the machines (with some customization options), allowing me to use both computers at the same time from the same keyboard and mouse, including clipboard and file drag-and-drop. I won't go into details on Mouse Without Borders, suffice to say that it is really rather lovely1.

However, I was having issues when working from home when it would just stop working. Both machines would report everything was fine and it seemed configured properly, yet the mouse would stop at the edge of one screen and no longer move other to the other. It was perplexing and annoying and I had no idea what was going on.

Then it hit me: I was using the work VPN. Mouse Without Borders uses the network to communicate between machines, so I quickly checked the Mouse Without Borders settings on my work laptop. There I discovered that it had switched over to the VPN.

Settings dialog for changing network binding in Mouse without Borders
Changing network binding in Mouse without Borders

I don't know idea why Mouse Without Borders does this on detecting my VPN IP address, but a quick change in the handy drop down fixes everything. Unfortunately, I appear to have to do this every time I use my VPN, but at least I now know what the heck is going on. Hopefully this will be helpful should you encounter the same issue.

  1. Amusing aside, while typing this on my home desktop, the wife brought me a lovely cup of tea and knocked the mouse over to my work laptop, stalling my blogging for a moment. I guess Mouse Without Borders has its downsides. []

I Have An Announcement To Make

This is going to come as a shock to friends and family alike, so please, take a seat. I have to tell you that Chrissy and I are, as of Friday, the proud parents of a child. One imaginary, completely made-up, sexless, physically unmanifested and nameless child.

As with most fake children, the conception, gestation and birth occurred within moments of one another. And it is all my fault (typical that I get the blame, huh, gents?).

If you would be so kind as to remain seated, I will explain myself (I apologise if this gets a bit graphic as I'm going to be honest about the details which may include cussing, just be grateful I did not video the birth, I certainly am).

A Typical Friday Morning

It all happened on Friday morning when I took my car for a scheduled service. The service greeter guy (official title, I believe) greeted me by name, having remembered me from my last service six months ago when he had kindly arranged for important work to be done under warranty1. He proceeded to fill out paperwork and inspect the car.

The car had not done many miles since the last service, so he wanted to double check if the tyres needed rotating (tire, as he said it, because he is American and therefore speaks in different spellings). From a quick check of the tread, he decided that only the right-side tyres needed rotating "to keep my kids safe". And this is where I made my first mistake. I started thinking.

He thinks we have kids. Shit. Do we? I don't know. Of course we don't, how don't you know? Oh fuck. What do I do? Correct him. Correct him! Shit, too late. We've moved on. Now it will just be weird. Nevermind.

So, I did not correct him. In my defense, it did feel a bit asinine to point that out. After all, he was really just saying he wanted people in my car to be safe and that is a nice thing, so I let the small inaccuracy of "kids" slip by, leaving Service Greeter Guy to continue in his belief that I had kids. Instead, I had the bright idea to change the subject.

ME: "I'm probably going to get a new car soon."

SGG: "Well, how many kids have you got?"

What?! Clearly Service Greeter Guy did not know the rules of changing the subject.

“At first sign of crisis, the ignorant don’t panic because they don’t know what’s going on, and then later they panic precisely because they don’t know what’s going on.
”2

At this point my subconscious started to determine what my next move should be in this battle of wits. The sane part of me said I should come clean and tell him we did not have any kids, but that is too much like normal. I do not do normal very well.

Shit! He asked how many kids we have. Are we supposed to have kids? Is it wrong not to have any kids? Fuck. Fuck. FUCK! We have…er…shit. Don't hesitate. Now he looks puzzled, "Why doesn't he know how many kids he has?" Why are you not speaking?

ME: "It depends."

It depends?! Depends on what? How many I've kidnapped on a given day? What the fuck?

I had somehow determined that this hole was far from deep enough and started furiously digging. Service Greeter Guy looked confused and why would he not? I was confused and panicking.

SGG: "No, just you and your wife."

Fortunately for me, while I was panicking, Service Greeter Guy appeared to have been searching for a rational reason why the strange British man might say "It depends" to such a straightforward question. I can only assume he had decided that we ferry local kids around for some after school club or some equally normal activity where the number of kids in my car might vary. Of course, he was not going to get off so lightly. Tossing aside this opportunity to set everything straight, take the hit of embarrassment and move on, I kept digging.

ME: "One."

All of a sudden and there it was, our imaginary child, fresh from the womb of insanity, waiting to be saved by the tyre rotation that had conceived it.

Service Greeter Guy continued with his day, unaware that I had lied to him for no reason whatsoever other than the growing panic inside me, feeling like I might be judged for not having children. While he calmly tapped at keys and got me a ride to work, I calmly considered the impact of my new ward's inexistence.

One? We have one? FUCK! Now I have to have at least one kid for the rest of my days coming here to fix my car. Fuck. Will he remember? Yes, he'll remember! He remembered your fucking name when you drove in this morning from six months ago. Arse. Can I borrow a kid?

"Parenthood always comes as a shock. Postpartum blues? Postpartum panic is more like it. We set out to have a baby; what we get is a total takeover of our lives."3

If it were not for a chat with my wife later in the day, our happy news of  September 28th, 2012 may have been known only to me. However, it was her fake kid too, so I wanted to share with her the overwhelming burden of parenthood. Of course, she happily wanted me to share it with everyone, which is why I have written it down here for all to revel in my weirdity.

If you want to send birthday cards, gifts (no obligation, but it loves beer) or just a comment, have at it. Perhaps you even have ideas on what we can do with our new child. Name it? Give it a sibling? Kill it? Please share.

  1. I do know Service Greeter Guy's name, I'm just choosing to omit it. []
  2. Jarod Kintz, At even one penny, this book would be overpriced. In fact, free is too expensive, because you'd still waste time by reading it. []
  3. Polly Berrien Berends []