Factory File Manager Updated to Ver. 1.2.1.0

The Factory File Manager was updated:

Ver. 1.2.1.0:
AppBar Seperator Style adjusted
#341: Copy path of focused item to clipboard and show the copied path in lower left corner
#348: Active index immediately changed when opening active tab selection (Ctrl+Tab)
#350: Close ButtonAppBar when “Same Path” was pressed
#352: Changed TextTrimming from WordEllipsis to CharacterEllipsis

Download the latest version from the Windows Store.

Factory Commander Updated to Ver. 1.1.0.6

The Factory Commander was updated:

Ver. 1.1.0.6: Fixed item #324 – app crashes when clicking the rename button and then a different item while renaming an item

Ver. 1.1.0.5: Fixed item #322 – app might crash when renaming / copying / moving single item on machines with US region settings; uninstall and re-install might be required for this fix to take effect

Download the latest version from the Windows Store.

Keep Local User Account When Upgrading to Windows 8.1

I have a Windows RT device and prefer to use it with a local system account.

When upgrading the device to Windows 8.1 via the Windows Store, the system wanted me to switch to a Microsoft account. Well, I still did not want to switch. But what to do? There is no option to skip this.

Well, there is no obvious option, but a “hidden” one.

You need to be connected to the Internet to install the update from the Windows Store. The update itself takes a while. When finished so far, after some reeboots, the update asks you to configure some settings.

At that point, I have chosen the custom configuration – but I’m not sure if this is necessary for skipping the user account switch.

Anyway, after configuring the settings, the update asks you to confirm the local user by entering the password. After this step, it asks you to enter the credentials of a Microsoft account. You cannot cancel or skip this step.

But what you can do is to go back where you have to enter the password of the local user account, disconnect the device from the internet (e.g. by turning of the WLAN), enter the password, et voilà 🙂

The update, instead of asking you to connect to the internet before proceeding, finishes the installation and keeps the user account as is it was.

Change Color of ToggleSwitch

Given you implement an app using the dark theme. This app contains some configuration values, which can be changed using a settings flyout. According to the design guidelines, the background of the settings flyout should be white.

Unfortunately, the default color theme for all controls is dark. So they are optimized for a dark background, but almost invisible on a white. To make a ToggleSwitch visible on the white background of the settings page while leaving the app’s theme dark, some theme resources needs to be overridden. This can be done inside the App.xaml, the StandardsStyles.xaml, or any other ResourceDictionary that is used by the app.

To make the ToggleSwitch visible on a white background while the app uses a dark theme, set these values:

<SolidColorBrush
 x:Key="ToggleSwitchCurtainBackgroundThemeBrush"
 Color="#FF4617B4" />
<SolidColorBrush
 x:Key="ToggleSwitchCurtainDisabledBackgroundThemeBrush"
 Color="Transparent" />
<SolidColorBrush
 x:Key="ToggleSwitchCurtainPointerOverBackgroundThemeBrush"
 Color="#FF5F37BE" />
<SolidColorBrush
  x:Key="ToggleSwitchCurtainPressedBackgroundThemeBrush"
  Color="#FF7241E4" />

<SolidColorBrush
  x:Key="ToggleSwitchDisabledForegroundThemeBrush"
  Color="#66000000" />
<SolidColorBrush
  x:Key="ToggleSwitchForegroundThemeBrush"
  Color="#FF000000" />

<SolidColorBrush
  x:Key="ToggleSwitchHeaderDisabledForegroundThemeBrush"
  Color="#66000000" />
<SolidColorBrush
  x:Key="ToggleSwitchHeaderForegroundThemeBrush"
  Color="#FF000000" />

<SolidColorBrush
  x:Key="ToggleSwitchOuterBorderBorderThemeBrush"
  Color="#59000000" />
<SolidColorBrush
  x:Key="ToggleSwitchOuterBorderDisabledBorderThemeBrush"
  Color="#33000000" />

<SolidColorBrush
  x:Key="ToggleSwitchThumbBackgroundThemeBrush"
  Color="#FF000000" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbBorderThemeBrush"
  Color="#FF000000" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbDisabledBackgroundThemeBrush"
  Color="#FF929292" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbDisabledBorderThemeBrush"
  Color="#FF929292" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbPointerOverBackgroundThemeBrush"
  Color="#FF000000" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbPointerOverBorderThemeBrush"
  Color="#FF000000" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbPressedBackgroundThemeBrush"
  Color="#FF000000" />
