简体   繁体   中英

How to get index of sender item from "multiplexed" event handler?

I've got a single OnDownloadProgress event handler for an ordered list of BitmapImage items that I'm putting into a FlipView , and I'm wondering the best way to get the index of the sending BitmapImage in the event handler.

It's easy to do this kind of thing with objects derived from FrameworkElement , because they have a Tag property that you can set to the index (or whatever you want). But the OnDownloadProgress event is sent not by the Image , but by the BitmapImage, and that doesn't have a Tag .

I can think of a couple of ways to achieve this, but they seem hackish or heavy.

One way is by setting the Image's Tag to the BitmapImage instance, and then searching for that instance in the handler until you've found the sender:

private FlipView PhotosView;

private void AddImages(List<string> photoUrls)
{
    PhotosView.Items.Clear();
    foreach (var url in photoUrls)
    {
        var image = new Image();
        var source = new BitmapImage(new Uri(url));
        source.DownloadProgress += OnDownloadProgress;
        image.Source = source;
        image.Tag = source;
        PhotosView.Items.Add(image);
    }
}

private void OnDownloadProgress(object sender, DownloadProgressEventArgs args)
{
    int n = 0;
    foreach (var item in PhotosView.Items)
    {
        var image = (Image)item;
        if (image.Tag == sender)
        {
            Debug.WriteLine("image {0} progress={1}%", n, args.Progress);
            break;
        }
        n++;
    }
}

But that seems kinda wrong. A better way would be to maintain a mapping of BitmapImage instances to the index ( Dictionary<BitmapImage, int> ), and while more speed-efficient, that seems kinda heavy too.

Or, finally, I could subclass BitmapImage and add a Tag or Index member. Oh wait ... it's a sealed class. Scratch that one.

Is there a simpler or more standardized way to do this kind of thing?

You could do this:

private void AddImages(List<string> photoUrls)
{
    PhotosView.Items.Clear();
    int nextIndex = 0;
    foreach (var url in photoUrls)
    {
        int n = nextIndex++;
        var image = new Image();
        var source = new BitmapImage(new Uri(url));
        source.DownloadProgress += (sender, args) => 
        {
            Debug.WriteLine("image {0} progress={1}%", n, args.Progress);
        };
        image.Source = source;
        image.Tag = source;
        PhotosView.Items.Add(image);
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM