GithubHelp home page GithubHelp logo

Comments (11)

yasirkula avatar yasirkula commented on August 11, 2024 1

For security reasons, Android team decided to prevent full file system access using raw file paths on Android 10 and later. You can google "android 10 scoped storage" to learn more about this change.

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

Working on Android 11 btw

from unitysimplefilebrowser.

yasirkula avatar yasirkula commented on August 11, 2024

That path comes from Storage Access Framework which is the native framework that is used on Android 11+ (because there is no alternative). While working with paths returned by file browser, you need to use FileBrowserHelpers functions which also support Storage Access Framework. Just be sure to pass only the paths returned by FileBrowser to FileBrowserHelpers (except for CopyFile/MoveFile functions that also accept raw file paths so that a file can be copied from/to persistentDataPath or temporaryCachePath).

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

I am using your testclass from the git page. When I try to add this line in the coroutine to get the path with the helper:

Debug.Log("Filepath in FileBrowser with Helper: " + FileBrowserHelpers.GetDirectoryName(FileBrowser.Result[0]));

I get the same result for the path.

from unitysimplefilebrowser.

yasirkula avatar yasirkula commented on August 11, 2024

Example code doesn't do anything special in particular. Can I see your code and we continue from there?

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

Sure:

using UnityEngine;
using System.Collections;
using System.IO;
using SimpleFileBrowser;
using System.Collections.Generic;
using UnityEngine.UI;
using TMPro;
using UnityEngine.Events;
using System;

public class FileBrowserTest : MonoBehaviour
{
	// Warning: paths returned by FileBrowser dialogs do not contain a trailing '\' character
	// Warning: FileBrowser can only show 1 dialog at a time

	[Serializable]
	public class FilePathEvent : UnityEvent<string> { };

	public MenuManager mm;
	public InputField InputField;
	public Button btn;
	public Button delete;	
	[SerializeField] public FilePathEvent OnFilepathChanged = new FilePathEvent();
	[HideInInspector]
	public string absoluteFilePath;

    protected virtual void Start()
    {
		GameObject MenuSystem = GameObject.FindGameObjectWithTag("MenuManager");
		mm = MenuSystem.GetComponent<MenuManager>();

		btn.onClick.AddListener(openBrowserMenu);
    }

    public void openBrowserMenu()
	{
		// Set filters (optional)
		// It is sufficient to set the filters just once (instead of each time before showing the file browser dialog), 
		// if all the dialogs will be using the same filters
		FileBrowser.SetFilters(true, new FileBrowser.Filter("Bilder", ".jpg", ".png"), new FileBrowser.Filter("PDF Dateien", ".pdf"));

		// Set default filter that is selected when the dialog is shown (optional)
		// Returns true if the default filter is set successfully
		// In this case, set Images filter as the default filter
		FileBrowser.SetDefaultFilter(".jpg");

		// Set excluded file extensions (optional) (by default, .lnk and .tmp extensions are excluded)
		// Note that when you use this function, .lnk and .tmp extensions will no longer be
		// excluded unless you explicitly add them as parameters to the function
		FileBrowser.SetExcludedExtensions(".lnk", ".tmp", ".zip", ".rar", ".exe");

		// Add a new quick link to the browser (optional) (returns true if quick link is added successfully)
		// It is sufficient to add a quick link just once
		// Name: Users
		// Path: C:\Users
		// Icon: default (folder icon)
		//FileBrowser.AddQuickLink("Dokumente", "content://com.android.externalstorage.documents", null);		

		// Show a select folder dialog 
		// onSuccess event: print the selected folder's path
		// onCancel event: print "Canceled"
		// Load file/folder: folder, Allow multiple selection: false
		// Initial path: default (Documents), Initial filename: empty
		// Title: "Select Folder", Submit button text: "Select"

		StartCoroutine(ShowLoadDialogCoroutine());

	}

