Introducción a Xamarin

1

Todo lo que aprenderás sobre Xamarin Forms

2

¿Qué es Xamarin?

Instalación y configuración

3

Requerimientos de hardware y software

4

Introducción a Instalación de Visual Studio .NET y Herramientas

5

Instalación de Visual Studio .NET en Windows

6

Instalación de Visual Studio .NET for Mac

7

Configuración de Xamarin para iOS

Fundamentos de Xamarin.Forms

8

Mi primera app con Xamarin.Forms

9

Xamarin.Forms vs. Xamarin clásico

10

Estrategias para compartir código

Arquitectura de Xamarin.Forms

11

Anatomía de una aplicación

12

Arquitectura de Xamarin.Forms

Sistema de Propiedades Enlazables

13

Sistema de Propiedades Enlazables

14

Usando y creando Propiedades Enlazables

15

Propiedades Adjuntas

Manejo de Eventos

16

Manejo de eventos

17

Ciclo de vida

El Lenguaje XAML

18

¿Qué es XAML?

19

Espacios de Nombres XML

20

Sintaxis de subelementos y de contenido

21

Extensiones de Marcado

22

Recursos

23

XAML compilado

Interfaz de Usuario

24

Contenedores

25

Controles comunes

26

Creación de controles personalizados

27

Estilos

28

Triggers en Estilos

29

Diccionarios Mezclados

30

Transformaciones y Animaciones

31

Navegación

32

DisplayAlert y DisplayActionSheet

33

MessagingCenter

Enlace de Datos

34

Enlace de Datos

35

Interfaces de notificación

36

La clase ObservableCollection<t>

37

Contexto de Enlace de Datos

38

Enlace entre elementos

39

Propiedad StringFormat

40

Plantillas de Datos

41

Convertidores de Valor

Comandos

42

¿Qué son los Comandos?

43

Implementación básica e implementaciones existentes

El Patrón de Diseño Model-View-ViewModel (MVVM)

44

Introducción al patrón de diseño MVVM

45

¿Qué es MVVM?

46

Componentes del Patrón

47

Proyecto: Pomodoro

48

App Pomodoro

49

Continuando con la app Pomodoro

50

Concluyendo nuestra app Pomodoro

Aún no tienes acceso a esta clase

Crea una cuenta y continúa viendo este curso

Curso de Xamarin.Forms

Curso de Xamarin.Forms

Rodrigo Díaz Concha

Rodrigo Díaz Concha

Contenedores

24/50
Recursos

Los contenedores nos ayudan a organizar y acomodar en pantalla los elementos visuales. Estos controles heredan de la clase Layout.

Los más utilizados son

  • StackLayout
  • Grid
  • FlexLayout

El permite apilar los elementos hijos de manera vertical u horizontal seg[un se haya definido la propiedad Orientation.

El contenedor es similar a una tabla, organizada en filas y columnas. Es el más flexible de todos los contenedores. El tamaño de filas y columnas puede ser uno de los siguientes: Fijo, Automático y Proporcional.

Aportes 29

Preguntas 2

Ordenar por:

¿Quieres ver más aportes, preguntas y respuestas de la comunidad? Crea una cuenta o inicia sesión.

Yo cree uno dinamico, para poder agregar y quitar columnas/filas a gusto:

xaml

  <Grid x:Name="grid"
          BackgroundColor="Gray">
        <Grid.ColumnDefinitions>
            <ColumnDefinition/>
            <ColumnDefinition/>
            <ColumnDefinition/>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>
    </Grid>

cs

    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();

            var cols = grid.ColumnDefinitions.Count;
            var rows = grid.RowDefinitions.Count;

            for (int col = 0; col < cols; col++)
            {
                for (int row = 0; row < rows; row++)
                {
                    var newButton = new Button();
                    newButton.Clicked += OnClicked;
                    newButton.BackgroundColor = Color.White;

                    Grid.SetColumn(newButton, col);
                    Grid.SetRow(newButton, row);
                    grid.Children.Add(newButton);
                }
            }
        }

        private void OnClicked(object sender, EventArgs e)
        {
            var currentButton = sender as Button;
            currentButton.BackgroundColor = Color.Red;
            currentButton.Clicked -= OnClicked;
        }
    }