<SolidColorBrush
  x:Key="ToggleSwitchThumbPressedForegroundThemeBrush"
  Color="#FF000000" />

<SolidColorBrush
  x:Key="ToggleSwitchTrackBackgroundThemeBrush"
  Color="#59000000" />
<SolidColorBrush
  x:Key="ToggleSwitchTrackBorderThemeBrush"
  Color="Transparent" />
<SolidColorBrush
  x:Key="ToggleSwitchTrackDisabledBackgroundThemeBrush"
  Color="#1F000000" />
<SolidColorBrush
  x:Key="ToggleSwitchTrackPointerOverBackgroundThemeBrush"
  Color="#4A000000" />
<SolidColorBrush
  x:Key="ToggleSwitchTrackPressedBackgroundThemeBrush"
  Color="#42000000" />

For more options to change ToggleSwitch styles and templates, please have a look at ToggleSwitch styles and templates.

Microsoft Advertising Services AdControl Error Handling in XAML/C#

Preface

The Do’s + Don’ts of the Advertising SDK say “DO plan for times when no ads are available.” The links of that item leads to the ErrorCode enumeration and a rudimentarily error handling sample, writing text to debug output.

In this post, I will show an error handling where the AdControl is replaced by a TextBlock when an error occurs. Of course, this is still not a high sophisticated error handling. But it might give an idea what to do when no ad is available.

Ian Ferreira suggests in his blog post Keep Users First By Using These Resources For Ad Control Error Handling to hard code a house ad into the real-estate where an ad will appear.

Error Handling by Convention

The error handling is based on naming conventions. What it does is looking for a TextBlock having a name matching the naming pattern.

Following the convention, the name of the TextBlock has to be the name of the AdControl to be replaced, extended by ErrorTextBlock.

Sample: The name of the AdControl receiving an error is AdControlBottom. According to the naming convention, the name of the TextBlock to handle the error is AdControlBottomErrorTextBlock.

This makes it easy to implement a search for the correct replacement control. No additional properties need to be defined for the AdControl. And it follows MVC’s “Convention instead of Configuration” approach.

When an error occurs, the AdControl is made invisible, while the TextBlock at the same position will become visible. To make sure the design of the page does not change, the control that replaces the AdControl must have the same size as the AdControl.

In the sample app, just the name of the error-causing control, the reason, and the error text is displayed, no matter what the error code is. In real world scenarios, one should handle different errors differently. For example, just because an ad cannot be refreshed, I would not replace the existing one.

Here is how the handler is implemented:

protected virtual void OnAdControlErrorOccurred
  (
  object sender,
  AdErrorEventArgs args
  )
{
  AdControl adControl = sender as AdControl;

  // If event is not thrown by an Ad Control, do nothing
  if (adControl == null)
  {
    return;
  }

  // Just write out an error message.
  Debug.WriteLine("AdControl error (" + adControl.Name + "): " 
    + args.Error + " ErrorCode: " + args.ErrorCode.ToString());

  // Replace adControl by TextBlock showing error message.
  // Find the TextBlock by naming conventions. 
  // The name of the TextBlock is the name of the AdControl plus "ErrorTextBlock".
  TextBlock textBlock = FindName(
    String.Format("{0}ErrorTextBlock", adControl.Name)) 
  as TextBlock;

  if (textBlock == null)
  {
    return;
  }

  // Hide the AdControl
  adControl.Visibility = Visibility.Collapsed;

  // Show the TextBlock and copy properties.
  textBlock.Visibility = Visibility.Visible;

  textBlock.Height = adControl.Height;

  textBlock.Width = adControl.Width;

  // Set some text.
  textBlock.Text = String.Format("Sorry!{0}"
    + "Can't show AdControl '{1}'.{0}{0}ErrorCode: {2}{0}{0}ErrorMessage: {3}", 
    Environment.NewLine, adControl.Name, args.ErrorCode, args.Error.Message);
}

Please have a look at the sample code to see the XAML implementation. You can look at SubPages/SamplePage300x250.xaml, SubPages/SamplePage300x600.xaml, or SubPages/ SamplePageMultiple.xaml.

Sample Code

The sample code is part of the post Configure Microsoft Advertising Services’ AdControl using XAML/C#.

Links

Ads in Apps for Windows 8

AdControl Error Handling

AdControl ErrorCode Enumeration

Implement Settings Popup Pages for Windows Store Apps

Preface

