title: xamarin forms Android How to add Metadata to an image being copied to a Public Directory
body: <p>In our Xamarin Forms app, I have to</p>
  <ol>
  <li>take a picture and save it locally.</li>
  <li>add a variety of metadata to it.</li>
  <li>make a copy of the picture, complete with all metadata, available on a globally accessible location so that it can be easily added to an email or shared some other way.</li>
  </ol>
  <ol>
  <li><p>is easy and can be accomplished for Android, iOS and UWP using
  Xamarin Forms.</p>
  </li>
  <li><p>can be done on each platform using a DependencyService. For <strong>Android</strong> I access the EXIF values of an image by using:</p>
  <p>ExifInterface newExif = new ExifInterface(filePath);</p>
  </li>
  </ol>
  <p>Then I set all the EXIF values that I need to and save them back to the image.</p>
  <ol start="3">
  <li>Using another DependencyService I can write out a copy of the image to, say, Pictures.</li>
  </ol>
  <p><strong>What I can't figure out is how to access the resulting image to add the EXIF data.</strong></p>
  <p>This is what I've got:</p>
  <pre><code>public void SaveFileToPublicDirectory(string internalPath, string name)
  {
      string path = &quot;&quot;;
      try 
      {                
          // decode a bitmap from a local file path.
          Bitmap bitmap = BitmapFactory.DecodeFile(internalPath);
          System.IO.Stream fos;
  
          // today I am concentrating on BuildVersionCodes.Q and later
          if (Build.VERSION.SdkInt &gt;= BuildVersionCodes.Q)
          {
              ContentValues contentValues = new ContentValues();
              contentValues.Put(MediaStore.IMediaColumns.DisplayName, name);
              contentValues.Put(MediaStore.IMediaColumns.MimeType, &quot;image/jpg&quot;);
              contentValues.Put(MediaStore.IMediaColumns.RelativePath,
                  Android.OS.Environment.DirectoryPictures);
  
              var imageUri = Android.App.Application.Context.ContentResolver.
                  Insert(MediaStore.Images.Media.ExternalContentUri, contentValues);
              fos = Android.App.Application.Context.ContentResolver.OpenOutputStream(imageUri);
              bitmap.Compress(Bitmap.CompressFormat.Jpeg, 100, fos);
  
              path = imageUri.ToString(); // + &quot;/&quot; + name;
              Log.Debug(&quot;i-Trax Droid&quot;, &quot;Path for saving file in Pictures = &quot; + path);
              // path looks something like : content:/media/external/images/media/594
          }
          else
          {
              String imagesDir = Android.OS.Environment.GetExternalStoragePublicDirectory(
                  Android.OS.Environment.DirectoryPictures).ToString();
              path = System.IO.Path.Combine(imagesDir, name);
              fos = new FileStream(path, FileMode.Create);
              bitmap.Compress(Bitmap.CompressFormat.Jpeg, 100, fos);
              Util.PathFilenameForPicturesDir_Android = path;
          }
      }
      catch (Exception ex)
      {
          string msg = string.Format(&quot;** Exception in SaveFileToPublicDirectory: {0} &quot;, ex.ToString());
          System.Diagnostics.Debug.WriteLine(msg);
          Util.WriteExceptionToSQL(msg);
      }
  
      return;
  }
  </code></pre>
  <p>What I am expecting to be able to do is get the ExifInterface from the recently written out file, <strong>but how do I read in EXIF data from</strong></p>
  <pre><code>content:/media/external/images/media/594
  </code></pre>
  <p>And then I am hoping to be able make the required changes to the EXIF and save it back.</p>