Rename a recorded file every time I save a record in xamarin - xamarin

I am saving my records using this code:
string path = Android.OS.Environment.ExternalStorageDirectory.AbsolutePath;
public string fileName { get; set; }
fileName = Path.Combine(path, "sample.wav");
if (!recorder.IsRecording)
{
recorder.StopRecordingOnSilence = TimeoutSwitch.IsToggled;
//Start recording
var audioRecordTask = await recorder.StartRecording();
BtnDoneRec.IsEnabled = false;
await audioRecordTask;
RecEditor.IsEnabled = true;
BtnDoneRec.IsEnabled = false;
PlayButton.IsEnabled = true;
var filePath = recorder.GetAudioFilePath();
if (filePath != null)
{
var stream = recorder.GetAudioFileStream();
using (var fileStream = new FileStream(fileName, FileMode.Create, FileAccess.Write))
{
stream.CopyTo(fileStream);
}
}
}
else
{
//stop recording ...
await recorder.StopRecording();
}
I want my record to have a specific name which is labeled with my RecEditor
using (var streamReader = new StreamReader(fileName))
{
File.Move("sample.wav", RecEditor.Text + ".wav");
}
So it will rename "sample.wav" to "RecEditor text.wav" every time I click my save button.
But when I click save, it gives me this record
System.IO.FileNotFoundException: 'Could not find file '/sample.wav'.'
The record is stored in /storage/emulated/0/sample.wav
The sample.wav is created in my device but I don't know why it give me 'Could not find file '/sample.wav'.' error. What am i doing wrong here?

I believe that what you're looking is something like this:
if(File.Exists(fileName))
{
var newFileName = Path.Combine(path, $"{RecEditor.Text}.wav");
File.Move(fileName, newFileName);
}
You don't need to open a new Stream as you are doing. Also, you need to put the full file path not only the file name.
You might want to validate that RecEditor.Text is not empty before using its value for the newfileName
Hope this helps.-

Related

Xamarin forms: Picture extension is not saving with path in android when do multiple photo selection

I am following this article for Select Multiple Images From Gallery in Xamarin Forms.
I completed the feature in android part but the picture path contains only the picture name, extensions are missing when saving path.
To upload the image to the server I need the complete image name with extension. So how can I save the complete path of the selected images with the extension?
Following method capture the image path:
public String GetRealPathFromURI(Android.Net.Uri contentURI)
{
try
{
ICursor imageCursor = null;
string fullPathToImage = "";
imageCursor = ContentResolver.Query(contentURI, null, null, null, null);
imageCursor.MoveToFirst();
int idx = imageCursor.GetColumnIndex(MediaStore.Images.ImageColumns.Data);
if (idx != -1)
{
fullPathToImage = imageCursor.GetString(idx);
}
else
{
ICursor cursor = null;
var docID = DocumentsContract.GetDocumentId(contentURI);
var id = docID.Split(':')[1];
var whereSelect = MediaStore.Images.ImageColumns.Id + "=?";
var projections = new string[] { MediaStore.Images.ImageColumns.Data };
cursor = ContentResolver.Query(MediaStore.Images.Media.InternalContentUri, projections, whereSelect, new string[] { id }, null);
if (cursor.Count == 0)
{
cursor = ContentResolver.Query(MediaStore.Images.Media.ExternalContentUri, projections, whereSelect, new string[] { id }, null);
}
var colData = cursor.GetColumnIndexOrThrow(MediaStore.Images.ImageColumns.Data);
cursor.MoveToFirst();
fullPathToImage = cursor.GetString(colData);
}
return fullPathToImage;
}
catch (Exception ex)
{
Toast.MakeText(Xamarin.Forms.Forms.Context, "Unable to get path", ToastLength.Long).Show();
}
return null;
}
The extension(.png or .jpg) was missing not from the GetRealPathFromURI(), it happens in ImageHelpers.SaveFile(). So I save the filename to another variable from the path using Path.GetFileName() like below and pass the complete filename when call ImageHelpers.SaveFile().
var fileName = Path.GetFileName(picturepath);