No, this is not the first sample to be found in the internet on this topic. Anyway, I decided to add another one because the two I was looking at (see links below) gave good ideas, but did not satisfied me at all.

Changes to App.xaml.cs

To begin, new items need to be added to the settings charm somehow. I did this by changing the app.xaml.cs. This is my starting point here.

First thing is to add a new using statement:

using Windows.UI.ApplicationSettings

Next, we need to know when to add our items to the settings charm. The class SettingPane has an event called CommandsRequested, which “… occurs when the user opens the settings pane. Listening for this event lets the app initialize the setting commands and pause its UI until the user closes the pane.” (description copied from MSDN docs).

So I added an event handler as the last statement of the App.OnLaunched method.

SettingsPane.GetForCurrentView().CommandsRequested 
  += OnSettingsCommandsRequested;

The handling method OnSettingsCommandsRequested is implemented in this sample like this:

private void OnSettingsCommandsRequested
  (
  SettingsPane settingsPane,
  SettingsPaneCommandsRequestedEventArgs args
  )
{
  args.Request.ApplicationCommands
    .Add(new SettingsCommand("about", "About", OnSettingsInvoked));

  args.Request.ApplicationCommands
    .Add(new SettingsCommand("popupHeaderBackgroundSlidesIn", 
     "Background slides in", OnSettingsInvoked));

  args.Request.ApplicationCommands
    .Add(new SettingsCommand("popupHeaderWithoutTransition", 
     "Header without transition", OnSettingsInvoked));

  args.Request.ApplicationCommands
    .Add(new SettingsCommand("popupHeaderWithTransition", 
     "Header with transition", OnSettingsInvoked));
}

As you can see, no matter which command is selected by the user, the method OnSettingsInvoked is called. Because the SettingsCommand constructor takes a settingsCommandId as first parameter, I am able to distinguish between the actions to be taken inside OnSettingsInvoked. Of course, one can also implement different handlers for each new command. I decided to us a single one in this sample because the action to be taken is very similar.

private void OnSettingsInvoked
  (
  IUICommand command
  )
{
  // Get the command id.
  string commandId = command.Id as string;

  // Has to be set, otherwise return.
  if (commandId == null)
  {
    return;
  }

  switch (commandId)
  {
    case "about":
      OpenSettingsPage<AboutPage>();
      break;
    case "popupHeaderBackgroundSlidesIn":
      OpenSettingsPage<HeaderBackgroundSlidesInPage>();
      break;
    case "popupHeaderWithoutTransition":
      OpenSettingsPage<HeaderWithoutTransitionPage>();
      break;
    case "popupHeaderWithTransition":
      OpenSettingsPage<HeaderWithTransitionPage>();
      break;
    default:
      break;

  }
}

The magic of opening a settings popup page is encapsulated by the method OpenSettingsPage<TPage>. It takes a type parameter to know what kind of popup page should be created. The type needs to be derived from SettingsPageBase to make sure the correct kind of page will be opened.

private void OpenSettingsPage()
  where TPage : SettingsPageBase, new()
{
  SettingsPopup = new Popup();

  SettingsPopup.IsLightDismissEnabled = true;
  SettingsPopup.Width = App.SettingsPopupWidth;
  SettingsPopup.Height = Window.Current.Bounds.Height;

  // Add the proper animation for the panel.
  SettingsPopup.ChildTransitions = new TransitionCollection();
  SettingsPopup.ChildTransitions.Add(new PaneThemeTransition()
  {
    Edge = (SettingsPane.Edge == SettingsEdgeLocation.Right) ?
           EdgeTransitionLocation.Right :
           EdgeTransitionLocation.Left
  });

  // Create a SettingsFlyout the same dimenssions as the Popup.
  TPage settingsFlyout = new TPage();
  settingsFlyout.Width = SettingsPopup.Width;
  settingsFlyout.Height = SettingsPopup.Height;

  // Place the SettingsFlyout inside our Popup window.
  SettingsPopup.Child = settingsFlyout;

  // define the location of our Popup.
  SettingsPopup.SetValue(Canvas.LeftProperty, 
    SettingsPane.Edge == SettingsEdgeLocation.Right 
    ? (Window.Current.Bounds.Width - SettingsPopup.Width) 
      : 0);
  SettingsPopup.SetValue(Canvas.TopProperty, 0);
  SettingsPopup.IsOpen = true;
}

