Universal Windows Platform – Codes Game

Codes Game demonstrates how to create a game where you need to guess the correct combination of four numbers between 1 and 4 – when you check your guess any incorrect ones will show with a black background and white text.

Step 1

If not already, follow Setup and Start on how to Install and get Started with Visual Studio 2017 or in Windows 10 choose Start, and then from the Start Menu find and select Visual Studio 2017.

vs2017

Step 2

Once Visual Studio Community 2017 has started, from the Menu choose File, then New then Project…

vs2017-file-new-project

Step 3

From New Project choose Visual C# from Installed, Templates then choose Blank App (Universal Windows) and then type in a Name and select a Location and then select Ok to create the Project
vs2017-new-project-window

Step 4

Then in New Universal Windows Project you need to select the Target Version this should be at least the Windows 10, version 1803 (10.0; Build 17134) which is the April 2018 Update and the Minimum Version to be the same.

vs2017-target-platform

The Target Version will control what features your application can use in Windows 10 so by picking the most recent version you’ll be able to take advantage of those features. To make sure you always have the most recent version, in Visual Studio 2017 select Tools Extensions and Updates… then and then see if there are any Updates

Step 5

Once done select from the Menu, Project, then Add New Item…

vs2017-project-add-new-item

Step 6

From the Add New Item window select Visual C#, then Code from Installed then select Code File from the list, then type in the Name as Library.cs before selecting Add to add the file to the Project

vs2017-add-new-item-library

Step 7

Once in the Code View for Library.cs the following should be entered:

using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Windows.Input;
using Windows.Foundation;
using Windows.UI;
using Windows.UI.Popups;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Media;

public class CommandHandler : ICommand
{
    public event EventHandler CanExecuteChanged = null;
    private Action _action;

    public CommandHandler(Action action)
    {
        _action = action;
    }

    public bool CanExecute(object parameter)
    {
        return true;
    }

    public void Execute(object parameter)
    {
        _action();
    }
}

public class Code : INotifyPropertyChanged
{
    private int _value;
    private SolidColorBrush _foreground;
    private SolidColorBrush _background;

    public virtual void OnPropertyChanged(string propertyName)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }

    public int Index { get; set; }
    public int Value { get { return _value; } set { _value = value; OnPropertyChanged("Value"); } }
    public SolidColorBrush Foreground { get { return _foreground; } set { _foreground = value; OnPropertyChanged("Foreground"); } }
    public SolidColorBrush Background { get { return _background; } set { _background = value; OnPropertyChanged("Background"); } }
    public Func<int, int> Action { get; set; }
    public ICommand Command { get { return new CommandHandler(() => this.Action(Index)); } }
    public event PropertyChangedEventHandler PropertyChanged;
}

public class Library
{
    private const string app_title = "Codes Game";
    private const int size = 4;

    private ObservableCollection<Code> _codes = new ObservableCollection<Code>();
    private Random _random = new Random((int)DateTime.Now.Ticks);
    private List<int> _numbers = new List<int>();
    private int _turns = 0;

    private List<int> Shuffle(int start, int total)
    {
        return Enumerable.Range(start, total).OrderBy(r => _random.Next(start, total)).ToList();
    }

    public void Show(string content, string title)
    {
        IAsyncOperation<IUICommand> command = new MessageDialog(content, title).ShowAsync();
    }

    private Code GetCode(int value, int index)
    {
        return new Code()
        {
            Action = (int i) =>
            {
                Code code = _codes[i];
                code.Value = (code.Value == size) ? 1 : code.Value + 1;
                code.Foreground = new SolidColorBrush(Colors.Black);
                code.Background = new SolidColorBrush(Colors.WhiteSmoke);
                return code.Value;
            },
            Index = index,
            Value = value,
            Foreground = new SolidColorBrush(Colors.Black),
            Background = new SolidColorBrush(Colors.WhiteSmoke)
        };
    }

    private bool Check(int number, int index)
    {
        Code code = _codes[index];
        if (number == code.Value)
        {
            code.Foreground = new SolidColorBrush(Colors.Black);
            code.Background = new SolidColorBrush(Colors.WhiteSmoke);
            return true;
        }
        else
        {
            code.Foreground = new SolidColorBrush(Colors.WhiteSmoke);
            code.Background = new SolidColorBrush(Colors.Black);
            return false;
        }
    }

    public void New(ref ItemsControl items)
    {
        _turns = 0;
        _codes.Clear();
        for (int i = 0; i < size; i++)
        {
            _codes.Add(GetCode(i + 1, i));
        }
        items.ItemsSource = _codes;
        _numbers = Shuffle(1, size);
    }

    public void Accept(ref ItemsControl items)
    {
        int index = 0;
        int correct = 0;
        foreach (int number in _numbers)
        {
            if (Check(number, index))
            {
                correct++;
            }
            index++;
        }
        _turns++;
        if (correct == size)
        {
            Show($"You got all the numbers correct in {_turns} turns!", app_title);
            New(ref items);
        }
    }
}

