2010-06-24 4 views
9

Versuchen, die ausgewählte Texthintergrundfarbe für ein NSTextField zu ändern (wir haben eine dunkle UI, und ausgewählter Texthintergrund ist fast der selbe wie der Text selbst), aber nur NSTextView scheint uns zu erlauben, dies zu ändern.Fälschen ein NSTextField mit einem NSTextView, um schöne Färbung zu bekommen?

Also versuchen wir, ein NSTextField mit einem NSTextView zu fälschen, aber nicht Text scrollen, um das gleiche zu arbeiten.

Die nächstgelegene wir mit diesem Code erhalten ist:

NSTextView *tf = [ [ NSTextView alloc ] initWithFrame: NSMakeRect(30.0, 20.0, 80.0, 22.0) ]; 

// Dark UI 
[tf setTextColor:[NSColor whiteColor]]; 
[tf setBackgroundColor:[NSColor darkGrayColor]]; 

// Fixed size 
[tf setVerticallyResizable:FALSE]; 
[tf setHorizontallyResizable:FALSE]; 

[tf setAlignment:NSRightTextAlignment]; // Make it right-aligned (yup, we need this too) 

[[tf textContainer] setContainerSize:NSMakeSize(2000, 20)]; // Try to Avoid line wrapping with this ugly hack 
[tf setFieldEditor:TRUE]; // Make Return key accept the textfield 

// Set text properties 
NSMutableDictionary *dict = [[[tf selectedTextAttributes] mutableCopy ] autorelease]; 
[dict setObject:[NSColor orangeColor] forKey:NSBackgroundColorAttributeName]; 
[tf setSelectedTextAttributes:dict]; 

Das funktioniert fast in Ordnung, mit der Ausnahme, dass, wenn der Text länger als das Textfeld ist, können Sie nicht in irgendeiner Art und Weise bewegen können.

Irgendeine Idee, wie dies zu erreichen ist?

Vielen Dank im Voraus

Edit: Lösung unterhalb von Joshua Nozzi

vorgeschlagen Joshua

Dank, das ist eine große Lösung zu dem, was ich suchte:

@interface ColoredTextField : NSTextField 
- (BOOL)becomeFirstResponder; 
@end 

@implementation ColoredTextField 
- (BOOL)becomeFirstResponder 
{ 
    if (![super becomeFirstResponder]) 
     return NO; 

    NSDictionary * attributes = [NSDictionary dictionaryWithObjectsAndKeys : 
        [NSColor orangeColor], NSBackgroundColorAttributeName, nil]; 

    NSTextView * fieldEditor = (NSTextView *)[[self window] fieldEditor:YES forObject:self]; 
    [fieldEditor setSelectedTextAttributes:attributes]; 
    return YES; 
} 
@end 

Statt fälschen Mit NSTextView ist es nur ein NSTextField, das die ausgewählte Textfarbe ändert, wenn es Ersthelfer wird.

Bearbeiten: Der obige Code fällt auf die Standardauswahlfarbe zurück, sobald Sie die Eingabetaste im Textfeld drücken. Hier ist ein Weg, das zu vermeiden.

@interface ColoredTextField : NSTextField 
- (BOOL)becomeFirstResponder; 
- (void)textDidEndEditing:(NSNotification *)notification; 

- (void)setSelectedColor; 
@end 

@implementation ColoredTextField 
- (BOOL)becomeFirstResponder 
{ 
    if (![super becomeFirstResponder]) 
     return NO; 
    [self setSelectedColor]; 
    return YES; 
} 

- (void)textDidEndEditing:(NSNotification *)notification 
{ 
    [super textDidEndEditing:notification]; 
    [self setSelectedColor]; 
} 

- (void) setSelectedColor 
{ 
    NSDictionary * attributes = [NSDictionary dictionaryWithObjectsAndKeys : 
           [NSColor orangeColor], NSBackgroundColorAttributeName, nil]; 

    NSTextView * fieldEditor = (NSTextView *)[[self window] fieldEditor:YES forObject:self]; 
    [fieldEditor setSelectedTextAttributes:attributes]; 
} 
@end 

Antwort

6

Warum nicht einfach die Eigenschaften des Textfelds gesetzt field editor direkt, wenn das Feld becomes first responder?

In einem typischen Textfeld ist die Auswahl nur dann sichtbar, wenn das Feld First Responder ist, also, wenn Sie für das Textfeld Feldeditor fragen, stellen Sie dann seine ausgewählten Textattribute Sie die gleichen Auswirkungen auf bekäme, wouldn Bist du?

NSDictionary * attributes = [NSDictionary dictionaryWithObjectsAndKeys: 
    [NSColor orangeColor], NSBackgroundColorAttributeName, nil]; 
NSTextView * fieldEditor = (NSTextView *)[[self window] fieldEditor:YES 
    forObject:textField]; 
[fieldEditor setSelectedTextAttributes:attributes]; 

Hinweis: Wie unten in den Kommentaren diskutiert, die Dokumentation ist richtig zu sagen, das Feld Editor eine Instanz von NSTextView ist, aber die - [NSWindow fieldEditor: forObject:] Methode beansprucht eine NSText zurückzukehren (NSTextView's sofortige Superklasse). Wenn Sie planen, die NSTextView-only-Methoden des Feldeditors zu senden, müssen Sie sie als NSTextView umwandeln, um die Warnungen des Compilers zu unterdrücken. Das Casting wird nichts in Ihrem Code brechen, sollte der Methodenprototyp in der Zukunft korrigiert werden, damit er sicher an seinem Platz bleibt.

+0

Werfen Sie einen Blick auf diese Antwort auf eine andere Frage. Es zeigt, wie man den Feld-Editor für ein NSTokenField manipuliert (was eine Unterklasse von NSTextField ist, so dass es genau so funktioniert). http://stackoverflow.com/questions/2995205/prevent-selecting-all-tokens-in-nstokenfield –

+0

Der Feldeditor des Textfelds ist ein NSText-Objekt, und diese Klasse verfügt nicht über die setSelectedTextAttributes-Methode. Wenn ich etwas nicht vermisse, scheint es nicht so zu sein. – hasvn

+0

@hasvn: Dies ist verwirrend ... der Prototyp für '- [NSWindow fieldEditor: forObject:]' sagt, dass es 'NSText *' zurückgibt, aber die Dokumentation sagt, dass der Feldeditor ein NSTextView-Objekt ist. – JWWalker