Trying to get Static 3D touch Quick Actions to work in Obj-C
Asked Answered
E

2

6

So I want a pretty basic 3D touch setup. On my main UI, I have a 2 option segmented control and I basically want to have one option of it selected upon open when 3DQuickActionA is used, and the other option when 3DTouchQuickActionB is used.

I've looked at other questions on this site, and one suggested I use:

- (void)handleShortCutItem:(UIApplicationShortcutItem *)shortcutItem  {
if([shortcutItem.type isEqualToString:@"3DQuickActionA"]){
    self.quote_opt.selectedSegmentIndex = 0;    }
if([shortcutItem.type isEqualToString:@"3DQuickActionB"]){
    self.quote_opt.selectedSegmentIndex = 1;    }
}

where quote_opt is the name of my segmented control.

However, this doesn't work. My app launches ok, but just has whatever the last value of quote_opt was as the current option-- the 3D touch actions do nothing. I'm sure I'm missing something, but I don't know what. Does something need to go in viewdidload?

Any advice would be appreciated, and I'm happy to post whatever other portions of code/answer any other questions needed to solve the problem.

Thank you!

Ezraezri answered 21/8, 2017 at 13:51 Comment(2)
quote_opt seems like a switch, are you sure it's already loaded? Maybe you could raise a flag in handleShortcutItem then after loading the view, you could select segment index accordingly.Arianearianie
how would I do that? (sorry, I'm still learning to code)Ezraezri
A
1

You also need to check the launchOptions in didFinishLaunchingWithOptions.

So, as the result of the ongoing chat, here's the latest code:

AppDelegate

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    [FIRApp configure];

    if(launchOptions)
    {
        UIApplicationShortcutItem *selectedItem = [launchOptions objectForKey:UIApplicationLaunchOptionsShortcutItemKey];

        if(selectedItem)
        {
            [self applyShortcutItem:selectedItem];
        }
    }
    return YES;
}

- (void)application:(UIApplication *)application performActionForShortcutItem:(UIApplicationShortcutItem *)shortcutItem completionHandler:(void (^)(BOOL))completionHandler
{
    [self applyShortcutItem:shortcutItem];
}

- (void)applyShortcutItem:(UIApplicationShortcutItem *)shortcutItem
{
    ViewController *rootViewController = (ViewController *)[self.window rootViewController];

    if([shortcutItem.type isEqualToString:@"DogModeShortcut"])
    {
        [rootViewController setShortcutAction:LaunchDogMode];
    }
    else if([shortcutItem.type isEqualToString:@"CatModeShortcut"])
    {
        [rootViewController setShortcutAction:LaunchCatMode];
    }
}
Arianearianie answered 15/9, 2017 at 10:12 Comment(0)
A
1

Note: Before this, you should check if handleShortCutItem is called, and if-cases are working as expected, and self.quote_opt is not nil.

Another Note: 3D's are generally handled in AppDelegate, is this done as such?

Last Note: You may want to take a look at:

- (void)application:(UIApplication *)application performActionForShortcutItem:(UIApplicationShortcutItem *)shortcutItem completionHandler:(void (^)(BOOL))completionHandler

Since 3D actions are handled right after the app is opened, it is highly possible that your view elements are not loaded yet. Hence, you need to save the info from your 3D actions and load accordingly.

You can add a flag in your responsible class and then modify accordingly after the view is loaded.

An enum for easy switch:

// You may add additional items to your enum.

typedef NS_ENUM(NSUInteger, ShortcutAction) {
    ShortcutActionNone,
    ShortcutActionA,
    ShortcutActionB,
};

Handling shortcut:

- (void)handleShortCutItem:(UIApplicationShortcutItem *)shortcutItem
{
    if([shortcutItem.type isEqualToString:@"3DQuickActionA"])
    {
        self.shortcutAction = ShortcutActionA;
    }
    else if([shortcutItem.type isEqualToString:@"3DQuickActionB"])
    {
        self.shortcutAction = ShortcutActionB;
    }
    // self.shortcutAction will be defaulted to 0 -> ShortcutActionNone.
}

Handling Segment Switch:

// You should put this in the interface of your class.

@property ShortcutAction shortcutAction;

// And the implementation:

- (void)viewDidLoad
{
    [super viewDidLoad];

    if(!self.quote_opt)
    {
        // You have other problems, the quote_opt is not initialized yet, or properly.

        NSLog(@"ERR");
    }

    switch(self.shortcutAction)
    {
        case ShortcutActionNone:
        {
            // no-op
            break;
        }
        case ShortcutActionA:
        {
            self.quote_opt.selectedSegmentIndex = 0;

            break;
        }
        case ShortcutActionB:
        {
            self.quote_opt.selectedSegmentIndex = 1;

            break;
        }
    }
}
Arianearianie answered 22/8, 2017 at 11:41 Comment(9)
So everything worked good until I added @property shortcutAction shortcutAction;, it said "unknown type name shortcutAction"Ezraezri
ShortcutAction should be defined where you're adding it (maybe you need to define in multiple places, but I don't advise that), and it should be ShortcutAction, not shortcutAction.Arianearianie
Sorry, I don't follow. It's in the same file (ViewController.m), and putting it anywhere other than with my other @properties causes a host of errors to appear.Ezraezri
I meant the Enum definition, it should be defined before using it as a property. Well, you can also go with an integer if that would be easier.Arianearianie
no I understood that, I just don't know how to define it. would an integer be easier?Ezraezri
It would be better in this situation to see what's the real problem (being unable to set the segment right after 3D touch). FYI, I've already included the definition of enum, too.Arianearianie
ok, so i figured out the problem (enum was below @property in my code). no errors, but it still won't launch in OptionB when that's used. :(Ezraezri
Let us continue this discussion in chat.Arianearianie
This wasn't resolved in chat, adding bounty to question.Ezraezri
A
1

You also need to check the launchOptions in didFinishLaunchingWithOptions.

So, as the result of the ongoing chat, here's the latest code:

AppDelegate

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    [FIRApp configure];

    if(launchOptions)
    {
        UIApplicationShortcutItem *selectedItem = [launchOptions objectForKey:UIApplicationLaunchOptionsShortcutItemKey];

        if(selectedItem)
        {
            [self applyShortcutItem:selectedItem];
        }
    }
    return YES;
}

- (void)application:(UIApplication *)application performActionForShortcutItem:(UIApplicationShortcutItem *)shortcutItem completionHandler:(void (^)(BOOL))completionHandler
{
    [self applyShortcutItem:shortcutItem];
}

- (void)applyShortcutItem:(UIApplicationShortcutItem *)shortcutItem
{
    ViewController *rootViewController = (ViewController *)[self.window rootViewController];

    if([shortcutItem.type isEqualToString:@"DogModeShortcut"])
    {
        [rootViewController setShortcutAction:LaunchDogMode];
    }
    else if([shortcutItem.type isEqualToString:@"CatModeShortcut"])
    {
        [rootViewController setShortcutAction:LaunchCatMode];
    }
}
Arianearianie answered 15/9, 2017 at 10:12 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.