Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

Native Gallery for Android & iOS [Open Source]

Discussion in 'Assets and Asset Store' started by yasirkula, Feb 28, 2018.

  1. NatsupyYui

    NatsupyYui

    Joined:
    Jul 11, 2017
    Posts:
    18
    yah I mean loading, I just need to get path audios in the device, not saving, if u have options filter files(ex: *.txt, *.blabla) will be great, but this's still great
     
  2. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    The reason NativeGallery only works with images and videos is that audio files and/or other files can not be browsed in Gallery, they can only be accessed via a file manager app or music player. Supporting them would require me to create a custom UI.

    On Android, you can give this plugin a shot for custom files: https://github.com/yasirkula/UnitySimpleFileBrowser
     
  3. LuisBL

    LuisBL

    Joined:
    May 31, 2018
    Posts:
    4
    Hi, I found your asset today, and i've got to say thanks for this, it's really good!

    Also, I was wondering if you could post an example of how to use the *NativeGallery.GetImagesFromGallery* function, I tried to use it with the following code and it didn't work, I don't know where i'm wrong, thanks!

    Code:

    public void PickImages(int maxSize = 1080)
    {
    NativeGallery.GetImagesFromGallery((path) =>
    {
    if (path != null)
    {
    foreach (string imagePath in path)
    {
    // Create Texture from selected image
    Texture2D texture = NativeGallery.LoadImageAtPath(imagePath, maxSize);
    if (texture == null)
    {
    Debug.Log("Couldn't load texture from " + path);
    return;
    }
    GameObject newImage = Instantiate(imagePrefab, containerRect.transform);
    newImage.GetComponent<RawImage>().texture = texture;
    float aspectRatio = 1.5f;
    if (texture.width > texture.height)
    {
    aspectRatio = texture.width / texture.height;
    }
    else
    {
    aspectRatio = texture.height / texture.width;
    }
    newImage.GetComponent<AspectRatioFitter>().aspectRatio = aspectRatio;
    newImage.GetComponent<AspectRatioFitter>().aspectMode = AspectRatioFitter.AspectMode.HeightControlsWidth;
    LayoutRebuilder.ForceRebuildLayoutImmediate(containerRect.GetComponent<RectTransform>());
    }
    }
    }, maxSize: maxSize);
    }// End of SelectImages
     
  4. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Your code looks correct. Are you sure that
    NativeGallery.CanSelectMultipleFilesFromGallery()
    returns true? This feature is only supported on Android 18 and later, iOS not supported. If that function returns true, please check Logcat for any error messages.
     
  5. LuisBL

    LuisBL

    Joined:
    May 31, 2018
    Posts:
    4
    Wait, now it works just fine, I must have written something else yesterday, sorry for that!
     
    yasirkula likes this.
  6. LuisBL

    LuisBL

    Joined:
    May 31, 2018
    Posts:
    4
    Another question, I was just testing the function that saves a video to the gallery(Android), and I don't know where I'm wrong, could you help me? The code I'm using is:

    Code (CSharp):
    1. private IEnumerator SaveVideo()
    2.     {
    3.         yield return new WaitForEndOfFrame();
    4.      
    5.         Debug.Log("Premission result: " + NativeGallery.SaveVideoToGallery( Application.streamingAssetsPath + "/Dewey.mp4" , "CustomVideos", "Video {0}.mp4"));
    6.      
    7.     }// End of SaveVideo
     
  7. edsalazar

    edsalazar

    Joined:
    Jun 23, 2018
    Posts:
    1
    Hi. First of all, thank you for your great asset.

    I have a method that is fired when I press a button in the UI for loading an Image from gallery. I noticed that when I want to change to another image and I pick it quickly, I have a delay in the replacement of the texture. To avoid this, I tried to set a "Loading" text and hide the Image just when I press the button, but seems is not working because I'm still having the same behavior. Here is the code:

    Code (CSharp):
    1.  
    2.  
    3.     public Image image;
    4.     public GameObject loadingText;
    5.  
    6.     public void PickImage(int maxSize)
    7.     {
    8.  
    9.         loadingText.SetActive(true);
    10.         image.gameObject.SetActive(false);
    11.        
    12.         NativeGallery.Permission permission = NativeGallery.GetImageFromGallery((path) =>
    13.         {
    14.             if (path != null)
    15.             {
    16.                 Texture2D texture = NativeGallery.LoadImageAtPath(path, maxSize);
    17.                 if (texture == null)
    18.                 {
    19.                     Debug.Log("Couldn't load texture from " + path);
    20.                     return;
    21.                 }
    22.  
    23.                 loadingText.SetActive(false);
    24.                 image.gameObject.SetActive(true);
    25.  
    26.                 Sprite sprite = Sprite.Create(texture, new Rect(0.0f, 0.0f, texture.width, texture.height), new Vector2(0.5f, 0.5f));
    27.                 image.sprite = sprite;
    28.  
    29.             }
    30.         }, "Select an image", "image/*", maxSize);
    31.     }
    I'm wondering if this delay is normal when I pick the image quickly after pressing the button (around 3 seconds) or it's there any way to set my "loading" text while the new texture is loaded.

    Thank you in advance!
     
  8. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    @LuisBL On Android, files inside Application.streamingAssetsPath can only be accessed via WWW (or UnityWebRequest, I guess). Try this one:

    Code (CSharp):
    1. private IEnumerator SaveVideo()
    2. {
    3.     WWW fileAccess = new WWW( System.IO.Path.Combine( Application.streamingAssetsPath, "Dewey.mp4" ) );
    4.     yield return fileAccess;
    5.  
    6.     Debug.Log("Premission result: " + NativeGallery.SaveVideoToGallery( fileAccess.bytes, "CustomVideos", "Video {0}.mp4"));
    7. }// End of SaveVideo
    @edsalazar I didn't notice it myself but I wasn't really paying attention to timing. To show your loading text, you can put your code inside a coroutine and insert a "yield return null;" statement after the
    image.gameObject.SetActive(false);
    line (add two yield statements, if one doesn't work).
     
    edsalazar likes this.
  9. LuisBL

    LuisBL

    Joined:
    May 31, 2018
    Posts:
    4
    Wow, I didn't knew that(still learning a lot of things), It works like you said, Thank you so much!
     
  10. drordoit

    drordoit

    Joined:
    Sep 7, 2013
    Posts:
    36
    Hi , I'm trying to share a screenshot with no success , what am I doing wrong ?
    Code (CSharp):
    1.  ScreenCapture.CaptureScreenshot("ScreenShotTest");
    2.         shareFromShareBtn.AddFile(Application.persistentDataPath + "/ScreenShotTest.png");
    3.         shareFromShareBtn.Share();
     
  11. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    CaptureScreenshot function does not create the screenshot file immediately, i.e. ScreenShotTest.png does not exist at the moment you call AddFile. Try the example code, which does the same thing but should work properly in this case.

    P.S. FYI, NativeShare has its own dedicated forum topic, as well :D
     
  12. drordoit

    drordoit

    Joined:
    Sep 7, 2013
    Posts:
    36
    AAA... I'm in the wrong forum ! Sorry , was browsing throw you plugins. Any way, the example works perfectly , Thanks.
     
    yasirkula likes this.
  13. NatsupyYui

    NatsupyYui

    Joined:
    Jul 11, 2017
    Posts:
    18
  14. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Does audio selection really work on some devices? Which app does the system allow you to pick an audio with? Maybe that app is not available on all devices. In any case, I think it is just lucky that some devices can pick audio with NativeGallery, as there is no audio-related code in NativeGallery.

    For consistent results across all devices, you really should use a plugin that is dedicated to picking audios, or use the SimpleFileBrowser plugin to let the user select the audio files with a file browser.
     
  15. NatsupyYui

    NatsupyYui

    Joined:
    Jul 11, 2017
    Posts:
    18
    Actually, pick audio files working on my phone, lol, just don't test another device yet
    I added this function bc I have seen in jar class have if else "audio"
    Code (CSharp):
    1. public static Permission GetAudioFromGallery(MediaPickCallback callback, string title = "", string mime = "audio/*")
    2.     {
    3.         return GetMediaFromGallery(callback, false, mime, title, -1);
    4.     }
     
  16. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    To possibly support audio files in a more reliable way, you have to insert the following condition here:

    Code (CSharp):
    1. else if( mime.startsWith( "audio/" ) )
    2.     intent = new Intent( Intent.ACTION_PICK, MediaStore.Audio.Media.EXTERNAL_CONTENT_URI );
    I actually did it for you, in case you are not familiar with plugin build process. You can try replacing NativeGallery.jar with the attached file. Note that picking audio files is still not supported on iOS.
     

    Attached Files:

  17. nasos_333

    nasos_333

    Joined:
    Feb 13, 2013
    Posts:
    13,288
    Hi,

    Thanks for the great tool.

    Is it possible to grab the image from the home page of the phone using the library (like the on button + low volume combo) ? Or have access to the icons positions in the launcher ? e.g. if need to create an app that manages the launcher icons.
     
  18. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    It can only read existing images from Gallery or write new images there. It doesn't have any native screenshot functionality.
     
    nasos_333 likes this.
  19. look001

    look001

    Joined:
    Mar 23, 2017
    Posts:
    111
    Very usefull asset! Would it be possible to implement this file Browser in an android Plugin somehow? I can't find anyone who did it. Before i learn more about building android native plugins i want to ask you why there is no asset that uses storage access framework.
     
  20. nasos_333

    nasos_333

    Joined:
    Feb 13, 2013
    Posts:
    13,288
    Thanks.

    I have found this code that reads directly the frame buffer in C, how hard do you gather would it be to create a plugin that will read this in Unity ?

    https://github.com/oNaiPs/droidVncServer/tree/master/jni/vnc/screenMethods

    This would open great new ways of interaction with the phone
     
  21. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    @look001 Yes it seems doable. You'll probably have to save the selected document to a temporary file via an InputStream. I didn't use this framework because I didn't know about it. But I believe a plugin using this framework could be pretty useful in certain scenarios.

    @nasos_333 I have no experience with C/C++ plugins and have only basic C++ knowledge, that repository is simply too complex for me, sorry :)
     
    nasos_333 likes this.
  22. nasos_333

    nasos_333

    Joined:
    Feb 13, 2013
    Posts:
    13,288
    np :), just asking to see if would be something doable. I will do a try with it, though i am not experienced in this either so i dont know what to expect of it.
     
    yasirkula likes this.
  23. unity_Z7yHIzu8n21eLw

    unity_Z7yHIzu8n21eLw

    Joined:
    May 8, 2018
    Posts:
    1
    Hi, I'm fairly new to Unity and scripting and i'm having trouble setting up a custom name for my videos, and making them show up on my phone's gallery. They save under the data folders but they just don't show up on my gallery. If someone is able to take me through the steps to set up this Asset for this I would greatly appreciate it.
     
  24. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
  25. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    3,296
    Just started using this asset recently, and it's very cool!

    One thing though, for some reason, on some devices gallery isn't updated after saving the video.
    I'm trying to save the video to the gallery like so:
    Code (CSharp):
    1. NativeGallery.SaveVideoToGallery(path, _galleryAlbumName, Path.GetFileName(path), OnGallerySaveCallback)
    I can confirm that video is actually being copied to DCIM/*_galleryAlbumName*/*filename*, but it doesn't appear in the native gallery application. MediaSaveCallback returns no errors.

    This occurs on Android 4.4.2 @ Fly IQ4516 Octa.
    Also, generating screenshots and saving them to the gallery (via .SaveImageToGallery) works fine for this device. It is updated properly.

    On the other two devices that I've tested on, this works just fine. (Android 6.0 & Android 6.0.1)
    Any suggestions on how to make sure that gallery is updated properly?
     
  26. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    3,296
    Don't know if it's related, but I'm getting this warning when I'm pushing video to the gallery:
    Code (CSharp):
    1. 08-02 10:27:09.253: W/SocketClient(163): write error (Broken pipe)
    2. 08-02 10:27:10.904: W/System.err(4177): android.content.pm.PackageManager$NameNotFoundException
    3. 08-02 10:27:10.904: W/System.err(4177):     at android.app.ApplicationPackageManager.getPackageInfo(ApplicationPackageManager.java:84)
    4. 08-02 10:27:10.905: W/System.err(4177):     at com.estrongs.android.pop.app.b.q.c(Unknown Source)
    5. 08-02 10:27:10.905: W/System.err(4177):     at com.estrongs.android.pop.app.b.q.a(Unknown Source)
    6. 08-02 10:27:10.905: W/System.err(4177):     at com.estrongs.android.pop.app.scene.e.h$1.a(Unknown Source)
    7. 08-02 10:27:10.905: W/System.err(4177):     at com.estrongs.android.scanner.c.j$a$1.run(Unknown Source)
    8. 08-02 10:27:10.905: W/System.err(4177):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
    9. 08-02 10:27:10.905: W/System.err(4177):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
    10. 08-02 10:27:10.905: W/System.err(4177):     at java.lang.Thread.run(Thread.java:841)
    11. 08-02 10:27:33.310: W/SocketClient(163): write error (Broken pipe)
    12.  
    Will debug further, might find something else.
     
    Last edited: Aug 2, 2018
  27. rinkusaru

    rinkusaru

    Joined:
    Sep 7, 2017
    Posts:
    14
    Hi Yasir,
    I'm trying to use your plugin and for getting videos an image the prompt will appear is there any workaround where I can get the path of all the file from devices like if I put .mp3 all the .mp3 file present in the device should be return as string list without pop up.
    similarly for other extension like .jpg for image and .mp4 for videos.
     
  28. kartoonist435

    kartoonist435

    Joined:
    Feb 14, 2015
    Posts:
    73
    Your plugin is great! I am wondoering if anyone has had the issue I’m having though. When I save an image from my app to the gallery the size seems wrong. I basically get a bunch of black space around the image and the image is smaller than it should be.
     
  29. unity_m5UmPW9BdXWtsg

    unity_m5UmPW9BdXWtsg

    Joined:
    Aug 9, 2018
    Posts:
    1
    Hi Yasir,

    I'm having a problem on android devices where its giving me a permission denied for picking an image from the gallery while the app settings shows the permission is given. Any clue what is going on here? On iOS it works fine.
    Here is the function that I use : https://hastebin.com/qanolafodo.cs

    When i run it in a clean project it works.. So it should be something with the runtime permissions we are using

    Regards,
    Steven
     
    Last edited: Aug 15, 2018
  30. jkl12zys_unity

    jkl12zys_unity

    Joined:
    Dec 14, 2017
    Posts:
    1
    Hi Yasir,

    Is it possible to show the newest picture on the unity app, and click it to open the gallery.

    and by the way to record store the video is it follow bellow ?

    https://docs.unity3d.com/ScriptReference/XR.WSA.WebCam.VideoCapture.html


    1. private IEnumerator SaveVideo()
    2. {
    3. WWW fileAccess = new WWW( System.IO.Path.Combine( Application.streamingAssetsPath, "Dewey.mp4" ) );
    4. yield return fileAccess;

    5. Debug.Log("Premission result: " + NativeGallery.SaveVideoToGallery( fileAccess.bytes, "CustomVideos", "Video {0}.mp4"));
    6. }//
     
  31. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    @VergilUa That does sound like an annoying issue but I'm not sure why media scanner is not working for some devices. You can see that it is a simple call to the MediaScannerConnection.scanFile function:
    https://github.com/yasirkula/UnityN...dde35cf/JAR Source/NativeGallery.java#L49-L52

    There is an alternative solution described here, but it will require using a FileProvider (which will require some AndroidManifest changes) on newer Android versions and I don't know if it eliminates this issue: https://stackoverflow.com/a/36446985/2373034

    @rinkusaru It is not possible with NativeGallery. Though, you can try using Directory.GetFiles with "*.mp3" searchPattern and "SearchOption.AllDirectories" searchOption.

    @kartoonist435 This is the first time I hear about such an issue. I think the texture you are trying to save is broken somehow. You can assign the texture to an object to see if the issue is indeed related to the texture itself.

    @unity_m5UmPW9BdXWtsg Please try adding READ_EXTERNAL_STORAGE and WRITE_EXTERNAL_STORAGE permissions to Assets/Plugins/Android/AndroidManifest.xml manually.

    @jkl12zys_unity If you are trying to fetch the newest image from the Gallery without displaying the image picker UI, then it is not possible with NativeGallery. BTW, your SaveVideo function seems correct. Is it not working? Are there any error messages in the console/logcat? If you are trying to record videos with VideoCapture, then I can't really help with that because I haven't used VideoCapture myself.
     
  32. spaolo1234

    spaolo1234

    Joined:
    Jun 18, 2018
    Posts:
    5
    Hi Yasir,
    First of all I want to say your plugin is GREAT !
    I'm facing a little bug, after 2 or 3 seconds calling the PickImage( ) the android screen flash 1 time but everything is working perfect. Do you know if there is a way to avoid this ? Thank you.
     
  33. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Hi! I haven't noticed such a flash during my tests. Does it also happen on an emulator and/or another device?
     
  34. spaolo1234

    spaolo1234

    Joined:
    Jun 18, 2018
    Posts:
    5
    Hi, no, only in my android phones, galaxy s8 with android 8 and galaxy s7. Everything on the screen disappear for less than a second. Any idea of what I can check ? Thank you.
     
  35. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    I am not really sure, as I am not familiar with this behaviour. You can check logcat logs but it'll probably be hard to pinpoint relevant log(s).
     
  36. spaolo1234

    spaolo1234

    Joined:
    Jun 18, 2018
    Posts:
    5
    Ok, Thank you so much anyway Yasir !
     
  37. spaolo1234

    spaolo1234

    Joined:
    Jun 18, 2018
    Posts:
    5
    Hi, just for an info. The screen flash seems due to a program freeze...
    Just calling this function, the program freeze for 2 or 3 second, than flash the screen and everything works fine. Maybe android 8 is not fully compatible. Thank you.

    public void PickImage()
    {
    int maxSize = 1024;
    NativeGallery.Permission permission = NativeGallery.GetImageFromGallery( ( path ) =>
    {


    }, "Select a PNG image", "image/png", maxSize );

    Debug.Log( "Permission result: " + permission );
    }
     
  38. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Yes, unfortunately some NativeGallery functions seem to freeze the app for a short time, which may be related to runtime permissions. Still, I am not sure why screen flashes on some high-tech devices during that freeze. But thanks for sharing this issue with me.
     
  39. spaolo1234

    spaolo1234

    Joined:
    Jun 18, 2018
    Posts:
    5
    You're wellcome Yasir !
     
  40. vatsanpb

    vatsanpb

    Joined:
    Oct 28, 2015
    Posts:
    4
    Hi , great asset. I wanted to know if this thing works on android emulators?
     
  41. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Yes, as long as the Gallery works properly on the emulator.
     
  42. vatsanpb

    vatsanpb

    Joined:
    Oct 28, 2015
    Posts:
    4
    That was a quick response :) . I'm currently using Nox. I was able to open the gallery and select a file , but the callback's param string is empty. Is it something that you faced at any point of time?
     
  43. vatsanpb

    vatsanpb

    Joined:
    Oct 28, 2015
    Posts:
    4
    Oh never mind. My bad! I forgot the change the write permission to external. But the asset is amazing. Thank you good sir XD
     
    yasirkula likes this.
  44. TRPK

    TRPK

    Joined:
    Jun 22, 2018
    Posts:
    1
    Hi Yasirkula,

    First of all, good job!

    But I´m strugling to get and save the path the user choose. I want to use the path for loading the image when the user starts the application.

    I hope you can help me.

    private string thePath;

    NativeGallery.GetImageFromGallery((path) =>
    {
    if (path != null)
    {
    thePath = path;
    pickedImage = NativeGallery.LoadImageAtPath(path, maxSize);
    }
    }, maxSize: maxSize);

    When i try debug.log or anything else thePath, nothing happens. Do you know why?

    Best Regards,
     
  45. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
    Hi!

    Firstly, please make sure that Write Permission is set to External (SDCard) in Player Settings. Then, put the Debug.Log function inside
    if (path != null)
    . Also wrap the whole NativeGallery.GetImageFromGallery function inside a Debug.Log function to see the returned permission value. If it is Permission.Denied, then your app doesn't have permission to access the gallery, so it is normal to see nothing happening in this case. Try uninstalling and then reinstalling the app to see if it changes anything.
     
  46. PizzaGuy213

    PizzaGuy213

    Joined:
    Nov 23, 2010
    Posts:
    305
    Hi,

    Great asset, from installing it to getting it to work was literally 5 minutes for me, great stuff, absolutely perfect!

    One question, and I know this is not something implemented, but what would be the correct way to open a file with the device's native gallery after saving it to the correct gallery folder? Is there an easy way to cover both iOS & Android?

    Thanks in advance!
     
  47. bosiapps

    bosiapps

    Joined:
    Aug 27, 2018
    Posts:
    1
    Hi, first thing first thank you very much for this great asset!
    I only have one question: when I pick an image or video from gallery after I select it and return to the application the UI freeze for some seconds and the screen flash once before finally display the chosen image and this happen on Android on all the three devices I tried. Is it normal or I'm doing something wrong?
     
  48. unity_yUAfSYVSfFt1sA

    unity_yUAfSYVSfFt1sA

    Joined:
    Aug 31, 2018
    Posts:
    5
    Hi there,

    Can I save the image to sdCard? I tried your plugin file browser and change location to store image, saving in the internal drive is ok, but when trying to save on the sdCard, it was denied, can you help, what was I mistaken?

    Code (CSharp):
    1. UnauthorizedAccessException: Access to the path "/storage/84FE-1AE1/Images/Capture.png" is denied.
    2. System.IO.FileStream..ctor (System.String path, FileMode mode, FileAccess access, FileShare share, Int32 bufferSize, Boolean anonymous, FileOptions options) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System.IO/FileStream.cs:354)
     
  49. yasirkula

    yasirkula

    Joined:
    Aug 1, 2011
    Posts:
    2,865
  50. unity_yUAfSYVSfFt1sA

    unity_yUAfSYVSfFt1sA

    Joined:
    Aug 31, 2018
    Posts:
    5