Algo asi estaría bien?

mas Simple

public MainPage()
        {
            InitializeComponent();

            Button newbutton;
            for (int i = 0; i <= 2; i++)
            {
                for (int col = 0; col <= 2; col++)
                {
                    newbutton = new Button();
                    newbutton.SetValue(Grid.RowProperty, i);
                    newbutton.SetValue(Grid.ColumnProperty, col);
                    newbutton.Clicked += Newbutton_Clicked;
                    newbutton.BackgroundColor = Color.White; 
                    miGrid.Children.Add(newbutton);
                }
            }
        }

        private void Newbutton_Clicked(object sender, EventArgs e)
        {
            var thebutton = sender as Button;
            var row = Grid.GetRow(thebutton);
            var col = Grid.GetColumn(thebutton);

            BoxView newbox = new BoxView();
            newbox.SetValue(Grid.RowProperty, row);
            newbox.SetValue(Grid.ColumnProperty, col);
            newbox.Color = Color.Red;
            miGrid.Children.Add(newbox);
        }

MainPage.xaml

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:Totito"
             x:Class="Totito.MainPage">
    <Grid x:Name="MainGrid">
        
        <Grid.ColumnDefinitions>
            <ColumnDefinition />
            <ColumnDefinition />
            <ColumnDefinition />
        </Grid.ColumnDefinitions>

        <Grid.RowDefinitions>
            <RowDefinition />
            <RowDefinition />
            <RowDefinition />
        </Grid.RowDefinitions>

    </Grid>
  
</ContentPage>

MainPage.xaml.cs

using System;
using Xamarin.Forms;

namespace Totito
{
    public partial class MainPage : ContentPage
    {
        bool turno;
        public MainPage()
        {
            InitializeComponent();

            for (int i = 0; i< 3; i++) //columna
            {
                for (int j= 0; j < 3; j++) //fila
                {
                    //se crea el botón
                    Button btn = new Button();
                    btn.BackgroundColor = Color.White;
                    btn.BorderColor = Color.Black;

                    //se agrega el manejador del evento click
                    btn.Clicked += Button_Clicked;

                    //se agrega el botón al grid y se coloca en la celda apropiada
                    MainGrid.Children.Add(btn);
                    Grid.SetColumn(btn, i);
                    Grid.SetRow(btn, j);                    
                }
            }
            turno = false;
        }
        
        private void Button_Clicked(object sender, EventArgs e)
        {
            Button boton = (sender as Button);

            Color color = Color.White;
            
            //se selecciona el color a mostrar en el cuadro en base al jugador en turno 
            //(Jugador 1: AZUL, jugador 2: AMARILLO)            
            if (boton.BackgroundColor.Equals(Color.White))                
                color = turno ? Color.Yellow : Color.Blue;

            //se aplica el color al botón
            boton.BackgroundColor = color;

            //se cambia de turno
            turno = !turno;
        }
        
    }
}

XML

    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition />
            <ColumnDefinition />
            <ColumnDefinition />
        </Grid.ColumnDefinitions>
        
        <Grid.RowDefinitions>
            <RowDefinition />
            <RowDefinition />
            <RowDefinition />
        </Grid.RowDefinitions>

        <Button BackgroundColor="Gray" Clicked="OnClick" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="1" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="2" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Row="1" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="1" Grid.Row="1" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="2" Grid.Row="1" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Row="2"/>
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="1" Grid.Row="2" />
        <Button BackgroundColor="Gray" Clicked="OnClick" Grid.Column="2" Grid.Row="2" />
    </Grid>

</ContentPage>

CS

 public int turn = 0;
        private void OnClick(object sender, EventArgs e)
        {
            var BtSelect = sender as Button;
            if (BtSelect.BackgroundColor == Color.Gray)
            {
                if (turn == 0)
                {
                    BtSelect.BackgroundColor = Color.Red;
                    turn = 1;
                }
                else
                {
                    BtSelect.BackgroundColor = Color.Blue;
                    turn = 0;
                }
            }
        }

lo hice todo en C# cambia el color dependiendo del turno rojo y azul


XAML

C#

Resultado

