I am on some document sharing issue. My iPhone has two applications. One app "SharingApp" shares a file from its bundle to another app "ViewerApp" using Document Interaction Controller. By default, the shared file will be saved to the document directory of "ViewerApp" under folder named "Inbox". I can get the url in didFinishLaunchingWithOptions: of "ViewerApp" as
NSURL *url = (NSURL*)[launchOptions valueForKey: UIApplicationLaunchOptionsURLKey];
This scenario works perfectly if the "ViewerApp" is not been launched.
The problem I have is, incase, if the "ViewerApp" is in background state(or not killed) and if the file is shared from "SharingApp", applicationDidBecomeActive: is called in appDelegate of "ViewerApp". So, I couldn't able to get the url as the didFinishLaunchingWithOptions: method is not called(ViewerApp is already launched). "ViewerApp" just opens with the last shared url before entering to the background state.
How can I handle to get the url in applicationDidBecomeActive:? Please, share some ideas if you have come across this kind of issue.
Thanks for your ideas.
You should implement the following UIApplicationDelegate method
- (BOOL)application:(UIApplication *)application
openURL:(NSURL *)url
sourceApplication:(NSString *)sourceApplication
annotation:(id)annotation
This should solve your problem since this method will be called when your viewer app is in background
I ran into this exact same issue. The problem is that didFinishLaunchingWithOptions is not called when an application is already open but brought to the foreground. I took my code out of didFinishLaunchingWithOptions and instead put it inside handleOpenURL (also on the app delegate page)
- (BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url{
if (url != nil && [url isFileURL])
{
MainViewController *frontViewController = [[MainViewController alloc] init];
[frontViewController handleOpenURL:url]; //function on my main view controller class to do the necessary action
return YES;
}
else
{
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:#"Error" message:#"Cannot Handle Opening This File." delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil];
[alert performSelectorOnMainThread:#selector(show) withObject:nil waitUntilDone:YES];
return NO;
}
}
Related
I am newbie in iOS Development. i want to add deep linking on my app so i prefer url schema for that, so now i want to open my app from another app then app is open and instantly crashed not any one method is called.
like as here i added alert on didFinishLaunchingWithOptions method
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
UIAlertView *alert=[[UIAlertView alloc]initWithTitle:#"Info" message:#"Finish Called" delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil,nil];
[alert show];
[self.window makeKeyAndVisible];
return YES;
}
And also this method is not call when my app is open
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation
{
UIAlertView *alert=[[UIAlertView alloc]initWithTitle:#"Info" message:[NSString stringWithFormat:#"%#",url] delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil,nil];
[alert show];
return YES;
}
It just open Splash screen and crashed can any one help me for this?
Thank you in advance.
There are 2 situations
1. app is in suspended state
- when u click on url then applicationdidFinishLaunchingWithOptions will get called and u will get url in options dictionary and the openUrl method will get skipped
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
return YES;
}
2. if app is in background then openUrl method only get called .
Alright I think I am close to a solution here. I think I must be missing something small. Hope you guy can help.'
I am trying to have another app open another custom app and run a method from that app that is being called through the URL scheme. I understand that in ios 9 they made it manitory to define in the info.plist the key
<key>LSApplicationQueriesSchemes</key>
<array>
<string>URLScheme0</string>
<string>URLScheme1</string>
<string>URLScheme2</string>
ect....
</array>
And I think I have done that properly. Though I want a confirm on this and other thing. Firstly, do I add this to the info.plist of the "calling" app, or the "receiving" app, or BOTH? As, I have it now it is with both. When I remove it from the calling apps plist I get the error.
"This app is not allowed to query for scheme xxx”
Keep in mind I have also included in the plist for the receiving app the URL types and URL schemes array with the same scheme names.
The the calling app I have a button mapped with this methods code:
- (IBAction)killMethod:(id)sender {
NSString *customURL = #"TurnOffRelay://";
if ([[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:customURL]]) {
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:customURL]];
} else {
UIAlertController* alert = [UIAlertController alertControllerWithTitle:#"URL error" message:#"No custom URL defined for Kill Relay" preferredStyle:UIAlertControllerStyleAlert];
[self presentViewController:alert animated:YES completion:nil];
}
}
and for the receiving app I have in the appDelegate.m :
- (BOOL)application:(UIApplication *)application OpenURL:(NSURL *)url sourceApplication:(NSString *) sourceApplication annotation:(id)annotation {
NSLog(#" Calling application: %#", sourceApplication);
NSLog(#"URL scheme: %#", [url scheme]);
if ([sourceApplication isEqualToString:#"net.ble.relay"]) {
if ([[url scheme] isEqualToString:#"TurnOffRelay://"]) {
ViewController *viewController = [[ViewController alloc] init];
[viewController killSwitch];
NSLog(#"Running killSwitch");
}
return YES;
}
else
return NO;
}
With what I have right now running I am able to actually press the button in the "calling" app and from there the "receiving" app opens, but alas, the method I want to run doesn't run inside of the if statements. I am wondering what I am doing wrong. I will gladly answer any questions about things I may have missed. This has been bothering me all day. Would like some sort of guidance. Thanks in advance.
pay attention to if ([[url scheme] isEqualToString:#"TurnOffRelay://"]) 。 url scheme is TurnOffRelay rather than TurnOffRelay://.
So, after changing the OpenURL to openURL and then noticing that the sourceApplication name was wrong. I am guessing that if I had typed in the correct application to use, as in, the actual name of the application that was "calling" the If block would have proceeded correctly. But I am sure, also, that if I had not changed the openURL I would have been stuck again.
Thanks for the help. Its now working as intended.
I am using local notification for alarm system but I am facing some problem while handling local notification, When i clicked on alarm notification (When app is closed) its launches app but the problem is it should go to didFinishLaunchingWithOptions function but it's not going inside any of the function in appDelegate (I used breakpoints to check).
I'm using story board with navigation controller, I want to open a specific view controller on notification click when app is closed.
but when I'm launching that app normally it's going inside didFinishLaunchingWithOptions function.
Please suggest.
Any help would be appreciated.
main.m
#import "DEMOAppDelegate.h"
int main(int argc, char * argv[])
{
#autoreleasepool
{
return UIApplicationMain(argc, argv, nil, NSStringFromClass([DEMOAppDelegate class]));
}
}
DEMOAppDelegate.m
#import "DEMOAppDelegate.h"
#implementation DEMOAppDelegate
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
UILocalNotification *localNotif = [launchOptions objectForKey: UIApplicationLaunchOptionsLocalNotificationKey];
if (localNotif)
{
NSLog(#"Recieved Notification %#",localNotif);
}
return YES;
}
- (void)applicationWillResignActive:(UIApplication *)application
{
}
- (void)applicationDidEnterBackground:(UIApplication *)application
{
}
- (void)applicationWillEnterForeground:(UIApplication *)application
{
}
- (void)applicationDidBecomeActive:(UIApplication *)application
{
}
- (void)applicationWillTerminate:(UIApplication *)application
{
}
-(void) application:(UIApplication *)application didReceiveLocalNotification:(UILocalNotification *)notification
{
UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:notification.alertAction message:notification.alertBody delegate:self cancelButtonTitle:#"OK" otherButtonTitles:nil];
[alertView show];
}
#end
It's not possible, when your app is not running notification it will not react on notification directly.
didFinishLaunchingWithOptions will contain information about notification only when user opened your app through this notifcation. If he cancels it and opens your app through dashboard icon you are not gonna see this in this method.
Unfortunatelly if you need to react on all notification that happened from last time the user opened the app, only way is to build your own tracking logic and get all events that were in the past based on time.
Also there is no way to even get a list of notification you scheduled for your app, so usually it is a good idea to build in time-based event logic and use notification on top of it, but all the logic happens on your own time-based code. This way even if user disable notifications your critical logic will work.
When the application is running in background you will get notification through application:didReceiveRemoteNotification. You can gather those notifications inside your app, and process them on applicationDidBecomeActive if you want to do anything specific inside your application for them after user comes back to the app from background.
I have registered my app to be able to open HTML files. I would like the app to keep the last HTML file it opened... If I open a new HTML file, I would like it to overwrite the last one opened.
I have attempted to user the Documents directory and its not working for me. I have also tried using NSUserDefaultsto no avail. Here is what i currently have:
-(BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url
{
ViewController *vc = (ViewController *)self.window.rootViewController;
[vc loadFileWithUrl:url];
[[NSUserDefaults standardUserDefaults] setURL:[url fileReferenceURL] forKey:#"amd"];
return YES;
}
I kill the application entirely, then - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions is called. Here is how that method looks:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
NSURL *url = [[NSUserDefaults standardUserDefaults] URLForKey:#"amd"];
if (url)
{
ViewController *vc = (ViewController *)self.window.rootViewController;
[vc loadFileWithUrl:url];
}
return YES;
}
url is always nil :(
PS: I have also tried storing the HTML file in its string representation, and I am able to get that to persist in the Documents folder, but when I try to load that string using:
[webView loadHTMLString:htmlString]; the page never loads. I think that has something to do with the Javascript but I'm not too sure.
The user defaults are saved when the app goes to the background, or when you call -synchronize on the user defaults. When developing, you often don't put the app into background, but just kill it through XCode, in which case nothing gets saved. You can save the user defaults by pressing the home button on your iPhone/iPad, and killing the app in XCode 1second later.
Also, you should put a log statement into your first method, like NSLog(#"saving amd to %#", [url fileReferenceURL]); to be sure that it really gets saved!
It seems that you forgot to call
[[NSUserDefaults standardUserDefaults] synchronize];
Docs:
Writes any modifications to the persistent domains to disk and updates
all unmodified persistent domains to what is on disk.
I'm trying to implement SSO following the Tutorial:
https://developers.facebook.com/docs/mobile/ios/build/
At the end of Step 3, I'm supposed to Test my App running it on Simulator. The Run succeeded but all I see is a Blank View (screen). I'm not sure if I need to create the view called "authorization dialog" including the FB logo, buttons, etc or if it's automatically created by code I've implemented using Facebook SDK.
Also, I'm using a storyboard and wonder if that's the problem.
I think that it's because you have once signed in and now you haven't logged out so it is already authorized and hence you cannot see anything :)
Is your initial ViewController blankView ? Because the SSO only validates/autorize the session, you need to implement the UI in your ViewController.
If you implement it in Storyboard I suggest you to do most of the code in your controller file, since I was stucked there for quite long time. But make sure to put this code in the app delegate file.
#pragma mark Facebook
- (BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url {
return [self.facebook handleOpenURL:url];
}
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication: (NSString *)sourceApplication annotation:(id)annotation {
return [self.facebook handleOpenURL:url];
}
Also in the delegate file you should instantiate the Facebook object before you use the in the above methods.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
viewController *controller = [[viewController alloc] init];
// Initialize Facebook
facebook = [[Facebook alloc] initWithAppId:#"Your app ID in string" andDelegate:controller];
// Override point for customization after application launch.
return YES;
}