objective kits development developer apple app cocoa nstextfield nspopover

cocoa - kits - No se puede editar NSTextField en NSPopover aunque se haya establecido un comportamiento editable



xcode kits (8)

Tengo una aplicación, que abre popover con NSTextField . El campo de texto no es editable. El comportamiento del campo de texto se establece en Editable . Todavía puedo pegar y copiar texto en este campo, pero no puedo editarlo.

Alguien sabe, ¿qué puede estar mal?


Definitivamente un error. Ese informe de error es exactamente lo que estaba tratando de hacer. Incluso hasta la creación del elemento de estado y el mousdown primordial.

Puedo confirmar que la respuesta de Balazs Toth funciona. Solo me pregunto si podría interponerse en el camino.



La respuesta de Balazs Toth funciona, pero si está adjuntando el popover a NSStatusItem.view, el ítem de estado deja de responder, requiriendo dos clics para enfocar.


Lo que encontré al trabajar con esta solución es que cuando NSStatusItem deja de responder, puede anular fácilmente este comportamiento como este

- (BOOL)canBecomeKeyWindow { if([self class]==NSClassFromString(@"NSStatusBarWindow")) { CBStatusBarView* view = [((CBAppDelegate*)[NSApp delegate]) statusItemView]; if(![view isActive]) return NO; } return YES; }

Verificará la clase de la ventana, si coincide con NSStatusBarWindow , podemos verificar de alguna manera si NSStatusItem está activo. Si es así, eso significa que tenemos que devolver SÍ, porque de esta manera el NSPopover de NSStatusItem tendrá todos los eventos del teclado.

Lo que estoy usando para comprobar si se hizo clic en NSStatusItem (o está activo) es que en mi propia vista personalizada tengo un valor bool que cambia cuando el usuario hace clic en NSStatusItem , el sistema busca automáticamente "canBecomeKeyWindow" y cuando lo hace devolverá NO y después de que el usuario haga clic en él (mientras devuelve el NO ) cambiará el valor bool y devolverá SÍ cuando el sistema lo solicite nuevamente (cuando se hace clic en NSPopover para la edición NSTextField ).

Sidenotes :

  • CBStatusBarView es mi vista personalizada para NSStatusItem
  • CBAppDelegate es mi clase de delegado de aplicaciones

Luché con esto por un tiempo también, hasta que me di cuenta de que era un error.

Sin embargo, en lugar de confiar en un estado isActive de una vista NSStatusItem, me parece mucho más confiable utilizar la propiedad isShown del NSPopover que ha implementado.

En mi código, tengo un NSPopover en NSViewController:

- (BOOL)canBecomeKeyWindow { if([self class]==NSClassFromString(@"NSStatusBarWindow")) { NSPopover *mainPopover = [[((AppDelegate*)[NSApp delegate]) mainViewController] mainPopover]; if(![mainPopover isShown]) return NO; } return YES; }


Si alguien lo consigue y la solución anterior no le hizo el truco. El problema en mi aplicación estaba en la pestaña de info en los targets mi aplicación estaba configurada para

Application is background only = true

y shulde de estado

Application is agent = true

Pasé un día entero en esto.


Si alguien todavía está buscando una respuesta a esto, estoy trabajando en Swift.

En el momento en que desea que el campo permita la entrada de texto, he utilizado myTextField.becomeFirstReponder()

Para darse de baja; solo use myTextField.resignFirstResponder()


No estoy seguro de si todavía necesita la respuesta, pero puede haber otros que todavía estén buscando. Encontré una solución en los foros de desarrolladores de Apple. Citando al autor original:

El principal problema es la forma en que funcionan los eventos del teclado. Aunque NSTextField (y todas sus supervistas) recibe eventos de teclado, no realiza ninguna acción. Eso sucede porque la vista donde está conectado el popover está en una ventana que no puede convertirse en una ventana clave. No puede acceder a esa ventana de ninguna manera, al menos no pude. Entonces, la solución reemplaza el método canBecomeKeyWindow para cada NSWindow en nuestra aplicación usando una categoría.

NSWindow+canBecomeKeyWindow.h @interface NSWindow (canBecomeKeyWindow) @end NSWindow+canBecomeKeyWindow.m @implementation NSWindow (canBecomeKeyWindow) //This is to fix a bug with 10.7 where an NSPopover with a text field cannot be edited if its parent window won''t become key //The pragma statements disable the corresponding warning for overriding an already-implemented method #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wobjc-protocol-method-implementation" - (BOOL)canBecomeKeyWindow { return YES; } #pragma clang diagnostic pop @end

Eso hace que el popover sea completamente resposivo. Si necesita otra ventana que responda NO a canBecomeKeyWindow, siempre puede hacer una subclase.