Me quedó así, pero no pude usar BoxView, usé botones

MainPage.xaml

<code> 
    <Grid x:Name="grid"
          BackgroundColor="{x:Static Color.Gray}">
        <Grid.ColumnDefinitions>
            <ColumnDefinition />
            <ColumnDefinition />
            <ColumnDefinition />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition />
            <RowDefinition />
            <RowDefinition />
        </Grid.RowDefinitions>
    </Grid>
</code>

MainPage.xaml.cs

<code> 
public MainPage()
        {
            InitializeComponent();

            startApp();
        }

        private void startApp()
        {
            for (int i = 0; i < grid.ColumnDefinitions.Count; i++)
            {
                for (int y = 0; y < grid.RowDefinitions.Count; y++)
                {
                    var tap = new TapGestureRecognizer();
                    var boxView = new BoxView();
                    boxView.SetValue(BoxView.ColorProperty, Color.White);
                    tap.Tapped += (s, e) =>
                    {
                        boxView.SetValue(BoxView.ColorProperty, Color.Orange);
                        boxView.SetValue(WidthRequestProperty, 200);
                        boxView.SetValue(HeightRequestProperty, 200);
                    };
                    boxView.GestureRecognizers.Add(tap);
                    grid.Children.Add(boxView, i, y);
                }
            }
        }
</code>

MainPage.xaml

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage 
             x:Class="TicTacToe.MainPage">

    <Grid x:Name="grid"/>
</ContentPage>

MainPage.xaml.cs

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

using Xamarin.Forms;

namespace TicTacToe
{
    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();
            createUI();
        }


        private void createUI()
        {
            //Establece el color del background del grid
            grid.BackgroundColor = Color.LightGray;

            //crea columnas y filas
            for (int i = 0; i < 3; i++)
            {
                grid.ColumnDefinitions.Add(new ColumnDefinition());
                grid.RowDefinitions.Add(new RowDefinition());
            }

            //Crea boton por cada celda del grid y asigna manejador de evento
            for (int i = 0; i < 3; i++)
            {
                for (int j = 0; j < 3; j++)
                {
                    var button = new Button();

                    button.SetValue(Grid.ColumnProperty, i);
                    button.SetValue(Grid.RowProperty, j);
                    button.BackgroundColor = Color.White;
                    
                    button.Clicked += OnClicked;
                    grid.Children.Add(button);
                }
            }
        }

        private void OnClicked(object sender, EventArgs e)
        {
            var button = sender as Button;

            //obtiene la columna y la fila del boton
            var column = button.GetValue(Grid.ColumnProperty);
            var row = button.GetValue(Grid.RowProperty);

            //verifica si el grid ya tiene un hijo BoxView en la posición del botón
            BoxView boxView = grid.Children.FirstOrDefault(x => x is BoxView && x.GetValue(Grid.ColumnProperty) == column && x.GetValue(Grid.RowProperty) == row) as BoxView;

            //si no es así crea el BoxView, y se le establecen las propiedades.
            if(boxView is null)
            {
                boxView = new BoxView();
                boxView.SetValue(Grid.ColumnProperty, column);
                boxView.SetValue(Grid.RowProperty, row);

                boxView.WidthRequest = button.Width * 0.65;
                boxView.HeightRequest = button.Width * 0.65;
                boxView.HorizontalOptions = LayoutOptions.Center;
                boxView.VerticalOptions = LayoutOptions.Center;
                boxView.Color = Color.Red;
                grid.Children.Add(boxView);
            }
        }
    }
}

Resultado

El resultado de mi RETO
XAML

C#

RESULTADO

var cols = grid.ColumnDefinitions.Count;
var rows = grid.RowDefinitions.Count;

        for (int col = 0; col < cols; col++)
        {
            for (int row = 0; row < rows; row++)
            {
                var newButton = new Button();
                newButton.Clicked += OnClicked;
                newButton.BackgroundColor = Color.White;
               
                Grid.SetColumn(newButton, col);
                Grid.SetRow(newButton, row);
                grid.Children.Add(newButton);
            }
        }

