swiftswiftuiappintentsapp-shortcut

Provide example parameter in a Siri Tip View


I am implementing iOS16 App Shortcuts. I am using SiriTipView to show users the possibilities.

My AddItem intent has a parameter for which Box entity to add the Item to. The shortcut will prompt for this.

@available(iOS 16.0, *)
struct MyShortcuts: AppShortcutsProvider { 
    @AppShortcutsBuilder static var appShortcuts: [AppShortcut] {  
        AppShortcut(intent: AddItem(), phrases: [
            "Add new item to \(\.$box) in \(.applicationName)",
            "Add new item in \(.applicationName)",
        ],
            shortTitle: "Add New Item",
            systemImageName: "pills"
        )
    }
}

I would like to add an example Box (from the user's existing data, like I do for the disambiguation) to the SiriTipView.

Currently, the tip view does not fill in the entity placeholder:

"Add new item to ${box} in <My App Name>"

The tip view is defined like this.

SiriTipView(intent: AddItem())

I realise I could just change the topmost phrase and have it use the phrase without the parameter, but I think it would be useful to the user to see that they can speak the box parameter.

I tried initialising the tip view with an IntentParameter like this:

SiriTipView(intent: AddItem(box: IntentParameter<BoxAppEntity>))

But I could not figure out how to just give it an example box entity. I guess I need to know how to initialise an IntentParameter with a concrete entity.


Solution

  • I found that with many of the IntentParameter initialisers, the name of my concrete entity was being ignored, or there were compile time errors.

    In the end, I had to set the wrappedValue like this.

    func getIntentParameter() -> IntentParameter<BoxAppEntity?> {
        let parameter = IntentParameter<BoxAppEntity?>(title: "Example Parameter")
        parameter.wrappedValue = BoxAppEntity(id: "boxID", displayString: "Box Name")
        return parameter
    }
    

    Then I used this in the SiriTipView:

    SiriTipView(intent: AddItem(box: getIntentParameter()))
    

    In the getIntentParameter method I can simply set the displayString based on some arbitrary user data.