Chromium Code Reviews| Index: ui/views/cocoa/bridged_content_view.mm |
| diff --git a/ui/views/cocoa/bridged_content_view.mm b/ui/views/cocoa/bridged_content_view.mm |
| index fda514016bf89e228e0b7ea3c044b6b6e1a5d5d3..4af2aeaf14d1ba24343c537af5ac49f9f6c683f7 100644 |
| --- a/ui/views/cocoa/bridged_content_view.mm |
| +++ b/ui/views/cocoa/bridged_content_view.mm |
| @@ -5,7 +5,14 @@ |
| #import "ui/views/cocoa/bridged_content_view.h" |
| #include "base/logging.h" |
| +#include "base/strings/sys_string_conversions.h" |
| +#include "grit/ui_strings.h" |
| +#include "ui/accessibility/ax_view_state.h" |
| +#include "ui/base/ime/text_input_client.h" |
| +#include "ui/gfx/canvas.h" |
| #include "ui/gfx/canvas_paint_mac.h" |
| +#include "ui/gfx/geometry/rect.h" |
| +#import "ui/views/cocoa/bridged_native_widget.h" |
| #include "ui/views/view.h" |
| #include "ui/views/widget/widget.h" |
| @@ -15,27 +22,40 @@ |
| // the event to NativeWidgetMac for handling. |
| - (void)handleMouseEvent:(NSEvent*)theEvent; |
| +// Execute a command on the currently focused TextInputClient. |
|
tapted
2014/06/19 01:29:16
nit: mention that |commandId| should be a resource
Andre
2014/06/19 23:20:26
Done.
|
| +- (void)doCommandByID:(int)commandId; |
| + |
| @end |
| @implementation BridgedContentView |
| @synthesize hostedView = hostedView_; |
| +@synthesize textInputClient = textInputClient_; |
| -- (id)initWithView:(views::View*)viewToHost { |
| +- (id)initWithView:(views::View*)viewToHost |
| + parent:(views::BridgedNativeWidget*)parent { |
| DCHECK(viewToHost); |
| + DCHECK(parent); |
| gfx::Rect bounds = viewToHost->bounds(); |
| // To keep things simple, assume the origin is (0, 0) until there exists a use |
| // case for something other than that. |
| DCHECK(bounds.origin().IsOrigin()); |
| NSRect initialFrame = NSMakeRect(0, 0, bounds.width(), bounds.height()); |
| - if ((self = [super initWithFrame:initialFrame])) |
| + if ((self = [super initWithFrame:initialFrame])) { |
| hostedView_ = viewToHost; |
| - |
| + parent_ = parent; |
| + if (hostedView_->GetFocusManager()) |
| + hostedView_->GetFocusManager()->AddFocusChangeListener(parent_); |
|
tapted
2014/06/19 01:29:15
Hm - I just looked at this some more. Does this al
Andre
2014/06/19 23:20:26
I like it, moved this to BridgedNativeWidget.
|
| + } |
| return self; |
| } |
| - (void)clearView { |
| - hostedView_ = NULL; |
| + if (hostedView_) { |
|
tapted
2014/06/19 01:29:16
if (!hostedView_)
return;
or perhaps even
DCHE
Andre
2014/06/19 23:20:26
Removed this change from the patch.
|
| + if (hostedView_->GetFocusManager()) |
|
tapted
2014/06/19 01:29:16
note that we'll have to ensure the lifetime of thi
|
| + hostedView_->GetFocusManager()->RemoveFocusChangeListener(parent_); |
| + hostedView_ = NULL; |
| + } |
| } |
| // BridgedContentView private implementation. |
| @@ -48,8 +68,17 @@ |
| hostedView_->GetWidget()->OnMouseEvent(&event); |
| } |
| +- (void)doCommandByID:(int)commandId { |
| + if (textInputClient_ && textInputClient_->IsEditingCommandEnabled(commandId)) |
| + textInputClient_->ExecuteEditingCommand(commandId); |
| +} |
| + |
| // NSView implementation. |
| +- (BOOL)acceptsFirstResponder { |
| + return YES; |
| +} |
| + |
| - (void)setFrameSize:(NSSize)newSize { |
| [super setFrameSize:newSize]; |
| if (!hostedView_) |
| @@ -118,4 +147,116 @@ |
| [self handleMouseEvent:theEvent]; |
| } |
| +- (void)keyDown:(NSEvent*)theEvent { |
| + if (textInputClient_) |
| + [self interpretKeyEvents:@[ theEvent ]]; |
| + else |
| + [super keyDown:theEvent]; |
| +} |
| + |
| +- (void)deleteBackward:(id)sender { |
| + [self doCommandByID:IDS_DELETE_BACKWARD]; |
| +} |
| + |
| +- (void)deleteForward:(id)sender { |
| + [self doCommandByID:IDS_DELETE_FORWARD]; |
| +} |
| + |
| +- (void)moveLeft:(id)sender { |
| + [self doCommandByID:IDS_MOVE_LEFT]; |
| +} |
| + |
| +- (void)moveRight:(id)sender { |
| + [self doCommandByID:IDS_MOVE_RIGHT]; |
| +} |
| + |
| +// NSTextInputClient protocol implementation. |
| + |
| +- (NSAttributedString*) |
| + attributedSubstringForProposedRange:(NSRange)range |
| + actualRange:(NSRangePointer)actualRange { |
| + base::string16 substring; |
| + if (textInputClient_) { |
| + gfx::Range textRange; |
| + textInputClient_->GetTextRange(&textRange); |
| + gfx::Range subrange = textRange.Intersect(gfx::Range(range)); |
| + textInputClient_->GetTextFromRange(subrange, &substring); |
| + if (actualRange) |
| + *actualRange = subrange.ToNSRange(); |
| + } |
| + return [[[NSAttributedString alloc] |
| + initWithString:base::SysUTF16ToNSString(substring)] autorelease]; |
| +} |
| + |
| +- (NSUInteger)characterIndexForPoint:(NSPoint)aPoint { |
| + NOTIMPLEMENTED(); |
| + return 0; |
| +} |
| + |
| +- (void)doCommandBySelector:(SEL)selector { |
| + if ([self respondsToSelector:selector]) |
| + [self performSelector:selector withObject:nil]; |
| + else |
| + [[self nextResponder] doCommandBySelector:selector]; |
| +} |
| + |
| +- (NSRect)firstRectForCharacterRange:(NSRange)range |
| + actualRange:(NSRangePointer)actualRange { |
| + NOTIMPLEMENTED(); |
| + return NSZeroRect; |
| +} |
| + |
| +- (BOOL)hasMarkedText { |
| + return textInputClient_ && textInputClient_->HasCompositionText(); |
| +} |
| + |
| +- (void)insertText:(id)text replacementRange:(NSRange)replacementRange { |
| + if (textInputClient_) { |
| + if ([text isKindOfClass:[NSAttributedString class]]) |
| + text = [text string]; |
| + textInputClient_->DeleteRange(gfx::Range(replacementRange)); |
| + textInputClient_->InsertText(base::SysNSStringToUTF16(text)); |
| + } |
| +} |
| + |
| +- (NSRange)markedRange { |
| + if (!textInputClient_) |
| + return NSMakeRange(0, 0); |
|
tapted
2014/06/19 01:29:16
oops - my bad. this should be NSMakeRange(NSNotFou
Andre
2014/06/19 23:20:26
Done.
|
| + |
| + gfx::Range range; |
| + textInputClient_->GetCompositionTextRange(&range); |
| + return range.ToNSRange(); |
| +} |
| + |
| +- (NSRange)selectedRange { |
| + if (!textInputClient_) |
| + return NSMakeRange(0, 0); |
| + |
| + gfx::Range range; |
| + textInputClient_->GetSelectionRange(&range); |
| + return range.ToNSRange(); |
| +} |
| + |
| +- (void)setMarkedText:(id)text |
| + selectedRange:(NSRange)selectedRange |
| + replacementRange:(NSRange)replacementRange { |
| + if (textInputClient_) { |
|
tapted
2014/06/19 01:29:16
same here - prefer early return / less indenting
Andre
2014/06/19 23:20:26
Done.
|
| + if ([text isKindOfClass:[NSAttributedString class]]) |
| + text = [text string]; |
| + ui::CompositionText composition; |
| + composition.text = base::SysNSStringToUTF16(text); |
| + composition.selection = gfx::Range(selectedRange); |
| + textInputClient_->SetCompositionText(composition); |
| + } |
| +} |
| + |
| +- (void)unmarkText { |
| + if (textInputClient_) |
| + textInputClient_->ConfirmCompositionText(); |
| +} |
| + |
| +- (NSArray*)validAttributesForMarkedText { |
| + return @[]; |
| +} |
| + |
| @end |