blob: b962e6d937b91eb46bd06ce9f74ac179003e8fee [file] [log] [blame]
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001// Copyright 2014 PDFium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
Lei Zhanga6d9f0e2015-06-13 00:48:38 -07004
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07005// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6
Dan Sinclairc411eb92017-07-25 09:39:30 -04007#include "fpdfsdk/pwl/cpwl_edit_impl.h"
Lei Zhangc2fb35f2016-01-05 16:46:58 -08008
Lei Zhang375a8642016-01-11 11:59:17 -08009#include <algorithm>
thestigd4c34f22016-09-28 17:04:51 -070010#include <memory>
Henrique Nakashima2e2da132017-06-27 13:43:22 -040011#include <sstream>
thestigd4c34f22016-09-28 17:04:51 -070012#include <utility>
Lei Zhang375a8642016-01-11 11:59:17 -080013
dsinclairbc5e6d22016-10-04 11:08:49 -070014#include "core/fpdfapi/font/cpdf_font.h"
dsinclair41872fa2016-10-04 11:29:35 -070015#include "core/fpdfapi/page/cpdf_pageobject.h"
16#include "core/fpdfapi/page/cpdf_pageobjectholder.h"
17#include "core/fpdfapi/page/cpdf_pathobject.h"
18#include "core/fpdfapi/page/cpdf_textobject.h"
dsinclair488b7ad2016-10-04 11:55:50 -070019#include "core/fpdfapi/parser/fpdf_parser_decode.h"
dsinclair69d9c682016-10-04 12:18:35 -070020#include "core/fpdfapi/render/cpdf_renderoptions.h"
21#include "core/fpdfapi/render/cpdf_textrenderer.h"
dsinclair1727aee2016-09-29 13:12:56 -070022#include "core/fpdfdoc/cpvt_section.h"
23#include "core/fpdfdoc/cpvt_word.h"
24#include "core/fpdfdoc/ipvt_fontmap.h"
Dan Sinclairf51a02a2017-04-19 12:46:53 -040025#include "core/fxcrt/fx_codepage.h"
dsinclair74a34fc2016-09-29 16:41:42 -070026#include "core/fxge/cfx_graphstatedata.h"
27#include "core/fxge/cfx_pathdata.h"
28#include "core/fxge/cfx_renderdevice.h"
dsinclaire35af1e2016-07-13 11:26:20 -070029#include "fpdfsdk/cfx_systemhandler.h"
Dan Sinclairc411eb92017-07-25 09:39:30 -040030#include "fpdfsdk/pwl/cpwl_edit.h"
31#include "fpdfsdk/pwl/cpwl_edit_ctrl.h"
32#include "fpdfsdk/pwl/cpwl_scroll_bar.h"
tsepez36eb4bd2016-10-03 15:24:27 -070033#include "third_party/base/ptr_util.h"
Tom Sepez3509d162017-01-30 13:22:02 -080034#include "third_party/base/stl_util.h"
dsinclaire35af1e2016-07-13 11:26:20 -070035
dsinclair8f4bf9a2016-05-04 13:51:51 -070036namespace {
37
38const int kEditUndoMaxItems = 10000;
39
dsinclaire35af1e2016-07-13 11:26:20 -070040void DrawTextString(CFX_RenderDevice* pDevice,
Dan Sinclairf528eee2017-02-14 11:52:07 -050041 const CFX_PointF& pt,
dsinclaire35af1e2016-07-13 11:26:20 -070042 CPDF_Font* pFont,
Dan Sinclair05df0752017-03-14 14:43:42 -040043 float fFontSize,
dsinclaire35af1e2016-07-13 11:26:20 -070044 CFX_Matrix* pUser2Device,
45 const CFX_ByteString& str,
46 FX_ARGB crTextFill,
dsinclaire35af1e2016-07-13 11:26:20 -070047 int32_t nHorzScale) {
Dan Sinclaira0061af2017-02-23 09:25:17 -050048 CFX_PointF pos = pUser2Device->Transform(pt);
dsinclaire35af1e2016-07-13 11:26:20 -070049
50 if (pFont) {
51 if (nHorzScale != 100) {
52 CFX_Matrix mt(nHorzScale / 100.0f, 0, 0, 1, 0, 0);
53 mt.Concat(*pUser2Device);
54
55 CPDF_RenderOptions ro;
56 ro.m_Flags = RENDER_CLEARTYPE;
Dan Sinclairf55e72e2017-07-13 14:53:28 -040057 ro.m_ColorMode = CPDF_RenderOptions::kNormal;
dsinclaire35af1e2016-07-13 11:26:20 -070058
Dan Sinclaira0061af2017-02-23 09:25:17 -050059 CPDF_TextRenderer::DrawTextString(pDevice, pos.x, pos.y, pFont, fFontSize,
60 &mt, str, crTextFill, nullptr, &ro);
dsinclaire35af1e2016-07-13 11:26:20 -070061 } else {
62 CPDF_RenderOptions ro;
63 ro.m_Flags = RENDER_CLEARTYPE;
Dan Sinclairf55e72e2017-07-13 14:53:28 -040064 ro.m_ColorMode = CPDF_RenderOptions::kNormal;
dsinclaire35af1e2016-07-13 11:26:20 -070065
Dan Sinclaira0061af2017-02-23 09:25:17 -050066 CPDF_TextRenderer::DrawTextString(pDevice, pos.x, pos.y, pFont, fFontSize,
67 pUser2Device, str, crTextFill, nullptr,
68 &ro);
dsinclaire35af1e2016-07-13 11:26:20 -070069 }
70 }
71}
72
dsinclair8f4bf9a2016-05-04 13:51:51 -070073} // namespace
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070074
Dan Sinclair6b0158f2017-07-24 09:42:55 -040075CPWL_EditImpl_Iterator::CPWL_EditImpl_Iterator(
76 CPWL_EditImpl* pEdit,
77 CPDF_VariableText::Iterator* pVTIterator)
Nico Weber9d8ec5a2015-08-04 13:00:21 -070078 : m_pEdit(pEdit), m_pVTIterator(pVTIterator) {}
79
Dan Sinclair6b0158f2017-07-24 09:42:55 -040080CPWL_EditImpl_Iterator::~CPWL_EditImpl_Iterator() {}
Nico Weber9d8ec5a2015-08-04 13:00:21 -070081
Dan Sinclair6b0158f2017-07-24 09:42:55 -040082bool CPWL_EditImpl_Iterator::NextWord() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -070083 return m_pVTIterator->NextWord();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070084}
85
Dan Sinclair6b0158f2017-07-24 09:42:55 -040086bool CPWL_EditImpl_Iterator::PrevWord() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -070087 return m_pVTIterator->PrevWord();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070088}
89
Dan Sinclair6b0158f2017-07-24 09:42:55 -040090bool CPWL_EditImpl_Iterator::GetWord(CPVT_Word& word) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -070091 ASSERT(m_pEdit);
92
93 if (m_pVTIterator->GetWord(word)) {
94 word.ptWord = m_pEdit->VTToEdit(word.ptWord);
tsepez4cf55152016-11-02 14:37:54 -070095 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -070096 }
tsepez4cf55152016-11-02 14:37:54 -070097 return false;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070098}
99
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400100bool CPWL_EditImpl_Iterator::GetLine(CPVT_Line& line) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700101 ASSERT(m_pEdit);
102
103 if (m_pVTIterator->GetLine(line)) {
104 line.ptLine = m_pEdit->VTToEdit(line.ptLine);
tsepez4cf55152016-11-02 14:37:54 -0700105 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700106 }
tsepez4cf55152016-11-02 14:37:54 -0700107 return false;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700108}
109
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400110void CPWL_EditImpl_Iterator::SetAt(int32_t nWordIndex) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700111 m_pVTIterator->SetAt(nWordIndex);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700112}
113
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400114void CPWL_EditImpl_Iterator::SetAt(const CPVT_WordPlace& place) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700115 m_pVTIterator->SetAt(place);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700116}
117
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400118const CPVT_WordPlace& CPWL_EditImpl_Iterator::GetAt() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700119 return m_pVTIterator->GetAt();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700120}
121
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400122CPWL_EditImpl_Provider::CPWL_EditImpl_Provider(IPVT_FontMap* pFontMap)
dsinclairc7a73492016-04-05 12:01:42 -0700123 : CPDF_VariableText::Provider(pFontMap), m_pFontMap(pFontMap) {
Lei Zhang96660d62015-12-14 18:27:25 -0800124 ASSERT(m_pFontMap);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700125}
126
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400127CPWL_EditImpl_Provider::~CPWL_EditImpl_Provider() {}
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700128
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400129IPVT_FontMap* CPWL_EditImpl_Provider::GetFontMap() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700130 return m_pFontMap;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700131}
132
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400133int32_t CPWL_EditImpl_Provider::GetCharWidth(int32_t nFontIndex,
134 uint16_t word) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700135 if (CPDF_Font* pPDFFont = m_pFontMap->GetPDFFont(nFontIndex)) {
tsepezc3255f52016-03-25 14:52:27 -0700136 uint32_t charcode = word;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700137
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700138 if (pPDFFont->IsUnicodeCompatible())
139 charcode = pPDFFont->CharCodeFromUnicode(word);
140 else
141 charcode = m_pFontMap->CharCodeFromUnicode(nFontIndex, word);
142
Wei Li89409932016-03-28 10:33:33 -0700143 if (charcode != CPDF_Font::kInvalidCharCode)
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700144 return pPDFFont->GetCharWidthF(charcode);
145 }
146
147 return 0;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700148}
149
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400150int32_t CPWL_EditImpl_Provider::GetTypeAscent(int32_t nFontIndex) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700151 if (CPDF_Font* pPDFFont = m_pFontMap->GetPDFFont(nFontIndex))
152 return pPDFFont->GetTypeAscent();
153
154 return 0;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700155}
156
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400157int32_t CPWL_EditImpl_Provider::GetTypeDescent(int32_t nFontIndex) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700158 if (CPDF_Font* pPDFFont = m_pFontMap->GetPDFFont(nFontIndex))
159 return pPDFFont->GetTypeDescent();
160
161 return 0;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700162}
163
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400164int32_t CPWL_EditImpl_Provider::GetWordFontIndex(uint16_t word,
165 int32_t charset,
166 int32_t nFontIndex) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700167 return m_pFontMap->GetWordFontIndex(word, charset, nFontIndex);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700168}
169
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400170int32_t CPWL_EditImpl_Provider::GetDefaultFontIndex() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700171 return 0;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700172}
173
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400174bool CPWL_EditImpl_Provider::IsLatinWord(uint16_t word) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700175 return FX_EDIT_ISLATINWORD(word);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700176}
177
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400178CPWL_EditImpl_Refresh::CPWL_EditImpl_Refresh() {}
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700179
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400180CPWL_EditImpl_Refresh::~CPWL_EditImpl_Refresh() {}
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700181
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400182void CPWL_EditImpl_Refresh::BeginRefresh() {
Tom Sepez3509d162017-01-30 13:22:02 -0800183 m_RefreshRects.Clear();
184 m_OldLineRects = std::move(m_NewLineRects);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700185}
186
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400187void CPWL_EditImpl_Refresh::Push(const CPVT_WordRange& linerange,
188 const CFX_FloatRect& rect) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700189 m_NewLineRects.Add(linerange, rect);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700190}
191
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400192void CPWL_EditImpl_Refresh::NoAnalyse() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700193 {
194 for (int32_t i = 0, sz = m_OldLineRects.GetSize(); i < sz; i++)
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400195 if (CPWL_EditImpl_LineRect* pOldRect = m_OldLineRects.GetAt(i))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700196 m_RefreshRects.Add(pOldRect->m_rcLine);
197 }
198
199 {
200 for (int32_t i = 0, sz = m_NewLineRects.GetSize(); i < sz; i++)
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400201 if (CPWL_EditImpl_LineRect* pNewRect = m_NewLineRects.GetAt(i))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700202 m_RefreshRects.Add(pNewRect->m_rcLine);
203 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700204}
205
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400206const CPWL_EditImpl_RectArray* CPWL_EditImpl_Refresh::GetRefreshRects() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700207 return &m_RefreshRects;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700208}
209
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400210void CPWL_EditImpl_Refresh::EndRefresh() {
Tom Sepez3509d162017-01-30 13:22:02 -0800211 m_RefreshRects.Clear();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700212}
213
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400214CPWL_EditImpl_Undo::CPWL_EditImpl_Undo(int32_t nBufsize)
215 : m_nCurUndoPos(0), m_nBufSize(nBufsize), m_bWorking(false) {}
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700216
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400217CPWL_EditImpl_Undo::~CPWL_EditImpl_Undo() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700218 Reset();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700219}
220
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400221bool CPWL_EditImpl_Undo::CanUndo() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700222 return m_nCurUndoPos > 0;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700223}
224
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400225void CPWL_EditImpl_Undo::Undo() {
tsepez4cf55152016-11-02 14:37:54 -0700226 m_bWorking = true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700227 if (m_nCurUndoPos > 0) {
Tom Sepez3509d162017-01-30 13:22:02 -0800228 m_UndoItemStack[m_nCurUndoPos - 1]->Undo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700229 m_nCurUndoPos--;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700230 }
tsepez4cf55152016-11-02 14:37:54 -0700231 m_bWorking = false;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700232}
233
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400234bool CPWL_EditImpl_Undo::CanRedo() const {
Tom Sepez3509d162017-01-30 13:22:02 -0800235 return m_nCurUndoPos < m_UndoItemStack.size();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700236}
237
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400238void CPWL_EditImpl_Undo::Redo() {
tsepez4cf55152016-11-02 14:37:54 -0700239 m_bWorking = true;
Tom Sepez3509d162017-01-30 13:22:02 -0800240 if (m_nCurUndoPos < m_UndoItemStack.size()) {
241 m_UndoItemStack[m_nCurUndoPos]->Redo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700242 m_nCurUndoPos++;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700243 }
tsepez4cf55152016-11-02 14:37:54 -0700244 m_bWorking = false;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700245}
246
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400247void CPWL_EditImpl_Undo::AddItem(std::unique_ptr<IFX_Edit_UndoItem> pItem) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700248 ASSERT(!m_bWorking);
Lei Zhang96660d62015-12-14 18:27:25 -0800249 ASSERT(pItem);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700250 ASSERT(m_nBufSize > 1);
Tom Sepez3509d162017-01-30 13:22:02 -0800251 if (m_nCurUndoPos < m_UndoItemStack.size())
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700252 RemoveTails();
253
Lei Zhang1a89e362017-03-23 15:27:25 -0700254 if (m_UndoItemStack.size() >= m_nBufSize)
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700255 RemoveHeads();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700256
Tom Sepez3509d162017-01-30 13:22:02 -0800257 m_UndoItemStack.push_back(std::move(pItem));
258 m_nCurUndoPos = m_UndoItemStack.size();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700259}
260
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400261void CPWL_EditImpl_Undo::RemoveHeads() {
Tom Sepez3509d162017-01-30 13:22:02 -0800262 ASSERT(m_UndoItemStack.size() > 1);
263 m_UndoItemStack.pop_front();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700264}
265
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400266void CPWL_EditImpl_Undo::RemoveTails() {
Tom Sepez3509d162017-01-30 13:22:02 -0800267 while (m_UndoItemStack.size() > m_nCurUndoPos)
268 m_UndoItemStack.pop_back();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700269}
270
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400271void CPWL_EditImpl_Undo::Reset() {
Tom Sepez3509d162017-01-30 13:22:02 -0800272 m_UndoItemStack.clear();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700273 m_nCurUndoPos = 0;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700274}
275
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400276CPWL_EditImpl_UndoItem::CPWL_EditImpl_UndoItem()
277 : m_bFirst(true), m_bLast(true) {}
weili625ad662016-06-15 11:21:33 -0700278
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400279CPWL_EditImpl_UndoItem::~CPWL_EditImpl_UndoItem() {}
weili625ad662016-06-15 11:21:33 -0700280
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400281CFX_WideString CPWL_EditImpl_UndoItem::GetUndoTitle() const {
Tom Sepez3509d162017-01-30 13:22:02 -0800282 return CFX_WideString();
weili625ad662016-06-15 11:21:33 -0700283}
284
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400285void CPWL_EditImpl_UndoItem::SetFirst(bool bFirst) {
weili625ad662016-06-15 11:21:33 -0700286 m_bFirst = bFirst;
287}
288
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400289void CPWL_EditImpl_UndoItem::SetLast(bool bLast) {
weili625ad662016-06-15 11:21:33 -0700290 m_bLast = bLast;
291}
292
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400293bool CPWL_EditImpl_UndoItem::IsLast() {
weili625ad662016-06-15 11:21:33 -0700294 return m_bLast;
295}
296
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400297CFXEU_InsertWord::CFXEU_InsertWord(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700298 const CPVT_WordPlace& wpOldPlace,
299 const CPVT_WordPlace& wpNewPlace,
Tom Sepez62a70f92016-03-21 15:00:20 -0700300 uint16_t word,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700301 int32_t charset,
302 const CPVT_WordProps* pWordProps)
303 : m_pEdit(pEdit),
304 m_wpOld(wpOldPlace),
305 m_wpNew(wpNewPlace),
306 m_Word(word),
307 m_nCharset(charset),
308 m_WordProps() {
309 if (pWordProps)
310 m_WordProps = *pWordProps;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700311}
312
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700313CFXEU_InsertWord::~CFXEU_InsertWord() {}
314
315void CFXEU_InsertWord::Redo() {
316 if (m_pEdit) {
317 m_pEdit->SelectNone();
318 m_pEdit->SetCaret(m_wpOld);
tsepez4cf55152016-11-02 14:37:54 -0700319 m_pEdit->InsertWord(m_Word, m_nCharset, &m_WordProps, false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700320 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700321}
322
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700323void CFXEU_InsertWord::Undo() {
324 if (m_pEdit) {
325 m_pEdit->SelectNone();
326 m_pEdit->SetCaret(m_wpNew);
tsepez4cf55152016-11-02 14:37:54 -0700327 m_pEdit->Backspace(false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700328 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700329}
330
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400331CFXEU_InsertReturn::CFXEU_InsertReturn(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700332 const CPVT_WordPlace& wpOldPlace,
333 const CPVT_WordPlace& wpNewPlace,
334 const CPVT_SecProps* pSecProps,
335 const CPVT_WordProps* pWordProps)
336 : m_pEdit(pEdit),
337 m_wpOld(wpOldPlace),
338 m_wpNew(wpNewPlace),
339 m_SecProps(),
340 m_WordProps() {
341 if (pSecProps)
342 m_SecProps = *pSecProps;
343 if (pWordProps)
344 m_WordProps = *pWordProps;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700345}
346
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700347CFXEU_InsertReturn::~CFXEU_InsertReturn() {}
348
349void CFXEU_InsertReturn::Redo() {
350 if (m_pEdit) {
351 m_pEdit->SelectNone();
352 m_pEdit->SetCaret(m_wpOld);
tsepez4cf55152016-11-02 14:37:54 -0700353 m_pEdit->InsertReturn(&m_SecProps, &m_WordProps, false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700354 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700355}
356
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700357void CFXEU_InsertReturn::Undo() {
358 if (m_pEdit) {
359 m_pEdit->SelectNone();
360 m_pEdit->SetCaret(m_wpNew);
tsepez4cf55152016-11-02 14:37:54 -0700361 m_pEdit->Backspace(false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700362 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700363}
364
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400365CFXEU_Backspace::CFXEU_Backspace(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700366 const CPVT_WordPlace& wpOldPlace,
367 const CPVT_WordPlace& wpNewPlace,
Tom Sepez62a70f92016-03-21 15:00:20 -0700368 uint16_t word,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700369 int32_t charset,
370 const CPVT_SecProps& SecProps,
371 const CPVT_WordProps& WordProps)
372 : m_pEdit(pEdit),
373 m_wpOld(wpOldPlace),
374 m_wpNew(wpNewPlace),
375 m_Word(word),
376 m_nCharset(charset),
377 m_SecProps(SecProps),
378 m_WordProps(WordProps) {}
379
380CFXEU_Backspace::~CFXEU_Backspace() {}
381
382void CFXEU_Backspace::Redo() {
Tom Sepez52f69b32017-03-21 13:42:38 -0700383 if (!m_pEdit)
384 return;
385
386 m_pEdit->SelectNone();
387 m_pEdit->SetCaret(m_wpOld);
388 m_pEdit->Backspace(false, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700389}
390
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700391void CFXEU_Backspace::Undo() {
Tom Sepez52f69b32017-03-21 13:42:38 -0700392 if (!m_pEdit)
393 return;
394
395 m_pEdit->SelectNone();
396 m_pEdit->SetCaret(m_wpNew);
397 if (m_wpNew.nSecIndex != m_wpOld.nSecIndex)
398 m_pEdit->InsertReturn(&m_SecProps, &m_WordProps, false, true);
399 else
400 m_pEdit->InsertWord(m_Word, m_nCharset, &m_WordProps, false, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700401}
402
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400403CFXEU_Delete::CFXEU_Delete(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700404 const CPVT_WordPlace& wpOldPlace,
405 const CPVT_WordPlace& wpNewPlace,
Tom Sepez62a70f92016-03-21 15:00:20 -0700406 uint16_t word,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700407 int32_t charset,
408 const CPVT_SecProps& SecProps,
409 const CPVT_WordProps& WordProps,
tsepez4cf55152016-11-02 14:37:54 -0700410 bool bSecEnd)
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700411 : m_pEdit(pEdit),
412 m_wpOld(wpOldPlace),
413 m_wpNew(wpNewPlace),
414 m_Word(word),
415 m_nCharset(charset),
416 m_SecProps(SecProps),
417 m_WordProps(WordProps),
418 m_bSecEnd(bSecEnd) {}
419
420CFXEU_Delete::~CFXEU_Delete() {}
421
422void CFXEU_Delete::Redo() {
423 if (m_pEdit) {
424 m_pEdit->SelectNone();
425 m_pEdit->SetCaret(m_wpOld);
tsepez4cf55152016-11-02 14:37:54 -0700426 m_pEdit->Delete(false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700427 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700428}
429
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700430void CFXEU_Delete::Undo() {
431 if (m_pEdit) {
432 m_pEdit->SelectNone();
433 m_pEdit->SetCaret(m_wpNew);
434 if (m_bSecEnd) {
tsepez4cf55152016-11-02 14:37:54 -0700435 m_pEdit->InsertReturn(&m_SecProps, &m_WordProps, false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700436 } else {
tsepez4cf55152016-11-02 14:37:54 -0700437 m_pEdit->InsertWord(m_Word, m_nCharset, &m_WordProps, false, true);
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700438 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700439 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700440}
441
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400442CFXEU_Clear::CFXEU_Clear(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700443 const CPVT_WordRange& wrSel,
444 const CFX_WideString& swText)
445 : m_pEdit(pEdit), m_wrSel(wrSel), m_swText(swText) {}
446
447CFXEU_Clear::~CFXEU_Clear() {}
448
449void CFXEU_Clear::Redo() {
450 if (m_pEdit) {
451 m_pEdit->SelectNone();
Diana Gage4d02e902017-07-20 17:20:31 -0700452 m_pEdit->SetSelection(m_wrSel.BeginPos, m_wrSel.EndPos);
tsepez4cf55152016-11-02 14:37:54 -0700453 m_pEdit->Clear(false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700454 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700455}
456
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700457void CFXEU_Clear::Undo() {
458 if (m_pEdit) {
459 m_pEdit->SelectNone();
460 m_pEdit->SetCaret(m_wrSel.BeginPos);
Dan Sinclairf51a02a2017-04-19 12:46:53 -0400461 m_pEdit->InsertText(m_swText, FX_CHARSET_Default, false, true);
Diana Gage4d02e902017-07-20 17:20:31 -0700462 m_pEdit->SetSelection(m_wrSel.BeginPos, m_wrSel.EndPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700463 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700464}
465
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400466CFXEU_InsertText::CFXEU_InsertText(CPWL_EditImpl* pEdit,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700467 const CPVT_WordPlace& wpOldPlace,
468 const CPVT_WordPlace& wpNewPlace,
469 const CFX_WideString& swText,
dsinclairefd5a992016-07-18 10:04:07 -0700470 int32_t charset)
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700471 : m_pEdit(pEdit),
472 m_wpOld(wpOldPlace),
473 m_wpNew(wpNewPlace),
474 m_swText(swText),
dsinclairefd5a992016-07-18 10:04:07 -0700475 m_nCharset(charset) {}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700476
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700477CFXEU_InsertText::~CFXEU_InsertText() {}
478
479void CFXEU_InsertText::Redo() {
480 if (m_pEdit && IsLast()) {
481 m_pEdit->SelectNone();
482 m_pEdit->SetCaret(m_wpOld);
tsepez4cf55152016-11-02 14:37:54 -0700483 m_pEdit->InsertText(m_swText, m_nCharset, false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700484 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700485}
486
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700487void CFXEU_InsertText::Undo() {
488 if (m_pEdit) {
489 m_pEdit->SelectNone();
Diana Gage4d02e902017-07-20 17:20:31 -0700490 m_pEdit->SetSelection(m_wpOld, m_wpNew);
tsepez4cf55152016-11-02 14:37:54 -0700491 m_pEdit->Clear(false, true);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700492 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700493}
494
dsinclaire35af1e2016-07-13 11:26:20 -0700495// static
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400496void CPWL_EditImpl::DrawEdit(CFX_RenderDevice* pDevice,
497 CFX_Matrix* pUser2Device,
498 CPWL_EditImpl* pEdit,
499 FX_COLORREF crTextFill,
500 const CFX_FloatRect& rcClip,
501 const CFX_PointF& ptOffset,
502 const CPVT_WordRange* pRange,
503 CFX_SystemHandler* pSystemHandler,
504 CFFL_FormFiller* pFFLData) {
dsinclaire35af1e2016-07-13 11:26:20 -0700505 const bool bContinuous =
506 pEdit->GetCharArray() == 0 && pEdit->GetCharSpace() <= 0.0f;
507 uint16_t SubWord = pEdit->GetPasswordChar();
Dan Sinclair05df0752017-03-14 14:43:42 -0400508 float fFontSize = pEdit->GetFontSize();
dsinclaire35af1e2016-07-13 11:26:20 -0700509 CPVT_WordRange wrSelect = pEdit->GetSelectWordRange();
510 int32_t nHorzScale = pEdit->GetHorzScale();
511
512 FX_COLORREF crCurFill = crTextFill;
513 FX_COLORREF crOldFill = crCurFill;
514
tsepez4cf55152016-11-02 14:37:54 -0700515 bool bSelect = false;
dsinclaire35af1e2016-07-13 11:26:20 -0700516 const FX_COLORREF crWhite = ArgbEncode(255, 255, 255, 255);
517 const FX_COLORREF crSelBK = ArgbEncode(255, 0, 51, 113);
518
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400519 std::ostringstream sTextBuf;
dsinclaire35af1e2016-07-13 11:26:20 -0700520 int32_t nFontIndex = -1;
Dan Sinclairf528eee2017-02-14 11:52:07 -0500521 CFX_PointF ptBT;
Tom Sepez1629f602017-04-21 14:11:26 -0700522 CFX_RenderDevice::StateRestorer restorer(pDevice);
dsinclaire35af1e2016-07-13 11:26:20 -0700523 if (!rcClip.IsEmpty()) {
524 CFX_FloatRect rcTemp = rcClip;
525 pUser2Device->TransformRect(rcTemp);
526 pDevice->SetClip_Rect(rcTemp.ToFxRect());
527 }
528
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400529 CPWL_EditImpl_Iterator* pIterator = pEdit->GetIterator();
dsinclaire35af1e2016-07-13 11:26:20 -0700530 if (IPVT_FontMap* pFontMap = pEdit->GetFontMap()) {
531 if (pRange)
532 pIterator->SetAt(pRange->BeginPos);
533 else
534 pIterator->SetAt(0);
535
536 CPVT_WordPlace oldplace;
537 while (pIterator->NextWord()) {
538 CPVT_WordPlace place = pIterator->GetAt();
Tom Sepez52f69b32017-03-21 13:42:38 -0700539 if (pRange && place > pRange->EndPos)
dsinclaire35af1e2016-07-13 11:26:20 -0700540 break;
541
Tom Sepez52f69b32017-03-21 13:42:38 -0700542 if (!wrSelect.IsEmpty()) {
543 bSelect = place > wrSelect.BeginPos && place <= wrSelect.EndPos;
dsinclaire35af1e2016-07-13 11:26:20 -0700544 crCurFill = bSelect ? crWhite : crTextFill;
545 }
546 if (pSystemHandler && pSystemHandler->IsSelectionImplemented()) {
547 crCurFill = crTextFill;
548 crOldFill = crCurFill;
549 }
550 CPVT_Word word;
551 if (pIterator->GetWord(word)) {
552 if (bSelect) {
553 CPVT_Line line;
554 pIterator->GetLine(line);
555
556 if (pSystemHandler && pSystemHandler->IsSelectionImplemented()) {
557 CFX_FloatRect rc(word.ptWord.x, line.ptLine.y + line.fLineDescent,
558 word.ptWord.x + word.fWidth,
559 line.ptLine.y + line.fLineAscent);
560 rc.Intersect(rcClip);
561 pSystemHandler->OutputSelectedRect(pFFLData, rc);
562 } else {
563 CFX_PathData pathSelBK;
564 pathSelBK.AppendRect(
565 word.ptWord.x, line.ptLine.y + line.fLineDescent,
566 word.ptWord.x + word.fWidth, line.ptLine.y + line.fLineAscent);
567
568 pDevice->DrawPath(&pathSelBK, pUser2Device, nullptr, crSelBK, 0,
569 FXFILL_WINDING);
570 }
571 }
572
573 if (bContinuous) {
574 if (place.LineCmp(oldplace) != 0 || word.nFontIndex != nFontIndex ||
575 crOldFill != crCurFill) {
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400576 if (sTextBuf.tellp() > 0) {
dsinclaire35af1e2016-07-13 11:26:20 -0700577 DrawTextString(
Dan Sinclairf528eee2017-02-14 11:52:07 -0500578 pDevice, CFX_PointF(ptBT.x + ptOffset.x, ptBT.y + ptOffset.y),
dsinclaire35af1e2016-07-13 11:26:20 -0700579 pFontMap->GetPDFFont(nFontIndex), fFontSize, pUser2Device,
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400580 CFX_ByteString(sTextBuf), crOldFill, nHorzScale);
dsinclaire35af1e2016-07-13 11:26:20 -0700581
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400582 sTextBuf.str("");
dsinclaire35af1e2016-07-13 11:26:20 -0700583 }
584 nFontIndex = word.nFontIndex;
585 ptBT = word.ptWord;
586 crOldFill = crCurFill;
587 }
588
Dan Sinclairc08dc392017-07-24 08:57:35 -0400589 sTextBuf << pEdit->GetPDFWordString(word.nFontIndex, word.Word,
590 SubWord);
dsinclaire35af1e2016-07-13 11:26:20 -0700591 } else {
592 DrawTextString(
Dan Sinclairc08dc392017-07-24 08:57:35 -0400593 pDevice,
594 CFX_PointF(word.ptWord.x + ptOffset.x,
595 word.ptWord.y + ptOffset.y),
dsinclaire35af1e2016-07-13 11:26:20 -0700596 pFontMap->GetPDFFont(word.nFontIndex), fFontSize, pUser2Device,
Dan Sinclairc08dc392017-07-24 08:57:35 -0400597 pEdit->GetPDFWordString(word.nFontIndex, word.Word, SubWord),
Dan Sinclaira0061af2017-02-23 09:25:17 -0500598 crCurFill, nHorzScale);
dsinclaire35af1e2016-07-13 11:26:20 -0700599 }
600 oldplace = place;
601 }
602 }
603
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400604 if (sTextBuf.tellp() > 0) {
Dan Sinclaira0061af2017-02-23 09:25:17 -0500605 DrawTextString(pDevice,
606 CFX_PointF(ptBT.x + ptOffset.x, ptBT.y + ptOffset.y),
607 pFontMap->GetPDFFont(nFontIndex), fFontSize, pUser2Device,
Henrique Nakashima2e2da132017-06-27 13:43:22 -0400608 CFX_ByteString(sTextBuf), crOldFill, nHorzScale);
dsinclaire35af1e2016-07-13 11:26:20 -0700609 }
610 }
dsinclaire35af1e2016-07-13 11:26:20 -0700611}
612
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400613CPWL_EditImpl::CPWL_EditImpl()
Lei Zhang5688d622017-08-12 07:04:19 -0700614 : m_pVT(pdfium::MakeUnique<CPDF_VariableText>()),
tsepez4cf55152016-11-02 14:37:54 -0700615 m_bEnableScroll(false),
dsinclair8f4bf9a2016-05-04 13:51:51 -0700616 m_Undo(kEditUndoMaxItems),
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700617 m_nAlignment(0),
tsepez4cf55152016-11-02 14:37:54 -0700618 m_bNotifyFlag(false),
619 m_bEnableOverflow(false),
620 m_bEnableRefresh(true),
Lei Zhang5688d622017-08-12 07:04:19 -0700621 m_bEnableUndo(true) {}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700622
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400623CPWL_EditImpl::~CPWL_EditImpl() {}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700624
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400625void CPWL_EditImpl::Initialize() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700626 m_pVT->Initialize();
627 SetCaret(m_pVT->GetBeginWordPlace());
628 SetCaretOrigin();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700629}
630
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400631void CPWL_EditImpl::SetFontMap(IPVT_FontMap* pFontMap) {
632 m_pVTProvider = pdfium::MakeUnique<CPWL_EditImpl_Provider>(pFontMap);
thestig821d59e2016-05-11 12:59:22 -0700633 m_pVT->SetProvider(m_pVTProvider.get());
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700634}
635
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400636void CPWL_EditImpl::SetNotify(CPWL_EditCtrl* pNotify) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700637 m_pNotify = pNotify;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700638}
639
Lei Zhang5688d622017-08-12 07:04:19 -0700640void CPWL_EditImpl::SetOperationNotify(CPWL_Edit* pOperationNotify) {
641 m_pOperationNotify = pOperationNotify;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700642}
643
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400644CPWL_EditImpl_Iterator* CPWL_EditImpl::GetIterator() {
tsepez36eb4bd2016-10-03 15:24:27 -0700645 if (!m_pIterator) {
646 m_pIterator =
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400647 pdfium::MakeUnique<CPWL_EditImpl_Iterator>(this, m_pVT->GetIterator());
tsepez36eb4bd2016-10-03 15:24:27 -0700648 }
thestig821d59e2016-05-11 12:59:22 -0700649 return m_pIterator.get();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700650}
651
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400652IPVT_FontMap* CPWL_EditImpl::GetFontMap() {
thestig821d59e2016-05-11 12:59:22 -0700653 return m_pVTProvider ? m_pVTProvider->GetFontMap() : nullptr;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700654}
655
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400656void CPWL_EditImpl::SetPlateRect(const CFX_FloatRect& rect) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700657 m_pVT->SetPlateRect(rect);
Dan Sinclairf528eee2017-02-14 11:52:07 -0500658 m_ptScrollPos = CFX_PointF(rect.left, rect.top);
dsinclairefd5a992016-07-18 10:04:07 -0700659 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700660}
661
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400662void CPWL_EditImpl::SetAlignmentH(int32_t nFormat, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700663 m_pVT->SetAlignment(nFormat);
664 if (bPaint)
665 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700666}
667
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400668void CPWL_EditImpl::SetAlignmentV(int32_t nFormat, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700669 m_nAlignment = nFormat;
670 if (bPaint)
671 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700672}
673
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400674void CPWL_EditImpl::SetPasswordChar(uint16_t wSubWord, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700675 m_pVT->SetPasswordChar(wSubWord);
676 if (bPaint)
677 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700678}
679
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400680void CPWL_EditImpl::SetLimitChar(int32_t nLimitChar) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700681 m_pVT->SetLimitChar(nLimitChar);
dsinclairefd5a992016-07-18 10:04:07 -0700682 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700683}
684
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400685void CPWL_EditImpl::SetCharArray(int32_t nCharArray) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700686 m_pVT->SetCharArray(nCharArray);
dsinclairefd5a992016-07-18 10:04:07 -0700687 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700688}
689
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400690void CPWL_EditImpl::SetCharSpace(float fCharSpace) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700691 m_pVT->SetCharSpace(fCharSpace);
dsinclairefd5a992016-07-18 10:04:07 -0700692 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700693}
694
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400695void CPWL_EditImpl::SetMultiLine(bool bMultiLine, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700696 m_pVT->SetMultiLine(bMultiLine);
697 if (bPaint)
698 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700699}
700
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400701void CPWL_EditImpl::SetAutoReturn(bool bAuto, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700702 m_pVT->SetAutoReturn(bAuto);
703 if (bPaint)
704 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700705}
706
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400707void CPWL_EditImpl::SetAutoFontSize(bool bAuto, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700708 m_pVT->SetAutoFontSize(bAuto);
709 if (bPaint)
710 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700711}
712
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400713void CPWL_EditImpl::SetFontSize(float fFontSize) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700714 m_pVT->SetFontSize(fFontSize);
dsinclairefd5a992016-07-18 10:04:07 -0700715 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700716}
717
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400718void CPWL_EditImpl::SetAutoScroll(bool bAuto, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700719 m_bEnableScroll = bAuto;
720 if (bPaint)
721 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700722}
723
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400724void CPWL_EditImpl::SetTextOverflow(bool bAllowed, bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700725 m_bEnableOverflow = bAllowed;
726 if (bPaint)
727 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700728}
729
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400730void CPWL_EditImpl::SetSelection(int32_t nStartChar, int32_t nEndChar) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700731 if (m_pVT->IsValid()) {
732 if (nStartChar == 0 && nEndChar < 0) {
733 SelectAll();
734 } else if (nStartChar < 0) {
735 SelectNone();
736 } else {
737 if (nStartChar < nEndChar) {
Diana Gage4d02e902017-07-20 17:20:31 -0700738 SetSelection(m_pVT->WordIndexToWordPlace(nStartChar),
739 m_pVT->WordIndexToWordPlace(nEndChar));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700740 } else {
Diana Gage4d02e902017-07-20 17:20:31 -0700741 SetSelection(m_pVT->WordIndexToWordPlace(nEndChar),
742 m_pVT->WordIndexToWordPlace(nStartChar));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700743 }
744 }
745 }
746}
747
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400748void CPWL_EditImpl::SetSelection(const CPVT_WordPlace& begin,
749 const CPVT_WordPlace& end) {
Tom Sepez52f69b32017-03-21 13:42:38 -0700750 if (!m_pVT->IsValid())
751 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700752
Tom Sepez52f69b32017-03-21 13:42:38 -0700753 SelectNone();
754 m_SelState.Set(begin, end);
755 SetCaret(m_SelState.EndPos);
756 ScrollToCaret();
757 if (!m_SelState.IsEmpty())
758 Refresh();
759 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700760}
761
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400762void CPWL_EditImpl::GetSelection(int32_t& nStartChar, int32_t& nEndChar) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700763 nStartChar = -1;
764 nEndChar = -1;
Tom Sepez52f69b32017-03-21 13:42:38 -0700765 if (!m_pVT->IsValid())
766 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700767
Tom Sepez52f69b32017-03-21 13:42:38 -0700768 if (m_SelState.IsEmpty()) {
769 nStartChar = m_pVT->WordPlaceToWordIndex(m_wpCaret);
770 nEndChar = m_pVT->WordPlaceToWordIndex(m_wpCaret);
771 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700772 }
Tom Sepez52f69b32017-03-21 13:42:38 -0700773 if (m_SelState.BeginPos < m_SelState.EndPos) {
774 nStartChar = m_pVT->WordPlaceToWordIndex(m_SelState.BeginPos);
775 nEndChar = m_pVT->WordPlaceToWordIndex(m_SelState.EndPos);
776 return;
777 }
778 nStartChar = m_pVT->WordPlaceToWordIndex(m_SelState.EndPos);
779 nEndChar = m_pVT->WordPlaceToWordIndex(m_SelState.BeginPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700780}
781
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400782int32_t CPWL_EditImpl::GetCaret() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700783 if (m_pVT->IsValid())
784 return m_pVT->WordPlaceToWordIndex(m_wpCaret);
785
786 return -1;
787}
788
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400789CPVT_WordPlace CPWL_EditImpl::GetCaretWordPlace() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700790 return m_wpCaret;
791}
792
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400793CFX_WideString CPWL_EditImpl::GetText() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700794 CFX_WideString swRet;
thestig821d59e2016-05-11 12:59:22 -0700795 if (!m_pVT->IsValid())
796 return swRet;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700797
thestig821d59e2016-05-11 12:59:22 -0700798 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
799 pIterator->SetAt(0);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700800
thestig821d59e2016-05-11 12:59:22 -0700801 CPVT_Word wordinfo;
802 CPVT_WordPlace oldplace = pIterator->GetAt();
803 while (pIterator->NextWord()) {
804 CPVT_WordPlace place = pIterator->GetAt();
thestig821d59e2016-05-11 12:59:22 -0700805 if (pIterator->GetWord(wordinfo))
806 swRet += wordinfo.Word;
Tom Sepez52f69b32017-03-21 13:42:38 -0700807 if (oldplace.nSecIndex != place.nSecIndex)
thestig821d59e2016-05-11 12:59:22 -0700808 swRet += L"\r\n";
thestig821d59e2016-05-11 12:59:22 -0700809 oldplace = place;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700810 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700811 return swRet;
812}
813
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400814CFX_WideString CPWL_EditImpl::GetRangeText(const CPVT_WordRange& range) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700815 CFX_WideString swRet;
thestig821d59e2016-05-11 12:59:22 -0700816 if (!m_pVT->IsValid())
817 return swRet;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700818
thestig821d59e2016-05-11 12:59:22 -0700819 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
820 CPVT_WordRange wrTemp = range;
821 m_pVT->UpdateWordPlace(wrTemp.BeginPos);
822 m_pVT->UpdateWordPlace(wrTemp.EndPos);
823 pIterator->SetAt(wrTemp.BeginPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700824
thestig821d59e2016-05-11 12:59:22 -0700825 CPVT_Word wordinfo;
826 CPVT_WordPlace oldplace = wrTemp.BeginPos;
827 while (pIterator->NextWord()) {
828 CPVT_WordPlace place = pIterator->GetAt();
Tom Sepez52f69b32017-03-21 13:42:38 -0700829 if (place > wrTemp.EndPos)
thestig821d59e2016-05-11 12:59:22 -0700830 break;
thestig821d59e2016-05-11 12:59:22 -0700831 if (pIterator->GetWord(wordinfo))
832 swRet += wordinfo.Word;
Tom Sepez52f69b32017-03-21 13:42:38 -0700833 if (oldplace.nSecIndex != place.nSecIndex)
thestig821d59e2016-05-11 12:59:22 -0700834 swRet += L"\r\n";
thestig821d59e2016-05-11 12:59:22 -0700835 oldplace = place;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700836 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700837 return swRet;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700838}
839
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400840CFX_WideString CPWL_EditImpl::GetSelectedText() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700841 return GetRangeText(m_SelState.ConvertToWordRange());
842}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700843
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400844int32_t CPWL_EditImpl::GetTotalLines() const {
thestig821d59e2016-05-11 12:59:22 -0700845 int32_t nLines = 1;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700846
thestig821d59e2016-05-11 12:59:22 -0700847 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
848 pIterator->SetAt(0);
849 while (pIterator->NextLine())
850 ++nLines;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700851
thestig821d59e2016-05-11 12:59:22 -0700852 return nLines;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700853}
854
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400855CPVT_WordRange CPWL_EditImpl::GetSelectWordRange() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700856 return m_SelState.ConvertToWordRange();
857}
858
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400859void CPWL_EditImpl::SetText(const CFX_WideString& sText) {
dsinclairefd5a992016-07-18 10:04:07 -0700860 Empty();
Dan Sinclairf51a02a2017-04-19 12:46:53 -0400861 DoInsertText(CPVT_WordPlace(0, 0, -1), sText, FX_CHARSET_Default);
dsinclairefd5a992016-07-18 10:04:07 -0700862 Paint();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700863}
864
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400865bool CPWL_EditImpl::InsertWord(uint16_t word, int32_t charset) {
tsepez4cf55152016-11-02 14:37:54 -0700866 return InsertWord(word, charset, nullptr, true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700867}
868
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400869bool CPWL_EditImpl::InsertReturn() {
tsepez4cf55152016-11-02 14:37:54 -0700870 return InsertReturn(nullptr, nullptr, true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700871}
872
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400873bool CPWL_EditImpl::Backspace() {
tsepez4cf55152016-11-02 14:37:54 -0700874 return Backspace(true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700875}
876
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400877bool CPWL_EditImpl::Delete() {
tsepez4cf55152016-11-02 14:37:54 -0700878 return Delete(true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700879}
880
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400881bool CPWL_EditImpl::ClearSelection() {
tsepez4cf55152016-11-02 14:37:54 -0700882 return Clear(true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700883}
884
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400885bool CPWL_EditImpl::InsertText(const CFX_WideString& sText, int32_t charset) {
tsepez4cf55152016-11-02 14:37:54 -0700886 return InsertText(sText, charset, true, true);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700887}
888
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400889float CPWL_EditImpl::GetFontSize() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700890 return m_pVT->GetFontSize();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700891}
892
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400893uint16_t CPWL_EditImpl::GetPasswordChar() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700894 return m_pVT->GetPasswordChar();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700895}
896
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400897int32_t CPWL_EditImpl::GetCharArray() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700898 return m_pVT->GetCharArray();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700899}
900
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400901CFX_FloatRect CPWL_EditImpl::GetContentRect() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700902 return VTToEdit(m_pVT->GetContentRect());
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700903}
904
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400905int32_t CPWL_EditImpl::GetHorzScale() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700906 return m_pVT->GetHorzScale();
907}
908
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400909float CPWL_EditImpl::GetCharSpace() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700910 return m_pVT->GetCharSpace();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700911}
912
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400913CPVT_WordRange CPWL_EditImpl::GetWholeWordRange() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700914 if (m_pVT->IsValid())
915 return CPVT_WordRange(m_pVT->GetBeginWordPlace(), m_pVT->GetEndWordPlace());
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700916
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700917 return CPVT_WordRange();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700918}
919
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400920CPVT_WordRange CPWL_EditImpl::GetVisibleWordRange() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700921 if (m_bEnableOverflow)
922 return GetWholeWordRange();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700923
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700924 if (m_pVT->IsValid()) {
Tom Sepez281a9ea2016-02-26 14:24:28 -0800925 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700926
Dan Sinclairf528eee2017-02-14 11:52:07 -0500927 CPVT_WordPlace place1 =
928 m_pVT->SearchWordPlace(EditToVT(CFX_PointF(rcPlate.left, rcPlate.top)));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700929 CPVT_WordPlace place2 = m_pVT->SearchWordPlace(
Dan Sinclairf528eee2017-02-14 11:52:07 -0500930 EditToVT(CFX_PointF(rcPlate.right, rcPlate.bottom)));
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700931
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700932 return CPVT_WordRange(place1, place2);
933 }
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700934
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700935 return CPVT_WordRange();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700936}
937
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400938CPVT_WordPlace CPWL_EditImpl::SearchWordPlace(const CFX_PointF& point) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700939 if (m_pVT->IsValid()) {
940 return m_pVT->SearchWordPlace(EditToVT(point));
941 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700942
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700943 return CPVT_WordPlace();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700944}
945
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400946void CPWL_EditImpl::Paint() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700947 if (m_pVT->IsValid()) {
948 RearrangeAll();
949 ScrollToCaret();
dsinclairefd5a992016-07-18 10:04:07 -0700950 Refresh();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700951 SetCaretOrigin();
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700952 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700953 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700954}
955
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400956void CPWL_EditImpl::RearrangeAll() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700957 if (m_pVT->IsValid()) {
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700958 m_pVT->UpdateWordPlace(m_wpCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700959 m_pVT->RearrangeAll();
960 m_pVT->UpdateWordPlace(m_wpCaret);
961 SetScrollInfo();
962 SetContentChanged();
963 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700964}
965
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400966void CPWL_EditImpl::RearrangePart(const CPVT_WordRange& range) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700967 if (m_pVT->IsValid()) {
968 m_pVT->UpdateWordPlace(m_wpCaret);
969 m_pVT->RearrangePart(range);
970 m_pVT->UpdateWordPlace(m_wpCaret);
971 SetScrollInfo();
972 SetContentChanged();
973 }
974}
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700975
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400976void CPWL_EditImpl::SetContentChanged() {
dsinclaira2919b32016-07-13 10:55:48 -0700977 if (m_pNotify) {
Tom Sepez281a9ea2016-02-26 14:24:28 -0800978 CFX_FloatRect rcContent = m_pVT->GetContentRect();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700979 if (rcContent.Width() != m_rcOldContent.Width() ||
980 rcContent.Height() != m_rcOldContent.Height()) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700981 m_rcOldContent = rcContent;
982 }
983 }
984}
985
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400986void CPWL_EditImpl::SelectAll() {
Tom Sepez52f69b32017-03-21 13:42:38 -0700987 if (!m_pVT->IsValid())
988 return;
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400989 m_SelState = CPWL_EditImpl_Select(GetWholeWordRange());
Tom Sepez52f69b32017-03-21 13:42:38 -0700990 SetCaret(m_SelState.EndPos);
991 ScrollToCaret();
992 Refresh();
993 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700994}
995
Dan Sinclair6b0158f2017-07-24 09:42:55 -0400996void CPWL_EditImpl::SelectNone() {
Tom Sepez52f69b32017-03-21 13:42:38 -0700997 if (!m_pVT->IsValid() || m_SelState.IsEmpty())
998 return;
999
1000 m_SelState.Reset();
1001 Refresh();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001002}
1003
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001004bool CPWL_EditImpl::IsSelected() const {
Tom Sepez52f69b32017-03-21 13:42:38 -07001005 return !m_SelState.IsEmpty();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001006}
1007
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001008CFX_PointF CPWL_EditImpl::VTToEdit(const CFX_PointF& point) const {
Tom Sepez281a9ea2016-02-26 14:24:28 -08001009 CFX_FloatRect rcContent = m_pVT->GetContentRect();
1010 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001011
Dan Sinclair05df0752017-03-14 14:43:42 -04001012 float fPadding = 0.0f;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001013
1014 switch (m_nAlignment) {
1015 case 0:
1016 fPadding = 0.0f;
1017 break;
1018 case 1:
1019 fPadding = (rcPlate.Height() - rcContent.Height()) * 0.5f;
1020 break;
1021 case 2:
1022 fPadding = rcPlate.Height() - rcContent.Height();
1023 break;
1024 }
1025
Dan Sinclairf528eee2017-02-14 11:52:07 -05001026 return CFX_PointF(point.x - (m_ptScrollPos.x - rcPlate.left),
1027 point.y - (m_ptScrollPos.y + fPadding - rcPlate.top));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001028}
1029
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001030CFX_PointF CPWL_EditImpl::EditToVT(const CFX_PointF& point) const {
Tom Sepez281a9ea2016-02-26 14:24:28 -08001031 CFX_FloatRect rcContent = m_pVT->GetContentRect();
1032 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001033
Dan Sinclair05df0752017-03-14 14:43:42 -04001034 float fPadding = 0.0f;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001035
1036 switch (m_nAlignment) {
1037 case 0:
1038 fPadding = 0.0f;
1039 break;
1040 case 1:
1041 fPadding = (rcPlate.Height() - rcContent.Height()) * 0.5f;
1042 break;
1043 case 2:
1044 fPadding = rcPlate.Height() - rcContent.Height();
1045 break;
1046 }
1047
Dan Sinclairf528eee2017-02-14 11:52:07 -05001048 return CFX_PointF(point.x + (m_ptScrollPos.x - rcPlate.left),
1049 point.y + (m_ptScrollPos.y + fPadding - rcPlate.top));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001050}
1051
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001052CFX_FloatRect CPWL_EditImpl::VTToEdit(const CFX_FloatRect& rect) const {
Dan Sinclairf528eee2017-02-14 11:52:07 -05001053 CFX_PointF ptLeftBottom = VTToEdit(CFX_PointF(rect.left, rect.bottom));
1054 CFX_PointF ptRightTop = VTToEdit(CFX_PointF(rect.right, rect.top));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001055
Tom Sepez281a9ea2016-02-26 14:24:28 -08001056 return CFX_FloatRect(ptLeftBottom.x, ptLeftBottom.y, ptRightTop.x,
1057 ptRightTop.y);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001058}
1059
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001060void CPWL_EditImpl::SetScrollInfo() {
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001061 if (!m_pNotify)
1062 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001063
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001064 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
1065 CFX_FloatRect rcContent = m_pVT->GetContentRect();
1066 if (m_bNotifyFlag)
1067 return;
1068
1069 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
1070 m_bNotifyFlag = true;
1071
1072 PWL_SCROLL_INFO Info;
1073 Info.fPlateWidth = rcPlate.top - rcPlate.bottom;
1074 Info.fContentMin = rcContent.bottom;
1075 Info.fContentMax = rcContent.top;
1076 Info.fSmallStep = rcPlate.Height() / 3;
1077 Info.fBigStep = rcPlate.Height();
1078 m_pNotify->SetScrollInfo(Info);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001079}
1080
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001081void CPWL_EditImpl::SetScrollPosX(float fx) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001082 if (!m_bEnableScroll)
1083 return;
1084
1085 if (m_pVT->IsValid()) {
dsinclair448c4332016-08-02 12:07:35 -07001086 if (!IsFloatEqual(m_ptScrollPos.x, fx)) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001087 m_ptScrollPos.x = fx;
dsinclairefd5a992016-07-18 10:04:07 -07001088 Refresh();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001089 }
1090 }
1091}
1092
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001093void CPWL_EditImpl::SetScrollPosY(float fy) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001094 if (!m_bEnableScroll)
1095 return;
1096
1097 if (m_pVT->IsValid()) {
dsinclair448c4332016-08-02 12:07:35 -07001098 if (!IsFloatEqual(m_ptScrollPos.y, fy)) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001099 m_ptScrollPos.y = fy;
dsinclairefd5a992016-07-18 10:04:07 -07001100 Refresh();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001101
dsinclaira2919b32016-07-13 10:55:48 -07001102 if (m_pNotify) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001103 if (!m_bNotifyFlag) {
Lei Zhanga8c2b912017-03-22 17:41:02 -07001104 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
tsepez4cf55152016-11-02 14:37:54 -07001105 m_bNotifyFlag = true;
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001106 m_pNotify->SetScrollPosition(fy);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001107 }
1108 }
1109 }
1110 }
1111}
1112
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001113void CPWL_EditImpl::SetScrollPos(const CFX_PointF& point) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001114 SetScrollPosX(point.x);
1115 SetScrollPosY(point.y);
1116 SetScrollLimit();
1117 SetCaretInfo();
1118}
1119
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001120CFX_PointF CPWL_EditImpl::GetScrollPos() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001121 return m_ptScrollPos;
1122}
1123
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001124void CPWL_EditImpl::SetScrollLimit() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001125 if (m_pVT->IsValid()) {
Tom Sepez281a9ea2016-02-26 14:24:28 -08001126 CFX_FloatRect rcContent = m_pVT->GetContentRect();
1127 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001128
1129 if (rcPlate.Width() > rcContent.Width()) {
1130 SetScrollPosX(rcPlate.left);
1131 } else {
dsinclair448c4332016-08-02 12:07:35 -07001132 if (IsFloatSmaller(m_ptScrollPos.x, rcContent.left)) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001133 SetScrollPosX(rcContent.left);
dsinclair448c4332016-08-02 12:07:35 -07001134 } else if (IsFloatBigger(m_ptScrollPos.x,
1135 rcContent.right - rcPlate.Width())) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001136 SetScrollPosX(rcContent.right - rcPlate.Width());
1137 }
1138 }
1139
1140 if (rcPlate.Height() > rcContent.Height()) {
1141 SetScrollPosY(rcPlate.top);
1142 } else {
dsinclair448c4332016-08-02 12:07:35 -07001143 if (IsFloatSmaller(m_ptScrollPos.y,
1144 rcContent.bottom + rcPlate.Height())) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001145 SetScrollPosY(rcContent.bottom + rcPlate.Height());
dsinclair448c4332016-08-02 12:07:35 -07001146 } else if (IsFloatBigger(m_ptScrollPos.y, rcContent.top)) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001147 SetScrollPosY(rcContent.top);
1148 }
1149 }
1150 }
1151}
1152
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001153void CPWL_EditImpl::ScrollToCaret() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001154 SetScrollLimit();
1155
thestig821d59e2016-05-11 12:59:22 -07001156 if (!m_pVT->IsValid())
1157 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001158
thestig821d59e2016-05-11 12:59:22 -07001159 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1160 pIterator->SetAt(m_wpCaret);
1161
Dan Sinclairf528eee2017-02-14 11:52:07 -05001162 CFX_PointF ptHead;
1163 CFX_PointF ptFoot;
thestig821d59e2016-05-11 12:59:22 -07001164 CPVT_Word word;
1165 CPVT_Line line;
1166 if (pIterator->GetWord(word)) {
1167 ptHead.x = word.ptWord.x + word.fWidth;
1168 ptHead.y = word.ptWord.y + word.fAscent;
1169 ptFoot.x = word.ptWord.x + word.fWidth;
1170 ptFoot.y = word.ptWord.y + word.fDescent;
1171 } else if (pIterator->GetLine(line)) {
1172 ptHead.x = line.ptLine.x;
1173 ptHead.y = line.ptLine.y + line.fLineAscent;
1174 ptFoot.x = line.ptLine.x;
1175 ptFoot.y = line.ptLine.y + line.fLineDescent;
1176 }
1177
Dan Sinclairf528eee2017-02-14 11:52:07 -05001178 CFX_PointF ptHeadEdit = VTToEdit(ptHead);
1179 CFX_PointF ptFootEdit = VTToEdit(ptFoot);
thestig821d59e2016-05-11 12:59:22 -07001180 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
dsinclair448c4332016-08-02 12:07:35 -07001181 if (!IsFloatEqual(rcPlate.left, rcPlate.right)) {
1182 if (IsFloatSmaller(ptHeadEdit.x, rcPlate.left) ||
1183 IsFloatEqual(ptHeadEdit.x, rcPlate.left)) {
thestig821d59e2016-05-11 12:59:22 -07001184 SetScrollPosX(ptHead.x);
dsinclair448c4332016-08-02 12:07:35 -07001185 } else if (IsFloatBigger(ptHeadEdit.x, rcPlate.right)) {
thestig821d59e2016-05-11 12:59:22 -07001186 SetScrollPosX(ptHead.x - rcPlate.Width());
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001187 }
thestig821d59e2016-05-11 12:59:22 -07001188 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001189
dsinclair448c4332016-08-02 12:07:35 -07001190 if (!IsFloatEqual(rcPlate.top, rcPlate.bottom)) {
1191 if (IsFloatSmaller(ptFootEdit.y, rcPlate.bottom) ||
1192 IsFloatEqual(ptFootEdit.y, rcPlate.bottom)) {
1193 if (IsFloatSmaller(ptHeadEdit.y, rcPlate.top)) {
thestig821d59e2016-05-11 12:59:22 -07001194 SetScrollPosY(ptFoot.y + rcPlate.Height());
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001195 }
dsinclair448c4332016-08-02 12:07:35 -07001196 } else if (IsFloatBigger(ptHeadEdit.y, rcPlate.top)) {
1197 if (IsFloatBigger(ptFootEdit.y, rcPlate.bottom)) {
thestig821d59e2016-05-11 12:59:22 -07001198 SetScrollPosY(ptHead.y);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001199 }
1200 }
1201 }
1202}
1203
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001204void CPWL_EditImpl::Refresh() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001205 if (m_bEnableRefresh && m_pVT->IsValid()) {
1206 m_Refresh.BeginRefresh();
1207 RefreshPushLineRects(GetVisibleWordRange());
1208
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001209 m_Refresh.NoAnalyse();
1210 m_ptRefreshScrollPos = m_ptScrollPos;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001211
dsinclaira2919b32016-07-13 10:55:48 -07001212 if (m_pNotify) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001213 if (!m_bNotifyFlag) {
Lei Zhanga8c2b912017-03-22 17:41:02 -07001214 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
tsepez4cf55152016-11-02 14:37:54 -07001215 m_bNotifyFlag = true;
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001216 if (const CPWL_EditImpl_RectArray* pRects =
1217 m_Refresh.GetRefreshRects()) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001218 for (int32_t i = 0, sz = pRects->GetSize(); i < sz; i++)
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001219 m_pNotify->InvalidateRect(pRects->GetAt(i));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001220 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001221 }
1222 }
1223
1224 m_Refresh.EndRefresh();
1225 }
1226}
1227
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001228void CPWL_EditImpl::RefreshPushLineRects(const CPVT_WordRange& wr) {
thestig821d59e2016-05-11 12:59:22 -07001229 if (!m_pVT->IsValid())
1230 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001231
thestig821d59e2016-05-11 12:59:22 -07001232 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1233 CPVT_WordPlace wpBegin = wr.BeginPos;
1234 m_pVT->UpdateWordPlace(wpBegin);
1235 CPVT_WordPlace wpEnd = wr.EndPos;
1236 m_pVT->UpdateWordPlace(wpEnd);
1237 pIterator->SetAt(wpBegin);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001238
thestig821d59e2016-05-11 12:59:22 -07001239 CPVT_Line lineinfo;
1240 do {
1241 if (!pIterator->GetLine(lineinfo))
1242 break;
1243 if (lineinfo.lineplace.LineCmp(wpEnd) > 0)
1244 break;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001245
thestig821d59e2016-05-11 12:59:22 -07001246 CFX_FloatRect rcLine(lineinfo.ptLine.x,
1247 lineinfo.ptLine.y + lineinfo.fLineDescent,
1248 lineinfo.ptLine.x + lineinfo.fLineWidth,
1249 lineinfo.ptLine.y + lineinfo.fLineAscent);
1250
1251 m_Refresh.Push(CPVT_WordRange(lineinfo.lineplace, lineinfo.lineEnd),
1252 VTToEdit(rcLine));
1253 } while (pIterator->NextLine());
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001254}
1255
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001256void CPWL_EditImpl::RefreshWordRange(const CPVT_WordRange& wr) {
thestig821d59e2016-05-11 12:59:22 -07001257 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1258 CPVT_WordRange wrTemp = wr;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001259
thestig821d59e2016-05-11 12:59:22 -07001260 m_pVT->UpdateWordPlace(wrTemp.BeginPos);
1261 m_pVT->UpdateWordPlace(wrTemp.EndPos);
1262 pIterator->SetAt(wrTemp.BeginPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001263
thestig821d59e2016-05-11 12:59:22 -07001264 CPVT_Word wordinfo;
1265 CPVT_Line lineinfo;
1266 CPVT_WordPlace place;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001267
thestig821d59e2016-05-11 12:59:22 -07001268 while (pIterator->NextWord()) {
1269 place = pIterator->GetAt();
Tom Sepez52f69b32017-03-21 13:42:38 -07001270 if (place > wrTemp.EndPos)
thestig821d59e2016-05-11 12:59:22 -07001271 break;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001272
thestig821d59e2016-05-11 12:59:22 -07001273 pIterator->GetWord(wordinfo);
1274 pIterator->GetLine(lineinfo);
thestig821d59e2016-05-11 12:59:22 -07001275 if (place.LineCmp(wrTemp.BeginPos) == 0 ||
1276 place.LineCmp(wrTemp.EndPos) == 0) {
1277 CFX_FloatRect rcWord(wordinfo.ptWord.x,
1278 lineinfo.ptLine.y + lineinfo.fLineDescent,
1279 wordinfo.ptWord.x + wordinfo.fWidth,
1280 lineinfo.ptLine.y + lineinfo.fLineAscent);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001281
dsinclaira2919b32016-07-13 10:55:48 -07001282 if (m_pNotify) {
thestig821d59e2016-05-11 12:59:22 -07001283 if (!m_bNotifyFlag) {
Lei Zhanga8c2b912017-03-22 17:41:02 -07001284 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
tsepez4cf55152016-11-02 14:37:54 -07001285 m_bNotifyFlag = true;
thestig821d59e2016-05-11 12:59:22 -07001286 CFX_FloatRect rcRefresh = VTToEdit(rcWord);
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001287 m_pNotify->InvalidateRect(&rcRefresh);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001288 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001289 }
thestig821d59e2016-05-11 12:59:22 -07001290 } else {
1291 CFX_FloatRect rcLine(lineinfo.ptLine.x,
1292 lineinfo.ptLine.y + lineinfo.fLineDescent,
1293 lineinfo.ptLine.x + lineinfo.fLineWidth,
1294 lineinfo.ptLine.y + lineinfo.fLineAscent);
1295
dsinclaira2919b32016-07-13 10:55:48 -07001296 if (m_pNotify) {
thestig821d59e2016-05-11 12:59:22 -07001297 if (!m_bNotifyFlag) {
Lei Zhanga8c2b912017-03-22 17:41:02 -07001298 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
tsepez4cf55152016-11-02 14:37:54 -07001299 m_bNotifyFlag = true;
thestig821d59e2016-05-11 12:59:22 -07001300 CFX_FloatRect rcRefresh = VTToEdit(rcLine);
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001301 m_pNotify->InvalidateRect(&rcRefresh);
thestig821d59e2016-05-11 12:59:22 -07001302 }
1303 }
1304
1305 pIterator->NextLine();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001306 }
1307 }
1308}
1309
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001310void CPWL_EditImpl::SetCaret(const CPVT_WordPlace& place) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001311 m_wpOldCaret = m_wpCaret;
1312 m_wpCaret = place;
1313}
1314
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001315void CPWL_EditImpl::SetCaretInfo() {
dsinclaira2919b32016-07-13 10:55:48 -07001316 if (m_pNotify) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001317 if (!m_bNotifyFlag) {
thestig821d59e2016-05-11 12:59:22 -07001318 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1319 pIterator->SetAt(m_wpCaret);
tsepez63f545c2016-09-13 16:08:49 -07001320
Dan Sinclairf528eee2017-02-14 11:52:07 -05001321 CFX_PointF ptHead;
1322 CFX_PointF ptFoot;
thestig821d59e2016-05-11 12:59:22 -07001323 CPVT_Word word;
1324 CPVT_Line line;
1325 if (pIterator->GetWord(word)) {
1326 ptHead.x = word.ptWord.x + word.fWidth;
1327 ptHead.y = word.ptWord.y + word.fAscent;
1328 ptFoot.x = word.ptWord.x + word.fWidth;
1329 ptFoot.y = word.ptWord.y + word.fDescent;
1330 } else if (pIterator->GetLine(line)) {
1331 ptHead.x = line.ptLine.x;
1332 ptHead.y = line.ptLine.y + line.fLineAscent;
1333 ptFoot.x = line.ptLine.x;
1334 ptFoot.y = line.ptLine.y + line.fLineDescent;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001335 }
1336
Lei Zhanga8c2b912017-03-22 17:41:02 -07001337 CFX_AutoRestorer<bool> restorer(&m_bNotifyFlag);
tsepez4cf55152016-11-02 14:37:54 -07001338 m_bNotifyFlag = true;
Dan Sinclair0fdd1ae2017-07-05 16:00:48 -04001339 m_pNotify->SetCaret(m_SelState.IsEmpty(), VTToEdit(ptHead),
1340 VTToEdit(ptFoot));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001341 }
1342 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001343}
1344
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001345void CPWL_EditImpl::OnMouseDown(const CFX_PointF& point,
1346 bool bShift,
1347 bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001348 if (!m_pVT->IsValid())
1349 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001350
Tom Sepez52f69b32017-03-21 13:42:38 -07001351 SelectNone();
1352 SetCaret(m_pVT->SearchWordPlace(EditToVT(point)));
1353 m_SelState.Set(m_wpCaret, m_wpCaret);
1354 ScrollToCaret();
1355 SetCaretOrigin();
1356 SetCaretInfo();
1357}
1358
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001359void CPWL_EditImpl::OnMouseMove(const CFX_PointF& point,
1360 bool bShift,
1361 bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001362 if (!m_pVT->IsValid())
1363 return;
1364
1365 SetCaret(m_pVT->SearchWordPlace(EditToVT(point)));
1366 if (m_wpCaret == m_wpOldCaret)
1367 return;
1368
1369 m_SelState.SetEndPos(m_wpCaret);
1370 ScrollToCaret();
1371 Refresh();
1372 SetCaretOrigin();
1373 SetCaretInfo();
1374}
1375
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001376void CPWL_EditImpl::OnVK_UP(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001377 if (!m_pVT->IsValid())
1378 return;
1379
1380 SetCaret(m_pVT->GetUpWordPlace(m_wpCaret, m_ptCaret));
1381 if (bShift) {
1382 if (m_SelState.IsEmpty())
1383 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1384 else
1385 m_SelState.SetEndPos(m_wpCaret);
1386
1387 if (m_wpOldCaret != m_wpCaret) {
1388 ScrollToCaret();
1389 Refresh();
1390 SetCaretInfo();
1391 }
1392 } else {
1393 SelectNone();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001394 ScrollToCaret();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001395 SetCaretInfo();
1396 }
1397}
1398
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001399void CPWL_EditImpl::OnVK_DOWN(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001400 if (!m_pVT->IsValid())
1401 return;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001402
Tom Sepez52f69b32017-03-21 13:42:38 -07001403 SetCaret(m_pVT->GetDownWordPlace(m_wpCaret, m_ptCaret));
1404 if (bShift) {
1405 if (m_SelState.IsEmpty())
1406 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1407 else
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001408 m_SelState.SetEndPos(m_wpCaret);
1409
Tom Sepez52f69b32017-03-21 13:42:38 -07001410 if (m_wpOldCaret != m_wpCaret) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001411 ScrollToCaret();
dsinclairefd5a992016-07-18 10:04:07 -07001412 Refresh();
Tom Sepez52f69b32017-03-21 13:42:38 -07001413 SetCaretInfo();
1414 }
1415 } else {
1416 SelectNone();
1417 ScrollToCaret();
1418 SetCaretInfo();
1419 }
1420}
1421
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001422void CPWL_EditImpl::OnVK_LEFT(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001423 if (!m_pVT->IsValid())
1424 return;
1425
1426 if (bShift) {
1427 if (m_wpCaret == m_pVT->GetLineBeginPlace(m_wpCaret) &&
1428 m_wpCaret != m_pVT->GetSectionBeginPlace(m_wpCaret)) {
1429 SetCaret(m_pVT->GetPrevWordPlace(m_wpCaret));
1430 }
1431 SetCaret(m_pVT->GetPrevWordPlace(m_wpCaret));
1432 if (m_SelState.IsEmpty())
1433 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1434 else
1435 m_SelState.SetEndPos(m_wpCaret);
1436
1437 if (m_wpOldCaret != m_wpCaret) {
1438 ScrollToCaret();
1439 Refresh();
1440 SetCaretInfo();
1441 }
1442 } else {
1443 if (!m_SelState.IsEmpty()) {
1444 if (m_SelState.BeginPos < m_SelState.EndPos)
1445 SetCaret(m_SelState.BeginPos);
1446 else
1447 SetCaret(m_SelState.EndPos);
1448
1449 SelectNone();
1450 ScrollToCaret();
1451 SetCaretInfo();
1452 } else {
1453 if (m_wpCaret == m_pVT->GetLineBeginPlace(m_wpCaret) &&
1454 m_wpCaret != m_pVT->GetSectionBeginPlace(m_wpCaret)) {
1455 SetCaret(m_pVT->GetPrevWordPlace(m_wpCaret));
1456 }
1457 SetCaret(m_pVT->GetPrevWordPlace(m_wpCaret));
1458 ScrollToCaret();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001459 SetCaretOrigin();
1460 SetCaretInfo();
1461 }
1462 }
1463}
1464
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001465void CPWL_EditImpl::OnVK_RIGHT(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001466 if (!m_pVT->IsValid())
1467 return;
1468
1469 if (bShift) {
1470 SetCaret(m_pVT->GetNextWordPlace(m_wpCaret));
1471 if (m_wpCaret == m_pVT->GetLineEndPlace(m_wpCaret) &&
1472 m_wpCaret != m_pVT->GetSectionEndPlace(m_wpCaret))
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001473 SetCaret(m_pVT->GetNextWordPlace(m_wpCaret));
1474
Tom Sepez52f69b32017-03-21 13:42:38 -07001475 if (m_SelState.IsEmpty())
1476 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1477 else
1478 m_SelState.SetEndPos(m_wpCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001479
Tom Sepez52f69b32017-03-21 13:42:38 -07001480 if (m_wpOldCaret != m_wpCaret) {
1481 ScrollToCaret();
1482 Refresh();
1483 SetCaretInfo();
1484 }
1485 } else {
1486 if (!m_SelState.IsEmpty()) {
1487 if (m_SelState.BeginPos > m_SelState.EndPos)
1488 SetCaret(m_SelState.BeginPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001489 else
Tom Sepez52f69b32017-03-21 13:42:38 -07001490 SetCaret(m_SelState.EndPos);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001491
Tom Sepez52f69b32017-03-21 13:42:38 -07001492 SelectNone();
1493 ScrollToCaret();
1494 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001495 } else {
Tom Sepez52f69b32017-03-21 13:42:38 -07001496 SetCaret(m_pVT->GetNextWordPlace(m_wpCaret));
1497 if (m_wpCaret == m_pVT->GetLineEndPlace(m_wpCaret) &&
1498 m_wpCaret != m_pVT->GetSectionEndPlace(m_wpCaret)) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001499 SetCaret(m_pVT->GetNextWordPlace(m_wpCaret));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001500 }
Tom Sepez52f69b32017-03-21 13:42:38 -07001501 ScrollToCaret();
1502 SetCaretOrigin();
1503 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001504 }
1505 }
1506}
1507
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001508void CPWL_EditImpl::OnVK_HOME(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001509 if (!m_pVT->IsValid())
1510 return;
1511
1512 if (bShift) {
1513 if (bCtrl)
1514 SetCaret(m_pVT->GetBeginWordPlace());
1515 else
1516 SetCaret(m_pVT->GetLineBeginPlace(m_wpCaret));
1517
1518 if (m_SelState.IsEmpty())
1519 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1520 else
1521 m_SelState.SetEndPos(m_wpCaret);
1522
1523 ScrollToCaret();
1524 Refresh();
1525 SetCaretInfo();
1526 } else {
1527 if (!m_SelState.IsEmpty()) {
1528 SetCaret(std::min(m_SelState.BeginPos, m_SelState.EndPos));
1529 SelectNone();
1530 ScrollToCaret();
1531 SetCaretInfo();
1532 } else {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001533 if (bCtrl)
1534 SetCaret(m_pVT->GetBeginWordPlace());
1535 else
1536 SetCaret(m_pVT->GetLineBeginPlace(m_wpCaret));
1537
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001538 ScrollToCaret();
Tom Sepez52f69b32017-03-21 13:42:38 -07001539 SetCaretOrigin();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001540 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001541 }
1542 }
1543}
1544
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001545void CPWL_EditImpl::OnVK_END(bool bShift, bool bCtrl) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001546 if (!m_pVT->IsValid())
1547 return;
1548
1549 if (bShift) {
1550 if (bCtrl)
1551 SetCaret(m_pVT->GetEndWordPlace());
1552 else
1553 SetCaret(m_pVT->GetLineEndPlace(m_wpCaret));
1554
1555 if (m_SelState.IsEmpty())
1556 m_SelState.Set(m_wpOldCaret, m_wpCaret);
1557 else
1558 m_SelState.SetEndPos(m_wpCaret);
1559
1560 ScrollToCaret();
1561 Refresh();
1562 SetCaretInfo();
1563 } else {
1564 if (!m_SelState.IsEmpty()) {
1565 SetCaret(std::max(m_SelState.BeginPos, m_SelState.EndPos));
1566 SelectNone();
1567 ScrollToCaret();
1568 SetCaretInfo();
1569 } else {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001570 if (bCtrl)
1571 SetCaret(m_pVT->GetEndWordPlace());
1572 else
1573 SetCaret(m_pVT->GetLineEndPlace(m_wpCaret));
1574
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001575 ScrollToCaret();
Tom Sepez52f69b32017-03-21 13:42:38 -07001576 SetCaretOrigin();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001577 SetCaretInfo();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001578 }
1579 }
1580}
1581
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001582bool CPWL_EditImpl::InsertWord(uint16_t word,
1583 int32_t charset,
1584 const CPVT_WordProps* pWordProps,
1585 bool bAddUndo,
1586 bool bPaint) {
Tom Sepez3509d162017-01-30 13:22:02 -08001587 if (IsTextOverflow() || !m_pVT->IsValid())
tsepez4cf55152016-11-02 14:37:54 -07001588 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001589
Tom Sepez3509d162017-01-30 13:22:02 -08001590 m_pVT->UpdateWordPlace(m_wpCaret);
1591 SetCaret(m_pVT->InsertWord(m_wpCaret, word,
1592 GetCharSetFromUnicode(word, charset), pWordProps));
1593 m_SelState.Set(m_wpCaret, m_wpCaret);
1594 if (m_wpCaret == m_wpOldCaret)
1595 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001596
Tom Sepez3509d162017-01-30 13:22:02 -08001597 if (bAddUndo && m_bEnableUndo) {
1598 AddEditUndoItem(pdfium::MakeUnique<CFXEU_InsertWord>(
1599 this, m_wpOldCaret, m_wpCaret, word, charset, pWordProps));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001600 }
Tom Sepez3509d162017-01-30 13:22:02 -08001601 if (bPaint)
1602 PaintInsertText(m_wpOldCaret, m_wpCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001603
Lei Zhang5688d622017-08-12 07:04:19 -07001604 if (m_pOperationNotify)
1605 m_pOperationNotify->OnInsertWord(m_wpCaret, m_wpOldCaret);
Tom Sepez3509d162017-01-30 13:22:02 -08001606
1607 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001608}
1609
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001610bool CPWL_EditImpl::InsertReturn(const CPVT_SecProps* pSecProps,
1611 const CPVT_WordProps* pWordProps,
1612 bool bAddUndo,
1613 bool bPaint) {
Tom Sepez3509d162017-01-30 13:22:02 -08001614 if (IsTextOverflow() || !m_pVT->IsValid())
tsepez4cf55152016-11-02 14:37:54 -07001615 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001616
Tom Sepez3509d162017-01-30 13:22:02 -08001617 m_pVT->UpdateWordPlace(m_wpCaret);
1618 SetCaret(m_pVT->InsertSection(m_wpCaret, pSecProps, pWordProps));
1619 m_SelState.Set(m_wpCaret, m_wpCaret);
1620 if (m_wpCaret == m_wpOldCaret)
1621 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001622
Tom Sepez3509d162017-01-30 13:22:02 -08001623 if (bAddUndo && m_bEnableUndo) {
1624 AddEditUndoItem(pdfium::MakeUnique<CFXEU_InsertReturn>(
1625 this, m_wpOldCaret, m_wpCaret, pSecProps, pWordProps));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001626 }
Tom Sepez3509d162017-01-30 13:22:02 -08001627 if (bPaint) {
1628 RearrangePart(CPVT_WordRange(m_wpOldCaret, m_wpCaret));
1629 ScrollToCaret();
1630 Refresh();
1631 SetCaretOrigin();
1632 SetCaretInfo();
1633 }
Lei Zhang5688d622017-08-12 07:04:19 -07001634 if (m_pOperationNotify)
1635 m_pOperationNotify->OnInsertReturn(m_wpCaret, m_wpOldCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001636
Tom Sepez3509d162017-01-30 13:22:02 -08001637 return true;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001638}
1639
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001640bool CPWL_EditImpl::Backspace(bool bAddUndo, bool bPaint) {
Tom Sepez3509d162017-01-30 13:22:02 -08001641 if (!m_pVT->IsValid() || m_wpCaret == m_pVT->GetBeginWordPlace())
1642 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001643
Tom Sepez3509d162017-01-30 13:22:02 -08001644 CPVT_Section section;
1645 CPVT_Word word;
1646 if (bAddUndo) {
1647 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1648 pIterator->SetAt(m_wpCaret);
1649 pIterator->GetSection(section);
1650 pIterator->GetWord(word);
1651 }
1652 m_pVT->UpdateWordPlace(m_wpCaret);
1653 SetCaret(m_pVT->BackSpaceWord(m_wpCaret));
1654 m_SelState.Set(m_wpCaret, m_wpCaret);
1655 if (m_wpCaret == m_wpOldCaret)
1656 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001657
Tom Sepez3509d162017-01-30 13:22:02 -08001658 if (bAddUndo && m_bEnableUndo) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001659 if (m_wpCaret.nSecIndex != m_wpOldCaret.nSecIndex) {
Tom Sepez3509d162017-01-30 13:22:02 -08001660 AddEditUndoItem(pdfium::MakeUnique<CFXEU_Backspace>(
1661 this, m_wpOldCaret, m_wpCaret, word.Word, word.nCharset,
1662 section.SecProps, section.WordProps));
1663 } else {
1664 AddEditUndoItem(pdfium::MakeUnique<CFXEU_Backspace>(
1665 this, m_wpOldCaret, m_wpCaret, word.Word, word.nCharset,
1666 section.SecProps, word.WordProps));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001667 }
1668 }
Tom Sepez3509d162017-01-30 13:22:02 -08001669 if (bPaint) {
1670 RearrangePart(CPVT_WordRange(m_wpCaret, m_wpOldCaret));
1671 ScrollToCaret();
1672 Refresh();
1673 SetCaretOrigin();
1674 SetCaretInfo();
1675 }
Lei Zhang5688d622017-08-12 07:04:19 -07001676 if (m_pOperationNotify)
1677 m_pOperationNotify->OnBackSpace(m_wpCaret, m_wpOldCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001678
Tom Sepez3509d162017-01-30 13:22:02 -08001679 return true;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001680}
1681
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001682bool CPWL_EditImpl::Delete(bool bAddUndo, bool bPaint) {
Tom Sepez3509d162017-01-30 13:22:02 -08001683 if (!m_pVT->IsValid() || m_wpCaret == m_pVT->GetEndWordPlace())
1684 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001685
Tom Sepez3509d162017-01-30 13:22:02 -08001686 CPVT_Section section;
1687 CPVT_Word word;
1688 if (bAddUndo) {
1689 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1690 pIterator->SetAt(m_pVT->GetNextWordPlace(m_wpCaret));
1691 pIterator->GetSection(section);
1692 pIterator->GetWord(word);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001693 }
Tom Sepez3509d162017-01-30 13:22:02 -08001694 m_pVT->UpdateWordPlace(m_wpCaret);
1695 bool bSecEnd = (m_wpCaret == m_pVT->GetSectionEndPlace(m_wpCaret));
1696 SetCaret(m_pVT->DeleteWord(m_wpCaret));
1697 m_SelState.Set(m_wpCaret, m_wpCaret);
1698 if (bAddUndo && m_bEnableUndo) {
1699 if (bSecEnd) {
1700 AddEditUndoItem(pdfium::MakeUnique<CFXEU_Delete>(
1701 this, m_wpOldCaret, m_wpCaret, word.Word, word.nCharset,
1702 section.SecProps, section.WordProps, bSecEnd));
1703 } else {
1704 AddEditUndoItem(pdfium::MakeUnique<CFXEU_Delete>(
1705 this, m_wpOldCaret, m_wpCaret, word.Word, word.nCharset,
1706 section.SecProps, word.WordProps, bSecEnd));
1707 }
1708 }
1709 if (bPaint) {
1710 RearrangePart(CPVT_WordRange(m_wpOldCaret, m_wpCaret));
1711 ScrollToCaret();
1712 Refresh();
1713 SetCaretOrigin();
1714 SetCaretInfo();
1715 }
Lei Zhang5688d622017-08-12 07:04:19 -07001716 if (m_pOperationNotify)
1717 m_pOperationNotify->OnDelete(m_wpCaret, m_wpOldCaret);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001718
Tom Sepez3509d162017-01-30 13:22:02 -08001719 return true;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001720}
1721
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001722bool CPWL_EditImpl::Empty() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001723 if (m_pVT->IsValid()) {
1724 m_pVT->DeleteWords(GetWholeWordRange());
1725 SetCaret(m_pVT->GetBeginWordPlace());
1726
tsepez4cf55152016-11-02 14:37:54 -07001727 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001728 }
1729
tsepez4cf55152016-11-02 14:37:54 -07001730 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001731}
1732
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001733bool CPWL_EditImpl::Clear(bool bAddUndo, bool bPaint) {
Tom Sepez52f69b32017-03-21 13:42:38 -07001734 if (!m_pVT->IsValid() || m_SelState.IsEmpty())
tsepez4cf55152016-11-02 14:37:54 -07001735 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001736
thestig821d59e2016-05-11 12:59:22 -07001737 CPVT_WordRange range = m_SelState.ConvertToWordRange();
Diana Gage22bf7a52017-07-21 11:33:18 -07001738 if (bAddUndo && m_bEnableUndo) {
Diana Gage89e65622017-07-20 18:09:31 -07001739 AddEditUndoItem(
1740 pdfium::MakeUnique<CFXEU_Clear>(this, range, GetSelectedText()));
Diana Gage22bf7a52017-07-21 11:33:18 -07001741 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001742
thestig821d59e2016-05-11 12:59:22 -07001743 SelectNone();
1744 SetCaret(m_pVT->DeleteWords(range));
1745 m_SelState.Set(m_wpCaret, m_wpCaret);
thestig821d59e2016-05-11 12:59:22 -07001746 if (bPaint) {
1747 RearrangePart(range);
1748 ScrollToCaret();
dsinclairefd5a992016-07-18 10:04:07 -07001749 Refresh();
thestig821d59e2016-05-11 12:59:22 -07001750 SetCaretOrigin();
1751 SetCaretInfo();
1752 }
Lei Zhang5688d622017-08-12 07:04:19 -07001753 if (m_pOperationNotify)
1754 m_pOperationNotify->OnClear(m_wpCaret, m_wpOldCaret);
thestig821d59e2016-05-11 12:59:22 -07001755
tsepez4cf55152016-11-02 14:37:54 -07001756 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001757}
1758
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001759bool CPWL_EditImpl::InsertText(const CFX_WideString& sText,
1760 int32_t charset,
1761 bool bAddUndo,
1762 bool bPaint) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001763 if (IsTextOverflow())
tsepez4cf55152016-11-02 14:37:54 -07001764 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001765
1766 m_pVT->UpdateWordPlace(m_wpCaret);
tsepeza31da742016-09-08 11:28:14 -07001767 SetCaret(DoInsertText(m_wpCaret, sText, charset));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001768 m_SelState.Set(m_wpCaret, m_wpCaret);
tsepeza31da742016-09-08 11:28:14 -07001769 if (m_wpCaret == m_wpOldCaret)
tsepez4cf55152016-11-02 14:37:54 -07001770 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001771
tsepeza31da742016-09-08 11:28:14 -07001772 if (bAddUndo && m_bEnableUndo) {
Tom Sepez3509d162017-01-30 13:22:02 -08001773 AddEditUndoItem(pdfium::MakeUnique<CFXEU_InsertText>(
1774 this, m_wpOldCaret, m_wpCaret, sText, charset));
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001775 }
tsepeza31da742016-09-08 11:28:14 -07001776 if (bPaint)
1777 PaintInsertText(m_wpOldCaret, m_wpCaret);
1778
Lei Zhang5688d622017-08-12 07:04:19 -07001779 if (m_pOperationNotify)
1780 m_pOperationNotify->OnInsertText(m_wpCaret, m_wpOldCaret);
tsepeza31da742016-09-08 11:28:14 -07001781
tsepez4cf55152016-11-02 14:37:54 -07001782 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001783}
1784
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001785void CPWL_EditImpl::PaintInsertText(const CPVT_WordPlace& wpOld,
1786 const CPVT_WordPlace& wpNew) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001787 if (m_pVT->IsValid()) {
1788 RearrangePart(CPVT_WordRange(wpOld, wpNew));
1789 ScrollToCaret();
dsinclairefd5a992016-07-18 10:04:07 -07001790 Refresh();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001791 SetCaretOrigin();
1792 SetCaretInfo();
1793 }
1794}
1795
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001796bool CPWL_EditImpl::Redo() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001797 if (m_bEnableUndo) {
1798 if (m_Undo.CanRedo()) {
1799 m_Undo.Redo();
tsepez4cf55152016-11-02 14:37:54 -07001800 return true;
Tom Sepez2f2ffec2015-07-23 14:42:09 -07001801 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001802 }
1803
tsepez4cf55152016-11-02 14:37:54 -07001804 return false;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001805}
1806
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001807bool CPWL_EditImpl::Undo() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001808 if (m_bEnableUndo) {
1809 if (m_Undo.CanUndo()) {
1810 m_Undo.Undo();
tsepez4cf55152016-11-02 14:37:54 -07001811 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001812 }
1813 }
1814
tsepez4cf55152016-11-02 14:37:54 -07001815 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001816}
1817
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001818void CPWL_EditImpl::SetCaretOrigin() {
thestig821d59e2016-05-11 12:59:22 -07001819 if (!m_pVT->IsValid())
1820 return;
1821
1822 CPDF_VariableText::Iterator* pIterator = m_pVT->GetIterator();
1823 pIterator->SetAt(m_wpCaret);
1824 CPVT_Word word;
1825 CPVT_Line line;
1826 if (pIterator->GetWord(word)) {
1827 m_ptCaret.x = word.ptWord.x + word.fWidth;
1828 m_ptCaret.y = word.ptWord.y;
1829 } else if (pIterator->GetLine(line)) {
1830 m_ptCaret.x = line.ptLine.x;
1831 m_ptCaret.y = line.ptLine.y;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001832 }
1833}
1834
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001835CPVT_WordPlace CPWL_EditImpl::WordIndexToWordPlace(int32_t index) const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001836 if (m_pVT->IsValid())
1837 return m_pVT->WordIndexToWordPlace(index);
1838
1839 return CPVT_WordPlace();
1840}
1841
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001842bool CPWL_EditImpl::IsTextFull() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001843 int32_t nTotalWords = m_pVT->GetTotalWords();
1844 int32_t nLimitChar = m_pVT->GetLimitChar();
1845 int32_t nCharArray = m_pVT->GetCharArray();
1846
1847 return IsTextOverflow() || (nLimitChar > 0 && nTotalWords >= nLimitChar) ||
1848 (nCharArray > 0 && nTotalWords >= nCharArray);
1849}
1850
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001851bool CPWL_EditImpl::IsTextOverflow() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001852 if (!m_bEnableScroll && !m_bEnableOverflow) {
Tom Sepez281a9ea2016-02-26 14:24:28 -08001853 CFX_FloatRect rcPlate = m_pVT->GetPlateRect();
1854 CFX_FloatRect rcContent = m_pVT->GetContentRect();
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001855
dsinclair448c4332016-08-02 12:07:35 -07001856 if (m_pVT->IsMultiLine() && GetTotalLines() > 1 &&
1857 IsFloatBigger(rcContent.Height(), rcPlate.Height())) {
tsepez4cf55152016-11-02 14:37:54 -07001858 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001859 }
1860
dsinclair448c4332016-08-02 12:07:35 -07001861 if (IsFloatBigger(rcContent.Width(), rcPlate.Width()))
tsepez4cf55152016-11-02 14:37:54 -07001862 return true;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001863 }
1864
tsepez4cf55152016-11-02 14:37:54 -07001865 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001866}
1867
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001868bool CPWL_EditImpl::CanUndo() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001869 if (m_bEnableUndo) {
1870 return m_Undo.CanUndo();
1871 }
1872
tsepez4cf55152016-11-02 14:37:54 -07001873 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001874}
1875
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001876bool CPWL_EditImpl::CanRedo() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001877 if (m_bEnableUndo) {
1878 return m_Undo.CanRedo();
1879 }
1880
tsepez4cf55152016-11-02 14:37:54 -07001881 return false;
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001882}
1883
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001884void CPWL_EditImpl::EnableRefresh(bool bRefresh) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001885 m_bEnableRefresh = bRefresh;
1886}
1887
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001888void CPWL_EditImpl::EnableUndo(bool bUndo) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001889 m_bEnableUndo = bUndo;
1890}
1891
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001892CPVT_WordPlace CPWL_EditImpl::DoInsertText(const CPVT_WordPlace& place,
1893 const CFX_WideString& sText,
1894 int32_t charset) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001895 CPVT_WordPlace wp = place;
1896
1897 if (m_pVT->IsValid()) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001898 for (int32_t i = 0, sz = sText.GetLength(); i < sz; i++) {
Tom Sepez62a70f92016-03-21 15:00:20 -07001899 uint16_t word = sText[i];
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001900 switch (word) {
1901 case 0x0D:
dsinclairefd5a992016-07-18 10:04:07 -07001902 wp = m_pVT->InsertSection(wp, nullptr, nullptr);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001903 if (sText[i + 1] == 0x0A)
1904 i++;
1905 break;
1906 case 0x0A:
dsinclairefd5a992016-07-18 10:04:07 -07001907 wp = m_pVT->InsertSection(wp, nullptr, nullptr);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001908 if (sText[i + 1] == 0x0D)
1909 i++;
1910 break;
1911 case 0x09:
1912 word = 0x20;
1913 default:
1914 wp = m_pVT->InsertWord(wp, word, GetCharSetFromUnicode(word, charset),
dsinclairefd5a992016-07-18 10:04:07 -07001915 nullptr);
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001916 break;
1917 }
1918 }
1919 }
1920
1921 return wp;
1922}
1923
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001924int32_t CPWL_EditImpl::GetCharSetFromUnicode(uint16_t word,
1925 int32_t nOldCharset) {
dsinclairc7a73492016-04-05 12:01:42 -07001926 if (IPVT_FontMap* pFontMap = GetFontMap())
Nico Weber9d8ec5a2015-08-04 13:00:21 -07001927 return pFontMap->CharSetFromUnicode(word, nOldCharset);
1928 return nOldCharset;
1929}
1930
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001931void CPWL_EditImpl::AddEditUndoItem(
1932 std::unique_ptr<CPWL_EditImpl_UndoItem> pEditUndoItem) {
Lei Zhang1a89e362017-03-23 15:27:25 -07001933 m_Undo.AddItem(std::move(pEditUndoItem));
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001934}
1935
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001936CFX_ByteString CPWL_EditImpl::GetPDFWordString(int32_t nFontIndex,
1937 uint16_t Word,
1938 uint16_t SubWord) {
Dan Sinclairc08dc392017-07-24 08:57:35 -04001939 IPVT_FontMap* pFontMap = GetFontMap();
1940 CPDF_Font* pPDFFont = pFontMap->GetPDFFont(nFontIndex);
1941 if (!pPDFFont)
1942 return CFX_ByteString();
1943
1944 CFX_ByteString sWord;
1945 if (SubWord > 0) {
1946 Word = SubWord;
1947 } else {
1948 uint32_t dwCharCode = pPDFFont->IsUnicodeCompatible()
1949 ? pPDFFont->CharCodeFromUnicode(Word)
1950 : pFontMap->CharCodeFromUnicode(nFontIndex, Word);
1951 if (dwCharCode > 0) {
1952 pPDFFont->AppendChar(&sWord, dwCharCode);
1953 return sWord;
1954 }
1955 }
1956 pPDFFont->AppendChar(&sWord, Word);
1957 return sWord;
1958}
1959
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001960CPWL_EditImpl_LineRectArray::CPWL_EditImpl_LineRectArray() {}
weili625ad662016-06-15 11:21:33 -07001961
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001962CPWL_EditImpl_LineRectArray::~CPWL_EditImpl_LineRectArray() {}
weili625ad662016-06-15 11:21:33 -07001963
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001964void CPWL_EditImpl_LineRectArray::operator=(
1965 CPWL_EditImpl_LineRectArray&& that) {
Tom Sepez3509d162017-01-30 13:22:02 -08001966 m_LineRects = std::move(that.m_LineRects);
weili625ad662016-06-15 11:21:33 -07001967}
1968
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001969void CPWL_EditImpl_LineRectArray::Add(const CPVT_WordRange& wrLine,
1970 const CFX_FloatRect& rcLine) {
1971 m_LineRects.push_back(
1972 pdfium::MakeUnique<CPWL_EditImpl_LineRect>(wrLine, rcLine));
weili625ad662016-06-15 11:21:33 -07001973}
1974
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001975int32_t CPWL_EditImpl_LineRectArray::GetSize() const {
Tom Sepez3509d162017-01-30 13:22:02 -08001976 return pdfium::CollectionSize<int32_t>(m_LineRects);
weili625ad662016-06-15 11:21:33 -07001977}
1978
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001979CPWL_EditImpl_LineRect* CPWL_EditImpl_LineRectArray::GetAt(
1980 int32_t nIndex) const {
Tom Sepez3509d162017-01-30 13:22:02 -08001981 if (nIndex < 0 || nIndex >= GetSize())
weili625ad662016-06-15 11:21:33 -07001982 return nullptr;
1983
Tom Sepez3509d162017-01-30 13:22:02 -08001984 return m_LineRects[nIndex].get();
weili625ad662016-06-15 11:21:33 -07001985}
1986
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001987CPWL_EditImpl_Select::CPWL_EditImpl_Select() {}
weili625ad662016-06-15 11:21:33 -07001988
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001989CPWL_EditImpl_Select::CPWL_EditImpl_Select(const CPVT_WordRange& range) {
weili625ad662016-06-15 11:21:33 -07001990 Set(range.BeginPos, range.EndPos);
1991}
1992
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001993CPVT_WordRange CPWL_EditImpl_Select::ConvertToWordRange() const {
weili625ad662016-06-15 11:21:33 -07001994 return CPVT_WordRange(BeginPos, EndPos);
1995}
1996
Dan Sinclair6b0158f2017-07-24 09:42:55 -04001997void CPWL_EditImpl_Select::Reset() {
Tom Sepez52f69b32017-03-21 13:42:38 -07001998 BeginPos.Reset();
1999 EndPos.Reset();
weili625ad662016-06-15 11:21:33 -07002000}
2001
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002002void CPWL_EditImpl_Select::Set(const CPVT_WordPlace& begin,
2003 const CPVT_WordPlace& end) {
weili625ad662016-06-15 11:21:33 -07002004 BeginPos = begin;
2005 EndPos = end;
2006}
2007
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002008void CPWL_EditImpl_Select::SetEndPos(const CPVT_WordPlace& end) {
weili625ad662016-06-15 11:21:33 -07002009 EndPos = end;
2010}
2011
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002012bool CPWL_EditImpl_Select::IsEmpty() const {
Tom Sepez52f69b32017-03-21 13:42:38 -07002013 return BeginPos == EndPos;
weili625ad662016-06-15 11:21:33 -07002014}
2015
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002016CPWL_EditImpl_RectArray::CPWL_EditImpl_RectArray() {}
weili625ad662016-06-15 11:21:33 -07002017
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002018CPWL_EditImpl_RectArray::~CPWL_EditImpl_RectArray() {}
weili625ad662016-06-15 11:21:33 -07002019
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002020void CPWL_EditImpl_RectArray::Clear() {
Tom Sepez3509d162017-01-30 13:22:02 -08002021 m_Rects.clear();
weili625ad662016-06-15 11:21:33 -07002022}
2023
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002024void CPWL_EditImpl_RectArray::Add(const CFX_FloatRect& rect) {
weili625ad662016-06-15 11:21:33 -07002025 // check for overlapped area
Tom Sepez3509d162017-01-30 13:22:02 -08002026 for (const auto& pRect : m_Rects) {
weili625ad662016-06-15 11:21:33 -07002027 if (pRect && pRect->Contains(rect))
2028 return;
2029 }
Tom Sepez3509d162017-01-30 13:22:02 -08002030 m_Rects.push_back(pdfium::MakeUnique<CFX_FloatRect>(rect));
weili625ad662016-06-15 11:21:33 -07002031}
2032
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002033int32_t CPWL_EditImpl_RectArray::GetSize() const {
Tom Sepez3509d162017-01-30 13:22:02 -08002034 return pdfium::CollectionSize<int32_t>(m_Rects);
weili625ad662016-06-15 11:21:33 -07002035}
2036
Dan Sinclair6b0158f2017-07-24 09:42:55 -04002037CFX_FloatRect* CPWL_EditImpl_RectArray::GetAt(int32_t nIndex) const {
Tom Sepez3509d162017-01-30 13:22:02 -08002038 if (nIndex < 0 || nIndex >= GetSize())
weili625ad662016-06-15 11:21:33 -07002039 return nullptr;
2040
Tom Sepez3509d162017-01-30 13:22:02 -08002041 return m_Rects[nIndex].get();
weili625ad662016-06-15 11:21:33 -07002042}