Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles / desktop / XAML

CharmFrame – Adding CharmFlyout to Grid Apps

0.00/5 (No votes)
23 Oct 2012CPOL2 min read 7.2K  
Adding CharmFlyout to Grid Apps

It appears that adding CharmFlyouts to apps like those generated with the Grid App template is difficult. The problem comes from the fact that there is no MainPage.xaml. Placing the CharmFlyout in each page, like GroupedItemsPage, GroupDetailPage, and ItemDetailPage is fraught with problems as Martin Bennedik comments. Martin suggests placing the code in the LayoutAwarePage, and the UI in a UserControl. This makes a fair amount of sense and is worth pursuing.

Posts in this series:

In thinking about the problem, I wondered if there might be a different solution. Again, the root of the problem in Grid Apps is that there is no MainPage that is always visible (in which we can embed our CharmFlyouts). It turns out, though, there is another user interface element that is always visible that can suit our purposes. Grid Apps have a Frame. This can be seen here:

App.xaml.cs

C#
var rootFrame = new Frame();

Our goal is to embed our CharmFlyouts into this frame. It will take a few steps to get there, but I think the end result is worth it. Let’s set the stage by creating a Metro Grid App and adding the CharmFlyout library to it:

  1. Install the NuGet Package Manager if you have not already.
  2. Create your Metro Grid application in Visual Studio.
  3. Select Manage NuGet Packages from the Project menu.
  4. Click Online. Search for CharmFlyout. Click Install.

Create a UserControl to host your flyouts and call it MyCharmFlyouts. Here is what I created:

XML
<UserControl
   x:Class="CharmDemoGridApp.MyCharmFlyouts"
   xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
   xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
   xmlns:local="using:CharmDemoGridApp"
   xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
   xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
   xmlns:cfo="using:CharmFlyoutLibrary"
   mc:Ignorable="d">
    <Grid>
        <cfo:CharmFlyout
           x:Name="cfoAbout"
           Heading="My About"
           HeadingBackgroundBrush="#FF4E0000">
            <StackPanel>
                <TextBlock
                   FontSize="16">CharmFlyout by John Michael Hauck</TextBlock>
                <TextBlock
                   FontSize="16">For support:</TextBlock>
                <HyperlinkButton
                   Click="OnMailTo">support@bing.com</HyperlinkButton>
            </StackPanel>
        </cfo:CharmFlyout>
        <cfo:CharmFlyout
           x:Name="cfoSettings"
           Heading="My Settings"
           HeadingBackgroundBrush="#FF4E0000">
            <StackPanel>
                <TextBlock
                   FontSize="16">Setting A</TextBlock>
                <CheckBox />
                <TextBlock
                   FontSize="16">Setting B</TextBlock>
                <CheckBox />
                <TextBlock
                   FontSize="16">Setting C</TextBlock>
                <CheckBox />
            </StackPanel>
        </cfo:CharmFlyout>
    </Grid>
</UserControl>

MyCharmFlyouts.xaml.cs

C#
using System;
using Windows.UI.ApplicationSettings;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;

namespace CharmDemoGridApp
{
    public sealed partial class MyCharmFlyouts : UserControl
    {
        public MyCharmFlyouts()
        {
            this.InitializeComponent();
            SettingsPane.GetForCurrentView().CommandsRequested += CommandsRequested;
        }

        private void CommandsRequested(SettingsPane sender, SettingsPaneCommandsRequestedEventArgs args)
        {
            args.Request.ApplicationCommands.Add(new SettingsCommand
                     ("a", "My About", (p) => { cfoAbout.IsOpen = true; }));
            args.Request.ApplicationCommands.Add(new SettingsCommand
                     ("s", "My Settings", (p) => { cfoSettings.IsOpen = true; }));
        }

        private async void OnMailTo(object sender, RoutedEventArgs args)
        {
            var hyperlinkButton = sender as HyperlinkButton;
            if (hyperlinkButton != null)
            {
                var uri = new Uri("mailto:" + hyperlinkButton.Content);
                await Windows.System.Launcher.LaunchUriAsync(uri);
            }
        }
    }
}

Modify App.xaml.cs to use a frame that supports additional content, and add your new flyout user control to it. One such handy frame is now included in the CharmFlyoutLibrary, called CharmFrame.

App.xaml.cs

C#
var rootFrame = new CharmFrame { CharmContent = new MyCharmFlyouts() };

That’s it!

CharmFrame

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)