I have added an "App Intents Extension" target to my main application in macOS. This generated the below two files:
TWAppIntent.swift
import AppIntents
struct TWAppIntent: AppIntent {
static var title: LocalizedStringResource = "TWAppIntentExtension"
static var parameterSummary: some ParameterSummary {
Summary("Get information on \(\.$TWType)")
}
//launch app on running action
static var openAppWhenRun: Bool = true
// we can have multiple parameter of diff types
@Parameter(title: "TWType")
var TWType: String
func perform() async throws -> some IntentResult & ReturnsValue<String> & ProvidesDialog {
return .result(value: TWType, dialog: "Logged break.")
}
}
TWAppIntentExtension.swift
import AppIntents
@main
struct TWAppIntentExtension: AppIntentsExtension {
}
I m able to build the extension target and I my intent action is available in the shortcuts app. However, on launching a shortcut with the above created intent action. I m getting the below popups:
I have identified what is causing this error. Setting the openAppWhenRun to true is causing this error. I don't get this when it is set to false. This property is supposed to launch the application, but can someone help me understand why is it happening? This is only causing the error when using this property for AppIntent Extension and not for In app handling for the AppIntent.
Can we not launch our application from AppIntent extension?
Selecting any option will automatically load the page
Post
Replies
Boosts
Views
Activity
in iOS, user can set focus on UItextField and tapping a key in the virtual keyboard updates the text in the textfield. This user action causes the relevant delegates of UITextFieldDelegate to get invoked, i.e the handlers associated with action of user entering some text in the textfield.
I m trying to simulate this user action where I am trying to do this programatically. I want to simulate it in a way such that all the handlers/listeners which otherwise would have been invoked as a result of user typing in the textfield should also get invoked now when i am trying to do it programatically. I have a specific usecase of this in my application.
Below is how I m performing this simulation.
I m manually updating the text field associated(UITextField.text) and updating its value.
And then I m invoking the delegate manually as textField.delegate?.textField?(textField, shouldChangeCharactersIn: nsRange, replacementString: replacementString)
I wanted to know If this is the right way to do this. Is there something better available that can be used, such that simulation has the same affect as the user performing the update?
Hi everyone,
In UIKit, I can detect which key and modifier keys are pressed from an external hardware keyboard using the pressesBegan method in a UIResponder:
override func pressesBegan(_ presses: Set<UIPress>, with event: UIPressesEvent?) {
for press in presses {
if let key = press.key {
print("Key: \(key.charactersIgnoringModifiers ?? "")")
print("Modifiers: \(key.modifierFlags)")
}
}
}
I am now working in SwiftUI (iOS), and I couldn’t find a direct equivalent for pressesBegan.
What is the recommended way in SwiftUI to detect modifier keys + key presses from an external keyboard? Is there a built-in API, or should I always wrap a UIKit view/controller for this purpose?
Thanks in advance!
Hi all,
I’m working on a UIKit app where I embed a SwiftUI TextField using UIHostingController. I’m using an ObservableObject model to drive the textfield content:
class TextFieldModel: ObservableObject {
@Published var text: String
@Published var placeholder: String
@Published var isSecure: Bool
@Published var isFocused: Bool
init(pText: String, pPlaceholder: String, pIsSecure: Bool, pIsFocused: Bool) {
self.text = pText
self.placeholder = pPlaceholder
self.isSecure = pIsSecure
self.isFocused = pIsFocused
}
}
And my SwiftUI view:
struct TextFieldUI: View {
@ObservedObject var pModel: TextFieldModel
@FocusState private var pIsFocusedState: Bool
var body: some View {
TextField(pModel.placeholder, text: $pModel.text)
.focused($pIsFocusedState)
}
}
I embed it in UIKit like this:
let swiftUIContentView = TextFieldUI(pModel: model)
let hostingController = UIHostingController(rootView: swiftUIContentView)
addChild(hostingController)
view.addSubview(hostingController.view)
hostingController.didMove(toParent: self)
Question:
In UIKit, if I subclass UITextField, I can override insertText(_:) and choose not to call super, effectively preventing the textfield from updating when the user types.
Is there a SwiftUI equivalent to intercept and optionally prevent user input in a TextField, especially when it’s embedded inside UIKit?
What is the recommended approach in SwiftUI for this?
I’m running into an issue with TextField focus behavior in SwiftUI.
By default, when I set focus to a TextField programmatically (using @FocusState), SwiftUI behaves like AppKit — the entire contents of the text field are selected. This is causing problems for my use case, because I want the caret placed at the end of the text without selecting everything.
How I solved this in AppKit
In AppKit, I worked around this by subclassing NSTextField and overriding becomeFirstResponder to adjust the editor’s selection:
override func becomeFirstResponder() -> Bool {
let responderStatus = super.becomeFirstResponder()
// Ensure caret is placed at the end, no text selected
if let editor = self.currentEditor() {
let selectedRange = editor.selectedRange
editor.selectedRange = NSRange(location: selectedRange.length, length: 0)
}
return responderStatus
}
This successfully prevented AppKit from auto-selecting the entire string when focus changed.
The problem in SwiftUI
Now I see the same auto-select behavior in SwiftUI when I toggle focus with @FocusState. But unlike AppKit, SwiftUI doesn’t expose the underlying NSTextView or UITextField APIs, so I can’t directly adjust the selection or caret position.
Questions:
Is there a way in SwiftUI to control the caret/selection behavior when a TextField becomes focused?
Is there a built-in modifier or @FocusState trick I’m missing?
Has anyone found a reliable SwiftUI-idiomatic approach to ensure the caret is placed at the end of the text instead of selecting all text?
update:
adding my swiftUI code below:
struct TextFieldUI: View {
@ObservedObject var pModel:TextFieldModel
@FocusState private var pIsFocusedState: Bool
var body: some View {
VStack(spacing: 20) {
TextField(pModel.placeholder, text: $pModel.text)
.textFieldStyle(RoundedBorderTextFieldStyle())
.padding()
.focused($pIsFocusedState)
.onChange(of: pModel.isFocused) { old, newValue in
pIsFocusedState = newValue
}
.onChange(of: pIsFocusedState) { old, newValue in
pModel.isFocused = newValue
}
.onAppear {
pIsFocusedState = pModel.isFocused
}
Toggle("Secure Mode", isOn: $pModel.isSecure)
.padding()
}
.padding()
}
}
I’m trying to transform user keyboard input in a TextField so that, for example, whenever the user types the letter "a" it is stored and shown as the Greek letter "α".
I created a custom Binding to intercept and modify the typed text before saving it to my observable model.
Here’s a simplified version of my code:
import SwiftUI
class User: ObservableObject {
@Published var username: String = ""
}
struct ContentView: View {
@ObservedObject var user = User()
var usernameBinding: Binding<String> {
Binding(
get: { user.username },
set: { newValue in
// Replace all "a" with "α"
user.username = newValue.replacingOccurrences(of: "a", with: "α")
}
)
}
var body: some View {
TextField("Username", text: usernameBinding)
.padding()
.onChange(of: user.username) { newValue in
print("username changed to:", newValue)
}
}
}
When I type "a", I can see in the console that the onChange handler prints the transformed string ("α"), and the model (user.username) is updated.
However, the TextField on screen still shows the original "a" instead of updating to "α" immediately.
I expected the text field to update its displayed value whenever the bound property changes (since username is @Published on an ObservableObject), but that doesn’t seem to happen when I modify the text in the binding’s set closure.
Is this a known limitation of SwiftUI TextField?
Is there a better way to transform user input so the field shows the transformed text based on some processing?
Any advice or explanation would be appreciated.
Hi all,
In my AppKit app, I sometimes simulate events programmatically, for example:
func simulateKeyPress(characters: String, keyCode: UInt16) {
guard let keyDown = NSEvent.keyEvent(
with: .keyDown,
location: .zero,
modifierFlags: [],
timestamp: 0,
windowNumber: NSApp.mainWindow?.windowNumber ?? 0,
context: nil,
characters: characters,
charactersIgnoringModifiers: characters,
isARepeat: false,
keyCode: keyCode
) else { return }
NSApp.postEvent(keyDown, atStart: false)
}
At the same time, I install a local event monitor:
NSEvent.addLocalMonitorForEvents(matching: .any) { event in
// Ideally, detect whether this event came from a real user
// (mouse, keyboard, trackpad, etc.)
// or was programmatically generated via NSEvent + postEvent.
return event
}
The problem:
Events I generate with NSEvent.* factory methods and post using NSApp.postEvent look the same as real system events when received in the monitor.
My question:
Is there a supported way to tell whether an incoming NSEvent is system/user-generated vs programmatically posted?
Hi all,
I’m subclassing UITextView and overriding insertText(_:) to intercept and log input:
class TWTextView: UITextView {
override func insertText(_ text: String) {
print("insertText() : \(text)")
super.insertText(text)
}
}
This works fine, but I’ve noticed that insertText(_:) is invoked both when:
The user types something in the text view (via hardware/software keyboard).
I programmatically call myTextView.insertText("Hello") from my own code.
I’d like to be able to distinguish between these two cases — i.e., know whether the call was triggered by the user or by my own programmatic insert.
Is there any recommended way or system-provided signal to differentiate this?
Thanks in advance!
Hi,
I’m working with custom text input handling in a UITextView. For simulating user typing programmatically, the documented way is to call:
textView.insertText("H")
This correctly inserts text, triggers delegate callbacks, updates the caret, and behaves as expected.
However, since physical keyboard input normally goes through pressesBegan(:with:) before being translated into insertText(:), I was wondering:
Is it possible (or supported) to call pressesBegan ourselves with a constructed UIPress/UIKey to simulate key input events in the same way the system does?
Or
Is the intended approach strictly to use insertText(_:) for simulating text entry, and pressesBegan should only ever be used for listening to actual hardware key presses?
Thanks!
Topic:
UI Frameworks
SubTopic:
UIKit
Hello,
I am building a UIKit application where I need to handle key events in a UITextField with the following requirements:
Normal key presses (e.g. A, B, etc.) should insert characters into the text field.
A hotkey combination (Ctrl+K) should trigger a custom computation that runs on a background thread, and once completed, its result (e.g. $) should be inserted into the text field.
All events (normal keys and hotkeys) must appear in the exact order they were pressed by the user. For example:
If the user types A, B, then Ctrl+K, the field should show AB$.
If the user types A, Ctrl+K, C, the field should show A$C, even if the computation for $ takes longer.
I want strict sequential processing: no later keystroke should be inserted until an earlier hotkey computation finishes.
I have tried overriding pressesBegan(_:with:) in a custom UITextField subclass, and I can detect both normal keys and Ctrl+K.
Questions:
Is there a recommended UIKit API or pattern for handling this kind of ordered key event processing with hotkeys?
Are there best practices for mixing UI updates with background computations in this context, while preserving event order?
Thanks!
Hi,
I came across the following API:
@MainActor
func placeCursor(at position: UITextPosition!, animated: Bool)
From the signature, it seems intended to move the insertion point (caret) to a given UITextPosition, with an option for animation.
However, UITextView and UITextField don’t seem to expose this method as a public member — calling it gives the error:
Value of type 'UITextView' has no member 'placeCursor'
My questions are:
Is placeCursor(at:animated:) a public, supported API that we can safely use in apps?
If not, what is the Apple-recommended way to programmatically move the cursor without animation?
Right now, I only know of updating selectedTextRange, which works but doesn’t involve this placeCursor method. I want to confirm if placeCursor is meant for developer use or is an internal/private API.
Thanks!
I am observing an unexpected behavior with external keyboard input on iOS.
When I press Command + key (e.g., ⌘ + J) while a UITextView is focused, the system invokes
pressesBegan(_ presses: Set<UIPress>, with event: UIPressesEvent?)
twice:
-> Once with the key press event without any modifier flags.
-> A second time with the same key event but including the Command modifier flag.
This behavior is checked on an iPad with an external keyboard.
Additionally, I noticed that textView(_:shouldChangeTextIn:replacementText:) is not invoked in this case, even if I call super.pressesBegan for event propagation.
Questions:
Is it expected that pressesBegan fires twice for a Command + key combination?
If so, what is the recommended way to distinguish between these two invocations?
Should the UITextView delegate methods (like shouldChangeTextIn) be triggered for such key combinations, or is this by design?
I’m trying to understand the exact role of the return value in the UITextFieldDelegate method textFieldShouldReturn(_:).
From my experiments in Xcode, I observed:
Returning true vs false does not seem to cause any visible difference (e.g., the keyboard does not automatically dismiss either way).
I know that in shouldChangeCharactersIn returning true allows the system to insert the character, and returning false prevents it. That’s clear.
For textFieldShouldReturn, my current understanding is that returning true means “let the OS handle the Return press,” and returning false means “I’ll handle it myself.”
My confusion: what is it that the OS actually does when it “handles” the Return press?
Does UIKit do anything beyond calling this delegate method?
If the system is supposed to dismiss the keyboard when returning true, why doesn’t it happen automatically?
I’d appreciate clarification on the expected use of this return value — specifically, what default behavior the system performs (if any) when we return true.
Thanks!
In my SwiftUI iOS app, I need to detect which key (and modifier flags – Command, Option, Shift, Control) a user presses, but I don't want to pre-register them using .keyboardShortcut(_:modifiers:).
My use case is that keyboard shortcuts are user-configurable, so I need to capture the actual key + modifier combination dynamically at runtime and perform the appropriate action based on the user’s settings.
Questions:
What is the recommended way to detect arbitrary key + modifier combinations in SwiftUI on iOS?
Is there a SwiftUI-native solution for this, or should I rely on UIPressesEvent and wrap it with UIViewControllerRepresentable?
If UIKit bridging is necessary, what is the cleanest pattern for integrating this with SwiftUI views (e.g., Buttons)?
Any official guidance or best practices would be greatly appreciated!
I am building a centralized event handling system for UIKit controls and gesture recognizers. My current approach registers events using static methods inside a handler class, like this:
internal class TWOSInternalCommonEventKerneliOS {
internal static func RegisterTouchUpInside(_ pWidget: UIControl) -> Void {
pWidget.addTarget(
TWOSInternalCommonEventKerneliOS.self,
action: #selector(TWOSInternalCommonEventKerneliOS.WidgetTouchUpInsideListener(_:)),
for: .touchUpInside
)
}
@objc
internal static func WidgetTouchUpInsideListener(_ pWidget: UIView) -> Void {
print("WidgetTouchUpInside")
}
}
This works in my testing because the methods are marked @objc and static, but I couldn’t find Apple documentation explicitly confirming whether using ClassName.self (instead of an object instance) is officially supported.
Questions:
Is this approach (passing ClassName.self as the target) recommended or officially supported by UIKit?
If not, what is the safer alternative to achieve a similar pattern, where event registration can remain in static methods but still follow UIKit conventions?
Would using a shared singleton instance as the target (e.g., TWOSInternalCommonEventKerneliOS.shared) be the correct approach, or is there a better pattern?
Looking for official guidance to avoid undefined behavior in production.