How to display Dropbox Folders after logging in - ipad

I am in the process of learning the Dropbox SDK. I want to learn how to display the users Dropbox folders as well as give the user the option to upload the file from my app to their Dropbox account.
I have looked through their example app but it is not giving me the info that I need.
Can someone help me with this please?

I think you might find this tutorial useful.
http://www.nanaimostudio.com/blog/2011/1/20/how-to-synchronize-your-app-data-using-dropbox-api.html
You can call upload method on the DBRestClient object.
NSString* path = [self getDocumentPath];//or however you can obtain the path where your file is stored
[restClientObject uploadFile:#"filename" toPath:#"/" fromPath:path];
//you can choose to upload to the dropbox root directory(above) or a folder of your choice eg toPath:#"/myfolder"
Use loadMetaData for displaying the contents of dropbox folder
[restClientObject loadMetadata:#""];
you also have to implement loadedMetadatafunction. Refer the tutorial above.

-(void)restClient:(DBRestClient *)client loadedMetadata:(DBMetadata *)metadata{
NSMutableArray *list=[[NSMutableArray alloc] init];
for (DBMetadata *child in metadata.contents) {
[list addObject:child];
}
self.arrayFoldersList=[[NSMutableArray alloc] initWithArray:list];
[self.tableView reloadData];
}
[self.restClient loadMetadata:#""];
I think this will help you alot.

Related

How to share files for open-in-place on iOS

We have an iOS application that manages documents via Core Data. The actual files reside in the app's shared container so that the app's file provider extension can also access them for Files.app support. We want to give the user the option to open these files in third-party apps so that they can edit them in-place instead of sending a copy to the other app.
We provide a UIActivityViewController for sharing files with other apps. We also provide a UIActivity that shows a UIDocumentInteractionController which seems to work better in some cases. We give the UIActivityViewController the document's file URL, the raw text content, and printable data.
This works but all third-party editors are shown as Copy to … instead of Open in …
We've also set the UIFileSharingEnabled and LSSupportsOpeningDocumentsInPlace properties to YES in the app's info.plist but they seem to be only relevant for open-in-place when sharing files residing in the app's Documents folder.
Now we've stumbled upon the NSItemProviderFileOptionOpenInPlace option for NSItemProvider. As we're already supporting a file provider extension and from Apple's documentation this seemed like a great place to accomplish just what we want.
Adding a "pure" NSItemProvider works, in a way, but shows fewer options than when also sharing the file URL and text in addition (which is expected). However, when we use -[NSItemProvider registerFileRepresentationForTypeIdentifier:fileOptions:visibility:loadHandler:] with the said option (or just zero, same result) and return the file URL in the loadHandler's completionHandler() nothing is shared anymore. E.g., Mail no longer attaches the file, Messages doesn't show the document for sending.
These are the relevant bits of the code:
NSMutableArray *items = [NSMutableArray array];
NSMutableArray <UIActivity *> *activities = [NSMutableArray array];
NSURL *fileURL = self.record.metadata.fileURL;
NSString *fileUTI = self.record.metadata.uti;
NSItemProvider *itemProvider = [[NSItemProvider alloc] initWithItem: fileURL typeIdentifier: fileUTI];
[itemProvider registerFileRepresentationForTypeIdentifier:fileUTI fileOptions:NSItemProviderFileOptionOpenInPlace visibility:YES loadHandler:^NSProgress * _Nullable(void (^ _Nonnull completionHandler)(NSURL * _Nullable, BOOL, NSError * _Nullable))
{
if (fileURL)
completionHandler(fileURL, YES, nil);
else
completionHandler(nil, YES, [NSError errorWithDomain:NSCocoaErrorDomain code:NSURLErrorFileDoesNotExist userInfo:nil]);
return nil;
}];
[items addObject:itemProvider];
self.activityViewController = [[UIActivityViewController alloc] initWithActivityItems:items applicationActivities:activities];
[UIAppDelegate.splitViewController presentViewController:self.activityViewController animated:YES completion:nil];
The using the Share menu the item provider's load handler is correctly called and the file's actual URL returned.
Is that not how NSItemProviderFileOptionOpenInPlace is intended to be used? Or are we using it simply wrong? Apple's description is extremely sparse and we couldn't find any information elsewhere on the internet except for the official documentation.
I've found out what my problem was: Not deep enough understanding of the relationship between the activity view controller and file providers.
As all my files reside in the shared container and are published also through the file provider extension, what I need to share through the activity view controller is the exact same URL that is shared through the file provider extension. Technically then the app that opens the file accesses it through there file provider mechanism.

Can I upload an MP3 file to my server from iOS?

I was googling this question but nothing useful or current came up. I'd like to know if (and if, how) you can select an MP3 file (from itunes?) and upload the contents to one of my own servers on iOS (iphone & ipad app).
One of my clients is asking me if it's possible to do this, and I havn't found the answer yet.
Thanks in advance!
The short answer would be YES.
Here is a working solution for me. But you need to use a third party library. Then this is what you need to do:
Create a temp folder either in the NSDocuments directory or a temp directory.
Use MPMediaQuery to load the music files.
The object that you will get from the MPMediaQuery is an MPMediaItem. With this you can get the asset URL of the media item.
Code:
NSString *assetURL = [mediaItem valueForProperty:MPMediaItemPropertyAssetURL];
get the extension of with the asset URL
NSString *extension = [TSLibraryImport extensionForAssetURL:assetURL];
set a location URL (This will be the location where the mp3 music data will be imported).
NSString *locationURL = [[NSURL fileURLWithPath:[path stringByAppendingPathComponent:musicTitleYouWant]] URLByAppendingPathExtension:extension];
Now you can import the contents of the mp3 from to the directory you set earlier.
TSLibraryImport *libraryImport = [[TSLibraryImport alloc] init];
[libraryImport importAsset:assetURL toURL:locationURL completionBlock:^(TSLibraryImport *libraryImport)
{
if(libraryImport.status == AVAssetExportSessionStatusCompleted)
{
//Once complete the file will be store on the location URL you set earlier. Now you can get the file from that location and convert it to NSData and send it to the server. There are plenty of ways to do that.
}
else
{
//Here means import failed. :(
}
}];
Hope this helps. :)

Dropbox SDK Chooser download file

I would like to download a file from dropbox into my app i already implemented the Dropbox Drop-in API chooser so i get directed to the dropbox app and can choose a file but i don't know how to download the selected file
- (void)didPressChoose{
[[DBChooser defaultChooser] openChooserForLinkType:DBChooserLinkTypePreview
fromViewController:self completion:^(NSArray *results)
{
if ([results count]) {
fileurl = [[results[0] link] absoluteString];
NSLog(#"got results %#", results);
NSLog(#"link 0 = %#", [[results[0] link] absoluteString]);
} else {
// User canceled the action
}
}];
}
I tried this but i only get a link like "dropbox.com/s/2hro2i45h ..." but for this
[self.restClient loadFile:fileurl intoPath:localDir];
I need something like "/test.txt"
First, the documentation for the Dropbox iOS Chooser lists two different link types. If you want to download the file directly, you should use DBChooserLinkTypeDirect instead of DBChooserLinkTypePreview as you have in your code.
Second, once you have the direct link, you can use a normal HTTP request on the link to download the file content, e.g., using NSURLRequest. The loadFile method you have in your code is for the Dropbox iOS Core SDK which you don't need to use if you're just using the Chooser. That method won't work with the link returned by the Chooser anyway. That method is designed to take a relative path in a user's Dropbox account, but the Chooser is a simpler integration that just gives you a link instead.
I'm not sure but I have this before calling loadFile on restClient
NSString* filePath = [path stringByReplacingOccurrencesOfString:#"dropbox://" withString:#""];
[restClient loadFile:filePath intoPath:destinationPath];

Preview of dropbox file in iOS

I am integrating dropbox with my IOS application. I am able to fetch selected file meta data. But couldn't find the way to show preview after selecting the file. Can someone suggest which API is helpful.
Drop box i am using is : https://www.dropbox.com/developers/dropins/chooser/ios
Below piece of code is called when user wants to select file from dropbox :
- (void)didPressChoose
{
[[DBChooser defaultChooser] openChooserForLinkType:DBChooserLinkTypePreview fromViewController:self
completion:^(NSArray *results)
{
if ([results count]) {
_result = results[0];
//After getting the result, i want to preview the file
} else {
_result = nil;
[[[UIAlertView alloc] initWithTitle:#"CANCELLED" message:#"user cancelled!"
delegate:nil cancelButtonTitle:#"Okay" otherButtonTitles:nil]
show];
}
[[self tableView] reloadData];
}];
}
When you ask for DBChooserLinkTypePreview, the DBChooserResult you get back from the Chooser will have an NSURL link like this:
https://www.dropbox.com/s/toyzur6e0m34t7v/dropbox-logos_dropbox-glyph-blue.png
This link type is meant for direct user interaction, so you can send a user there and Dropbox will display the page with a preview of the file if possible.
Alternatively, you may want to use DBChooserLinkTypeDirect which gives you a direct link like this:
https://dl.dropboxusercontent.com/1/view/969vkzdys770277/Testing/Images/dropbox-logos_dropbox-glyph-blue.png
This is a direct (but temporary) link to the file contents. You can download the file contents programmatically (e.g., see How do I download and save a file locally on iOS using objective C? ) and then do whatever you want with it. For example, you may want to display it in an UIImageView if it's an image, etc.
Also, DBChooserResult contains a thumbnails property with links to thumbnails (if the selected file was an image or video) that might be similarly useful.

Invalidating QLPreviewController "cache"

QLPreviewController seems to cache file contents based on the local file's URL. In my application, the file contents can be updated remotely and would cause the new contents to be downloaded.
If I view a file in QLPreviewController, update it remotely, then re-preview it, the file does not show up as updated.
The file is definitely updated on disk, and other controls show the correct updated file.
The workaround I'm using right now is to basically move a file when it's previewed to a unique filename (using timestamp), which will of course not be in the QLPreviewController's cache. However, this has other repercussions, for example, if the app is killed or it crashes (god forbid), I won't know "where" to find the downloaded file.
I'm looking for less invasive hacks, or solutions to making QLPreviewController refresh its cache. The APIs don't seem to expose anything, so don't be afraid to submit a hack if it's less gross than the one I've presented above (not including copying/moving the file to a guaranteed unique URL, which I am already utilizing).
Just ran into this issue myself. I solved it by recreating the QLPreviewController each time I reload an item with the same name as the currently viewed item. Creating a new QLPreviewController clears the cache.
I know this is an old question but someone might have the same problem and find this answer helpful.
You should use refreshCurrentPreviewItem after downloading complete
I had the same problem. Opening a locally generated CSV file.
I have my _previewController* setup as a #property of my controller. Then what i did:
- (void)viewDidLoad
{
[super viewDidLoad];
self.previewController = [[QLPreviewController alloc] init];
_previewController.delegate=self;
_previewController.dataSource=self;
}
- (void)previewCSV
{
[_previewController reloadData]; // this triggers a reload
[self presentModalViewController:_previewController animated:YES];
}
IN other solution that comes to mind (not tested).
Depending on your URL, you could add something like http://url?time=123456 to your URL. Like this you change the URL but without side effect. The time (or any other parameter) you can change on each request.
It's the ugliest bug in iOS. Cache management in iOS 5 and beyond. I think is the same reason that makes iCloud buggy, Share-at-Home crashing and so on. Bad cache managements and so worst synchronization systems.
Well, my solution for this was to store the download file in a folder and use the current date to name the folder. It is equivalent to #Rogier's solution, but this works always. You get a name for the folder, for example, with [[NSDate date] description]. Instead of saving the file replacing the old one, you delete previous file, delete previous folder and save new file in a new folder. It's working fine for me.
Just remove all files from tmp directory like this:
- (void)clearCache
{
NSString *tempPath = NSTemporaryDirectory();
NSArray *dirContents = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:tempPath error:nil];
NSFileManager *fileManager = [NSFileManager defaultManager];
for (int i = 0; i < [dirContents count]; i++) {
NSLog(#"Directory Count: %i", [dirContents count]);
NSString *contentsOnly = [NSString stringWithFormat:#"%#%#", tempPath, [dirContents objectAtIndex:i]];
[fileManager removeItemAtPath:contentsOnly error:nil];
}
}

Resources