private void OnClicked(object sender, EventArgs e)
{
var thebutton = sender as Button;
var row = Grid.GetRow(thebutton);
var col = Grid.GetColumn(thebutton);

        BoxView newbox = new BoxView();
        newbox.SetValue(Grid.RowProperty, row);
        newbox.SetValue(Grid.ColumnProperty, col);
        newbox.WidthRequest = 50;
        newbox.HeightRequest = 50;
        newbox.VerticalOptions = LayoutOptions.Center;
        newbox.HorizontalOptions = LayoutOptions.Center;
        newbox.Color = Color.Red;
        grid.Children.Add(newbox);
    }

Excelente!!

Dejo mi solución
xaml

c#

Use estilos y si hubiera podido ver los videos de C# basicos de Platzi talves lo hubiese hecho mucho mejor. Aprender es genial.

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:Triqui"
             x:Class="Triqui.MainPage">
    <Grid ColumnSpacing="0" RowSpacing="0">
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>

        <StackLayout Orientation="Horizontal" Grid.ColumnSpan="3" HeightRequest="100">
            <!-- Place new controls here -->
            <Label Text="TrIQUI" 
           HorizontalOptions="Center"
           VerticalOptions="CenterAndExpand"
               />
            <Button Clicked="Button_Clicked" TextColor="Red" Text="Reset"/>
        </StackLayout>
<!-- Fila 2-->
        <Button Grid.Column="0" Grid.Row="1" x:Name="Btn1" Clicked="Btn1_Clicked"/>
        <Button Grid.Column="1" Grid.Row="1" x:Name="Btn2" Clicked="Btn2_Clicked"/>
        <Button Grid.Column="2" Grid.Row="1" x:Name="Btn3" Clicked="Btn3_Clicked" />
        <!-- Fila 3-->
        <Button Grid.Column="0" Grid.Row="2" x:Name="Btn4" Clicked="Btn4_Clicked"/>
        <Button Grid.Column="1" Grid.Row="2" x:Name="Btn5" Clicked="Btn5_Clicked" />
        <Button Grid.Column="2" Grid.Row="2" x:Name="Btn6" Clicked="Btn6_Clicked"/>
        <!-- Fila 4-->
        <Button Grid.Column="0" Grid.Row="3" x:Name="Btn7" Clicked="Btn7_Clicked"/>
        <Button Grid.Column="1" Grid.Row="3" x:Name="Btn8" Clicked="Btn8_Clicked"/>
        <Button Grid.Column="2" Grid.Row="3" x:Name="Btn9" Clicked="Btn9_Clicked"/>
        
        
        
        
        
    </Grid>
    
    
    