How to save image path in database and save image in specific folder of project.NET core

[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create(Employee emp)
{
if (ModelState.IsValid)
{
var files = HttpContext.Request.Form.Files;
foreach (var Image in files)
{
if (Image != null && Image.Length > 0)
{
var file = Image;
var root = _appEnvironment.WebRootPath;
var uploads = "uploads\\img";
if (file.Length > 0)
{
// you can change the Guid.NewGuid().ToString().Replace("-", "")
// to Guid.NewGuid().ToString("N") it will produce the same result
var fileName = Guid.NewGuid().ToString("N") + Path.GetExtension(file.FileName);
using (var fileStream = new FileStream(Path.Combine(root, uploads, fileName), FileMode.Create))
{
await file.CopyToAsync(fileStream);
// This will produce uploads\img\fileName.ext
emp.ImageUrl = Path.Combine(uploads, fileName);
}
}
}
}
db.Add(emp);
await db.SaveChangesAsync();
return RedirectToAction("Index");
}
else
{
var errors = ModelState.Values.SelectMany(v => v.Errors);
}
return View(emp);
}
HTML
<input asp-for="ImageUrl" type="file" Class="form-control" />
when i save image, image save successfully in database, but it takes full image path like this C:\Users\VIZO\Desktop\employee.jpg i dont want like this, i need to save image path something like this ~images\employee.jpg. The other problem is image doesnt saving in specific folder of project, i need to save image in this path of my project
uploads\img
So basically your _appEnvironment.WebRootPath by default will be:
%PathToProject%/wwwroot.
For the filePath on your database i would do something like this:
var root = _appEnvironment.WebRootPath
var uploads = "uploads\\img";
if (file.Length > 0)
{
// you can change the Guid.NewGuid().ToString().Replace("-", "")
// to Guid.NewGuid().ToString("N") it will produce the same result
var fileName = Guid.NewGuid().ToString("N") + Path.GetExtension(file.FileName);
using (var fileStream = new FileStream(Path.Combine(root, uploads, fileName), FileMode.Create))
{
await file.CopyToAsync(fileStream);
// This will produce uploads\img\fileName.ext
emp.BookPic = Path.Combine(uploads, fileName);
}
}
If you require any more clarification or guidance please feel free to comment and allow me to explain in more detail.
Thanks.

Android post image to Facebook comment

This is a followup to my previous question: Xamarin.Forms App return data to calling App
That works perfectly and I can share images to anywhere, except to Facebook comments. When I click the camera on the content box the app can be selected, I can select the image, Set result and Finish are called, and the app closes and it sends data to Facebook, and then however I then get the error : The image could not be uploaded, try again?
I can't find any fundamental differences between posting to a status or a comment, so I'm guessing it's subtle. Any thoughts on how I can change my intent to post properly?
Adding for completeness:
Bitmap b = null;
string url;
if (!string.IsNullOrEmpty(this.saleItems[i].ImageUrl))
{
url = this.saleItems[i].ImageUrl;
}
else
{
url = await FileHelper.GetLocalFilePathAsync(this.saleItems[i].Id);
}
//download
using (var webClient = new WebClient())
{
var imageBytes = webClient.DownloadData(url);
if (imageBytes != null && imageBytes.Length > 0)
{
b = BitmapFactory.DecodeByteArray(imageBytes, 0, imageBytes.Length);
}
}
//set local path
var tempFilename = "test.png";
var sdCardPath = Android.OS.Environment.ExternalStorageDirectory.AbsolutePath;
var filePath = System.IO.Path.Combine(sdCardPath, tempFilename);
using (var os = new FileStream(filePath, FileMode.Create))
{
b.Compress(Bitmap.CompressFormat.Png, 100, os);
}
b.Dispose();
var imageUri = Android.Net.Uri.Parse($"file://{sdCardPath}/{tempFilename}");
var sharingIntent = new Intent();
sharingIntent.SetAction(Intent.ActionSend);
sharingIntent.SetType("image/*");
sharingIntent.PutExtra(Intent.ExtraText, "some txt content");
sharingIntent.PutExtra(Intent.ExtraStream, imageUri);
sharingIntent.AddFlags(ActivityFlags.GrantReadUriPermission);
//await SaleItemDataService.Instance.BuySaleItemAsync(this.saleItem);
SetResult(Result.Ok, sharingIntent);
Finish();
Use below:
Intent sharingIntent = new Intent();
string imageUri = "file://" + requestedUri;
sharingIntent.SetData(Android.Net.Uri.Parse(imageUri));

Writing CSV to MemoryStream using LinqToCSV does not return any data

I've verified using System.Text.Encoding.ASCII.GetString(ms.ToArray)); that my memorystream has the expected data.
However using the LinqToCSV nuget library will not generate my csv file. I get no errors or exceptions thrown. I just get an empty file when I'm prompted to open the file.
Here is my Action Method
public FileStreamResult Export(){
var results = _service.GetProperties().Take(3);
System.IO.MemoryStream ms = new System.IO.MemoryStream();
System.IO.TextWriter txt = new System.IO.StreamWriter(ms);
CsvFileDescription inputFileDescription = new CsvFileDescription{
SeparatorChar =',',
FirstLineHasColumnNames = true
}
;
CsvContext csv = new CsvContext();
csv.Write(results,txt,inputFileDescription);
return File(ms , "application/x-excel");
}
I find it interesting, if I change the return type to contentResult, and the return method to Content() and pass it System.Text.Encoding.ASCII.GetString(ms.ToArray)); I do get a browser window showing my data.
Make sure you reset stream position to 0. Also make sure you flush your StreamWriter before that.
Calling the Web API method to return CVS file from JavaScript.
public HttpResponseMessage Bidreport([FromBody]int formData).....
Fill in your IEnumerable<YourObject>query = from LINQ query
....
This is how to return it:
using (var ms = new MemoryStream())
{
using (TextWriter txt = new StreamWriter(ms))
{
var cc = new CsvContext();
cc.Write(query, txt, outputFileDescription);
txt.Flush();
ms.Position = 0;
var fileData = Encoding.ASCII.GetString(ms.ToArray());
var result = new HttpResponseMessage(HttpStatusCode.OK) {Content = new StringContent(fileData)};
result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/x-excel");
return result;
}
}

