locked
How to share a captured image and add predefined text in a email compose task

    Question

  • Hey I am capturing a photo using the webcam how do I share that Image windows store app here is the code for the capturing image and sharing it. Problem is I cant share it without importing it. Moreover the other problem is I use the share status task but for Email I want the body to be predefined it is not how should I do that?

    CameraCaptureUI camera = new CameraCaptureUI();
                camera.PhotoSettings.CroppedAspectRatio = new Size(16, 9);
                StorageFile photo = await camera.CaptureFileAsync(CameraCaptureUIMode.Photo);
    
                //By default the photo will be stored at location
                //%localappdata%\Packages\APP_PACKAGE_ID\TempState
    
                if (photo != null)
                {
                    //await photo.MoveAsync(KnownFolders.PicturesLibrary);
                    //OR
                    await photo.MoveAsync(KnownFolders.PicturesLibrary, "resolvepic" + photo.FileType, NameCollisionOption.GenerateUniqueName);
                    BitmapImage bmp = new BitmapImage();
                    IRandomAccessStream stream = await photo.OpenAsync(FileAccessMode.Read);
                    bmp.SetSource(stream);
                    CapturedPhoto.Source = bmp;
    private void ShareTextHandler(DataTransferManager sender, DataRequestedEventArgs e)
            {
    
                if (this.imageFile != null)
                {
                    DataRequest requestData = e.Request;
                    requestData.Data.Properties.Title = "Please fix this problem as soon as possible";
                    requestData.Data.Properties.Description = TextInput.Text;
                    
                    List<IStorageItem> imageItems = new List<IStorageItem>();
                    imageItems.Add(this.imageFile);
                    requestData.Data.SetStorageItems(imageItems);
                    RandomAccessStreamReference imageStreamRef = RandomAccessStreamReference.CreateFromFile(this.imageFile);
                    requestData.Data.Properties.Thumbnail = imageStreamRef;
                    requestData.Data.SetBitmap(imageStreamRef);
                }
            }



    pratik

    Thursday, April 17, 2014 4:57 PM

Answers

  • Was busy all this week with work so could not look at it :(

    Anyway, there are few basic mistakes here

    (a) you did not register handler for sharing

    (b) In handler you did not have set text and/or HTML on Data

    (c) There was no need to save the stream you get from Camera Capture, use the same for sharing

    Here is updated code:

    using System; using System.Linq; using Windows.ApplicationModel.DataTransfer; using Windows.Foundation; using Windows.Media.Capture; using Windows.Storage; using Windows.Storage.Pickers; using Windows.Storage.Streams; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows.UI.Xaml.Media.Imaging; using Windows.UI.Xaml.Navigation; // The Blank Page item template is documented at http://go.microsoft.com/fwlink/?LinkId=234238 namespace Sample { /// <summary> /// An empty page that can be used on its own or navigated to within a Frame. /// </summary> public sealed partial class MainPage : Page { IRandomAccessStream stream; public MainPage() { this.InitializeComponent(); } protected override void OnNavigatedTo(NavigationEventArgs e) { base.OnNavigatedTo(e); //This was not there! DataTransferManager.GetForCurrentView().DataRequested += ShareTextHandler; } protected override void OnNavigatedFrom(NavigationEventArgs e) { base.OnNavigatedFrom(e); //This was not there! DataTransferManager.GetForCurrentView().DataRequested -= ShareTextHandler; } private StorageFile imageFile; private async void Capture_Click(object sender, RoutedEventArgs e) { CameraCaptureUI camera = new CameraCaptureUI(); camera.PhotoSettings.CroppedAspectRatio = new Size(16, 9); StorageFile photo = await camera.CaptureFileAsync(CameraCaptureUIMode.Photo); if (photo != null) { BitmapImage bmp = new BitmapImage(); stream = await photo.OpenAsync(FileAccessMode.Read); bmp.SetSource(stream); CapturedPhoto.Source = bmp; } } private void Import_Click(object sender, RoutedEventArgs e) { //Not needed, so removed all code } private void Share_Click(object sender, RoutedEventArgs e) { DataTransferManager.ShowShareUI(); } private void ShareTextHandler(DataTransferManager sender, DataRequestedEventArgs e) { if (this.stream != null) { DataRequest requestData = e.Request; requestData.Data.Properties.Title = "Please fix this problem as soon as possible"; requestData.Data.Properties.Description = TextInput.Text;

    //Changed to use same stream RandomAccessStreamReference imageStreamRef = RandomAccessStreamReference.CreateFromStream(stream); requestData.Data.Properties.Thumbnail = imageStreamRef; requestData.Data.SetBitmap(imageStreamRef);

    //Missing requestData.Data.SetHtmlFormat(String.Format("<HTML><B><font color='red'>{0}</font></B><BR>This is a test <a href='http://www.bing.com'>link</a></HTML>", TextInput.Text));                 //Missing requestData.Data.SetText(TextInput.Text); } } } }



    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!

    • Marked as answer by Pratik99 Sunday, April 27, 2014 9:20 AM
    Friday, April 25, 2014 7:40 PM

All replies

  • Pratik,

    There is no email compose task, what you are doing is implementing Share in your app  (which is one out of two parts of Share Contract i.e. Share Source) and setting whatever data on DataRequest. Once you initiate Share from your app it tells OS that you are trying to share something and based of properties that you have set in DataRequest (like Text, HTML, Image etc.) OS looks at installed apps that support that type of data as a Share Target (second part of Share Contract) and lists them on screen for user to select. In your case I think you are selecting Mail App. Actually a user is free to select any app and you as App owner of your App have no control on it. Now whatever user has selected is free to respect (use) all fields that you have set or may ignore some or all of them (although ignoring all is not good). How mail will show it while it opens in Share window is beyond your control as that is something Mail App will decide. As of now Mail App uses that bitmap as attachment to email not in body. You should not rely on this behavior as this is something Mail App owner can change any time.

    Outside of this I do not see any obvious mistake in your code that should cause issue, if you think you get some error then please post some working sample that I can use to help fix it.


    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!


    Thursday, April 17, 2014 6:53 PM
  • Hey Vishal,

    Thanks for the reply. See the code above I have given is capturing the image and showing it in the bitmap like the imageview but then I cant share it. If I want to share it I will have to import the image then only I am able to share. I want the user to be able to share the image once he clicks it on the webcam and not import it again. Coming to the email task I am able to predefine the subject but yes I am not able to predefine the body of the email but again is there any way I can do that because I really need it in my app.


    pratik


    • Edited by Pratik99 Friday, April 18, 2014 2:56 AM
    Friday, April 18, 2014 2:56 AM
  • Hi Pratik, I am sorry but I do not clearly understand your issue of importing image. Can you post some working project so that it is really easy for me to run it and suggest modifications? else this will take me a lot of time to prepare your scenario.

    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!

    Friday, April 18, 2014 12:39 PM
  • Sure I will do it please give me some time what about the email thing?

    pratik

    Friday, April 18, 2014 12:43 PM
  • Here is the sample app you can have a look please do get back to me after having a look

    http://1drv.ms/QmgJx3

    Thanks!


    pratik

    Saturday, April 19, 2014 8:13 AM
  • Hi Pratik, There were three projects at the link you have given. I presume on with the name Sample is what you mean I need to take. In that you have .shproj and a Windows Phone project. Either I open your project in  VS 2012 Ultimate or VS 2013 Ultimate, in both it runs upgrade wizard and then is unable to load your Windows Phone and Shared project. For this reason it is not able to compile. Can you post a working sample for either versions with proper prerequisites?

    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!

    Sunday, April 20, 2014 9:31 AM
  • Sure will do that will give you the link as soon as I compile it again.

    pratik

    Sunday, April 20, 2014 9:57 AM
  • Here you go the solution for Windows 8.1

    https://drive.google.com/file/d/0BzMqOFURHQfCcEFoR3Q3NjN1VjQ/edit?usp=sharing


    pratik

    Sunday, April 20, 2014 5:34 PM
  • Hey any updates?


    pratik

    Wednesday, April 23, 2014 2:08 PM
  • Was busy all this week with work so could not look at it :(

    Anyway, there are few basic mistakes here

    (a) you did not register handler for sharing

    (b) In handler you did not have set text and/or HTML on Data

    (c) There was no need to save the stream you get from Camera Capture, use the same for sharing

    Here is updated code:

    using System; using System.Linq; using Windows.ApplicationModel.DataTransfer; using Windows.Foundation; using Windows.Media.Capture; using Windows.Storage; using Windows.Storage.Pickers; using Windows.Storage.Streams; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows.UI.Xaml.Media.Imaging; using Windows.UI.Xaml.Navigation; // The Blank Page item template is documented at http://go.microsoft.com/fwlink/?LinkId=234238 namespace Sample { /// <summary> /// An empty page that can be used on its own or navigated to within a Frame. /// </summary> public sealed partial class MainPage : Page { IRandomAccessStream stream; public MainPage() { this.InitializeComponent(); } protected override void OnNavigatedTo(NavigationEventArgs e) { base.OnNavigatedTo(e); //This was not there! DataTransferManager.GetForCurrentView().DataRequested += ShareTextHandler; } protected override void OnNavigatedFrom(NavigationEventArgs e) { base.OnNavigatedFrom(e); //This was not there! DataTransferManager.GetForCurrentView().DataRequested -= ShareTextHandler; } private StorageFile imageFile; private async void Capture_Click(object sender, RoutedEventArgs e) { CameraCaptureUI camera = new CameraCaptureUI(); camera.PhotoSettings.CroppedAspectRatio = new Size(16, 9); StorageFile photo = await camera.CaptureFileAsync(CameraCaptureUIMode.Photo); if (photo != null) { BitmapImage bmp = new BitmapImage(); stream = await photo.OpenAsync(FileAccessMode.Read); bmp.SetSource(stream); CapturedPhoto.Source = bmp; } } private void Import_Click(object sender, RoutedEventArgs e) { //Not needed, so removed all code } private void Share_Click(object sender, RoutedEventArgs e) { DataTransferManager.ShowShareUI(); } private void ShareTextHandler(DataTransferManager sender, DataRequestedEventArgs e) { if (this.stream != null) { DataRequest requestData = e.Request; requestData.Data.Properties.Title = "Please fix this problem as soon as possible"; requestData.Data.Properties.Description = TextInput.Text;

    //Changed to use same stream RandomAccessStreamReference imageStreamRef = RandomAccessStreamReference.CreateFromStream(stream); requestData.Data.Properties.Thumbnail = imageStreamRef; requestData.Data.SetBitmap(imageStreamRef);

    //Missing requestData.Data.SetHtmlFormat(String.Format("<HTML><B><font color='red'>{0}</font></B><BR>This is a test <a href='http://www.bing.com'>link</a></HTML>", TextInput.Text));                 //Missing requestData.Data.SetText(TextInput.Text); } } } }



    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!

    • Marked as answer by Pratik99 Sunday, April 27, 2014 9:20 AM
    Friday, April 25, 2014 7:40 PM
  • Sir Thank you so much :D one more thing sir how do I pre define multiple recipients of the email? is there any way I can?

    pratik


    • Edited by Pratik99 Sunday, April 27, 2014 10:11 AM
    Sunday, April 27, 2014 9:34 AM
  • Sir I want import to also work as some people may want to import pictures instead of taking it.

    pratik

    Sunday, April 27, 2014 10:57 AM
  • With share contract you will not be able to specify email address of recipients.

    You already had Import logic so that should be good for you.


    -- Vishal Kaushik --

    Please 'Mark as Answer' if my post answers your question and 'Vote as Helpful' if it helps you. Happy Coding!!!

    Monday, April 28, 2014 9:16 AM
  • Sir my import logic is not working when I use your code with my share logic it dosent work

    pratik


    • Edited by Pratik99 Monday, April 28, 2014 9:24 AM
    Monday, April 28, 2014 9:24 AM