</ContentPage>```

Que tal algo como esto?

<StackLayout Padding="20" BackgroundColor="Gray">
        <Grid BackgroundColor="Black" VerticalOptions="FillAndExpand">
            <Grid.ColumnDefinitions>
                <ColumnDefinition />
                <ColumnDefinition />
                <ColumnDefinition />
            </Grid.ColumnDefinitions>

            <Grid.RowDefinitions>
                <RowDefinition />
                <RowDefinition />
                <RowDefinition />
            </Grid.RowDefinitions>

            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" />

            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Column="1" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Column="2" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="1" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="1" Grid.Column="1" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="1" Grid.Column="2" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="2" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="2" Grid.Column="1" />
            <Button FontSize="50" TextColor="White" Clicked="OnClick" BackgroundColor="White" Grid.Row="2" Grid.Column="2" />

        </Grid>
    </StackLayout>



public partial class MainPage : ContentPage
    {

        string tagValue = "X";

        public MainPage()
        {
            InitializeComponent();
        }

        private void Grid_Focused(object sender, FocusEventArgs e)
        {
            var cell = sender;

        }

        private void OnClick(object sender, EventArgs e)
        {
            var btn = sender as Button;
            setButtonConfig(ref btn);
        }



        private void setButtonConfig(ref Button btn)
        {
            if (string.IsNullOrEmpty(btn.Text))
            {
                string textValue = tagValue;
                Color colorValue;

                if (tagValue == "X")
                {
                    tagValue = "O";
                    colorValue = Color.Red;
                }
                else
                {
                    tagValue = "X";
                    colorValue = Color.Black;
                }

                btn.BackgroundColor = colorValue;
                btn.Text = textValue;
            }

        }
    }

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:Contenedores"
             x:Class="Contenedores.MainPage">

    <Grid x:Name="grilla" BackgroundColor="Black">
        <Grid.ColumnDefinitions>
            <ColumnDefinition />
            <ColumnDefinition/>
            <ColumnDefinition/>
        </Grid.ColumnDefinitions>

        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>


        <Button BorderColor="Black" Clicked="click"/>
        <Button BorderColor="Black" Clicked="click" Grid.Column="1"/>
        <Button BorderColor="Black" Clicked="click" Grid.Column="2"/>
        <Button BorderColor="Black" Clicked="click" Grid.Row="1"/>
        <Button BorderColor="Black" Clicked="click" Grid.Row="1" Grid.Column="1" />
        <Button BorderColor="Black" Clicked="click" Grid.Row="1" Grid.Column="2"/>
        <Button BorderColor="Black" Clicked="click" Grid.Row="2"/>
        <Button BorderColor="Black" Clicked="click" Grid.Row="2" Grid.Column="1" />
        <Button BorderColor="Black" Clicked="click" Grid.Row="2" Grid.Column="2" />

    </Grid>

</ContentPage>


namespace Contenedores
{
    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();
        }

        private void click(object sender, EventArgs e)
        {
            Button btn = (Button)sender;
            if (btn.Text == "O")
            {
                btn.FontSize = 30;
                btn.Text = "X";
            }
            else
            {
                btn.FontSize = 30;
                btn.Text = "O";
            }
            
           
        }
    }
}

código XAML:

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:Contenedores"
             x:Class="Contenedores.MainPage">
    <Grid WidthRequest="300" HeightRequest="400" x:Name="gridGato">
        
        <Grid.ColumnDefinitions>
             <ColumnDefinition Width="1*"/>        
            <ColumnDefinition Width="1*"/>
            <ColumnDefinition Width="1*"/>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>
        <Label Text="Práctica Platzi, Juego del gato" TextColor="Blue" Grid.ColumnSpan="3" FontSize="Medium" HorizontalTextAlignment="Center"/>
        <Button Grid.Row="1" Grid.Column="0" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b1"/>
        <Button Grid.Row="1" Grid.Column="1" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b2"/>
        <Button Grid.Row="1" Grid.Column="2" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b3"/>
        <Button Grid.Row="2" Grid.Column="0" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b4"/>
        <Button Grid.Row="2" Grid.Column="1" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b5"/>
        <Button Grid.Row="2" Grid.Column="2" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b6"/>
        <Button Grid.Row="3" Grid.Column="0" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b7"/>
        <Button Grid.Row="3" Grid.Column="1" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b8"/>
        <Button Grid.Row="3" Grid.Column="2" WidthRequest="100" HeightRequest="100" BackgroundColor="LightGray" x:Name="b9"/>

    </Grid>

</ContentPage>

código C#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Xamarin.Forms;

namespace Contenedores
{
    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();
            b1.Clicked += (s, a) => b1.BackgroundColor = Color.Red;
            b2.Clicked += (s, a) => b2.BackgroundColor = Color.Red;
            b3.Clicked += (s, a) => b3.BackgroundColor = Color.Red;
            b4.Clicked += (s, a) => b4.BackgroundColor = Color.Red;
            b5.Clicked += (s, a) => b5.BackgroundColor = Color.Red;
            b6.Clicked += (s, a) => b6.BackgroundColor = Color.Red;
            b7.Clicked += (s, a) => b7.BackgroundColor = Color.Red;
            b8.Clicked += (s, a) => b8.BackgroundColor = Color.Red;
            b9.Clicked += (s, a) => b9.BackgroundColor = Color.Red;
        }


    }
}


Esto realice en mi xaml

<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="1*"/>
        <ColumnDefinition Width="1*"/>
        <ColumnDefinition Width="1*"/>
    </Grid.ColumnDefinitions>
    
    <Grid.RowDefinitions>
        <RowDefinition Height="1*"/>
        <RowDefinition Height="1*"/>
        <RowDefinition Height="1*"/>
    </Grid.RowDefinitions>

    <BoxView BackgroundColor="White" />

    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1"
            WidthRequest="100" HeightRequest="100"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="0" Grid.Row="1"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="0" Grid.Row="2"/>
    
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="1" Grid.Row="0"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="1" Grid.Row="1"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="1" Grid.Row="2"/>

    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="2" Grid.Row="0"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="2" Grid.Row="1"/>
    <Button BorderColor="Black" BorderWidth="1" 
            BackgroundColor="White" Clicked="ClickB1" Grid.Column="2" Grid.Row="2"/>

    <BoxView WidthRequest="20" HeightRequest="20" 
             BackgroundColor="Red" VerticalOptions="Center" IsVisible="False"
             x:Name="Box00"/>
    <BoxView WidthRequest="20" HeightRequest="20" Grid.Column="0" Grid.Row="1"
             BackgroundColor="Black" VerticalOptions="Center" IsVisible="False"
             x:Name="Box01"/>
    <BoxView WidthRequest="20" HeightRequest="20" Grid.Column="0" Grid.Row="2"
             BackgroundColor="Yellow" VerticalOptions="Center" IsVisible="False"
             x:Name="Box02"/>
</Grid>

y esto en el .cs

pero no puedo hacer un cuadrado en el centro

    private void ClickB1(object sender, EventArgs e)
    {
        var button = sender as Button;
        var column = (int)button.GetValue(Grid.ColumnProperty);
        var row = (int)button.GetValue(Grid.RowProperty);
        switch(column)
        {
            case 0:
                if (row == 0) Box00.IsVisible = true;
                if (row == 1) Box01.IsVisible = true;
                if (row == 2) Box02.IsVisible = true;
                break;
        }
    }

Mi solución, de a poco lo iré mejorando.

`<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width=“1*”/>
<ColumnDefinition Width=“1*”/>
<ColumnDefinition Width=“1*”/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height=“1*”/>
<RowDefinition Height=“1*”/>
<RowDefinition Height=“1*”/>
</Grid.RowDefinitions>
<Button Clicked=“btn_click00” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Row=“1” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Row=“2” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“1” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“1” Grid.Row=“1” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“1” Grid.Row=“2” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“2” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“2” Grid.Row=“1” TextColor=“White”></Button>
<Button Clicked=“btn_click00” Grid.Column=“2” Grid.Row=“2” TextColor=“White”></Button>
</Grid>

