Index: win8/metro_driver/ime/text_store.cc |
diff --git a/ui/base/ime/win/tsf_text_store.cc b/win8/metro_driver/ime/text_store.cc |
similarity index 70% |
copy from ui/base/ime/win/tsf_text_store.cc |
copy to win8/metro_driver/ime/text_store.cc |
index 0ef34b5be89a56b649abc9e3a68e1d0ab4392da4..c2f60bbf9210103beb0e0b2f30cb9055b8361a13 100644 |
--- a/ui/base/ime/win/tsf_text_store.cc |
+++ b/win8/metro_driver/ime/text_store.cc |
@@ -1,9 +1,9 @@ |
-// Copyright (c) 2012 The Chromium Authors. All rights reserved. |
+// Copyright (c) 2013 The Chromium Authors. All rights reserved. |
// Use of this source code is governed by a BSD-style license that can be |
// found in the LICENSE file. |
#define INITGUID // required for GUID_PROP_INPUTSCOPE |
-#include "ui/base/ime/win/tsf_text_store.h" |
+#include "win8/metro_driver/ime/text_store.h" |
#include <InputScope.h> |
#include <OleCtl.h> |
@@ -11,11 +11,10 @@ |
#include <algorithm> |
#include "base/win/scoped_variant.h" |
-#include "ui/base/ime/text_input_client.h" |
-#include "ui/base/ime/win/tsf_input_scope.h" |
-#include "ui/gfx/rect.h" |
+#include "win8/metro_driver/ime/input_scope.h" |
+#include "win8/metro_driver/ime/text_store_delegate.h" |
-namespace ui { |
+namespace metro_driver { |
namespace { |
// We support only one view. |
@@ -23,12 +22,16 @@ const TsViewCookie kViewCookie = 1; |
} // namespace |
-TSFTextStore::TSFTextStore() |
+TextStore::TextStore(HWND window_handle, |
+ const std::vector<InputScope>& input_scopes, |
+ TextStoreDelegate* delegate) |
: ref_count_(0), |
text_store_acp_sink_mask_(0), |
- window_handle_(NULL), |
- text_input_client_(NULL), |
+ window_handle_(window_handle), |
+ delegate_(delegate), |
committed_size_(0), |
+ selection_start_(0), |
+ selection_end_(0), |
edit_flag_(false), |
current_lock_type_(0) { |
if (FAILED(category_manager_.CreateInstance(CLSID_TF_CategoryMgr))) { |
@@ -40,16 +43,17 @@ TSFTextStore::TSFTextStore() |
LOG(FATAL) << "Failed to initialize DisplayAttributeMgr."; |
return; |
} |
+ input_scope_ = CreteInputScope(input_scopes); |
} |
-TSFTextStore::~TSFTextStore() { |
+TextStore::~TextStore() { |
} |
-ULONG STDMETHODCALLTYPE TSFTextStore::AddRef() { |
+ULONG STDMETHODCALLTYPE TextStore::AddRef() { |
return InterlockedIncrement(&ref_count_); |
} |
-ULONG STDMETHODCALLTYPE TSFTextStore::Release() { |
+ULONG STDMETHODCALLTYPE TextStore::Release() { |
const LONG count = InterlockedDecrement(&ref_count_); |
if (!count) { |
delete this; |
@@ -58,7 +62,7 @@ ULONG STDMETHODCALLTYPE TSFTextStore::Release() { |
return static_cast<ULONG>(count); |
} |
-STDMETHODIMP TSFTextStore::QueryInterface(REFIID iid, void** result) { |
+STDMETHODIMP TextStore::QueryInterface(REFIID iid, void** result) { |
if (iid == IID_IUnknown || iid == IID_ITextStoreACP) { |
*result = static_cast<ITextStoreACP*>(this); |
} else if (iid == IID_ITfContextOwnerCompositionSink) { |
@@ -73,9 +77,9 @@ STDMETHODIMP TSFTextStore::QueryInterface(REFIID iid, void** result) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::AdviseSink(REFIID iid, |
- IUnknown* unknown, |
- DWORD mask) { |
+STDMETHODIMP TextStore::AdviseSink(REFIID iid, |
+ IUnknown* unknown, |
+ DWORD mask) { |
if (!IsEqualGUID(iid, IID_ITextStoreACPSink)) |
return E_INVALIDARG; |
if (text_store_acp_sink_) { |
@@ -93,7 +97,7 @@ STDMETHODIMP TSFTextStore::AdviseSink(REFIID iid, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::FindNextAttrTransition( |
+STDMETHODIMP TextStore::FindNextAttrTransition( |
LONG acp_start, |
LONG acp_halt, |
ULONG num_filter_attributes, |
@@ -112,17 +116,17 @@ STDMETHODIMP TSFTextStore::FindNextAttrTransition( |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetACPFromPoint(TsViewCookie view_cookie, |
- const POINT* point, |
- DWORD flags, |
- LONG* acp) { |
+STDMETHODIMP TextStore::GetACPFromPoint(TsViewCookie view_cookie, |
+ const POINT* point, |
+ DWORD flags, |
+ LONG* acp) { |
NOTIMPLEMENTED(); |
if (view_cookie != kViewCookie) |
return E_INVALIDARG; |
return E_NOTIMPL; |
} |
-STDMETHODIMP TSFTextStore::GetActiveView(TsViewCookie* view_cookie) { |
+STDMETHODIMP TextStore::GetActiveView(TsViewCookie* view_cookie) { |
if (!view_cookie) |
return E_INVALIDARG; |
// We support only one view. |
@@ -130,10 +134,10 @@ STDMETHODIMP TSFTextStore::GetActiveView(TsViewCookie* view_cookie) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetEmbedded(LONG acp_pos, |
- REFGUID service, |
- REFIID iid, |
- IUnknown** unknown) { |
+STDMETHODIMP TextStore::GetEmbedded(LONG acp_pos, |
+ REFGUID service, |
+ REFIID iid, |
+ IUnknown** unknown) { |
// We don't support any embedded objects. |
NOTIMPLEMENTED(); |
if (!unknown) |
@@ -142,7 +146,7 @@ STDMETHODIMP TSFTextStore::GetEmbedded(LONG acp_pos, |
return E_NOTIMPL; |
} |
-STDMETHODIMP TSFTextStore::GetEndACP(LONG* acp) { |
+STDMETHODIMP TextStore::GetEndACP(LONG* acp) { |
if (!acp) |
return E_INVALIDARG; |
if (!HasReadLock()) |
@@ -151,13 +155,13 @@ STDMETHODIMP TSFTextStore::GetEndACP(LONG* acp) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetFormattedText(LONG acp_start, LONG acp_end, |
+STDMETHODIMP TextStore::GetFormattedText(LONG acp_start, LONG acp_end, |
IDataObject** data_object) { |
NOTIMPLEMENTED(); |
return E_NOTIMPL; |
} |
-STDMETHODIMP TSFTextStore::GetScreenExt(TsViewCookie view_cookie, RECT* rect) { |
+STDMETHODIMP TextStore::GetScreenExt(TsViewCookie view_cookie, RECT* rect) { |
if (view_cookie != kViewCookie) |
return E_INVALIDARG; |
if (!rect) |
@@ -166,13 +170,6 @@ STDMETHODIMP TSFTextStore::GetScreenExt(TsViewCookie view_cookie, RECT* rect) { |
// {0, 0, 0, 0} means that the document rect is not currently displayed. |
SetRect(rect, 0, 0, 0, 0); |
- if (!IsWindow(window_handle_)) |
- return E_FAIL; |
- |
- // Currently ui::TextInputClient does not expose the document rect. So use |
- // the Win32 client rectangle instead. |
- // TODO(yukawa): Upgrade TextInputClient so that the client can retrieve the |
- // document rectangle. |
RECT client_rect = {}; |
if (!GetClientRect(window_handle_, &client_rect)) |
return E_FAIL; |
@@ -190,10 +187,10 @@ STDMETHODIMP TSFTextStore::GetScreenExt(TsViewCookie view_cookie, RECT* rect) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetSelection(ULONG selection_index, |
- ULONG selection_buffer_size, |
- TS_SELECTION_ACP* selection_buffer, |
- ULONG* fetched_count) { |
+STDMETHODIMP TextStore::GetSelection(ULONG selection_index, |
+ ULONG selection_buffer_size, |
+ TS_SELECTION_ACP* selection_buffer, |
+ ULONG* fetched_count) { |
if (!selection_buffer) |
return E_INVALIDARG; |
if (!fetched_count) |
@@ -203,8 +200,8 @@ STDMETHODIMP TSFTextStore::GetSelection(ULONG selection_index, |
*fetched_count = 0; |
if ((selection_buffer_size > 0) && |
((selection_index == 0) || (selection_index == TS_DEFAULT_SELECTION))) { |
- selection_buffer[0].acpStart = selection_.start(); |
- selection_buffer[0].acpEnd = selection_.end(); |
+ selection_buffer[0].acpStart = selection_start_; |
+ selection_buffer[0].acpEnd = selection_end_; |
selection_buffer[0].style.ase = TS_AE_END; |
selection_buffer[0].style.fInterimChar = FALSE; |
*fetched_count = 1; |
@@ -212,7 +209,7 @@ STDMETHODIMP TSFTextStore::GetSelection(ULONG selection_index, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetStatus(TS_STATUS* status) { |
+STDMETHODIMP TextStore::GetStatus(TS_STATUS* status) { |
if (!status) |
return E_INVALIDARG; |
@@ -223,15 +220,15 @@ STDMETHODIMP TSFTextStore::GetStatus(TS_STATUS* status) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetText(LONG acp_start, |
- LONG acp_end, |
- wchar_t* text_buffer, |
- ULONG text_buffer_size, |
- ULONG* text_buffer_copied, |
- TS_RUNINFO* run_info_buffer, |
- ULONG run_info_buffer_size, |
- ULONG* run_info_buffer_copied, |
- LONG* next_acp) { |
+STDMETHODIMP TextStore::GetText(LONG acp_start, |
+ LONG acp_end, |
+ wchar_t* text_buffer, |
+ ULONG text_buffer_size, |
+ ULONG* text_buffer_copied, |
+ TS_RUNINFO* run_info_buffer, |
+ ULONG run_info_buffer_size, |
+ ULONG* run_info_buffer_copied, |
+ LONG* next_acp) { |
if (!text_buffer_copied || !run_info_buffer_copied) |
return E_INVALIDARG; |
if (!text_buffer && text_buffer_size != 0) |
@@ -269,15 +266,13 @@ STDMETHODIMP TSFTextStore::GetText(LONG acp_start, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetTextExt(TsViewCookie view_cookie, |
- LONG acp_start, |
- LONG acp_end, |
- RECT* rect, |
- BOOL* clipped) { |
+STDMETHODIMP TextStore::GetTextExt(TsViewCookie view_cookie, |
+ LONG acp_start, |
+ LONG acp_end, |
+ RECT* rect, |
+ BOOL* clipped) { |
if (!rect || !clipped) |
return E_INVALIDARG; |
- if (!text_input_client_) |
- return E_UNEXPECTED; |
if (view_cookie != kViewCookie) |
return E_INVALIDARG; |
if (!HasReadLock()) |
@@ -293,8 +288,8 @@ STDMETHODIMP TSFTextStore::GetTextExt(TsViewCookie view_cookie, |
// indicates a last character's one. |
// We use RECT instead of gfx::Rect since left position may be bigger than |
// right position when composition has multiple lines. |
- RECT result; |
- gfx::Rect tmp_rect; |
+ RECT result = {}; |
+ RECT tmp_rect = {}; |
const uint32 start_pos = acp_start - committed_size_; |
const uint32 end_pos = acp_end - committed_size_; |
@@ -305,34 +300,27 @@ STDMETHODIMP TSFTextStore::GetTextExt(TsViewCookie view_cookie, |
// But when using Pinin IME of Windows 8, this method is called with the |
// equal values of |acp_start| and |acp_end|. So we handle this condition. |
if (start_pos == 0) { |
- if (text_input_client_->GetCompositionCharacterBounds(0, &tmp_rect)) { |
- tmp_rect.set_width(0); |
- result = tmp_rect.ToRECT(); |
+ if (delegate_->GetCompositionCharacterBounds(0, &tmp_rect)) { |
+ tmp_rect.right = tmp_rect.right; |
+ result = tmp_rect; |
} else if (string_buffer_.size() == committed_size_) { |
- result = text_input_client_->GetCaretBounds().ToRECT(); |
+ result = delegate_->GetCaretBounds(); |
} else { |
return TS_E_NOLAYOUT; |
} |
- } else if (text_input_client_->GetCompositionCharacterBounds(start_pos - 1, |
- &tmp_rect)) { |
- result.left = tmp_rect.right(); |
- result.right = tmp_rect.right(); |
- result.top = tmp_rect.y(); |
- result.bottom = tmp_rect.bottom(); |
+ } else if (delegate_->GetCompositionCharacterBounds(start_pos - 1, |
+ &tmp_rect)) { |
+ tmp_rect.left = tmp_rect.right; |
+ result = tmp_rect; |
} else { |
return TS_E_NOLAYOUT; |
} |
} else { |
- if (text_input_client_->GetCompositionCharacterBounds(start_pos, |
- &tmp_rect)) { |
- result.left = tmp_rect.x(); |
- result.top = tmp_rect.y(); |
- result.right = tmp_rect.right(); |
- result.bottom = tmp_rect.bottom(); |
- if (text_input_client_->GetCompositionCharacterBounds(end_pos - 1, |
- &tmp_rect)) { |
- result.right = tmp_rect.right(); |
- result.bottom = tmp_rect.bottom(); |
+ if (delegate_->GetCompositionCharacterBounds(start_pos, &tmp_rect)) { |
+ result = tmp_rect; |
+ if (delegate_->GetCompositionCharacterBounds(end_pos - 1, &tmp_rect)) { |
+ result.right = tmp_rect.right; |
+ result.bottom = tmp_rect.bottom; |
} else { |
// We may not be able to get the last character bounds, so we use the |
// first character bounds instead of returning TS_E_NOLAYOUT. |
@@ -342,7 +330,7 @@ STDMETHODIMP TSFTextStore::GetTextExt(TsViewCookie view_cookie, |
// it's better to return previous caret rectangle instead. |
// TODO(nona, kinaba): Remove this hack. |
if (start_pos == 0) { |
- result = text_input_client_->GetCaretBounds().ToRECT(); |
+ result = delegate_->GetCaretBounds(); |
} else { |
return TS_E_NOLAYOUT; |
} |
@@ -354,7 +342,7 @@ STDMETHODIMP TSFTextStore::GetTextExt(TsViewCookie view_cookie, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::GetWnd(TsViewCookie view_cookie, |
+STDMETHODIMP TextStore::GetWnd(TsViewCookie view_cookie, |
HWND* window_handle) { |
if (!window_handle) |
return E_INVALIDARG; |
@@ -364,7 +352,7 @@ STDMETHODIMP TSFTextStore::GetWnd(TsViewCookie view_cookie, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::InsertEmbedded(DWORD flags, |
+STDMETHODIMP TextStore::InsertEmbedded(DWORD flags, |
LONG acp_start, |
LONG acp_end, |
IDataObject* data_object, |
@@ -374,7 +362,7 @@ STDMETHODIMP TSFTextStore::InsertEmbedded(DWORD flags, |
return E_NOTIMPL; |
} |
-STDMETHODIMP TSFTextStore::InsertEmbeddedAtSelection(DWORD flags, |
+STDMETHODIMP TextStore::InsertEmbeddedAtSelection(DWORD flags, |
IDataObject* data_object, |
LONG* acp_start, |
LONG* acp_end, |
@@ -384,14 +372,14 @@ STDMETHODIMP TSFTextStore::InsertEmbeddedAtSelection(DWORD flags, |
return E_NOTIMPL; |
} |
-STDMETHODIMP TSFTextStore::InsertTextAtSelection(DWORD flags, |
+STDMETHODIMP TextStore::InsertTextAtSelection(DWORD flags, |
const wchar_t* text_buffer, |
ULONG text_buffer_size, |
LONG* acp_start, |
LONG* acp_end, |
TS_TEXTCHANGE* text_change) { |
- const LONG start_pos = selection_.start(); |
- const LONG end_pos = selection_.end(); |
+ const LONG start_pos = selection_start_; |
+ const LONG end_pos = selection_end_; |
const LONG new_end_pos = start_pos + text_buffer_size; |
if (flags & TS_IAS_QUERYONLY) { |
@@ -399,9 +387,8 @@ STDMETHODIMP TSFTextStore::InsertTextAtSelection(DWORD flags, |
return TS_E_NOLOCK; |
if (acp_start) |
*acp_start = start_pos; |
- if (acp_end) { |
+ if (acp_end) |
*acp_end = end_pos; |
- } |
return S_OK; |
} |
@@ -423,12 +410,12 @@ STDMETHODIMP TSFTextStore::InsertTextAtSelection(DWORD flags, |
text_change->acpOldEnd = end_pos; |
text_change->acpNewEnd = new_end_pos; |
} |
- selection_.set_start(start_pos); |
- selection_.set_end(new_end_pos); |
+ selection_start_ = start_pos; |
+ selection_end_ = new_end_pos; |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::QueryInsert( |
+STDMETHODIMP TextStore::QueryInsert( |
LONG acp_test_start, |
LONG acp_test_end, |
ULONG text_size, |
@@ -445,7 +432,7 @@ STDMETHODIMP TSFTextStore::QueryInsert( |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::QueryInsertEmbedded(const GUID* service, |
+STDMETHODIMP TextStore::QueryInsertEmbedded(const GUID* service, |
const FORMATETC* format, |
BOOL* insertable) { |
if (!format) |
@@ -456,7 +443,7 @@ STDMETHODIMP TSFTextStore::QueryInsertEmbedded(const GUID* service, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::RequestAttrsAtPosition( |
+STDMETHODIMP TextStore::RequestAttrsAtPosition( |
LONG acp_pos, |
ULONG attribute_buffer_size, |
const TS_ATTRID* attribute_buffer, |
@@ -467,7 +454,7 @@ STDMETHODIMP TSFTextStore::RequestAttrsAtPosition( |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::RequestAttrsTransitioningAtPosition( |
+STDMETHODIMP TextStore::RequestAttrsTransitioningAtPosition( |
LONG acp_pos, |
ULONG attribute_buffer_size, |
const TS_ATTRID* attribute_buffer, |
@@ -478,7 +465,7 @@ STDMETHODIMP TSFTextStore::RequestAttrsTransitioningAtPosition( |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::RequestLock(DWORD lock_flags, HRESULT* result) { |
+STDMETHODIMP TextStore::RequestLock(DWORD lock_flags, HRESULT* result) { |
if (!text_store_acp_sink_.get()) |
return E_FAIL; |
if (!result) |
@@ -516,12 +503,12 @@ STDMETHODIMP TSFTextStore::RequestLock(DWORD lock_flags, HRESULT* result) { |
current_lock_type_ = 0; |
} |
- if (!edit_flag_) { |
+ if (!edit_flag_) |
return S_OK; |
- } |
// If the text store is edited in OnLockGranted(), we may need to call |
- // TextInputClient::InsertText() or TextInputClient::SetCompositionText(). |
+ // TextStoreDelegate::ConfirmComposition() or |
+ // TextStoreDelegate::SetComposition(). |
const size_t new_committed_size = committed_size_; |
const string16& new_committed_string = |
string_buffer_.substr(last_committed_size, |
@@ -529,47 +516,42 @@ STDMETHODIMP TSFTextStore::RequestLock(DWORD lock_flags, HRESULT* result) { |
const string16& composition_string = |
string_buffer_.substr(new_committed_size); |
- // If there is new committed string, calls TextInputClient::InsertText(). |
- if ((!new_committed_string.empty()) && text_input_client_) { |
- text_input_client_->InsertText(new_committed_string); |
- } |
- |
- // Calls TextInputClient::SetCompositionText(). |
- CompositionText composition_text; |
- composition_text.text = composition_string; |
- composition_text.underlines = composition_undelines_; |
- // Adjusts the offset. |
- for (size_t i = 0; i < composition_text.underlines.size(); ++i) { |
- composition_text.underlines[i].start_offset -= new_committed_size; |
- composition_text.underlines[i].end_offset -= new_committed_size; |
- } |
- if (selection_.start() < new_committed_size) { |
- composition_text.selection.set_start(0); |
- } else { |
- composition_text.selection.set_start( |
- selection_.start() - new_committed_size); |
- } |
- if (selection_.end() < new_committed_size) { |
- composition_text.selection.set_end(0); |
- } else { |
- composition_text.selection.set_end(selection_.end() - new_committed_size); |
+ if (delegate_) { |
+ // If there is new committed string, calls |
+ // TextStoreDelegate::ConfirmComposition(). |
+ if ((!new_committed_string.empty())) |
+ delegate_->OnTextCommitted(new_committed_string); |
+ |
+ // Calls TextInputClient::SetCompositionText(). |
+ std::vector<metro_viewer::UnderlineInfo> underlines = underlines_; |
+ // Adjusts the offset. |
+ for (size_t i = 0; i < underlines_.size(); ++i) { |
+ underlines[i].start_offset -= new_committed_size; |
+ underlines[i].end_offset -= new_committed_size; |
+ } |
+ int32 selection_start = 0; |
+ int32 selection_end = 0; |
+ if (selection_start_ >= new_committed_size) |
+ selection_start = selection_start_ - new_committed_size; |
+ if (selection_end_ >= new_committed_size) |
+ selection_end = selection_end_ - new_committed_size; |
+ delegate_->OnCompositionChanged( |
+ composition_string, selection_start, selection_end, underlines); |
} |
- if (text_input_client_) |
- text_input_client_->SetCompositionText(composition_text); |
// If there is no composition string, clear the text store status. |
// And call OnSelectionChange(), OnLayoutChange(), and OnTextChange(). |
if ((composition_string.empty()) && (new_committed_size != 0)) { |
string_buffer_.clear(); |
committed_size_ = 0; |
- selection_.set_start(0); |
- selection_.set_end(0); |
+ selection_start_ = 0; |
+ selection_end_ = 0; |
if (text_store_acp_sink_mask_ & TS_AS_SEL_CHANGE) |
text_store_acp_sink_->OnSelectionChange(); |
if (text_store_acp_sink_mask_ & TS_AS_LAYOUT_CHANGE) |
text_store_acp_sink_->OnLayoutChange(TS_LC_CHANGE, 0); |
if (text_store_acp_sink_mask_ & TS_AS_TEXT_CHANGE) { |
- TS_TEXTCHANGE textChange; |
+ TS_TEXTCHANGE textChange = {}; |
textChange.acpStart = 0; |
textChange.acpOldEnd = new_committed_size; |
textChange.acpNewEnd = 0; |
@@ -580,13 +562,13 @@ STDMETHODIMP TSFTextStore::RequestLock(DWORD lock_flags, HRESULT* result) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::RequestSupportedAttrs( |
+STDMETHODIMP TextStore::RequestSupportedAttrs( |
DWORD /* flags */, // Seems that we should ignore this. |
ULONG attribute_buffer_size, |
const TS_ATTRID* attribute_buffer) { |
if (!attribute_buffer) |
return E_INVALIDARG; |
- if (!text_input_client_) |
+ if (!input_scope_) |
return E_FAIL; |
// We support only input scope attribute. |
for (size_t i = 0; i < attribute_buffer_size; ++i) { |
@@ -596,33 +578,32 @@ STDMETHODIMP TSFTextStore::RequestSupportedAttrs( |
return E_FAIL; |
} |
-STDMETHODIMP TSFTextStore::RetrieveRequestedAttrs( |
+STDMETHODIMP TextStore::RetrieveRequestedAttrs( |
ULONG attribute_buffer_size, |
TS_ATTRVAL* attribute_buffer, |
ULONG* attribute_buffer_copied) { |
if (!attribute_buffer_copied) |
return E_INVALIDARG; |
+ *attribute_buffer_copied = 0; |
if (!attribute_buffer) |
return E_INVALIDARG; |
- if (!text_input_client_) |
- return E_UNEXPECTED; |
+ if (!input_scope_) |
+ return E_FAIL; |
// We support only input scope attribute. |
- *attribute_buffer_copied = 0; |
if (attribute_buffer_size == 0) |
return S_OK; |
attribute_buffer[0].dwOverlapId = 0; |
attribute_buffer[0].idAttr = GUID_PROP_INPUTSCOPE; |
attribute_buffer[0].varValue.vt = VT_UNKNOWN; |
- attribute_buffer[0].varValue.punkVal = tsf_inputscope::CreateInputScope( |
- text_input_client_->GetTextInputType(), |
- text_input_client_->GetTextInputMode()); |
+ attribute_buffer[0].varValue.punkVal = input_scope_; |
attribute_buffer[0].varValue.punkVal->AddRef(); |
*attribute_buffer_copied = 1; |
+ |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::SetSelection( |
+STDMETHODIMP TextStore::SetSelection( |
ULONG selection_buffer_size, |
const TS_SELECTION_ACP* selection_buffer) { |
if (!HasReadWriteLock()) |
@@ -635,18 +616,18 @@ STDMETHODIMP TSFTextStore::SetSelection( |
(end_pos <= static_cast<LONG>(string_buffer_.size())))) { |
return TF_E_INVALIDPOS; |
} |
- selection_.set_start(start_pos); |
- selection_.set_end(end_pos); |
+ selection_start_ = start_pos; |
+ selection_end_ = end_pos; |
} |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::SetText(DWORD flags, |
- LONG acp_start, |
- LONG acp_end, |
- const wchar_t* text_buffer, |
- ULONG text_buffer_size, |
- TS_TEXTCHANGE* text_change) { |
+STDMETHODIMP TextStore::SetText(DWORD flags, |
+ LONG acp_start, |
+ LONG acp_end, |
+ const wchar_t* text_buffer, |
+ ULONG text_buffer_size, |
+ TS_TEXTCHANGE* text_change) { |
if (!HasReadWriteLock()) |
return TS_E_NOLOCK; |
if (!((static_cast<LONG>(committed_size_) <= acp_start) && |
@@ -655,20 +636,19 @@ STDMETHODIMP TSFTextStore::SetText(DWORD flags, |
return TS_E_INVALIDPOS; |
} |
- TS_SELECTION_ACP selection; |
+ TS_SELECTION_ACP selection = {}; |
selection.acpStart = acp_start; |
selection.acpEnd = acp_end; |
selection.style.ase = TS_AE_NONE; |
selection.style.fInterimChar = 0; |
- HRESULT ret; |
- ret = SetSelection(1, &selection); |
+ HRESULT ret = SetSelection(1, &selection); |
if (ret != S_OK) |
return ret; |
TS_TEXTCHANGE change; |
- ret = InsertTextAtSelection(0, text_buffer, text_buffer_size, |
- &acp_start, &acp_end, &change); |
+ ret = InsertTextAtSelection( |
+ 0, text_buffer, text_buffer_size, &acp_start, &acp_end, &change); |
if (ret != S_OK) |
return ret; |
@@ -678,7 +658,7 @@ STDMETHODIMP TSFTextStore::SetText(DWORD flags, |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::UnadviseSink(IUnknown* unknown) { |
+STDMETHODIMP TextStore::UnadviseSink(IUnknown* unknown) { |
if (!text_store_acp_sink_.IsSameObject(unknown)) |
return CONNECT_E_NOCONNECTION; |
text_store_acp_sink_.Release(); |
@@ -686,7 +666,7 @@ STDMETHODIMP TSFTextStore::UnadviseSink(IUnknown* unknown) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::OnStartComposition( |
+STDMETHODIMP TextStore::OnStartComposition( |
ITfCompositionView* composition_view, |
BOOL* ok) { |
if (ok) |
@@ -694,37 +674,33 @@ STDMETHODIMP TSFTextStore::OnStartComposition( |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::OnUpdateComposition( |
+STDMETHODIMP TextStore::OnUpdateComposition( |
ITfCompositionView* composition_view, |
ITfRange* range) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::OnEndComposition( |
+STDMETHODIMP TextStore::OnEndComposition( |
ITfCompositionView* composition_view) { |
return S_OK; |
} |
-STDMETHODIMP TSFTextStore::OnEndEdit(ITfContext* context, |
- TfEditCookie read_only_edit_cookie, |
- ITfEditRecord* edit_record) { |
+STDMETHODIMP TextStore::OnEndEdit(ITfContext* context, |
+ TfEditCookie read_only_edit_cookie, |
+ ITfEditRecord* edit_record) { |
if (!context || !edit_record) |
return E_INVALIDARG; |
- |
- size_t committed_size; |
- CompositionUnderlines undelines; |
- if (!GetCompositionStatus(context, read_only_edit_cookie, &committed_size, |
- &undelines)) { |
+ if (!GetCompositionStatus(context, read_only_edit_cookie, &committed_size_, |
+ &underlines_)) { |
+ // TODO(yukawa): Error handling. |
return S_OK; |
} |
- composition_undelines_ = undelines; |
- committed_size_ = committed_size; |
edit_flag_ = true; |
return S_OK; |
} |
-bool TSFTextStore::GetDisplayAttribute(TfGuidAtom guid_atom, |
- TF_DISPLAYATTRIBUTE* attribute) { |
+bool TextStore::GetDisplayAttribute(TfGuidAtom guid_atom, |
+ TF_DISPLAYATTRIBUTE* attribute) { |
GUID guid; |
if (FAILED(category_manager_->GetGUID(guid_atom, &guid))) |
return false; |
@@ -737,17 +713,17 @@ bool TSFTextStore::GetDisplayAttribute(TfGuidAtom guid_atom, |
return SUCCEEDED(display_attribute_info->GetAttributeInfo(attribute)); |
} |
-bool TSFTextStore::GetCompositionStatus( |
+bool TextStore::GetCompositionStatus( |
ITfContext* context, |
const TfEditCookie read_only_edit_cookie, |
size_t* committed_size, |
- CompositionUnderlines* undelines) { |
+ std::vector<metro_viewer::UnderlineInfo>* undelines) { |
DCHECK(context); |
DCHECK(committed_size); |
DCHECK(undelines); |
- const GUID* rgGuids[2] = {&GUID_PROP_COMPOSING, &GUID_PROP_ATTRIBUTE}; |
+ const GUID* kTargetGuids[2] = {&GUID_PROP_COMPOSING, &GUID_PROP_ATTRIBUTE}; |
base::win::ScopedComPtr<ITfReadOnlyProperty> track_property; |
- if (FAILED(context->TrackProperties(rgGuids, 2, NULL, 0, |
+ if (FAILED(context->TrackProperties(kTargetGuids, 2, NULL, 0, |
track_property.Receive()))) { |
return false; |
} |
@@ -786,7 +762,7 @@ bool TSFTextStore::GetCompositionStatus( |
if (FAILED(enum_prop_value.QueryFrom(value.AsInput()->punkVal))) |
return false; |
- TF_PROPERTYVAL property_value; |
+ TF_PROPERTYVAL property_value = {}; |
bool is_composition = false; |
bool has_display_attribute = false; |
TF_DISPLAYATTRIBUTE display_attribute; |
@@ -810,34 +786,17 @@ bool TSFTextStore::GetCompositionStatus( |
if (*committed_size < static_cast<size_t>(start_pos + length)) |
*committed_size = start_pos + length; |
} else { |
- CompositionUnderline underline; |
+ metro_viewer::UnderlineInfo underline; |
underline.start_offset = start_pos; |
underline.end_offset = start_pos + length; |
- underline.color = SK_ColorBLACK; |
- if (has_display_attribute) |
- underline.thick = !!display_attribute.fBoldLine; |
+ underline.thick = !!display_attribute.fBoldLine; |
undelines->push_back(underline); |
} |
} |
return true; |
} |
-void TSFTextStore::SetFocusedTextInputClient( |
- HWND focused_window, |
- TextInputClient* text_input_client) { |
- window_handle_ = focused_window; |
- text_input_client_ = text_input_client; |
-} |
- |
-void TSFTextStore::RemoveFocusedTextInputClient( |
- TextInputClient* text_input_client) { |
- if (text_input_client_ == text_input_client) { |
- window_handle_ = NULL; |
- text_input_client_ = NULL; |
- } |
-} |
- |
-bool TSFTextStore::CancelComposition() { |
+bool TextStore::CancelComposition() { |
// If there is an on-going document lock, we must not edit the text. |
if (edit_flag_) |
return false; |
@@ -856,8 +815,8 @@ bool TSFTextStore::CancelComposition() { |
const size_t previous_buffer_size = string_buffer_.size(); |
string_buffer_.clear(); |
committed_size_ = 0; |
- selection_.set_start(0); |
- selection_.set_end(0); |
+ selection_start_ = 0; |
+ selection_end_ = 0; |
if (text_store_acp_sink_mask_ & TS_AS_SEL_CHANGE) |
text_store_acp_sink_->OnSelectionChange(); |
if (text_store_acp_sink_mask_ & TS_AS_LAYOUT_CHANGE) |
@@ -872,7 +831,7 @@ bool TSFTextStore::CancelComposition() { |
return true; |
} |
-bool TSFTextStore::ConfirmComposition() { |
+bool TextStore::ConfirmComposition() { |
// If there is an on-going document lock, we must not edit the text. |
if (edit_flag_) |
return false; |
@@ -880,19 +839,19 @@ bool TSFTextStore::ConfirmComposition() { |
if (string_buffer_.empty()) |
return true; |
- // See the comment in TSFTextStore::CancelComposition. |
+ // See the comment in TextStore::CancelComposition. |
// This logic is based on the observation about how to emulate |
// ImmNotifyIME(NI_COMPOSITIONSTR, CPS_COMPLETE, 0) by CUAS. |
const string16& composition_text = string_buffer_.substr(committed_size_); |
if (!composition_text.empty()) |
- text_input_client_->InsertText(composition_text); |
+ delegate_->OnTextCommitted(composition_text); |
const size_t previous_buffer_size = string_buffer_.size(); |
string_buffer_.clear(); |
committed_size_ = 0; |
- selection_.set_start(0); |
- selection_.set_end(0); |
+ selection_start_ = 0; |
+ selection_end_ = 0; |
if (text_store_acp_sink_mask_ & TS_AS_SEL_CHANGE) |
text_store_acp_sink_->OnSelectionChange(); |
if (text_store_acp_sink_mask_ & TS_AS_LAYOUT_CHANGE) |
@@ -907,17 +866,17 @@ bool TSFTextStore::ConfirmComposition() { |
return true; |
} |
-void TSFTextStore::SendOnLayoutChange() { |
+void TextStore::SendOnLayoutChange() { |
if (text_store_acp_sink_ && (text_store_acp_sink_mask_ & TS_AS_LAYOUT_CHANGE)) |
text_store_acp_sink_->OnLayoutChange(TS_LC_CHANGE, 0); |
} |
-bool TSFTextStore::HasReadLock() const { |
+bool TextStore::HasReadLock() const { |
return (current_lock_type_ & TS_LF_READ) == TS_LF_READ; |
} |
-bool TSFTextStore::HasReadWriteLock() const { |
+bool TextStore::HasReadWriteLock() const { |
return (current_lock_type_ & TS_LF_READWRITE) == TS_LF_READWRITE; |
} |
-} // namespace ui |
+} // namespace metro_driver |