In my game, you can take screenshots of the world, which are saved in Application.persistentDataPath. I want to make a gallery where you can then see all these screenshots. Because you need to write to the file, I can't use Resources folder or Application.streamingAssetsPath. I could read the files one sprite at a time, using the name, but that's not really practical. So how could I load all files and add them to an array or list? I basically need the equivalent of Resources.LoadAll(). Does anyone know how to achieve this?
You can use Directory.GetFiles(string,string) to return all filepaths in the persistentData folder e.g. by file extension ("*.jpg")
Then you can use e.g. UnityWebRequestTexture.GetTexture also on local file paths and load assets from the persistent data path like
public Dictionary<string, Texture2D> textures = new Dictionary<string, Texture2D>();
private void Start()
{
var fileNames = Directory.GetFiles(Application.persistentDataPath, "*.jpg");
foreach(var fileName in fileNames)
{
StartCoroutine (LoadFile(fileName));
}
}
private IEnumerator LoadFile(string filePath)
{
using (UnityWebRequest uwr = UnityWebRequestTexture.GetTexture(filePath))
{
yield return uwr.SendWebRequest();
if (uwr.isNetworkError || uwr.isHttpError)
{
Debug.Log(uwr.error);
}
else
{
// Get downloaded asset bundle
var texture = DownloadHandlerTexture.GetContent(uwr);
// Something with the texture e.g.
// store it to later access it by fileName
var fileName = Path.GetFileName(filePath);
textures[fileName] = texture;
}
}
}
Related
I need to know how to check for the endings of all the files in the Assets folder.
Its for creating a list of saved files.
public static void Load()
{
if (File.Exists(Application.dataPath + "/data1.sav"))
{
BinaryFormatter bf = new BinaryFormatter();
FileStream file = File.Open(Application.dataPath + "/data1.sav", FileMode.Open);
SaveLoad.savedData = (List<saveData>)bf.Deserialize(file);
file.Close();
}
}
^this load function works fine.
Now i need something like this:
(pseudocode)
if (File.Exists(With the ending: ".sav") ????
{
Create a list of all those files in a String Array!
}
so if i would have in the Assets folder:
"data1.sav"
"data2.sav"
"test.sav" it should return a String Array with the
size of 3 and which include ["data1.sav"], ["data2.sav"] and ["test.sav"]
Just use GetFiles()
Code would be something like:
string[] files = Directory.GetFiles(DirectoryPath, "*.sav");
I need to download an image with GS and save it in a specific drive folder.
I'm able to save the image in the root folder but i cannot save it in a specific folder:
function downloadFile(fileURL,folder) {
var fileName = "";
var fileSize = 0;
var response = UrlFetchApp.fetch(fileURL, {muteHttpExceptions: true});
var rc = response.getResponseCode();
if (rc == 200) {
var fileBlob = response.getBlob()
var folder = DriveApp.getFoldersByName(folder);
if (folder != null) {
var file = DriveApp.createFile(fileBlob);
fileName = file.getName();
fileSize = file.getSize();
}
}
var fileInfo = { "rc":rc, "fileName":fileName, "fileSize":fileSize };
return fileInfo;
}
Question: what have I to add to use the variable "folder"?
I found a lot of examples with "DocList" Class that is not in use anymore
Many thanks
Well, I guess GAS has make a lot of progress on developing its API, the function
createFile(blob) of an object Folder will do the job:
https://developers.google.com/apps-script/reference/drive/folder#createfileblob
// Create an image file in Google Drive using the Maps service.
var blob = Maps.newStaticMap().setCenter('76 9th Avenue, New York NY').getBlob();
DriveApp.getRootFolder().createFile(blob);
It's quite late for the answer but just incase some one runs into the situation.
Are you familiar with this app? It does exactly what you're asking for.
However, if you want to re-create this for your own purposes, I would change your declaration of variable file to read as such:
var file = folder.next().createFile(fileBlob);
when you create your variable folder, the method you use creates a FolderIterator, not a single folder. You have to call the next() method to get a Folder object.
To be precise with your script and avoid saving to an incorrect-but-similarly-named folder, I would recommend passing the folder ID to your script rather than the folder Name. If you pass the folder ID, you could declare folder as:
var folder = DriveApp.getFolderById(folder);
and then continue the script as you have it written. I hope that helps.
Working on similar problem, I came up with the solution below to save a file to a folder. If the folder doesn't exist it creates it, otherwise it saves the file specified by "FOLDER_NAME"
var folderExists = checkFolderExists("FOLDER_NAME");
if (folderExists) {
saveFolder = DriveApp.getFolderById(folderExists);
} else {
saveFolder = DriveApp.createFolder("FOLDER_NAME");
}
// Make a copy of the file in the root drive.
var file = DriveApp.getFileById(sheetID);
// Take the copy of the file created above and move it into the folder:
var newFile = DriveApp.getFolderById(saveFolder.getId()).addFile(file);
// Remove the copy of the file in the root drive.
var docfile = file.getParents().next().removeFile(file);
Further to Eric's answer, I have also provided a utility function that checks if the folder exists. It's reusable in any project.
function checkFolderExists(fName) {
try {
var folderId;
var folders = DriveApp.getFolders();
while (folders.hasNext()) {
var folder = folders.next();
folderName = folder.getName();
if (folderName == fName) {
folderId = folder.getId();
}
}
} catch(e) {
log("Services::checkFolderExists()" + e.toString());
throw e;
}
return folderId;
}
Hello am using camera in my application.So i want to save Captured images into folder in gallery,floder name must be application name?please suggest me with some Example?
Thanks in advance
You can create any folder or file you want. Read this Android article Taking Photos Simply:
Add the Photo to a Gallery When you create a photo through an intent,
you should know where your image is located, because you said where to
save it in the first place. For everyone else, perhaps the easiest way
to make your photo accessible is to make it accessible from the
system's Media Provider.
The following example method demonstrates how to invoke the system's
media scanner to add your photo to the Media Provider's database,
making it available in the Android Gallery application and to other
apps.
private void galleryAddPic() {
Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
File f = new File(mCurrentPhotoPath);
Uri contentUri = Uri.fromFile(f);
mediaScanIntent.setData(contentUri);
this.sendBroadcast(mediaScanIntent);
}
Use below code and modify the path where you want to save your image.
mImageView.setDrawingCacheEnabled(true); Bitmap bitmap =
mImageView.getDrawingCache();
String root = Environment.getExternalStorageDirectory().toString();
File newDir = new File(root + "/app_name/saved_images"); newDir.mkdirs();
Random gen = new Random(); int n = 10000; n = gen.nextInt(n); String
fotoname = "photo-" + n + ".jpg"; File file = new File(newDir,
fotoname); String s = file.getAbsolutePath();
System.err.print("******************" + s); if (file.exists())
file.delete(); try { FileOutputStream out = new
FileOutputStream(file); bitmap.compress(Bitmap.CompressFormat.JPEG,
90, out); out.flush(); out.close();
Toast.makeText(getApplicationContext(), "Saved to your folder ",
Toast.LENGTH_SHORT).show();
} catch (Exception e) {
}
I have written
List<Attachment> lstAttachment = new List<Attachment>();
//Check if any error file is present in which case it needs to be send
if (new FileInfo(Path.Combine(errorFolder, errorFileName)).Exists)
{
Attachment unprocessedFile = new Attachment(Path.Combine(errorFolder, errorFileName));
lstAttachment.Add(unprocessedFile);
}
//Check if any processed file is present in which case it needs to be send
if (new FileInfo(Path.Combine(outputFolder, outputFileName)).Exists)
{
Attachment processedFile = new Attachment(Path.Combine(outputFolder, outputFileName));
lstAttachment.Add(processedFile);
}
Working fine and is giving the expected output.
Basically I am attaching the file to the list based on whether the file is present or not.
I am looking for any other elegant solution than the one I have written.
Reason: Want to learn differnt ways of representing the same program.
I am using C#3.0
Thanks.
Is it looks better?
...
var lstAttachment = new List<Attachment>();
string errorPath = Path.Combine(errorFolder, errorFileName);
string outputPath = Path.Combine(outputFolder, outputFileName);
AddAttachmentToCollection(lstAttachment, errorPath);
AddAttachmentToCollection(lstAttachment, outputPath);
...
public static void AddAttachmentToCollection(ICollection<Attachment> collection, string filePath)
{
if (File.Exists(filePath))
{
var attachment = new Attachment(filePath);
collection.Add(attachment);
}
}
How about a little LINQ?
var filenames = new List<string>()
{
Path.Combine(errorFolder, errorFilename),
Path.Combine(outputFolder, outputFilename)
};
var attachments = filenames.Where(f => File.Exists(f))
.Select(f => new Attachment(f));
Please let me know how can I drag and drop a directory from windows onto Adobe AIR panel.
The folder has subFolders inside. The subFolders have many files.
I want to drag the parent folder and drop it so that the whole structure has to get uploaded.
Please help.
It is rather easy to upload folders. When detecting a drop using the drop event, you get supplied wit ha list of files dropped. You can then determine if it is the dropped file is a folder, and if it is, then you can get all the files listed under it (which includes files) and if any of those are folders, then recurse further down.
Basically, adobe air treats files and folders as the same object.
In the drop event put
var files = event.dataTransfer.getData( "application/x-vnd.adobe.air.file-list" );
var fileData = [];
for (var f = 0; f < files.length; f++)
{
if (files[f].isDirectory) {
//process this folder recursing through subfolders
} else {
//we have a file
}
}
You can then recurse through the object adding files and files to the server as needed
Here is the complete Example. Just call onInit() method on application's initialization.
private function onInit(event:FlexEvent):void
{
this.addEventListener(NativeDragEvent.NATIVE_DRAG_ENTER, onDragIn);
this.addEventListener(NativeDragEvent.NATIVE_DRAG_DROP, onDrop);
}
private function onDragIn(event : NativeDragEvent):void
{
NativeDragManager.acceptDragDrop(this);
}
private function onDrop(event : NativeDragEvent):void
{
try
{
var dropfiles:Array = event.clipboard.getData(ClipboardFormats.FILE_LIST_FORMAT) as Array;
processDroppedFiles(dropfiles);
}
catch (error : IOError)
{
trace("Error during drag-and-drop procedure.");
}
}
private function processDroppedFiles(files : Array):void
{
for each (var file:File in files)
{
if (file.isDirectory)
{
processDirectory(file);
}
else
{
processFile(file);
}
}
}
private function processDirectory(dir : File):void
{
processDroppedFiles(dir.getDirectoryListing());
}
private function processFile(file:File):void
{
trace(file);
}