	IEnumerator ShowLoadDialogCoroutine() {
		yield return FileBrowser.WaitForLoadDialog(FileBrowser.PickMode.Files, false, null, null, "Wähle eine Datei", "Auswählen");

		if (FileBrowser.Success)
		{
			// Applies only Filename to UI Textfield to hide unix pathname
			// FileBrowser.Result[0] // Complete Path to selected file
			// Please do not change order otherwise shopFileBrowser will not work anymore!
			absoluteFilePath = FileBrowser.Result[0];

			Debug.Log("Filepath in FileBrowser with Helper: " + FileBrowserHelpers.GetDirectoryName(FileBrowser.Result[0]));
			Debug.Log("Filename in FileBrowser with Helper: " + FileBrowserHelpers.GetFilename(FileBrowser.Result[0]));

			absoluteFilePath = FileBrowserHelpers.GetDirectoryName(absoluteFilePath) + "\\" + FileBrowserHelpers.GetFilename(absoluteFilePath);

			Debug.Log("Filepath in FileBrowser: " + absoluteFilePath);
			InputField.text = FileBrowserHelpers.GetFilename(FileBrowser.Result[0]);

			OnFilepathChanged.Invoke(absoluteFilePath);
			mm.CreatedNewForm = false;
		}
		else
		{
			Debug.Log("Failed to load file!");
		}

	}

}

from unitysimplefilebrowser.

yasirkula avatar yasirkula commented on August 11, 2024

You can't modify Storage Access Framework (SAF) paths, it just won't work. So, the line absoluteFilePath = blabla + "\\" + blabla; isn't something you can do in the SAF world. You MUST pass the returned path AS IS to FileBrowserHelpers functions. If you are trying to get a readable path from SAF path, you can't. SAF is a native abstraction layer that doesn't allow such things. While working with SAF, you really need to forget all about how you could modify raw file paths, these don't apply to SAF.

The following code, however, is valid because it uses FileBrowserHelpers functions and doesn't attempt to modify the original path with + "\\" + (FYI, paths returned by FileBrowserHelpers are also SAF paths so you can't modify them with + "\\" + either):

// This code works on all platforms because it uses FileBrowserHelpers

// On Android 11+, returned path will be a SAF path
string returnedPath = FileBrowser.Result[0];

// Get the path of the selected file's parent directory (returned path will be a SAF path)
string parentDirectory = FileBrowserHelpers.GetDirectoryName(returnedPath);

// Create another file inside this folder (returned path will, again, be a SAF path)
string anotherFile = FileBrowserHelpers.CreateFileInDirectory(parentDirectory, "SomeFile.txt");

// Write some text to that file
FileBrowserHelpers.WriteTextToFile(anotherFile, "Hello world");

In summary, this code creates a second file in the selected file's directory and fills it with text "Hello world". As you can see, you can achieve almost anything by using FileBrowserHelpers function without modifying the returned paths with + "\\" +.

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

But Path.combine would work to get the full path including filename?
I dont need to create a file. I need to pass the whole path for firebase to upload.
I wonder why it was working before. Maybe there has been an Android update? I was using Android 11 before I think.

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

Alright, if I use this:

absoluteFilePath = FileBrowser.Result[0]; string parentDirectory = FileBrowserHelpers.GetDirectoryName(absoluteFilePath); string filename = FileBrowserHelpers.GetFilename(absoluteFilePath); Debug.Log("SAF Path" + parentDirectory); Debug.Log("SAF Filename" + filename);

It gets me this:

AndroidPlayer([email protected]:34999) SAF 
Pathcontent://com.android.externalstorage.documents/tree/primary%3ADCIM/document/primary%3ADCIM%2FScreenshots
AndroidPlayer([email protected]:34999) SAF FilenameScreenshot_20210505-152535_Brave.jpg

from unitysimplefilebrowser.

yasirkula avatar yasirkula commented on August 11, 2024

Path.Combine also wouldn't work with SAF paths. You must use FileBrowserHelpers. FileBrowserHelpers.CreateFileInDirectory is the closest thing to Path.Combine in SAF world, there is also FileBrowserHelpers.CreateFolderInDirectory.

In your case, you want to upload the file to some server but the service you are using only accepts raw file paths. The only solution to this problem is to copy the selected file to temporaryCachePath and upload it from there:

if( !File.Exists( filePath ) ) // This will return true on non-SAF platforms. No need to copy the file to temporaryCachePath since 'filePath' is already a raw file path
{
	string tempFilePath = Path.Combine( Application.temporaryCachePath, FileBrowserHelpers.GetFilename( filePath ) );
	FileBrowserHelpers.CopyFile( filePath, tempFilePath );
	filePath = tempFilePath;
}

// Upload file at filePath to Firebase here
...

from unitysimplefilebrowser.

designtology avatar designtology commented on August 11, 2024

Thank you.

Firebase now throws an error because there is no "file://" or similar so it cant find it.
But by putting it infront as a string works for now. I wonder why it doesnt return a full path.
You got any easy explained docs for SAF by any chance?

Thanks for now

from unitysimplefilebrowser.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.