Yan LimaBenua
Yan LimaBenua

Reputation: 85

How to select image from gallery and save to sql database in xamarin

I have used Xamarin Media Plugin for image upload and i want to save that image in Sqlite and retrieve it back from Sqlite. How can i do that ?

Store: Convert the Image bitmap into a Base64String and store it to SQLite.

public static string Base64Encode(string plainText) {
  var plainTextBytes = System.Text.Encoding.UTF8.GetBytes(plainText);
  return System.Convert.ToBase64String(plainTextBytes);
}

Retrieve: Fetch the Base64String and convert that to Bitmap again.

public static string Base64Decode(string base64EncodedData) {
  var base64EncodedBytes = System.Convert.FromBase64String(base64EncodedData);
  return System.Text.Encoding.UTF8.GetString(base64EncodedBytes);
}

And how to select image from gallery and save to sql database in xamarin -- if like this, where I to implement these Base64Encode?

using Plugin.Media;
using Plugin.Media.Abstractions;
using System;
using Xamarin.Forms;
using SQLite;
using System.Collections.Generic;
using System.Threading.Tasks;

namespace PersonListData
{
    public class Person
    {   
        [PrimaryKey, AutoIncrement]
        public int IdSis { get; set; }
        public string NamePerson { get; set; }
        public byte[] PersonImg { get; set; }
    }
    
    async void SaveOnClik(object sender, EventArgs e)
    {
        var person = (Person)BindingContext;
        await App.Database.SavePersonAsync(person);
        await Navigation.PopAsync();
    }

    async void PickPhotos(object sender, EventArgs e)
    {
        if (CrossMedia.Current.IsPickPhotoSupported)
        {
            var file = await CrossMedia.Current.PickPhotoAsync(new Plugin.Media.Abstractions.PickMediaOptions
            {
                PhotoSize = PhotoSize.Medium,
            });
            if (file == null)
                return;

            image.Source = ImageSource.FromStream(() =>
            {
                var stream = file.GetStream();
                file.Dispose();
                return stream;
            });          
        }
        else
        {
            await DisplayAlert("Image error", ":( Hcant do thid.", "Ok");
            return;
        }

    }
    readonly SQLiteAsyncConnection _database;
    public DataPerson(string dbPath)
    {
        _database = new SQLiteAsyncConnection(dbPath);
        _database.CreateTableAsync<Person>().Wait();
    }
    public Task<List<Person>> GetPersonListAsync()
    {
        return _database.Table<Person>().ToListAsync();
    }
    public Task<Person> GetPersonAsync(int id)
    {
        return _database.Table<Person>()
        .Where(i => i.IdSis == id)
        .FirstOrDefaultAsync();
    }
    public Task<int> SavePersonAsync(Person person)
    {
        if (person.IdSis != 0)
        {
            return _database.UpdateAsync(person);
        }
        else
        {
            return _database.InsertAsync(person);
        }
    }
    public Task<int> DeletePersonAsync(Person person)
    {
        return _database.DeleteAsync(person);
    }
}

I am confused in this placement

Upvotes: 0

Views: 693

Answers (2)

Yan LimaBenua
Yan LimaBenua

Reputation: 85

I no longer think about saving photos in base64

in c#

using Plugin.Media;
....

async void GetPersonImage(object sender, EventArgs e)
    {
        if (!CrossMedia.Current.IsPickPhotoSupported)
        {
            await DisplayAlert("Foto tidak didukung", ":( Hak akses dibatasi.", "Oke deh ..");
            return;
        }
        var file = await Plugin.Media.CrossMedia.Current.PickPhotoAsync(new Plugin.Media.Abstractions.PickMediaOptions
        {
            PhotoSize = Plugin.Media.Abstractions.PhotoSize.Medium,
    
        });
    
        if (file == null)
            return;
    
        string path = file.Path;
        FtSiswa.Text = path; //this label hide
    
        await DisplayAlert("Foto disimpan di: ", file.Path, "OK");
    
        KameraFotos.Source = ImageSource.FromStream(() =>
        {
            var stream = file.GetStream();
            file.Dispose();
            return stream;
        });
    }

in xaml

.... <Image x:Name="KameraFotos" BackgroundColor="Bisque" Grid.Column="2" Grid.RowSpan="2" Aspect="AspectFit"> <Image.Source> <FileImageSource File="{Binding PersonImg}" /> </Image.Source> <TapGestureRecognizer Tapped="GetPersonImage" NumberOfTapsRequired="1" /> </Image.GestureRecognizers> </Image> ....

I think it is more efficient to save the image in the path and the address of the file that is recorded in the database

Upvotes: 0

Wendy Zang - MSFT
Wendy Zang - MSFT

Reputation: 10978

You could try to save image path into sqlite database.

Create a path property into the model.

 public class Person
{   
    [PrimaryKey, AutoIncrement]
    public int IdSis { get; set; }
    public string NamePerson { get; set; }
    public string Path{ get; set; }
    public byte[] PersonImg { get; set; }
}

And then save the string into the database.

   public Task<int> SaveItemAsync(Person item)
    {
        if (item.ID != 0)
        {
            return Database.UpdateAsync(item);
        }
        else
        {
            return Database.InsertAsync(item);
        }
    }

You could check the link below with the code sample about how to save string into sqlite databsae. https://learn.microsoft.com/en-us/xamarin/xamarin-forms/data-cloud/data/databases

If you still want to save byte[] into sqlite database, you need to convert stream into byte[]. Please check the way about how to convert image from stream to bytes. How to save an image in SQLite in Xamarin Forms?

Upvotes: 1

Related Questions