Previous part: Passing an Object from a List to Another Page in MAUI MVVM .NET 9 [GamesCatalog] - Part 6
Step 1. Let's add icons to the system. For this, we will use the free version of FontAwesome.
https://docs.fontawesome.com/v5/desktop/setup/get-started
![FontAwesome]()
Step 1.1. After downloading the zip file, extract the desired font file and copy it into the project’s fonts folder. In this case, we will use Free-Solid-900.otf.
![Desired font file]()
With this, the font is now defined as a MauiFont.
![MauiFont]()
Step 2. Add the font to the system in MauiProgram.
![MauiProgram]()
Code
fonts.AddFont("Free-Solid-900.otf", "FontAwesomeIcons");
Step 3. Generate a file with the Unicode or use them individually. Here, we will work with a generated font class (class attached).
![Unicode]()
Step 3.1. To generate the class with the Unicode.
https://andreinitescu.github.io/IconFont2Code
Step 4. In AddGame, let's add the path to the file containing the icon Unicode.
![AddGame]()
Step 4.1. Code.
xmlns:Icons="clr-namespace:GamesCatalog.Resources.Fonts"
Step 5. Let's add more colors to the Colors.xaml file.
<Color x:Key="PrimaryElementColor">#4DACFF</Color>
<Color x:Key="SecondaryElementColor">#2B659B</Color>
<Color x:Key="SecondaryLabelColor">#98BDD3</Color>
<Color x:Key="Success">#2B9B74</Color>
Step 6. In AddGame.xaml, we will add one more column to the Grid and, between the image and the summary, we will insert a HorizontalStackLayout that will contain buttons with the icons.
![HorizontalStackLayout]()
Step 6.1. Code.
<VerticalStackLayout Grid.Row="2" Grid.Column="1">
<HorizontalStackLayout Padding="0,5,0,5" HorizontalOptions="Center">
</HorizontalStackLayout>
</VerticalStackLayout>
Step 6.2. Inside the HorizontalStackLayout, we will add a button with the icon representing the "Want to play" status. It will have a border with the default color we defined and the clock icon from the icon font we are using.
<Button
Margin="0,0,10,0"
BackgroundColor="{StaticResource SecondaryElementColor}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Want"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Clock}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
Step 6.3. After this button, we will add two more: one for the "Playing" status and another for "Played".
<Button
BackgroundColor="{StaticResource SecondaryElementColor}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Playing"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Gamepad}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
<Button
Margin="10,0,0,0"
BackgroundColor="{StaticResource SecondaryElementColor}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Played"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.CircleCheck}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
Step 6.4. After the HorizontalStackLayout group, inside the VerticalStackLayout, we will add a button that will serve as the confirmation button for the status and rating.
<Button
Margin="0,10,0,10"
BackgroundColor="{StaticResource Success}"
FontAttributes="Bold"
FontSize="20"
HorizontalOptions="Center"
Text="Confirm">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Check}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
Step 7. Now we have our buttons with their respective icons.
![Buttons]()
Step 8. Let's add variables to handle the visual behavior of these buttons in AddGameVM.cs.
private bool confirmIsVisible = false;
static readonly Color BgButtonStatusSelectedColor = Color.FromArgb("#2b9b74");
static readonly Color BgButtonStatusNormalColor = Color.FromArgb("#2B659B");
private enum GameStatus
{
Want,
Playing,
Played
}
private GameStatus? GameSelectedStatus = null;
private Color wantBgColor = BgButtonStatusNormalColor;
private Color playingBgColor = BgButtonStatusNormalColor;
private Color playedBgColor = BgButtonStatusNormalColor;
public Color WantBgColor
{
get => wantBgColor;
set => SetProperty(ref wantBgColor, value);
}
public Color PlayingBgColor
{
get => playingBgColor;
set => SetProperty(ref playingBgColor, value);
}
public Color PlayedBgColor
{
get => playedBgColor;
set => SetProperty(ref playedBgColor, value);
}
public bool ConfirmIsVisible
{
get => confirmIsVisible;
set => SetProperty(ref confirmIsVisible, value);
}
We will have a variable to control the visibility of the confirmation button, which will only be visible when a status is selected. And we will have variables to control the background color of the status buttons, to show which one is currently selected.
Step 9. Let's create the commands to define the visibility of the confirmation button and the colors of the status buttons.
[RelayCommand]
private Task Want()
{
GameSelectedStatus = GameStatus.Want;
WantBgColor = BgButtonStatusSelectedColor;
PlayingBgColor = BgButtonStatusNormalColor;
PlayedBgColor = BgButtonStatusNormalColor;
ConfirmIsVisible = true;
return Task.CompletedTask;
}
[RelayCommand]
private Task Playing()
{
GameSelectedStatus = GameStatus.Playing;
WantBgColor = BgButtonStatusNormalColor;
PlayingBgColor = BgButtonStatusSelectedColor;
PlayedBgColor = BgButtonStatusNormalColor;
ConfirmIsVisible = true;
return Task.CompletedTask;
}
[RelayCommand]
private Task Played()
{
GameSelectedStatus = GameStatus.Played;
WantBgColor = BgButtonStatusNormalColor;
PlayingBgColor = BgButtonStatusNormalColor;
PlayedBgColor = BgButtonStatusSelectedColor;
ConfirmIsVisible = false;
return Task.CompletedTask;
}
For the "Played" status, the confirmation button will only be enabled after defining the rating.
Step 10. Define the bindings for the buttons on the AddGame.xaml page.
![XML Page]()
Step 10.1. Code.
<VerticalStackLayout Grid.Row="2" Grid.Column="1">
<HorizontalStackLayout Padding="0,5,0,5" HorizontalOptions="Center">
<Button
Margin="0,0,10,0"
BackgroundColor="{Binding WantBgColor}"
Command="{Binding WantCommand}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Want"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Clock}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
<Button
BackgroundColor="{Binding PlayingBgColor}"
Command="{Binding PlayingCommand}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Playing"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Gamepad}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
<Button
Margin="10,0,0,0"
BackgroundColor="{Binding PlayedBgColor}"
Command="{Binding PlayedCommand}"
ContentLayout="Top,0"
HorizontalOptions="Start"
Text="Played"
WidthRequest="70">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.CircleCheck}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
</HorizontalStackLayout>
<Button
Margin="0,10,0,10"
BackgroundColor="{StaticResource Success}"
FontAttributes="Bold"
FontSize="20"
HorizontalOptions="Center"
IsVisible="{Binding ConfirmIsVisible}"
Text="Confirm">
<Button.ImageSource>
<FontImageSource
FontFamily="FontAwesomeIcons"
Glyph="{x:Static Icons:IconFont.Check}"
Size="30"
Color="White" />
</Button.ImageSource>
</Button>
</VerticalStackLayout>
Step 11. Now we have our status buttons with their behaviors defined.
![Status buttons]()
In the next step, we will create a rating bar for our project.
Code on git: GamesCatalog git