1

このアプリケーションは、この目的でMicrosoftLyncクライアントを使用しているメッセンジャーです。コンテキストの1つで、連絡先(名前、画像、可用性などのプロパティを持つLyncClientのオブジェクト)をリストビューで取得し、次のように定義されたデータテンプレートにロードしています。

<DataTemplate x:Key="ContactsTemplate">
        <Grid HorizontalAlignment="Left" Width="150" Height="150" Margin="10">
            <Border Background="{StaticResource ListViewItemPlaceholderBackgroundThemeBrush}">
                <Image Source="{Binding Image}" Stretch="UniformToFill" AutomationProperties.Name="{Binding Title}"/>
            </Border>
            <StackPanel VerticalAlignment="Bottom" Background="{Binding Availability, Converter={StaticResource AvailabilityToPresenceColor}}" Opacity="0.75">
                <TextBlock Text="{Binding Name}" Foreground="{StaticResource ListViewItemOverlayForegroundThemeBrush}" Style="{StaticResource TitleTextStyle}" Height="20" Margin="15,0,15,15"/>
            </StackPanel>
        </Grid>
    </DataTemplate>

グリッドコンテナがあり、連絡先の画像と名前を表示する画像とテキストブロックのコントロールがあります。以下に示すように、stackpanelの背景は、可用性ステータスをにマップするコンバータを使用して、lyncContactオブジェクトAvailabilityプロパティにバインドされます。たとえば、連絡先の可用性がビジーのときにスタックパネルの背景が赤になるように色を付けます。

画像制御にも同様の効果が欲しいです。

私はバインディングに不慣れなので、このバインディングの概念で完全に失われました。

私の考えは、画像用のエフェクト偶数ハンドラーがあるので、それをこの目的に使用して使用することを考えました。

ある条件下でのコンバーター内で、画像ソースを取得する必要があるコードを使用したいのですが、バインディングを介して画像ソースを取得しているためです。

あなたのアイデアを教えてください。


コードでわかるように、 私は画像コントロールのソースをContactオブジェクトのプロパティに<Image Source="{Binding Image}" Stretch="UniformToFill" AutomationProperties.Name="{Binding Title} effect="{Binding Availability, Converter={StaticResource AvailabilityToPresenceColor}}"/> バインドしているだけです 。ContactオブジェクトのAvailabilityプロパティをIValueConverterのConvertメソッドに送信するか、可能であれば画像をContactObject全体にバインドしたい...または他の方法で知らせてください。

#####################コメントの添付
var bitmap = new BitmapImage();
    bitmap.BeginInit();
    MemoreyStream ms=new MemoryStream(_image);
    bitmap.StreamSource = stream;
    bitmap.CacheOption = BitmapCacheOption.OnLoad;
    bitmap.EndInit();
 var grayBitmapSource = new FormatConvertedBitmap();
    grayBitmapSource.BeginInit();
    grayBitmapSource.Source = ms;
    grayBitmapSource.DestinationFormat = PixelFormats.Gray32Float;
    grayBitmapSource.EndInit();
.....

これで、FormatConvertedBitmapタイプのgrayBitmapSourceがあり、それを再びStreamに変換する方法がわかりません。

4

1 に答える 1

0

WPFでの画像処理に関するこの記事を参照することをお勧めします:http://www.codeproject.com/Articles/237226/Image-Processing-is-done-using-WPF

画像処理ロジックを使用して、可用性ステータスごとに異なる画像を作成します。IValueConverterを使用することもできますが、これは、可用性ステータスが変更されるたびにイメージを再処理する必要があることを意味します。代わりに、Contactクラスを変更するだけで、Availabilityプロパティを変更すると、Imageプロパティによって参照される画像を取得するようにWPFに自動的に通知されます。

public class Contact : INotifyPropertyChanged
{
    // EDIT: INotifyPropertyChanged implementation.
    public event PropertyChangedEventHandler PropertyChanged;

    public void NotifyPropertyChanged(String propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
    }
    // EDIT: INotifyPropertyChanged implementation.

    private ContactAvailability _Availability;

    public ContactAvailability Availability
    {
        get { return _Availability; }
        set
        {
            _Availability = value;
            NotifyPropertyChanged("Availability");
            NotifyPropertyChanged("Image");
        }
    }

    public BitmapImage _AvailablePicture;
    public BitmapImage _BusyPicture;

    public BitmapImage Image
    {
        get
        {
            switch (this.Availability)
            {
                case ContactAvailability.Available:
                    return this._AvailablePicture;
                case ContactAvailability.Busy:
                    return this._BusyPicture;
                default:
                    throw new NotImplementedException();
            }
        }
    }
}

編集(コメントするには長すぎます):

INotifyPropertyChangedインターフェイスを実装するためのコードを追加しました。これはWPFで非常に一般的であるため、このアプローチについてはすでにご存知だと思います。

あなたの例でImage.Sourceは、はDepencyPropertyです。クラスがを実装するINotifyPropertyChangedと、そのプロパティの1つが変更されたことをWPFに通知できます。NotifyPropertyChanged変更したプロパティの名前でイベントを発生させるだけです。DepencyPropertyこれは、指定されたプロパティにバインドするすべてのを更新するようにWPFに通知します。

これは、画像処理の観点から、バインディングとどのように異なりますか。つまり、可用性が変わるたびに、このようにして画像処理コードも実行する必要があります。私は正しいかどうか@bouvierr?

いいえ。この場合、画像処理を一定の回数だけ実行して、各可用性ステータスの画像を作成します(私の例では連絡先ごとに2回)。たとえば、アプリケーションの起動時にすべての画像を作成し(3つの連絡先x2つのステータス=6つの画像)、各連絡先_AvailablePicture_BusyPictureフィールドに保存できます。

重要な部分は次のとおりです。Availabilityプロパティを設定するときに、も呼び出しますNotifyPropertyChanged("Image")。これにより、WPFはにImage.Source DepencyPropertyバインドされるため、を強制的に更新しContact.Imageます。Availabilityが変更されたため、これは別の画像を返します。

私の例では、写真を保存することにしました。これはあなたにとって最善の解決策ではないかもしれません。より多くのメモリを消費しますが、処理時間を節約します。可用性ステータスが変更されるたびにイメージを再処理する場合は、Contact.Imageプロパティを次のように変更する必要があります。

    public BitmapImage Image
    {
        get
        {
            switch (this.Availability)
            {
                case ContactAvailability.Available:
                    return this._AvailablePicture;
                case ContactAvailability.Busy:
                    return GetImageWithColorFilter(this._AvailablePicture, Colors.Red);
                default:
                    throw new NotImplementedException();
            }
        }
    }
于 2013-01-20T16:31:28.523 に答える