Grid でビューを配置する
7x5 グリッドでイメージを表示するページを構築するとします。 複数の横方向と縦方向の StackLayout
コンテナーを使用して、このページを作成することができます。 しかし、コーディングが面倒になり、複数のレイアウト パネルのメモリと処理の要件により、パフォーマンスの問題が発生する可能性があります。 Grid
レイアウト パネルは、行と列の両方を必要とする UI により適した選択肢です。 このユニットでは、Grid
を定義し、そのセル内にビューを配置する方法について学習します。
Grid とは
Grid
は、行と列で構成されるレイアウト パネルです。 以下は、グリッドの概念図を示しています。
行と列の交差部分から作成されるセルにビューを配置します。 たとえば、列が 3 つあり、行が 2 つある Grid
を作成した場合、ビューで使用可能な 6 つのセルが存在することになります。 行と列を異なるサイズにすることも、その内部に配置されている子のサイズに応じて自動的に調整されるように設定することもできます。 子ビューでは単一のセルを占有することも、多くのセルにまたがるようにすることもできます。 この柔軟性により、Grid
が、多くのアプリのルート レイアウト パネルに適した選択肢となります。
Grid の行と列を指定する方法
Grid
を作成するときに、行と列をそれぞれ個別に定義できます。 このシステムによって、各行の高さと各列の幅を完全に制御できます。 すべての Grid
に、グリッドの形状を定義する RowDefinition
および ColumnDefinition
オブジェクトのコレクションがあります。 これらのコレクションに、UI で行または列を表す RowDefinition
と ColumnDefinition
のインスタンスを設定します。
以下は、RowDefinition
と ColumnDefinition
のクラス定義を示すコードの 2 つのスニペットです。
public sealed class RowDefinition : ...
{
...
public GridLength Height { get; set; }
}
public sealed class ColumnDefinition : ...
{
...
public GridLength Width { get; set; }
}
RowDefinition
には Height
というプロパティがあり、ColumnDefinition
には Width
というプロパティがあることに注目してください。 次のセクションで説明するように、これらのプロパティを使って、行の高さと列の幅を設定します。
GridLength とは
Width
および Height
プロパティのデータ型は GridLength
です。 この型には、GridUnitType
および Value
という 2 つのプロパティが含まれます。 以下は、型定義の一部を示すコードのスニペットです。
public struct GridLength
{
...
public GridUnitType GridUnitType { get; }
public double Value { get; }
}
GridUnitType
プロパティをこれらの値のいずれかに設定することができます。
Absolute
Auto
Star
これらの各値について詳しく見ていきましょう。
Absolute GridUnitType
Absolute
では、行または列のサイズが固定されるように指定します。 Value
プロパティを使ってサイズを指定します。 以下は、C# で行の高さを 100
デバイス単位の固定サイズに設定する方法を示す例です。 数値を受け取る GridLength
コンストラクターの使い方に注目してください。 このコンストラクターにより、GridUnitType
は自動的に Absolute
に設定されます。
var row = new RowDefinition() { Height = new GridLength(100) };
Extensible Application Markup Language (XAML) では、数値のみを指定します。 XAML パーサーによって、GridLength
インスタンスを作成するために型コンバーターが呼び出されます。 以下は、XAML での同じことを示す例です。
<RowDefinition Height="100" />
Auto GridUnitType
Auto
を使うと、子ビューに合わせて行または列のサイズが自動的に設定されます。 Grid
を使って、その行または列内のすべての子ビューをスキャンし、最大のビューを選んでから、行または列をその子に合う十分な大きさにします。 コードで行の定義を作成するときに、数値は無視されます。 任意の値を使用できます。 以下は、C# で行の高さを自動的にサイズ設定する方法を示す例です。 1
という値が任意に選択されていることに注目してください。
var row = new RowDefinition() { Height = new GridLength(1, GridUnitType.Auto) };
XAML では、Auto
という値を使用します。 以下は、XAML での同じことを示す例です。
<RowDefinition Height="Auto" />
Star GridUnitType
Star
では比例サイズ指定が提供されます。 比例サイズ設定では、使用できる合計領域と、個々の行または列に必要な比率によってサイズが決まります。 会話では、多くの場合、これは "比例サイズ指定" ではなく、"スター サイズ指定" と呼ばれます。
グリッドの行の比例サイズ指定を使用するプロセスについて見ていきましょう。
使用可能なスペースを決定します。
Grid
では、スター サイズ指定を使用Grid
すべての行をスキャンします。 これらすべての行の高さを合計し、Grid
自体の高さからその合計を減算します。 この計算では、スターサイズ指定されたすべての行で使用可能なスペースの量が提供されます。使用可能なスペースを定義します。
Grid
では、その後、各行のValue
設定に基づいて、スターサイズ指定されたすべての行の間で使用可能なスペースが分割されます。Value
プロパティは、スター サイズ指定されたものとして定義されたすべての行の間で比率を決定する乗数と考えてください。 たとえば、スターサイズ指定された 2 つの行があり、両方の乗数が1
である場合、それらに使用可能なスペースが等分されます。 しかし、それらのいずれかの Value が2
である場合、スペースは他の 2 倍になります。
以下は、C# で行の高さを 2 Star
に設定する方法を示す例です。
var row = new RowDefinition() { Height = new GridLength(2, GridUnitType.Star) };
XAML では、*
シンボルを使用して、スター サイズ指定を表します。 値と *
を単一の文字列に結合すると、型コンバーターによって自動的に GridLength
が作成されます。 XAML での同じ例を次に示します。
<RowDefinition Height="2*" />
グリッド コレクション
RowDefinition
と ColumnDefinition
を使って行と列を定義した後は、それらを Grid
に追加できます。 Grid
のコレクション プロパティ RowDefinitions
と ColumnDefinitions
を使います。 これらのコレクションの設定は、通常 XAML で行います。
この例では、4 つの行を定義し、RowDefinitions
プロパティを使用して、それらを Grid
に追加する方法を示します。
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="100" />
<RowDefinition Height="Auto" />
<RowDefinition Height="1*" />
<RowDefinition Height="2*" />
</Grid.RowDefinitions>
...
</Grid>
この定義は次のように短縮できます。
<Grid RowDefinitions="100, Auto, 1*, 2*">
...
</Grid>
列を定義するための XAML は、前の XAML に似ています。 ただし、ColumnDefinitions
を使用し、Width
を設定します。
実行時に、この XAML によって、4 行ある Grid
が生成されます。 1 行目は 100
デバイス単位の固定の高さになります。 2 行目は行の最も高いビューの高さとなります。 3 行目と 4 行目にはスター サイズ指定が使われます。これは、残りの使用可能な領域を取得し、それをその Value
乗数に基づいて比例的に分割することを意味します。 3 行目が 1*
、4 行目が 2*
であるため、4 行目は 3 行目の高さの 2 倍です。
行と列の既定のサイズ
行と列の既定のサイズは 1*
です。 たとえば、次の XAML を見てみましょう。
<Grid>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition />
</Grid.ColumnDefinitions>
...
</Grid>
この定義は次のように短縮できます。
<Grid RowDefinitions="*, *, *" ColumnDefinitions="*, *">
...
</Grid>
行と列のサイズが指定されていないため、1*
はそれらすべてに適用されます。 実行時に、この構成で均一の Grid
が作成されます。これは、すべての行の高さが同じになり、すべての列の幅が同じになることを意味します。
Grid にビューを追加する方法
Grid
にビューを追加するときは、特定のセルにそれを追加します。 セルは行と列が交差する位置に作成されます。 セルにビューを配置するには、セルの位置がわかっている必要があります。 行数と列数の組み合わせを使用して、セルを識別します。
行と列の番号付け
行と列の番号付けは 0 から始まります。 原点は左上隅です。 以下は、行が 4 つで列が 2 つの Grid
の番号付けを示す図です。
たとえば、右下のセルにビューを追加する場合、ビューの位置は row 3 column 1
になります。
添付プロパティを使用して Grid にビューを追加する
グリッドに追加するときは、ビューの行と列の番号を指定する方法が必要です。 1 つの解決策は、View
基底クラスで Row
および Column
プロパティを定義し、ビューでの位置を直接指定できるようにすることです。 この技法は機能しますが、最も効率的なアプローチではありません。 ビューが必ずしも Grid
に含まれるわけではないため、それらのプロパティが不要な場合もあります。 添付プロパティを使用することをお勧めします。
添付プロパティとは、あるクラスで定義されているものの、他の種類のオブジェクトに対して設定されているプロパティのことです。
添付プロパティは、ビューの一部であるキーと値のペアのコレクションと考えてください。 ビューを Grid
に追加するときは、行と列を指定します。 添付プロパティを使って、キー Grid.Row
と、行番号を指定する値で、キーと値のペアを追加することができます。 Grid
でビューを配置する準備ができると、コレクションで Grid.Row
というキーがあるかどうかが確認されます。 ある場合、Grid
ではその値を使って、ビューが配置されます。
この例では、添付プロパティを使用して、Grid
を作成し、ビューを追加する方法を示します。
<Grid RowDefinitions="*, *, *" ColumnDefinitions="*, *">
<BoxView Grid.Row="1" Grid.Column="0" Color="Navy" />
</Grid>
この例では、Grid.Row=1
と Grid.Column=0
は、BoxView
の内部コレクションに追加されるキーと値のペアです。 Grid
ではそれらの値を使って、ビューを配置する必要がある場所を決定します。 デバイス上でアプリケーションを実行した場合、この Grid
は次のようになります。
複数の行または列にまたがるビューを作成する方法
注意する必要がある、Grid.RowSpan
および Grid.ColumnSpan
というさらに 2 つの添付プロパティがあります。 これらのプロパティでは、ビューで占有する必要がある行または列の数が指定されます。 たとえば、次の XAML を見てみましょう。
<Grid RowDefinitions="*, *, *" ColumnDefinitions="*, *">
<BoxView Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="2" Color="Navy" />
</Grid>
この例では ColumnSpan
を 2
に設定していることに注意してください。 このビューは Column 0
から始まる 2 列を占有します。 デバイス上でアプリケーションを実行した場合、この Grid
は次のようになります。