public partial class MainPage : ContentPage
{
BoxView boxview = new BoxView();
public MainPage()
{
InitializeComponent();

    }

    private void btn_click00(object sender, EventArgs e)
    {
        var columna = sender as Button;
        if (columna.X==122 && columna.Y==191)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 0 && columna.Y == 0)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 0 && columna.Y == 191)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 122 && columna.Y == 0)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 0 && columna.Y == 382)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 122 && columna.Y == 382)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 244 && columna.Y == 382)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 244 && columna.Y == 191)
        {
            columna.BackgroundColor = Color.Red;
        }
        if (columna.X == 244 && columna.Y == 0)
        {
            columna.BackgroundColor = Color.Red;
        }

    }

}`

xaml ;

<Grid >
        <Grid.ColumnDefinitions>
            <ColumnDefinition />
            <ColumnDefinition />
            <ColumnDefinition />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition />
            <RowDefinition />
            <RowDefinition />
        </Grid.RowDefinitions>
        <Button Clicked="OnClickBox" BackgroundColor="White" />
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Column="1"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Column="2"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="1"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="1" Grid.Column="1"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="1" Grid.Column="2"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="2"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="2" Grid.Column="1"/>
        <Button Clicked="OnClickBox" BackgroundColor="White" Grid.Row="2" Grid.Column="2"/>

    </Grid>```



 codigo c#~


