読者です 読者をやめる 読者になる 読者になる

SIN@SAPPOROWORKSの覚書

C#を中心に、夜な夜な試行錯誤したコードの記録です。

Xamarin.Forms イメージ

【 Xamarin 記事一覧 】

Xamarin.Formsの、ビューの1つであるImageは、画像表示のためのコントロールです。

参考:Xamarin Developers Guide 「Working with Images」
http://developer.xamarin.com/guides/cross-platform/xamarin-forms/working-with/images/

イメージの指定 Source

プロパティSource(ImageSource型)には、表示する画像を指定します。
指定要領には、次のようなものがあります。

(1) ローカルファイルを使用する場合

var img = new Image();

//ローカルファイル(1)
img.Source = ImageSource.FromFile("xamarin.png");

//ローカルファイル(2)
//img.Source = "xamarin.png";

//ローカルファイル(3)
//img.Source = FileImageSource.FromFile("xamarin.png");

f:id:furuya02:20140727061731p:plain:w250:left
ローカルの画像ファイルは、iOSの場合は、Resourcesの階層下、Androidの場合は、Resources/Drawableの階層下に配置します。


(2) ダウンロードを使用する場合

var uri = "http://xxx/xamarin.png";
var img = new Image();

//ダウンロード(1)
img.Source = ImageSource.FromUri(new Uri(uri));

//ダウンロード(2)
//img.Source = uri;


//ダウンロード(3)
//img.Source = new UriImageSource {
//    Uri = new Uri(uri),
//    CachingEnabled = false
//};

UriImageSourceには、キャッシュ機能があります。

2014.07.27 何故か、VisualStudioからAndroid用をコンパイルするとUrlによる指定が動作しません
https://forums.xamarin.com/discussion/21123/uriimagesource-based-image-not-rendering
[2014.08.07 追記]Xamarin.Forms 1.2.2.6243 で正常に動作することを確認しました。

イメージの配置 Aspect

f:id:furuya02:20140727061802p:plain:w150:leftf:id:furuya02:20140727061800p:plain:w150:left
Imageのエリアに画像をどのように展開するかを、プロパティAspectに設定します。

  • Aspect.AspectFill(デフォルト) 画像の縦横比を保持したまま、Imageに収まるように縮小する
  • Aspect.AspectFit  画像の縦横比を保持したまま、Image全体に表示する(画像の一部が欠ける)
  • Aspect.Fill 画像の縦横比を無視して、Image全体に表示する(画像の縦横比が壊れる)

サンプルは、3種類のAspect値によるImageの比較です。

public class App {
    public static Page GetMainPage(){

        var layout = new AbsoluteLayout();
        const int x = 10;
        var y = 30;
        foreach (Aspect aspect in Enum.GetValues(typeof (Aspect))){
            layout.Children.Add( new Label{ Text = aspect.ToString() } , new Point(x, y));
            y += 20;
            layout.Children.Add(CreateImage(aspect), new Rectangle(x, y, 300, 120));
            y += 140;
        }
        return new ContentPage {
            Content = layout
        };
    }
    static Image CreateImage(Aspect aspect) {
        var image = new Image{
            Source = ImageSource.FromFile("sample.png"),
            BackgroundColor = Color.Aqua,
            Aspect = aspect
        };
        return image;
    }
}

透明度 Opacity

f:id:furuya02:20140727061841p:plain:w150:leftf:id:furuya02:20140727061840p:plain:w150:left
プロパティOpacity(0.0~1.0)で画像の透明度を指定します。
サンプルは、同じ画像を6段階の透明度で配置したものです。

public static Page GetMainPage(){
    //アブソレートレイアウトの生成
    var layout = new AbsoluteLayout();

    //背景画像を生成
    var imageBack = new Image {
        Source = ImageSource.FromFile("back.png"),
        Aspect = Aspect.Fill
    };
    //背景画像をレイアウトに配置
    layout.Children.Add(imageBack, new Point(0, 0));

    //前景画像とラベルを6個、縦に配置
    var y = 40;
    const int x = 20;//左余白
    const int w = 280; //前景画像の幅
    const int h = 50;//前景画像の高さ
    for (var i = 0; i < 6; i++) {
        var opacity = 0.2 * i; //透明度
        //透明度を表示するためのラベルを生成
        var label = new Label {
            Text = String.Format("Opacity={0}", opacity)
        };
        //ラベルをレイアウトに配置
        layout.Children.Add(label, new Point(x, y));
        y += 20;
        //前景画像の作成
        var imageFront = new Image {
            Source = ImageSource.FromFile("front.png"),
            Aspect = Aspect.Fill,
            Opacity = opacity,//透明度
        };
        //前景画像をレイアウトに配置
        layout.Children.Add(imageFront, new Rectangle(x, y, w, h));
        y += h + 10;
    }

    return new ContentPage{
        Content = layout //アブソレートレイアウトをContentにセットする
    };
}

レイアウト OptionLayout

レイアウトは、このイメージに固有のプロパティではありませんが・・・

(1)Center,End,Fill,Start

f:id:furuya02:20140727061919p:plain:w150:leftf:id:furuya02:20140727061920p:plain:w150:left
HorizontalOptions(横方向)及びVerticalOptions(縦方向)で配置を指定します。
サンプルは、HorizontalOptionsに各種のレイアウトを指定したものです。

var layout = new StackLayout();
public static Page GetMainPage(){
    var ar = new[]{
        LayoutOptions.Center, 
        LayoutOptions.End, 
        LayoutOptions.Fill, 
        LayoutOptions.Start, 
    };

    var layout = new StackLayout();
    foreach (var op in ar) {
        layout.Children.Add(new Label {
            Text = op.Alignment.ToString(),
        });
        var img = new Image{
            Source = ImageSource.FromFile("xamarin.png"),
            BackgroundColor = Color.Blue,
            HorizontalOptions = op,
        };
        layout.Children.Add(img);
    }

    return new ContentPage {
        Padding = new Thickness(0,Device.OnPlatform(20,0,0),0,0),
        Content = layout
    };
}

(2)FillとFillAndExpand

f:id:furuya02:20140727061958p:plain:w150:leftf:id:furuya02:20140727062000p:plain:w150:left
レイアウトオプションには、AndExpandが付いたものと、そうでないものがありますが、この違いは、余白を埋めるかどうかにあります。

次の例は、スタックレイアウトに同じイメージを3つ並べ、真ん中のイメージに、Fillを指定した場合とFillAndExpandを指定した場合の違いを示したものです。

var layout = new StackLayout();
for (var i = 0; i < 3; i++){
    var img = new Image{
        Source = ImageSource.FromFile("xamarin.png"), 
        BackgroundColor = Color.Blue
    };
    if(i==1){
        //img.VerticalOptions = LayoutOptions.Fill;
        img.VerticalOptions = LayoutOptions.FillAndExpand;
    }
    layout.Children.Add(img);
}



暮井 慧タクシープロジェクト@札幌 【痛タク】2014年、7月11日から暮井 慧(プロ生ちゃん)タクシーが札幌を走行中です!


【 Xamarin 記事一覧 】