It is worth to mention that SettingsPopup is a property of the App class. When implementing my first settings pages, I made this a local variable. But whenever I clicked somewhere into the main window while the settings page was open, my app crashes. I was not able to debug the problem. Even no UnhandledException handler helped me out.

SettingsPageBase

To avoid copy & paste development for the back button click handler, I created a base class for the settings pages. This is the class SettingsPageBase, located in the Common folder. The handler’s task is to close the Popup and re-open the settings charm when the back button is pressed.

protected virtual void OnGoBack
  (
  object sender,
  RoutedEventArgs args
  )
{
  // First close our Popup.
  Popup parent = this.Parent as Popup;

  if (parent != null)
  {
    parent.IsOpen = false;
  }

  // If the app is not snapped, then the back button shows the Settings pane again.
  if (ApplicationView.Value != ApplicationViewState.Snapped)
  {
    SettingsPane.Show();
  }
}

Mastering the Transition

When you open up the settings charm of this sample app, you will notice three different settings items: “Background slides in”, “Header without transition”, and “Header with transition”. You might ask why this. The answer is, that these are the three kinds of transitions I noticed when I was starting with settings pages. And it took me a while to figure out why my first attempts did not look the way I expected it (Header with transition).

Background slides in

When you open the “Background slides in” page, look at how the header block behaves, especially the background. It slides in, together with the button, text and logo. So when the page pops in, there is a tiny block on the left where the background color is the page’s background, not to the header’s.

The header controls slide in as expected, together with the content of the page, but that did not satisfied me. So I dig into the samples, because they did not behave that way. There, I found the next version:

Header without transition

On this page, the background of the header is set correctly. No slide in. But also, no slide in of the button, text, and image. Their position is fixed in relation to the upper left corner even when the page opens, while the describing text slides in. So still not satisfied (and not comply with the UX requirements).

Header with transition

This is the way I like it. The background is not sliding, while the header’s controls do, together with the page’s content.

To get this done, I had to change different things. When you find an easier way, I would be happy if you post it in a comment.

First, the root element of the page must not contain any Transitions definition. So no child element will slide in by default.

The settings pages consists of a Grid having two rows. One for the header, one for the content.

I put two Grids into the header row. The first, without transition, to have the background be in place when the page pops in. The second, containing the back button, text, and image, with a transition definition:

<Style x:Key="SettingsHeaderContentStyle" TargetType="Grid">
  <Setter Property="Transitions">
    <Setter.Value>
      <TransitionCollection>
        <EntranceThemeTransition/>
      </TransitionCollection>
    </Setter.Value>
  </Setter>
</Style>

This makes sure only the content of the header will slide in.

And because the root element of the page does not contain any transition definitions, also the content part, which is a StackPanel in the second row of the main Grid in my sample, needs the same transition definition.

All application-specific styles can be found in Common/ApplicationStyles.xaml.

UX Design Requirements

This app satisfies the following UX design requirements (all copied from Windows 8 User experience guidelines):

  • Place your settings Flyout on the same side of the screen as the charms. The charms and the settings window may be on the left side of the screen if the system’s text direction is right-to-left (like Arabic).
  • Settings Flyouts should be narrow (346 pixels) or wide (646 pixels).
  • Settings Flyouts should have a header that includes a back button, the name of the entry point that opened the Flyout, and the app’s icon (small one, 30x30px).
  • Use a light-dismiss surface, so that the settings Flyout disappears when the user touches anywhere on the screen outside of the surface.

The Dev Center sample “Settings Flyout” names a few more requirements, which I was not able to find in the guidelines. But they all seem reasonable, so I will list them here too:

  • Height has to be 100% of the screen.
  • Header is 80px high.
  • Header’s background must match the start tile’s background (from the manifest).
  • Flyout’s border must be darker than the header’s background (80% of its value). For instance, the background color in the example below is #999999, so the boarder color is rgb(0.8 * #99, 0.8 * #99, 0.8 * #99), which is rounded to #797979a.
  • The background of the main content area must be white. This can cause a problem if your app requests the dark theme; the text foreground color is white in the dark them, which renders it invisible when the background color is white. To request the light theme, set RequestedTheme="Light" in the app.xaml.
  • Both of the header’s and content’s controls must be animated.

The Sample Code

can be found here. To build an run the sample, you need Windows 8 and Visual Studio 2012.

Sample Screenshot

Links

Guidelines for app settings (Windows Store apps)

Store apps UX Guidelines Index

Dev Center Settings Flyout sample

Dev Center App settings sample (Windows 8)