In the Codes Game there’s a CommandHandler Class that will help handle any commanding events and actions from the Library Class. There’s also a Code class which represents a Number that will be displayed and defines the Index, Value plus Foreground and Background colours, then there’s the Action and the commanding Commmand plus this Class implements the INotifiedPropertyChanged event to help update UI for any changes in value.

Within the Library Class there’s an ObservableCollection used – this when any changes happen to it will also help update the UI for any changes as also uses INotifiedPropertyChanged, then there’s the Random number generator and list of numbers. There’s a Show method to display any messages on screen, the GetCode method helps create an instance of Code with the given values – it also sets up the Action Method which will determine what happens when during commanding. There’s a Check method to see if a guess has been correct and sets the Foreground and Background accordingly and there’s a Shuffle method to use the Random number generator. The New method starts the game and sets up the sequence of numbers to be guessed and the Accept method is used to confirm the selection and sees how many are correct, get them all and a message is displayed.

The layout of Code Game requires more XAML code to make the layout work, this is comprised of an ItemsControl which is used to display basic lists and within this there’s a DataTemplate which defines what each item in the list looks like and this is a Button which uses Data Binding to set various properties such as Background, Foreground, Value and Command – this last item is the commanding operation of the Button which is performed using the CommandHandler and performs the Action specified which is to cycle through the numbers 1 to 4 and guessing a number correctly or incorrectly determines what the Background and Foreground will be which is set against the Code class and when these values change the INotifiedPropertyChanged event is triggered and the UI knows to display the latest values.

Step 8

In the Solution Explorer select MainPage.xaml

vs2017-mainpage-library

Step 9

From the Menu choose View and then Designer

vs2017-view-designer

Step 10

The Design View will be displayed along with the XAML View and in this between the Grid and /Grid elements, enter the following XAML:

<Viewbox Margin="50">
	<ItemsControl Name="Display">
		<ItemsControl.ItemTemplate>
			<DataTemplate>
				<Button Height="100" Width="100" Background="{Binding Background}" Command="{Binding Command}">
					<TextBlock VerticalAlignment="Center" HorizontalAlignment="Center"
					FontSize="60" Foreground="{Binding Foreground}" Text="{Binding Value}"/>
				</Button>
			</DataTemplate>
		</ItemsControl.ItemTemplate>
		<ItemsControl.ItemsPanel>
			<ItemsPanelTemplate>
				<StackPanel Orientation="Horizontal"/>
			</ItemsPanelTemplate>
		</ItemsControl.ItemsPanel>
	</ItemsControl>
</Viewbox>
<CommandBar VerticalAlignment="Bottom">
	<AppBarButton Icon="Page2" Label="New" Click="New_Click"/>
	<AppBarButton Icon="Accept" Label="Accept" Click="Accept_Click"/>
</CommandBar>

The first block of XAML the main user interface of the Game, this features a ViewBox containing an ItemsControl and has a DataTemplate defined with a Button which will form part of the look-and-feel of the game, there’s also a ItemsPanelTemplate to define the layout of the Button Controls. The second block of XAML is is the CommandBar which contains New – to start a Game and Accept to confirm the currently selected set of four numbers is the correct combination.

Step 11

From the Menu choose View and then Code

vs2017-view-code

Step 12

Once in the Code View, below the end of public MainPage() { … } the following Code should be entered:

Library library = new Library();

private void New_Click(object sender, RoutedEventArgs e)
{
	library.New(ref Display);
}

private void Accept_Click(object sender, RoutedEventArgs e)
{
	library.Accept(ref Display);
}

Below the MainPage() Method an instance of the Library Class is created, then New_Click is used to call the New Method to setup the game and start playing. Accept_Click triggers the Accept Method in the Library Class.

Step 13

That completes the Universal Windows Platform Application so Save the Project then in Visual Studio select the Local Machine to run the Application

vs2017-local-machine

Step 14

After the Application has started running you can then select New to start the game then four numbers between 1 and 4 then you need to guess the secret combination by selecting those numbers you can go through them to find that combination and once happy select Accept if you guessed a number incorrectly then it will turn Black with White text or if correct it will remain the same and if all of them are the same as the secret combination of numbers then you win.

ran-codes-game

Step 15

To Exit the Application select the Close button in the top right of the Application

vs2017-close

In this example a CommandHandler has been used to perform an action on a Button but given the game mechanic of needing to click on the numbers to cycle through the values and then display whether a selection was right or wrong using it meant everything could work through Data Binding which again is a technique that’s not been used much in previous examples. The inspiration behind the game came from number guessing games and the goal was to create a simple to play game that helped show off what can be done with Data Binding and to use commanding rather than Event Handlers.

Creative Commons License

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s