I want to download an image and store it in specific folder in local storage.
I am using this to download image:
var imageData = await AzureStorage.GetFileAsync(ContainerType.Image, uploadedFilename);
var img = ImageSource.FromStream(() => new MemoryStream(imageData));
Create a FileService interface
in your Shared Code, create a new Interface, for instance, called IFileService.cs
public interface IFileService
{
void SavePicture(string name, Stream data, string location="temp");
}
Implementation Android
In your android project, create a new class called "Fileservice.cs".
Make sure it derives from your interface created before and decorate it with the dependency information:
[assembly: Dependency(typeof(FileService))]
namespace MyApp.Droid
{
public class FileService : IFileService
{
public void SavePicture(string name, Stream data, string location = "temp")
{
var documentsPath = Environment.GetFolderPath(Environment.SpecialFolder.Personal);
documentsPath = Path.Combine(documentsPath, "Orders", location);
Directory.CreateDirectory(documentsPath);
string filePath = Path.Combine(documentsPath, name);
byte[] bArray = new byte[data.Length];
using (FileStream fs = new FileStream(filePath , FileMode.OpenOrCreate))
{
using (data)
{
data.Read(bArray, 0, (int)data.Length);
}
int length = bArray.Length;
fs.Write(bArray, 0, length);
}
}
}
}
Implementation iOS The implementation for iOS is basically the same:
[assembly: Dependency(typeof(FileService))]
namespace MyApp.iOS
{
public class FileService: IFileService
{
public void SavePicture(string name, Stream data, string location = "temp")
{
var documentsPath = Environment.GetFolderPath(Environment.SpecialFolder.Personal);
documentsPath = Path.Combine(documentsPath, "Orders", location);
Directory.CreateDirectory(documentsPath);
string filePath = Path.Combine(documentsPath, name);
byte[] bArray = new byte[data.Length];
using (FileStream fs = new FileStream(filePath , FileMode.OpenOrCreate))
{
using (data)
{
data.Read(bArray, 0, (int)data.Length);
}
int length = bArray.Length;
fs.Write(bArray, 0, length);
}
}
}
}
In order to save your file, in your shared code, you call
DependencyService.Get<IFileService>().SavePicture("ImageName.jpg", imageData, "imagesFolder");
and should be good to go.
I really liked Karan's approach.
I've made a sort of combination of them both and I wanted to share them here. Worked pretty well actually.
public String DownloadImage(Uri URL)
{
WebClient webClient = new WebClient();
string folderPath = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), "Images", "temp");
string fileName = URL.ToString().Split('/').Last();
string filePath = System.IO.Path.Combine(folderPath, fileName);
webClient.DownloadDataCompleted += (s, e) =>
{
Directory.CreateDirectory(folderPath);
File.WriteAllBytes(filePath, e.Result);
};
webClient.DownloadDataAsync(URL);
return filePath;
}
public void DownloadImage(string URL)
{
var webClient = new WebClient();
webClient.DownloadDataCompleted += (s, e) =>
{
byte[] bytes = new byte[e.Result.Length];
bytes=e.Result; // get the downloaded data
string documentsPath = Android.OS.Environment.GetExternalStoragePublicDirectory(Android.OS.Environment.DirectoryPictures).AbsolutePath;
var partedURL = URL.Split('/');
string localFilename = partedURL[partedURL.Length-1];
string localPath = System.IO.Path.Combine(documentsPath, localFilename);
File.WriteAllBytes(localPath, bytes); // writes to local storage
Application.Current.MainPage.IsBusy = false;
Application.Current.MainPage.DisplayAlert("Download", "Download Finished", "OK");
MediaScannerConnection.ScanFile(Forms.Context,new string[] { localPath }, null, null);
};
var url = new Uri(URL);
webClient.DownloadDataAsync(url);
}
Here you have to use dependency service from xamarin forms PCL to call this method from android project.This will store your image to public folder. Will edit this if i get time to make a demo with iOS also.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With