Android では、例えば画面の幅に対して、複数のボタンを同じ幅でいい感じに Fill させることができます。(これを均等割り付けというのが正しいのかはよくわかりませんが)
これで画面の解像度が違っても、横向きになっても、同じ幅のボタンで埋まる、という事ができます。
Xamarin.Forms でこれを実現するにはどうしたら良いか、試してみました。
Xamarin.Forms では、LinearLayout に相当するレイアウトとして StackLayout があります。
まずはこれを利用してみます。
StackLayout
を Orientation = Horizontal
とし、Children
にボタンを3つ配置しています。ボタンの幅は全て HorizontalOptions = FillAndExpand
とします。
//App.cs
public class App
{
public static Page GetMainPage()
{
return new ContentPage
{
Content = new StackLayout
{
HorizontalOptions = LayoutOptions.FillAndExpand,
VerticalOptions = LayoutOptions.Center,
Orientation = StackOrientation.Horizontal,
Children =
{
new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "one",
TextColor = Color.Black,
BackgroundColor = Color.Aqua,
},
new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "two two",
TextColor = Color.Black,
BackgroundColor = Color.Fuschia,
},
new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "three three three",
TextColor = Color.Black,
BackgroundColor = Color.Lime,
},
},
},
};
}
}
これを iOS/Android 双方で実行すると、こうなりました。
うーん、そうじゃない(汗 どうやらボタンのテキストが全て表示されるように頑張ってくれちゃうようです。 まあ、これはこれで使える感じもします。
他のレイアウトで考えてみます。Android の TableLayout に相当する Grid を使ってみます。
さっきの App.cs
の実装を次のように変えます。
Grid
に1行3列の表を定義します。
列の定義 ColumnDefinition
で幅を new GridLength(1, GridUnitType.Star)
としているのは、「3列とも同じ比率の幅とする」ことを意味しています。(ということは比率を2:1:1にしたければ、最初の列だけ2
にすればOKです)
//App.cs
public class App
{
public static Page GetMainPage()
{
var grid = new Grid
{
HorizontalOptions = LayoutOptions.FillAndExpand,
VerticalOptions = LayoutOptions.Center,
RowDefinitions =
{
new RowDefinition() { Height = GridLength.Auto }
},
ColumnDefinitions =
{
new ColumnDefinition() { Width = new GridLength(1, GridUnitType.Star) },
new ColumnDefinition() { Width = new GridLength(1, GridUnitType.Star) },
new ColumnDefinition() { Width = new GridLength(1, GridUnitType.Star) },
}
};
grid.Children.Add(new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "one",
TextColor = Color.Black,
BackgroundColor = Color.Aqua,
}, 0, 0);
grid.Children.Add(new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "two two",
TextColor = Color.Black,
BackgroundColor = Color.Fuschia,
}, 1, 0);
grid.Children.Add(new Button
{
VerticalOptions = LayoutOptions.Center,
HorizontalOptions = LayoutOptions.FillAndExpand,
Text = "three three three",
TextColor = Color.Black,
BackgroundColor = Color.Lime,
}, 2, 0);
return new ContentPage
{
Content = grid,
};
}
}
これを iOS/Android 双方で実行すると、こうなりました。
おーけー、意図したレイアウトになりました。ボタンに入りきらないテキストはiOSだと省略され、Androidだと折り返されるという違いはありますが、レイアウトの一貫性は保つことができました。
ちなみに横向きにしても大丈夫です。
Xamarin.Forms でも、Android+LinearLayoutのような均等配置ができました。 クロスプラットフォームなので、iOSでも同じように動作します。 iPhone6 が発表されてiOS開発でも多解像度対応が必須になるので、これは有用な感じがします。 (というか Storyboard の AutoLayout では、これと同じことができる気がしないのですが。。。)