private void OnClickBox(object sender, EventArgs e) {
var buttonSelect=sender as Button;
if (buttonSelect.BackgroundColor == Color.White)
{
buttonSelect.BackgroundColor = IDColor % 2 == 0 ? Color.Red : Color.Blue;
buttonSelect.Margin = new Thickness(20, 60);
buttonSelect.CornerRadius = 10;
IDColor++;
}
}```

El método que utilicé crea colores aleatorios en los botones en cada una de las celdas. Al oprimir un botón cambiará a un color aleatorio, al oprimirlo por segunda vez volverá a ser gris.
El método utiliza una variable aleatoria entre 0 y 255, al momento de ejecutarse, cuando se selecciona el color, llama al método Color.FromRgb, este recibe 3 parámetros enteros, ahí entra la variable aleatoria y se invoca 3 veces.
XAML

<Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="1*" />
            <ColumnDefinition Width="1*" />
            <ColumnDefinition Width="1*" />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="1*" />
            <RowDefinition Height="1*" />
            <RowDefinition Height="1*" />
        </Grid.RowDefinitions>

    
        <Button BackgroundColor="Gray" 
                    Clicked="OnClick" />
        <Button BackgroundColor="Gray"
                    Clicked="OnClick"
                     Grid.Column="1" />
        <Button BackgroundColor="Gray"
                    Clicked="OnClick"
                     Grid.Column="2" />
        <Button BackgroundColor="Gray" 
                Clicked="OnClick"
                Grid.Row="1" />
        <Button BackgroundColor="Gray"
                Clicked="OnClick"
                 Grid.Row="1"
                 Grid.Column="1" />
        <Button BackgroundColor="Gray"
                Clicked="OnClick"
                 Grid.Row="1"
                 Grid.Column="2" />
        <Button BackgroundColor="Gray" 
                Clicked="OnClick"
                 Grid.Row="2" />
        <Button BackgroundColor="Gray"
                Clicked="OnClick"
                 Grid.Row="2" 
                 Grid.Column="1" />
        <Button BackgroundColor="Gray"
                Clicked="OnClick"
                 Grid.Row="2" 
                 Grid.Column="2" />
    </Grid>

Código CS.

private void OnClick(object sender, EventArgs e)
        {
            Random random = new Random();
            var button = sender as Button;
            if(button.BackgroundColor == Color.Gray)
            {
                button.BackgroundColor = Color.FromRgb(random.Next(0, 255), random.Next(0, 255), random.Next(0, 255));
            }
            else
            {
                button.BackgroundColor = Color.Gray;
            }
        }

Tenia conocimientos básicos de programación, este es el primer curso que hago en platzi, demore 2 días, pero esta es mi solución

XAML

<Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition/>
            <ColumnDefinition/>
            <ColumnDefinition/>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>

        <BoxView x:Name="box1" ClassId="box1">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box2" ClassId="box2" Grid.Column="1">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box3" ClassId="box3" Grid.Column="2">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box4" ClassId="box4" Grid.Row="1">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box5" ClassId="box5" Grid.Row="1" Grid.Column="1">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box6" ClassId="box6" Grid.Row="1" Grid.Column="2">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box7" ClassId="box7" Grid.Row="2">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box8" ClassId="box8" Grid.Row="2" Grid.Column="1">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView x:Name="box9" ClassId="box9" Grid.Row="2" Grid.Column="2">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
            </BoxView.GestureRecognizers>
        </BoxView>
    </Grid>

C#

void TapGestureRecognizer_Tapped(System.Object sender, System.EventArgs e)
        {
            BoxView box = (BoxView)sender;
            var boxClass = box.ClassId.ToString();

            switch (boxClass)
            {
                case nameof(box1):
                    box1.SetValue(BoxView.ColorProperty, "red");
                    break;

                case nameof(box2):
                    box2.SetValue(BoxView.ColorProperty, "AliceBlue");
                    break;

                case nameof(box3):
                    box3.SetValue(BoxView.ColorProperty, "Aqua");
                    break;

                case nameof(box4):
                    box4.SetValue(BoxView.ColorProperty, "Aquamarine");
                    break;

                case nameof(box5):
                    box5.SetValue(BoxView.ColorProperty, "Azure");
                    break;

                case nameof(box6):
                    box6.SetValue(BoxView.ColorProperty, "Beige");
                    break;

                case nameof(box7):
                    box7.SetValue(BoxView.ColorProperty, "Bisque");
                    break;

                case nameof(box8):
                    box8.SetValue(BoxView.ColorProperty, "Black");
                    break;

                case nameof(box9):
                    box9.SetValue(BoxView.ColorProperty, "BlanchedAlmond");
                    break;
            }
        }

Listo!!

Así me quedo

    <Grid  BackgroundColor="Black" Margin="10">
        <Grid.ColumnDefinitions>
            <ColumnDefinition ></ColumnDefinition>
            <ColumnDefinition ></ColumnDefinition>
            <ColumnDefinition ></ColumnDefinition>
        </Grid.ColumnDefinitions>

        <Grid.RowDefinitions>
            <RowDefinition Height="1*"></RowDefinition>
            <RowDefinition Height="1*"></RowDefinition>
            <RowDefinition Height="1*"></RowDefinition>
        </Grid.RowDefinitions>

        <BoxView BackgroundColor="White" x:Name="caja00" HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White"  Grid.Column="1"   x:Name="caja01"   HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White"  Grid.Column="2"   x:Name="caja02"  HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White" Grid.Row="1"  x:Name="caja10"  HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White" Grid.Row="1" Grid.Column="1" x:Name="caja11"   HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White"  Grid.Row="1" Grid.Column="2"  x:Name="caja12"  HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White"  Grid.Row="2" x:Name="caja20"  HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White" Grid.Row="2" Grid.Column="1"  x:Name="caja21"   HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
        <BoxView BackgroundColor="White" Grid.Row="2" Grid.Column="2"  x:Name="caja22"  HeightRequest="50" WidthRequest="50">
            <BoxView.GestureRecognizers>
                <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"></TapGestureRecognizer>
            </BoxView.GestureRecognizers>
        </BoxView>
    </Grid>
 private void TapGestureRecognizer_Tapped(object sender, EventArgs e)
        {
            var boxview = sender as BoxView;

          if ((Color)boxview.GetValue(BoxView.BackgroundColorProperty)  == Color.White)
            {
                boxview.SetValue(BoxView.BackgroundColorProperty, Color.Red);
            }
            else
            {
                boxview.SetValue(BoxView.BackgroundColorProperty, Color.White);
            }


        }```

