Xamarin.forms binds listview-imagecell imagesource to byte []

I am currently getting started with Xamarin.Forms. I have a ListView in my page that I am linking to my ViewModel. ItemTemplate is of type "ImageCell"

No problem binding Text and Detail properties to a cell. However, I am unable to bind the "ImageSourceProperty". This image source is generated using byte [] (My images are blocks in SQLite database)

I was wondering if anyone knows how to solve this problem (or another way to bind byte [] - image to listview element)

Here's some source code:

var model = Graanziekten.Select(g => new OnkruidViewModel
            {
                Id = g.Id, Naam = g.Naam, Omschrijving = g.Omschrijving, Afbeelding = g.BitmapThumbnail
            }).ToList();

            var cell = new DataTemplate(typeof(ImageCell));
            cell.SetBinding(TextCell.TextProperty, "Naam");
            cell.SetBinding(TextCell.DetailProperty, "Omschrijving");
            cell.SetBinding(ImageCell.ImageSourceProperty, "Afbeelding");

            var listview = new ListView
            {
                ItemsSource = model,
                ItemTemplate = cell
            };

      

The "BitmapThumbnail" property is defined as:

public ImageSource BitmapThumbnail
        {
            get
            {
                //AfbeeldingSmall is a byte[]
                return ImageSource.FromStream(() => new MemoryStream(Afbeeldingen.First().AfbeeldingSmall));
            }
        }

      

If I use a dummy image (from uri) it works fine. But if I use the code shown above, the content page is not even displayed at all (blank black screen).

At first I thought the problem might have something to do with the [] byte being retrieved from the property dynamically, but the same effect occurs when I retrieve all the [] bytes needed.

Also, when I add one image to my content page using the same method, it works. Just not on the list.

I'm trying to do this on WinPhone8 (although I don't think the platform matters)

Thanks in advance.

+3


source to share


1 answer


Have you tried linking it directly to your list? Instead of loading this model object.

    var cell = new DataTemplate(typeof(ImageCell));
    cell.SetBinding(ImageCell.ImageSourceProperty, "Afbeelding");
    cell.SetBinding(TextCell.TextProperty, "Naam");
    cell.SetBinding(TextCell.DetailProperty, "Omschrijving");

    var listview = new ListView
    {
        ItemsSource = Graanziekten,
        ItemTemplate = cell
    };

      


You can also leave the Image property like this:

    public ImageSource BitmapThumbnail
    {
        get
        {
             return Afbeeldingen.First().AfbeeldingSmall;
        }
    }

      

And use the Converter along with it:

    public class ByteArrayToImageConverter: IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            byte[] imageAsBytes = (byte[])value;
            return ImageSource.FromStream(() => new MemoryStream(imageAsBytes);
        }

        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }

      



If you will be using a converter, you will need to change your SetBinding to:

    cell.SetBinding(ImageCell.ImageSourceProperty, "Afbeelding", BindingMode.OneWay, new ByteArrayToImageConverter());

      

EDIT : Your SetBinding (TextCell) must be SetBinding (ImageCell). Can you also try to create a data template like this? It shouldn't matter, but I get ideas:

var listview = new ListView
{
    ItemsSource = Graanziekten,
    ItemTemplate = new DataTemplate(() =>
    {
        ImageCell imageCell = new ImageCell();
        imageCell.SetBinding(ImageCell.ImageSourceProperty, new Binding("Afbeelding", BindingMode.OneWay, new ByteArrayToImageConverter()));
        imageCell.SetBinding(ImageCell.TextProperty, "Naam");
        imageCell.SetBinding(ImageCell.DetailProperty, "Omschrijving");
        return imageCell;
    };
};

      

instead

var listview = new ListView
{
    ItemsSource = Graanziekten,
    ItemTemplate = cell
};

      

0


source







All Articles