I am learning iOS development and the following code is from the book Programming iOS8 by Matt Neuberg. It is an app delegate class to create a window. I do not understand -
In the second line what is #UIApplicationMain and why is it there? Is it a declaration of a global varibale?
What is the purpose of the parameter didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?? I don't see it used anywhere in the function body.
import UIKIT
#UIApplicationMain
class AppDelegate : UIResponder, UIApplicationDelegate {
var window : UIWindow?
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
self.window = UIWindow(frame:UIScreen.mainScreen().bounds)
self.window!.backgroundColor = UIColor.whiteColor()
self.window!.makeKeyAndVisible()
return true
}
}
The #UIApplicationMain attribute in Swift replaces the trivial
main.m file found in Objective-C projects (whose purpose is to
implement the main function that's the entry point for all C programs
and call UIApplicationMain to kick off the Cocoa Touch run loop and
app infrastructure).
In Objective-C, the main (heh) bit of per-app configuration that the
UIApplicationMain function provides is designating one of your app's
custom classes as the delegate of the shared UIApplication object.
In Swift, you can easily designate this class by adding the
#UIApplicationMain attribute to that class' declaration. (You can
also still invoke the UIApplicationMain function directly if you
have reason to. In Swift you put that call in top-level code in a
main.swift file.)
#UIApplicationMain is for iOS only. In OS X, the app delegate is
traditionally set in the main nib file designated by the Info.plist
(the same for Swift as for ObjC) — but with OS X storyboards there's
no main nib file, so #NSApplicationMain does the same thing there.
Reference from HERE.
And for your second point didFinishLaunchingWithOptions:
Every app begins with UIApplicationDelegate -application:didFinishLaunchingWithOptions: (or more accurately, -application:willFinishLaunchingWithOptions:, when implemented). It is called by the application to notify its delegate that the launch process is finishing, and nearly ready to run.
Related
I have this code that show a message "Msg Background" when the application is in Background. What I need is that as long as the application continues in the background show that message every 2 minutes (just an example of time). So far the code I have shows the message only once, apparently this sentence is not working properly.
UIApplication.shared.setMinimumBackgroundFetchInterval (UIApplication.backgroundFetchIntervalMinimum)
I also have this warning: 'setMinimumBackgroundFetchInterval' was deprecated in iOS 13.0: Use a BGAppRefreshTask in the BackgroundTasks framework instead
I am using swift 5 and Xcode 11
class AppDelegate: UIResponder, UIApplicationDelegate {
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
GMSServices.provideAPIKey("AIzaSyBSpAt5zqvbh73FmG_Kb6xpiFMkWRmHppg")
UIApplication.shared.setMinimumBackgroundFetchInterval(UIApplication.backgroundFetchIntervalMinimum)
return true
}
func application(_ application: UIApplication, performFetchWithCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void) {
print("Msg Background")
}
}
As Paulw11 said, it's not called in fixed interval. The OS controls when it is going to be executed. We cannot expect the specific time because of it.
You probably know this, but I'm going to add this bit just in case, setMinimumBackgroundFetchInterval has deprecated on iOS 13 and later. You might want to consider to use BackgroundTasks Framework instead.
but if you want to test performFetchWithCompletionHandler, you can use XCode Navigation Bar > Debug > perform Background Fetch.
screenshot of XCode navigation bar to find option
I hope it can help!
I had updated my Xcode 7.3 to Xcode 8.
It is showing multiple warnings in AppDelegate. The warning is as follows.
Extraneous '_' in parameter: 'application' has no keyword argument name
My AppDelagate.swift file is this:
import UIKit
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
return true
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
}
when I followed the Xcode suggestion to remove _ in the functions that shows warning.
I got rid of the above warning. But now I get a new warning for
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
return true
}
The warning is:
Non-#objc method 'application(_:didFinishLaunchingWithOptions:)' cannot satisfy optional requirement of #objc protocol 'UIApplicationDelegate'
I followed the solutions online. But had no luck in getting rid of this warning.
Any help would be appreciated.
Thanks.
Your code is correct for Swift 3. But the environment you are in clearly thinks it is supposed to be Swift 2, and that is the reason for the error messages.
It sounds as if you have accidentally opened the file in Xcode 7. That would explain it. Your code is now Swift 3. Xcode 7 is Swift 2; it does not know about Swift 3 and doesn't understand your code.
Now that you have converted to Swift 3, you can never use Xcode 7 with this project ever again.
Or maybe this is Xcode 8 but the legacy build setting is still on, so it thinks this is supposed to be Swift 2. But it isn't. It is Swift 3.
So, let me explain my problem first.
I don't want to relay on my web-server data, I want to stub data for my XCUITests.
So, I will be sure that it returns correct data in 100% times, as well as sometimes I need to test some specific(e.g. errors, or empty state) cases, which web-server may not return in exact that moment.
So, what I have tried, it is to run the local server in my XCUITest and then stub some requests, but turns out it didn't work out because XC UI Tests are running in complete separate bundle(even separate process) and local server can't be binded to localhost, so my Main app bundle can't connect to this server.
Another solution that I've tried is to pass some params through XCUIApplication().launchArguments, and based on this params - run stubs on main app, but then - it is a bit of a problem: "I have local-proxy server in main app", which I need only for UI testing.
I know, that also, I can just create stub-server and expose it to the web, so to say, create kind of development-env just for UI tesitng, but it seems to extreme for me. Because in that case maintaining only UI tests for my project is a big effort.
So, my question is, does anyone have better solution? Is there any way to get around this problem without modifying your main app and running external web-server?
You can use SBTUITestTunnel. This library allows to dynamically stub network requests (among other things) in a simple fashion.
The easiest way to add the library is to use cocoapods, then override the initialize method of your AppDelegate:
import UIKit
import SBTUITestTunnel
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
override class func initialize() {
SBTUITestTunnelServer.takeOff()
super.initialize()
}
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
return true
}
}
Once you added that, you're ready to go. You can add/remove stub to network requests to your UI Tests like in the example below:
func testThatSomethingStubbedWorks() {
let app = SBTUITunneledApplication()
app.launch()
let stubId = app.stubRequestsMatching:SBTRequestMatch(SBTRequestMatch.URL("google.com"), returnJsonDictionary: ["key": "value"], returnCode: 200, responseTime: SBTUITunnelStubsDownloadSpeed3G)
// from here on network request containing 'google.com' will return a JSON {"request" : "stubbed" }
...
app.stubRequestsRemoveWithId(stubId) // To remove the stub either use the identifier
app.stubRequestsRemoveAll() // or remove all active stubs
}
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 7 years ago.
Improve this question
What does it mean to put something in my application didFinishLaunchingWithOptions method:. And how do i do it in swift?
There is a boiler plate method provided in your iOS project's AppDelegate file defined as
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
// Override point for customization after application launch. Here you can out the code you want.
return true
}
If you want to handle cases such as if app is opened by a URL or by remote notification then you might want to put your code before return.
If the app can handle the url then keep the return value true otherwise false. In case of push notification, the return value would anyway be ignored.
Hope this would help.
This function gets invoked right before your app is fully loaded. If you're familiar with jQuery, it's sort of like $(document).ready(function() {}) Below is a link to documentation from Apple on how to implement this function:
https://developer.apple.com/library/ios/documentation/UIKit/Reference/UIApplicationDelegate_Protocol/index.html?hl=ar#//apple_ref/occ/intfm/UIApplicationDelegate/application:didFinishLaunchingWithOptions:
application:didFinishLaunchingWithOptions: is part of the UIApplicationDelegate protocol, which is responsible with handling different changes over your application state. You can find out more about this method and about the app delegate protocol in the Apple documentation from here. I strongly recommend reading it before moving forward.
You should get the below code automatically generated by Xcode if you create a brand new Swift iOS project:
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
// ...
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
// Override point for customization after application launch.
return true
}
You can place the code you need into that method, or add the method to your UIApplicationDelegate if it's not already there.
I started having an issue with Xcode 6.0.1 where the error "SourceKitService Crashed Crashlog generated in ~/Library/Logs/DiagnosticReports" started popping up and all syntax highlighting was gone in Swift. Then Apple released a new update Xcode 6.1.1 where mentioned this issue was resolved. So I updated my Xcode to 6.1.1 but this problem still exists. I my case the issue is just staying there and never disappearing.
I tried few solutions found in StackOverflow like deleting the content of: DerivedData/ModuleCache, cleaning up the project etc but the issue still exists.
I am not able to make a build and whenever I try to get these 2 errors.
/Users/MY_PROJECT/AppDelegate.swift:11:1: 'UIApplicationMain' class must conform to the 'UIApplicationDelegate'
protocol at UIApplicationMain in my AppDelegate.h file and this Command failed due to signal: Segmentation fault: 11
Here is the code of my AppDelegate.swift
import UIKit
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(application: UIApplication!, didFinishLaunchingWithOptions launchOptions: NSDictionary!) -> Bool {
return true
}
func applicationWillResignActive(application: UIApplication!) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game.
}
func applicationDidEnterBackground(application: UIApplication!) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(application: UIApplication!) {
// Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(application: UIApplication!) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(application: UIApplication!) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
}
I'am not sure about the cause of this error, i was getting this sourcekit crash for various reasons. For you if you look into UIApplicationDelegate methods, they are slightly changed in the signature. For eg UIApplication parameter is not optional now.
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
// Override point for customization after application launch.
return true
}
So if you compare your delegate methods with new UIApplicationDelegate methods(if you command+click you can check the method signature)and make changes you may get rid off this error. Give a try.