Show and Download a text file with Extension

I want to read a log file(txt file) and view this in txt file and save with txt format.
This is my code,which is working fine for showing and downloading the read content in txt file,i have few issues in that..
public FileResult Download(string id)
{
int rowId = Convert.ToInt32(id);
LoadFileInfoCache();
var fileDetails = from ff in _currentFileDetails
where ff.FileId == rowId
select new
{
name = ff.FileName,
location = ff.FileLocation
};
var fileDetailsList = fileDetails.ToList();
string fileLocation = fileDetailsList[0].location;
string fileName = fileDetailsList[0].name;
string contentType = "application/txt";
var file = System.IO.File.Open(fileLocation, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
var stream = (Stream)(file);
return File(stream, contentType, fileName);
}
when i click save button, in save as window i want filename with extension.but it shows only filename for me.
and also in textfile the header name should be filename.txt but it it shows Filename[1] for my code.
can anyone please give some idea to show Filename with extn in header and save as window.
Updated code
public FileResult FileOutput()
{
string filename = "alokdida.txt";
string filepath = "C:\\logs\\Structured_Exception_Log.txt";
return File(filepath, "application/octet-stream", filename);
}
This should work for you.
2nd time edit (see changed code in bold font)
public FileResult Download(string id)
{
int rowId = Convert.ToInt32(id);
LoadFileInfoCache();
var fileDetails = from ff in _currentFileDetails
where ff.FileId == rowId
select new
{
name = ff.FileName,
location = ff.FileLocation
};
var fileDetailsList = fileDetails.ToList();
string fileLocation = fileDetailsList[0].location;
string fileName = fileDetailsList[0].name+".txt"; // Here you need to append the .txt
string contentType = "application/txt";
var file = System.IO.File.Open(fileLocation, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
var stream = (Stream)(file);
return File(stream, contentType, fileName);
}

Resources