Hice el ta te ti y le agregué un boton para limpiar los cuadrantes

El código:

<Grid x:Name="grid" BackgroundColor="Black">
        <Grid.Resources>
        </Grid.Resources>
        
        <Grid.ColumnDefinitions>
            <ColumnDefinition></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="2*"></RowDefinition>
            <RowDefinition Height="2*"></RowDefinition>
            <RowDefinition Height="2*"></RowDefinition>
            <RowDefinition Height="1*"></RowDefinition>
        </Grid.RowDefinitions>

        <Button Clicked="Limpiar" Text="Limpiar" Grid.Column="1" Grid.Row="3"/>
    </Grid>
	bool turnoJ1 = true;
        Button[] cuadrantes;
        List<Button> casillas = new List<Button>();

        public MainPage()
        {
            InitializeComponent();

            int cols = grid.ColumnDefinitions.Count;
            int rows = grid.RowDefinitions.Count;

            cuadrantes = new Button[cols * rows];
            
            for(int i = 0; i < cols; i++)
            {
                for(int k = 0; k < rows - 1; k++)
                {
                    Button labelModel = new Button();
                    labelModel.FontSize = 40;
                    labelModel.BackgroundColor = Color.FromHex("#fafafa");
                    labelModel.Clicked += GridTouch;

                    Grid.SetColumn(labelModel, i);
                    Grid.SetRow(labelModel, k);
                    grid.Children.Add(labelModel);
                    casillas.Add(labelModel);
                }
            }
        }
        
        public void GridTouch(object sender, EventArgs args)
        {
            Button currentBtn = sender as Button;
            currentBtn.Clicked -= GridTouch;
            currentBtn.Text = ToggleTouch();
        }

        public string ToggleTouch()
        {
            this.turnoJ1 = !this.turnoJ1;
            if (this.turnoJ1)
            {
                return "O";
            }
            return "X";
        }

        public void Limpiar(object sender, EventArgs args)
        {
            int cols = grid.ColumnDefinitions.Count;
            int rows = grid.RowDefinitions.Count;

            for (int i = 0; i < casillas.Count(); i++)
            {
                casillas[i].Text = "";
                casillas[i].Clicked += GridTouch;
            }
        }

No logre hacer el rectangulo más pequeño que el botón