// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
 
// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "../../include/pdfwindow/PDFWindow.h"
#include "../../include/pdfwindow/PWL_Wnd.h"
#include "../../include/pdfwindow/PWL_EditCtrl.h"
#include "../../include/pdfwindow/PWL_Edit.h"
#include "../../include/pdfwindow/PWL_ScrollBar.h"
#include "../../include/pdfwindow/PWL_Utils.h"
#include "../../include/pdfwindow/PWL_Caret.h"
#include "../../include/pdfwindow/PWL_FontMap.h"

/* ---------------------------- CPWL_Edit ------------------------------ */

CPWL_Edit::CPWL_Edit() : m_pFillerNotify(NULL), 
	m_pSpellCheck(NULL),
	m_bFocus(FALSE)
{
	m_pFormFiller = NULL;
}

CPWL_Edit::~CPWL_Edit()
{
	ASSERT(m_bFocus == FALSE);
}

CFX_ByteString CPWL_Edit::GetClassName() const
{
	return PWL_CLASSNAME_EDIT;
}

void CPWL_Edit::OnDestroy()
{
}

void CPWL_Edit::SetText(FX_LPCWSTR csText)
{
	CFX_WideString swText = csText;

	if (HasFlag(PES_RICH))
	{		
		CFX_ByteString sValue = CFX_ByteString::FromUnicode(swText);
		
		if (CXML_Element * pXML = CXML_Element::Parse((FX_LPCSTR)sValue,sValue.GetLength()))
		{
			FX_INT32 nCount = pXML->CountChildren();
			FX_BOOL bFirst = TRUE;

			swText.Empty();

			for (FX_INT32 i=0; i<nCount; i++)
			{
				if (CXML_Element * pSubElement = pXML->GetElement(i))
				{
					CFX_ByteString tag=pSubElement->GetTagName();
		   			if (tag.EqualNoCase("p"))
					{
						int nChild = pSubElement->CountChildren();
						CFX_WideString swSection;
						for(FX_INT32 j=0; j<nChild; j++)
						{
							swSection += pSubElement->GetContent(j);
						}
						
						if (bFirst)bFirst = FALSE;
						else
							swText += FWL_VKEY_Return;
						swText += swSection;
					}
				}
			}

			delete pXML;
		}
	}	

	m_pEdit->SetText(swText);
}

void CPWL_Edit::RePosChildWnd()
{
	if (CPWL_ScrollBar * pVSB = this->GetVScrollBar())
	{
		//if (pVSB->IsVisible())
		{
			CPDF_Rect rcWindow = m_rcOldWindow;		
			CPDF_Rect rcVScroll = CPDF_Rect(rcWindow.right,
								rcWindow.bottom,
								rcWindow.right + PWL_SCROLLBAR_WIDTH,
								rcWindow.top);
			pVSB->Move(rcVScroll, TRUE, FALSE);
		}
	}

	if (m_pEditCaret && !HasFlag(PES_TEXTOVERFLOW))
		m_pEditCaret->SetClipRect(CPWL_Utils::InflateRect(GetClientRect(),1.0f)); //+1 for caret beside border

	CPWL_EditCtrl::RePosChildWnd();
}

CPDF_Rect CPWL_Edit::GetClientRect() const
{
	CPDF_Rect rcClient = CPWL_Utils::DeflateRect(GetWindowRect(),(FX_FLOAT)(GetBorderWidth()+GetInnerBorderWidth()));
	
	if (CPWL_ScrollBar * pVSB = this->GetVScrollBar())
	{
		if (pVSB->IsVisible())
		{
			rcClient.right -= PWL_SCROLLBAR_WIDTH;
		}
	}

	return rcClient;
}

void CPWL_Edit::SetAlignFormatH(PWL_EDIT_ALIGNFORMAT_H nFormat, FX_BOOL bPaint/* = TRUE*/)
{
	m_pEdit->SetAlignmentH((FX_INT32)nFormat, bPaint);
}

void CPWL_Edit::SetAlignFormatV(PWL_EDIT_ALIGNFORMAT_V nFormat, FX_BOOL bPaint/* = TRUE*/)
{
	m_pEdit->SetAlignmentV((FX_INT32)nFormat, bPaint);
}

FX_BOOL	CPWL_Edit::CanSelectAll() const
{
	return  GetSelectWordRange() != m_pEdit->GetWholeWordRange();
}

FX_BOOL	CPWL_Edit::CanClear() const
{
	return !IsReadOnly() && m_pEdit->IsSelected();
}

FX_BOOL	CPWL_Edit::CanCopy() const
{
	return 	!HasFlag(PES_PASSWORD) && !HasFlag(PES_NOREAD) && m_pEdit->IsSelected();
}

FX_BOOL	CPWL_Edit::CanCut() const
{
	return 	CanCopy() && !IsReadOnly();
}

FX_BOOL	CPWL_Edit::CanPaste() const
{
	if (IsReadOnly()) return FALSE;

	CFX_WideString swClipboard;
	if (IFX_SystemHandler* pSH = GetSystemHandler())
		swClipboard = pSH->GetClipboardText(GetAttachedHWnd());

	return !swClipboard.IsEmpty();
}

void CPWL_Edit::CopyText()
{
	if (!CanCopy()) return;

	CFX_WideString str = m_pEdit->GetSelText();

	if (IFX_SystemHandler* pSH = GetSystemHandler())
		pSH->SetClipboardText(GetAttachedHWnd(), str);
}

void CPWL_Edit::PasteText()
{
	if (!CanPaste()) return;

	CFX_WideString swClipboard;
	if (IFX_SystemHandler* pSH = GetSystemHandler())
		swClipboard = pSH->GetClipboardText(GetAttachedHWnd());

	if (m_pFillerNotify)
	{
		FX_BOOL bRC = TRUE;
		FX_BOOL bExit = FALSE;
		CFX_WideString strChangeEx;
		int nSelStart = 0;
		int nSelEnd = 0;
		GetSel(nSelStart, nSelEnd);
		m_pFillerNotify->OnBeforeKeyStroke(TRUE, GetAttachedData(), 0 , swClipboard, strChangeEx, nSelStart, nSelEnd, TRUE, bRC, bExit, 0);
		if (!bRC) return;
		if (bExit) return;
	}

	if (swClipboard.GetLength() > 0)
	{
		Clear();
		InsertText(swClipboard);
	}

	if (m_pFillerNotify)
	{
		FX_BOOL bExit = FALSE;
		m_pFillerNotify->OnAfterKeyStroke(TRUE, GetAttachedData(), bExit,0);
		if (bExit) return;
	}
}

void CPWL_Edit::CutText()
{
	if (!CanCut()) return;

	CFX_WideString str = m_pEdit->GetSelText();

	if (IFX_SystemHandler* pSH = GetSystemHandler())
		pSH->SetClipboardText(GetAttachedHWnd(), str);

	m_pEdit->Clear();
}

void CPWL_Edit::OnCreated()
{
	CPWL_EditCtrl::OnCreated();

	if (CPWL_ScrollBar * pScroll = GetVScrollBar())
	{
		pScroll->RemoveFlag(PWS_AUTOTRANSPARENT);
		pScroll->SetTransparency(255);
	}

	SetParamByFlag();

	m_rcOldWindow = GetWindowRect();

	m_pEdit->SetOprNotify(this);
	m_pEdit->EnableOprNotify(TRUE);
}

void CPWL_Edit::SetParamByFlag()
{	
	if (HasFlag(PES_RIGHT))
	{
		m_pEdit->SetAlignmentH(2, FALSE);
	}
	else if (HasFlag(PES_MIDDLE))
	{
		m_pEdit->SetAlignmentH(1, FALSE);
	}
	else
	{
		m_pEdit->SetAlignmentH(0, FALSE);
	}

	if (HasFlag(PES_BOTTOM))
	{
		m_pEdit->SetAlignmentV(2, FALSE);
	}
	else if (HasFlag(PES_CENTER))
	{
		m_pEdit->SetAlignmentV(1, FALSE);
	}
	else
	{
		m_pEdit->SetAlignmentV(0, FALSE);
	}

	if (HasFlag(PES_PASSWORD))
	{
		m_pEdit->SetPasswordChar('*', FALSE);
	}

	m_pEdit->SetMultiLine(HasFlag(PES_MULTILINE), FALSE);
	m_pEdit->SetAutoReturn(HasFlag(PES_AUTORETURN), FALSE);
	m_pEdit->SetAutoFontSize(HasFlag(PWS_AUTOFONTSIZE), FALSE);
	m_pEdit->SetAutoScroll(HasFlag(PES_AUTOSCROLL), FALSE);
	m_pEdit->EnableUndo(HasFlag(PES_UNDO));

	if (HasFlag(PES_TEXTOVERFLOW))
	{
		SetClipRect(CPDF_Rect(0.0f,0.0f,0.0f,0.0f));
		m_pEdit->SetTextOverflow(TRUE, FALSE);
	}
	else
	{
		if (m_pEditCaret)
		{
			m_pEditCaret->SetClipRect(CPWL_Utils::InflateRect(GetClientRect(),1.0f)); //+1 for caret beside border
		}
	}

	if (HasFlag(PES_SPELLCHECK))
	{
		m_pSpellCheck = GetCreationParam().pSpellCheck;
	}
}

void CPWL_Edit::GetThisAppearanceStream(CFX_ByteTextBuf & sAppStream)
{
	CPWL_Wnd::GetThisAppearanceStream(sAppStream);

	CPDF_Rect rcClient = GetClientRect();
	CFX_ByteTextBuf sLine;

	FX_INT32 nCharArray = m_pEdit->GetCharArray();

	if (nCharArray > 0)
	{
		switch (GetBorderStyle())
		{
		case PBS_SOLID:
			{
				sLine << "q\n" << GetBorderWidth() << " w\n" 
					<< CPWL_Utils::GetColorAppStream(GetBorderColor(),FALSE) << " 2 J 0 j\n";					

				for (FX_INT32 i=1;i<nCharArray;i++)
				{
					sLine << rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*i << " "
						<< rcClient.bottom << " m\n"
						<< rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*i << " "
						<< rcClient.top << " l S\n";						
				}

				sLine << "Q\n";					
			}
			break; 
		case PBS_DASH:
			{
				sLine << "q\n" << GetBorderWidth() << " w\n" 
					<< CPWL_Utils::GetColorAppStream(GetBorderColor(),FALSE) << " 2 J 0 j\n"
					<< "[" << GetBorderDash().nDash << " " 
					<< GetBorderDash().nGap << "] " 
					<< GetBorderDash().nPhase << " d\n";

				for (FX_INT32 i=1;i<nCharArray;i++)					
				{
					sLine << rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*i << " "
						<< rcClient.bottom << " m\n"
						<< rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*i << " "
						<< rcClient.top << " l S\n";	
				}

				sLine << "Q\n";
			}
			break;
		}		
	}

	sAppStream << sLine;

	CFX_ByteTextBuf sText;

	CPDF_Point ptOffset = CPDF_Point(0.0f,0.0f);

	CPVT_WordRange wrWhole = m_pEdit->GetWholeWordRange();
	CPVT_WordRange wrSelect = GetSelectWordRange();
	CPVT_WordRange wrVisible = (HasFlag(PES_TEXTOVERFLOW) ? wrWhole : m_pEdit->GetVisibleWordRange());
	CPVT_WordRange wrSelBefore(wrWhole.BeginPos,wrSelect.BeginPos);
	CPVT_WordRange wrSelAfter(wrSelect.EndPos,wrWhole.EndPos);

	CPVT_WordRange wrTemp = CPWL_Utils::OverlapWordRange(GetSelectWordRange(),wrVisible);
	CFX_ByteString sEditSel = CPWL_Utils::GetEditSelAppStream(m_pEdit, ptOffset,
			&wrTemp);

	if (sEditSel.GetLength() > 0)
		sText << CPWL_Utils::GetColorAppStream(PWL_DEFAULT_SELBACKCOLOR) << sEditSel ;

	wrTemp = CPWL_Utils::OverlapWordRange(wrVisible,wrSelBefore);
	CFX_ByteString sEditBefore = CPWL_Utils::GetEditAppStream(m_pEdit, ptOffset,  
			&wrTemp, !HasFlag(PES_CHARARRAY), m_pEdit->GetPasswordChar());			

	if (sEditBefore.GetLength() > 0)
		sText << "BT\n" << CPWL_Utils::GetColorAppStream(GetTextColor()) << sEditBefore << "ET\n";

	wrTemp = CPWL_Utils::OverlapWordRange(wrVisible,wrSelect);
	CFX_ByteString sEditMid = CPWL_Utils::GetEditAppStream(m_pEdit, ptOffset, 
			&wrTemp, !HasFlag(PES_CHARARRAY), m_pEdit->GetPasswordChar());			

	if (sEditMid.GetLength() > 0)
		sText << "BT\n" << CPWL_Utils::GetColorAppStream(CPWL_Color(COLORTYPE_GRAY,1)) << sEditMid << "ET\n";

	wrTemp = CPWL_Utils::OverlapWordRange(wrVisible,wrSelAfter);
	CFX_ByteString sEditAfter = CPWL_Utils::GetEditAppStream(m_pEdit, ptOffset, 
			&wrTemp, !HasFlag(PES_CHARARRAY), m_pEdit->GetPasswordChar());			

	if (sEditAfter.GetLength() > 0)
		sText << "BT\n" << CPWL_Utils::GetColorAppStream(GetTextColor()) << sEditAfter<< "ET\n";

	if (HasFlag(PES_SPELLCHECK))
	{
		CFX_ByteString sSpellCheck = CPWL_Utils::GetSpellCheckAppStream(m_pEdit, m_pSpellCheck, ptOffset, &wrVisible);
		if (sSpellCheck.GetLength() > 0)
			sText << CPWL_Utils::GetColorAppStream(CPWL_Color(COLORTYPE_RGB,1,0,0),FALSE) << sSpellCheck;
	}

	if (sText.GetLength() > 0)
	{
		CPDF_Rect rcClient = this->GetClientRect();
		sAppStream << "q\n/Tx BMC\n";
		
		if (!HasFlag(PES_TEXTOVERFLOW))
			sAppStream << rcClient.left << " " << rcClient.bottom << " "
				<< rcClient.right - rcClient.left << " " << rcClient.top - rcClient.bottom << " re W n\n";

		sAppStream << sText;

		sAppStream << "EMC\nQ\n";
	}
}

void CPWL_Edit::DrawThisAppearance(CFX_RenderDevice* pDevice, CPDF_Matrix* pUser2Device)
{
	CPWL_Wnd::DrawThisAppearance(pDevice,pUser2Device);

	CPDF_Rect rcClient = GetClientRect();
	CFX_ByteTextBuf sLine;

	FX_INT32 nCharArray = m_pEdit->GetCharArray();

	if (nCharArray > 0)
	{
		switch (GetBorderStyle())
		{
		case PBS_SOLID:
			{
				CFX_GraphStateData gsd;
				gsd.m_LineWidth = (FX_FLOAT)GetBorderWidth();

				CFX_PathData path;
				path.SetPointCount((nCharArray-1)*2);
				
				for (FX_INT32 i=0; i<nCharArray-1; i++)
				{					
					path.SetPoint(i*2, rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*(i+1), 
						rcClient.bottom, FXPT_MOVETO);
					path.SetPoint(i*2+1, rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*(i+1),
						rcClient.top, FXPT_LINETO);											
				}			
				if (path.GetPointCount() > 0)
					pDevice->DrawPath(&path, pUser2Device, &gsd,0,  
						CPWL_Utils::PWLColorToFXColor(GetBorderColor(),255), FXFILL_ALTERNATE);
			}
			break; 
		case PBS_DASH:
			{
				CFX_GraphStateData gsd;
				gsd.m_LineWidth = (FX_FLOAT)GetBorderWidth();

				gsd.SetDashCount(2);
				gsd.m_DashArray[0] = (FX_FLOAT)GetBorderDash().nDash;
				gsd.m_DashArray[1] = (FX_FLOAT)GetBorderDash().nGap;
				gsd.m_DashPhase = (FX_FLOAT)GetBorderDash().nPhase;

				CFX_PathData path;
				path.SetPointCount((nCharArray-1)*2);
				
				for (FX_INT32 i=0; i<nCharArray-1; i++)
				{					
					path.SetPoint(i*2, rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*(i+1), 
						rcClient.bottom, FXPT_MOVETO);
					path.SetPoint(i*2+1, rcClient.left + ((rcClient.right - rcClient.left)/nCharArray)*(i+1),
						rcClient.top, FXPT_LINETO);											
				}		
				if (path.GetPointCount() > 0)
					pDevice->DrawPath(&path, pUser2Device, &gsd,0,  
						CPWL_Utils::PWLColorToFXColor(GetBorderColor(),255), FXFILL_ALTERNATE);
			}
			break;
		}		
	}

	CPDF_Rect rcClip;
	CPVT_WordRange wrRange = m_pEdit->GetVisibleWordRange();
	CPVT_WordRange* pRange = NULL;

	if (!HasFlag(PES_TEXTOVERFLOW))
	{
		rcClip = GetClientRect();
		pRange = &wrRange;
	}
IFX_SystemHandler* pSysHandler = GetSystemHandler();
	IFX_Edit::DrawEdit(pDevice,pUser2Device,m_pEdit,
		CPWL_Utils::PWLColorToFXColor(GetTextColor(),this->GetTransparency()),
		CPWL_Utils::PWLColorToFXColor(GetTextStrokeColor(),this->GetTransparency()),
		rcClip,CPDF_Point(0.0f,0.0f),pRange, pSysHandler, m_pFormFiller);

	if (HasFlag(PES_SPELLCHECK))
	{
		CPWL_Utils::DrawEditSpellCheck(pDevice,pUser2Device,m_pEdit,rcClip,
			CPDF_Point(0.0f,0.0f),pRange, this->GetCreationParam().pSpellCheck);
	}
}

FX_BOOL CPWL_Edit::OnLButtonDown(const CPDF_Point & point, FX_DWORD nFlag)
{
	CPWL_Wnd::OnLButtonDown(point,nFlag);

	if (HasFlag(PES_TEXTOVERFLOW) || ClientHitTest(point))
	{
		if (m_bMouseDown)
			this->InvalidateRect();

		m_bMouseDown = TRUE;		
		SetCapture();

		m_pEdit->OnMouseDown(point,IsSHIFTpressed(nFlag),IsCTRLpressed(nFlag));
	}

	return TRUE;
}

FX_BOOL	CPWL_Edit::OnLButtonDblClk(const CPDF_Point & point, FX_DWORD nFlag)
{
	CPWL_Wnd::OnLButtonDblClk(point, nFlag);

	if (HasFlag(PES_TEXTOVERFLOW) || ClientHitTest(point))
	{
		m_pEdit->SelectAll();
	}

	return TRUE;
}

#define WM_PWLEDIT_UNDO					0x01
#define WM_PWLEDIT_REDO					0x02
#define WM_PWLEDIT_CUT					0x03
#define WM_PWLEDIT_COPY					0x04
#define WM_PWLEDIT_PASTE				0x05
#define WM_PWLEDIT_DELETE				0x06
#define WM_PWLEDIT_SELECTALL			0x07
#define WM_PWLEDIT_SUGGEST				0x08

FX_BOOL CPWL_Edit::OnRButtonUp(const CPDF_Point & point, FX_DWORD nFlag)
{
	if (m_bMouseDown) return FALSE;

	CPWL_Wnd::OnRButtonUp(point, nFlag);
	
	if (!HasFlag(PES_TEXTOVERFLOW) && !ClientHitTest(point)) return TRUE;

	IFX_SystemHandler* pSH = GetSystemHandler();
	if (!pSH) return FALSE;

	this->SetFocus();

	CPVT_WordRange wrLatin = GetLatinWordsRange(point);
	CFX_WideString swLatin = m_pEdit->GetRangeText(wrLatin);

	FX_HMENU hPopup = pSH->CreatePopupMenu();
	if (!hPopup) return FALSE;

	CFX_ByteStringArray sSuggestWords;
	CPDF_Point ptPopup = point;

	if (!IsReadOnly())
	{
		if (HasFlag(PES_SPELLCHECK) && !swLatin.IsEmpty())
		{
			if (m_pSpellCheck)
			{
				CFX_ByteString sLatin = CFX_ByteString::FromUnicode(swLatin);

				if (!m_pSpellCheck->CheckWord(sLatin))
				{						
					m_pSpellCheck->SuggestWords(sLatin,sSuggestWords);

					FX_INT32 nSuggest = sSuggestWords.GetSize();

					for (FX_INT32 nWord=0; nWord<nSuggest; nWord++)
					{	
						pSH->AppendMenuItem(hPopup, WM_PWLEDIT_SUGGEST+nWord, sSuggestWords[nWord].UTF8Decode());
					}

					if (nSuggest > 0)
						pSH->AppendMenuItem(hPopup, 0, L"");

					ptPopup = GetWordRightBottomPoint(wrLatin.EndPos);
				}
			}
		}
	}

	IPWL_Provider* pProvider = this->GetProvider();

	if (HasFlag(PES_UNDO))
	{
		pSH->AppendMenuItem(hPopup, WM_PWLEDIT_UNDO, 
			pProvider ? pProvider->LoadPopupMenuString(0) : L"&Undo");
		pSH->AppendMenuItem(hPopup, WM_PWLEDIT_REDO,
			pProvider ? pProvider->LoadPopupMenuString(1) : L"&Redo");
		pSH->AppendMenuItem(hPopup, 0, L"");

		if (!m_pEdit->CanUndo())
			pSH->EnableMenuItem(hPopup, WM_PWLEDIT_UNDO, FALSE);
		if (!m_pEdit->CanRedo())
			pSH->EnableMenuItem(hPopup, WM_PWLEDIT_REDO, FALSE);
	}

	pSH->AppendMenuItem(hPopup, WM_PWLEDIT_CUT, 
		pProvider ? pProvider->LoadPopupMenuString(2) : L"Cu&t");
	pSH->AppendMenuItem(hPopup, WM_PWLEDIT_COPY, 
		pProvider ? pProvider->LoadPopupMenuString(3) : L"&Copy");
	pSH->AppendMenuItem(hPopup, WM_PWLEDIT_PASTE, 
		pProvider ? pProvider->LoadPopupMenuString(4) : L"&Paste");
	pSH->AppendMenuItem(hPopup, WM_PWLEDIT_DELETE, 
		pProvider ? pProvider->LoadPopupMenuString(5) : L"&Delete");

	CFX_WideString swText = pSH->GetClipboardText(this->GetAttachedHWnd());
	if (swText.IsEmpty())
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_PASTE, FALSE);

	if (!m_pEdit->IsSelected())
	{
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_CUT, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_COPY, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_DELETE, FALSE);
	}

	if (IsReadOnly())
	{
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_CUT, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_DELETE, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_PASTE, FALSE);			
	}

	if (HasFlag(PES_PASSWORD))
	{
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_CUT, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_COPY, FALSE);
	}

	if (HasFlag(PES_NOREAD))
	{
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_CUT, FALSE);
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_COPY, FALSE);
	}

	pSH->AppendMenuItem(hPopup, 0, L"");
	pSH->AppendMenuItem(hPopup, WM_PWLEDIT_SELECTALL,
		pProvider ? pProvider->LoadPopupMenuString(6) : L"&Select All");

	if (m_pEdit->GetTotalWords() == 0)
	{
		pSH->EnableMenuItem(hPopup, WM_PWLEDIT_SELECTALL, FALSE);
	}

	FX_INT32 x, y;
	PWLtoWnd(ptPopup, x, y);
	pSH->ClientToScreen(GetAttachedHWnd(), x, y);
	pSH->SetCursor(FXCT_ARROW);
	FX_INT32 nCmd = pSH->TrackPopupMenu(hPopup,
					 x,
					 y,
					 GetAttachedHWnd());


	switch (nCmd)
	{
	case WM_PWLEDIT_UNDO:
		Undo();
		break;
	case WM_PWLEDIT_REDO:
		Redo();
		break;
	case WM_PWLEDIT_CUT:
		this->CutText();
		break;
	case WM_PWLEDIT_COPY:
		this->CopyText();
		break;
	case WM_PWLEDIT_PASTE:
		this->PasteText();
		break;
	case WM_PWLEDIT_DELETE:
		this->Clear();
		break;
	case WM_PWLEDIT_SELECTALL:
		this->SelectAll();
		break;
	case WM_PWLEDIT_SUGGEST + 0:
		SetSel(m_pEdit->WordPlaceToWordIndex(wrLatin.BeginPos),m_pEdit->WordPlaceToWordIndex(wrLatin.EndPos));
		ReplaceSel(sSuggestWords[0].UTF8Decode());
		break;
	case WM_PWLEDIT_SUGGEST + 1:
		SetSel(m_pEdit->WordPlaceToWordIndex(wrLatin.BeginPos),m_pEdit->WordPlaceToWordIndex(wrLatin.EndPos));
		ReplaceSel(sSuggestWords[1].UTF8Decode());
		break;
	case WM_PWLEDIT_SUGGEST + 2:
		SetSel(m_pEdit->WordPlaceToWordIndex(wrLatin.BeginPos),m_pEdit->WordPlaceToWordIndex(wrLatin.EndPos));
		ReplaceSel(sSuggestWords[2].UTF8Decode());
		break;
	case WM_PWLEDIT_SUGGEST + 3:
		SetSel(m_pEdit->WordPlaceToWordIndex(wrLatin.BeginPos),m_pEdit->WordPlaceToWordIndex(wrLatin.EndPos));
		ReplaceSel(sSuggestWords[3].UTF8Decode());
		break;
	case WM_PWLEDIT_SUGGEST + 4:		
		SetSel(m_pEdit->WordPlaceToWordIndex(wrLatin.BeginPos),m_pEdit->WordPlaceToWordIndex(wrLatin.EndPos));
		ReplaceSel(sSuggestWords[4].UTF8Decode());
		break;
	default:
		break;
	}

	pSH->DestroyMenu(hPopup);

	return TRUE;
}

void CPWL_Edit::OnSetFocus()
{
	SetEditCaret(TRUE);

	if (!IsReadOnly())
	{
		if (IPWL_FocusHandler* pFocusHandler = GetFocusHandler())
			pFocusHandler->OnSetFocus(this);
	}

	m_bFocus = TRUE;
}

void CPWL_Edit::OnKillFocus()
{
	ShowVScrollBar(FALSE);
	
	m_pEdit->SelectNone();
	SetCaret(FALSE, CPDF_Point(0.0f,0.0f), CPDF_Point(0.0f,0.0f));
	
	SetCharSet(0);

	if (!IsReadOnly())
	{
		if (IPWL_FocusHandler* pFocusHandler = GetFocusHandler())
			pFocusHandler->OnKillFocus(this);
	}

	m_bFocus = FALSE;
}

void CPWL_Edit::SetHorzScale(FX_INT32 nHorzScale, FX_BOOL bPaint/* = TRUE*/)
{
	m_pEdit->SetHorzScale(nHorzScale, bPaint);
}

void CPWL_Edit::SetCharSpace(FX_FLOAT fCharSpace, FX_BOOL bPaint/* = TRUE*/)
{
	m_pEdit->SetCharSpace(fCharSpace, bPaint);
}

void CPWL_Edit::SetLineLeading(FX_FLOAT fLineLeading, FX_BOOL bPaint/* = TRUE*/)
{
	m_pEdit->SetLineLeading(fLineLeading, bPaint);
}

CFX_ByteString CPWL_Edit::GetSelectAppearanceStream(const CPDF_Point & ptOffset) const
{
	CPVT_WordRange wr = GetSelectWordRange();
	return CPWL_Utils::GetEditSelAppStream(m_pEdit,ptOffset,&wr);
}

CPVT_WordRange CPWL_Edit::GetSelectWordRange() const
{
	if (m_pEdit->IsSelected())
	{
		FX_INT32 nStart = -1;
		FX_INT32 nEnd = -1;

		m_pEdit->GetSel(nStart, nEnd);

		CPVT_WordPlace wpStart = m_pEdit->WordIndexToWordPlace(nStart);
		CPVT_WordPlace wpEnd = m_pEdit->WordIndexToWordPlace(nEnd);

		return CPVT_WordRange(wpStart,wpEnd);
	}

	return CPVT_WordRange();
}

CFX_ByteString CPWL_Edit::GetTextAppearanceStream(const CPDF_Point & ptOffset) const
{
	CFX_ByteTextBuf sRet;
	CFX_ByteString sEdit = CPWL_Utils::GetEditAppStream(m_pEdit,ptOffset);
	
	if (sEdit.GetLength() > 0)
	{
		sRet << "BT\n" << CPWL_Utils::GetColorAppStream(GetTextColor()) << sEdit << "ET\n";
	}

	return sRet.GetByteString();
}

CFX_ByteString CPWL_Edit::GetCaretAppearanceStream(const CPDF_Point & ptOffset) const
{
	if (m_pEditCaret)
		return m_pEditCaret->GetCaretAppearanceStream(ptOffset);

	return CFX_ByteString();
}

CPDF_Point CPWL_Edit::GetWordRightBottomPoint(const CPVT_WordPlace& wpWord)
{
	CPDF_Point pt(0.0f, 0.0f);

	if (IFX_Edit_Iterator * pIterator = m_pEdit->GetIterator())
	{
		CPVT_WordPlace wpOld = pIterator->GetAt();
		pIterator->SetAt(wpWord);
		CPVT_Word word;
		if (pIterator->GetWord(word))
		{
			pt = CPDF_Point(word.ptWord.x + word.fWidth, word.ptWord.y + word.fDescent);
		}

		pIterator->SetAt(wpOld);
	}

	return pt;
}

FX_BOOL	CPWL_Edit::IsTextFull() const
{
	return m_pEdit->IsTextFull();
}

FX_FLOAT CPWL_Edit::GetCharArrayAutoFontSize(CPDF_Font* pFont, const CPDF_Rect& rcPlate, FX_INT32 nCharArray)
{
	if (pFont && !pFont->IsStandardFont())
	{
		FX_RECT rcBBox;
		pFont->GetFontBBox(rcBBox);

		CPDF_Rect rcCell = rcPlate;
		FX_FLOAT xdiv = rcCell.Width() / nCharArray * 1000.0f / rcBBox.Width();
		FX_FLOAT ydiv = - rcCell.Height() * 1000.0f / rcBBox.Height();

		return xdiv < ydiv ? xdiv : ydiv;
	}

	return 0.0f;
}

void CPWL_Edit::SetCharArray(FX_INT32 nCharArray)
{
	if (HasFlag(PES_CHARARRAY) && nCharArray > 0)
	{
		m_pEdit->SetCharArray(nCharArray);	
		m_pEdit->SetTextOverflow(TRUE);

		if (HasFlag(PWS_AUTOFONTSIZE))
		{
			if (IFX_Edit_FontMap* pFontMap = this->GetFontMap())
			{
				FX_FLOAT fFontSize = GetCharArrayAutoFontSize(pFontMap->GetPDFFont(0), GetClientRect(), nCharArray);
				if (fFontSize > 0.0f)
				{
					m_pEdit->SetAutoFontSize(FALSE);
					m_pEdit->SetFontSize(fFontSize);
				}
			}
		}
	}
}

void CPWL_Edit::SetLimitChar(FX_INT32 nLimitChar)
{
	m_pEdit->SetLimitChar(nLimitChar);
}

void CPWL_Edit::ReplaceSel(FX_LPCWSTR csText)
{
	m_pEdit->Clear();
	m_pEdit->InsertText(csText);
}

CPDF_Rect CPWL_Edit::GetFocusRect() const
{
	return CPDF_Rect();
}

void CPWL_Edit::ShowVScrollBar(FX_BOOL bShow)
{
	if (CPWL_ScrollBar * pScroll = GetVScrollBar())
	{
		if (bShow)
		{
			if (!pScroll->IsVisible())
			{
				pScroll->SetVisible(TRUE);
				CPDF_Rect rcWindow = GetWindowRect();
				m_rcOldWindow = rcWindow;
				rcWindow.right += PWL_SCROLLBAR_WIDTH;			
				Move(rcWindow, TRUE, TRUE);
			}
		}
		else
		{
			if (pScroll->IsVisible())
			{
				pScroll->SetVisible(FALSE);
				Move(m_rcOldWindow, TRUE, TRUE);
			}	
		}
	}
}

FX_BOOL	CPWL_Edit::IsVScrollBarVisible() const
{
	if (CPWL_ScrollBar * pScroll = GetVScrollBar())
	{
		return pScroll->IsVisible();
	}

	return FALSE;
}

void CPWL_Edit::EnableSpellCheck(FX_BOOL bEnabled)
{
	if (bEnabled)
		AddFlag(PES_SPELLCHECK);
	else
		RemoveFlag(PES_SPELLCHECK);
}

FX_BOOL CPWL_Edit::OnKeyDown(FX_WORD nChar, FX_DWORD nFlag)
{
	if (m_bMouseDown) return TRUE;

	if (nChar == FWL_VKEY_Delete)
	{
		if (m_pFillerNotify)
		{
			FX_BOOL bRC = TRUE;
			FX_BOOL bExit = FALSE;
			CFX_WideString strChange;
			CFX_WideString strChangeEx;

			int nSelStart = 0;
			int nSelEnd = 0;
			GetSel(nSelStart, nSelEnd);

			if (nSelStart == nSelEnd)
				nSelEnd = nSelStart + 1;
			m_pFillerNotify->OnBeforeKeyStroke(TRUE, GetAttachedData(), FWL_VKEY_Delete, strChange, strChangeEx, nSelStart, nSelEnd, TRUE, bRC, bExit, nFlag);
			if (!bRC) return FALSE;				
			if (bExit) return FALSE;
		}
	}

	FX_BOOL bRet = CPWL_EditCtrl::OnKeyDown(nChar,  nFlag);

	if (nChar == FWL_VKEY_Delete)
	{
		if (m_pFillerNotify)
		{
			FX_BOOL bExit = FALSE;
			m_pFillerNotify->OnAfterKeyStroke(TRUE, GetAttachedData(), bExit,nFlag);
			if (bExit) return FALSE;
		}
	}

	//In case of implementation swallow the OnKeyDown event.
	if(IsProceedtoOnChar(nChar, nFlag))
			return TRUE;

	return bRet;
}

/**
*In case of implementation swallow the OnKeyDown event. 
*If the event is swallowed, implementation may do other unexpected things, which is not the control means to do.
*/
FX_BOOL CPWL_Edit::IsProceedtoOnChar(FX_WORD nKeyCode, FX_DWORD nFlag)
{

	FX_BOOL bCtrl = IsCTRLpressed(nFlag);
	FX_BOOL bAlt = IsALTpressed(nFlag);
	if(bCtrl && !bAlt)
	{
	//hot keys for edit control.	
		switch(nKeyCode)
		{
		case 'C':
		case 'V':
		case 'X':
		case 'A':
		case 'Z':
			return TRUE;
		default:
			break;
		}
	}
	//control characters.
	switch(nKeyCode)
	{
	case FWL_VKEY_Escape:
	case FWL_VKEY_Back:
	case FWL_VKEY_Return:
	case FWL_VKEY_Space:
		return TRUE;
	default:
		break;
	}
	return FALSE;

}

FX_BOOL CPWL_Edit::OnChar(FX_WORD nChar, FX_DWORD nFlag)
{
	if (m_bMouseDown) return TRUE;

	FX_BOOL bRC = TRUE;
	FX_BOOL bExit = FALSE;

	FX_BOOL bCtrl = IsCTRLpressed(nFlag);
	if (!bCtrl)
	{
		if (m_pFillerNotify)
		{
			CFX_WideString swChange;
			FX_INT32 nKeyCode;

			int nSelStart = 0;
			int nSelEnd = 0;
			GetSel(nSelStart, nSelEnd);

			switch (nChar)
			{
			case FWL_VKEY_Back:
				nKeyCode = nChar;
				if (nSelStart == nSelEnd)
					nSelStart = nSelEnd - 1;
				break;
			case FWL_VKEY_Return:
				nKeyCode = nChar;
				break;
			default:
				nKeyCode = 0;
				swChange += nChar;
				break;
			}
		
			CFX_WideString strChangeEx;
			m_pFillerNotify->OnBeforeKeyStroke(TRUE, GetAttachedData(), nKeyCode, swChange, strChangeEx, nSelStart, nSelEnd, TRUE, bRC, bExit, nFlag);
		}
	}

	if (!bRC) return TRUE;
	if (bExit) return FALSE;

	if (IFX_Edit_FontMap * pFontMap = GetFontMap())
	{
		FX_INT32 nOldCharSet = GetCharSet();
		FX_INT32 nNewCharSet = pFontMap->CharSetFromUnicode(nChar, DEFAULT_CHARSET);
		if(nOldCharSet != nNewCharSet)
		{
			SetCharSet(nNewCharSet);
		}
	}
	FX_BOOL bRet = CPWL_EditCtrl::OnChar(nChar,nFlag);

	if (!bCtrl)
	{
		if (m_pFillerNotify)
		{
			m_pFillerNotify->OnAfterKeyStroke(TRUE, GetAttachedData(), bExit,nFlag);
			if (bExit) return FALSE;
		}
	}

	return bRet;
}

FX_BOOL	CPWL_Edit::OnMouseWheel(short zDelta, const CPDF_Point & point, FX_DWORD nFlag)
{
	if (HasFlag(PES_MULTILINE))
	{
		CPDF_Point ptScroll = GetScrollPos();

		if (zDelta > 0)
		{
			ptScroll.y += this->GetFontSize();
		}
		else
		{
			ptScroll.y -= this->GetFontSize();
		}
		this->SetScrollPos(ptScroll);

		return TRUE;
	}

	return FALSE;
}

void CPWL_Edit::OnInsertReturn(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnInsertReturn(place, oldplace);
	}
}

void CPWL_Edit::OnBackSpace(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnBackSpace(place, oldplace);
	}
}

void CPWL_Edit::OnDelete(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnDelete(place, oldplace);
	}
}

void CPWL_Edit::OnClear(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnClear(place, oldplace);
	}
}

void CPWL_Edit::OnInsertWord(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnInsertWord(place, oldplace);
	}
}

void CPWL_Edit::OnSetText(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
}

void CPWL_Edit::OnInsertText(const CPVT_WordPlace& place, const CPVT_WordPlace& oldplace)
{
	if (HasFlag(PES_SPELLCHECK))
	{
		m_pEdit->RefreshWordRange(CombineWordRange(GetLatinWordsRange(oldplace),GetLatinWordsRange(place)));
	}

	if (m_pEditNotify)
	{
		m_pEditNotify->OnInsertText(place, oldplace);
	}
}

void CPWL_Edit::OnAddUndo(IFX_Edit_UndoItem* pUndoItem)
{
	if (m_pEditNotify)
	{
		m_pEditNotify->OnAddUndo(this);
	}
}

CPVT_WordRange CPWL_Edit::CombineWordRange(const CPVT_WordRange& wr1, const CPVT_WordRange& wr2)
{
	CPVT_WordRange wrRet;

	if (wr1.BeginPos.WordCmp(wr2.BeginPos) < 0)
	{
		wrRet.BeginPos = wr1.BeginPos;
	}
	else
	{
		wrRet.BeginPos = wr2.BeginPos;
	}

	if (wr1.EndPos.WordCmp(wr2.EndPos) < 0)
	{
		wrRet.EndPos = wr2.EndPos;
	}
	else
	{
		wrRet.EndPos = wr1.EndPos;
	}

	return wrRet;
}

CPVT_WordRange CPWL_Edit::GetLatinWordsRange(const CPDF_Point& point) const
{
	return GetSameWordsRange(m_pEdit->SearchWordPlace(point), TRUE, FALSE);
}

CPVT_WordRange CPWL_Edit::GetLatinWordsRange(const CPVT_WordPlace & place) const
{
	return GetSameWordsRange(place, TRUE, FALSE);
}

CPVT_WordRange CPWL_Edit::GetArabicWordsRange(const CPVT_WordPlace & place) const
{
	return GetSameWordsRange(place, FALSE, TRUE);
}

#define PWL_ISARABICWORD(word) ((word >= 0x0600 && word <= 0x06FF) || (word >= 0xFB50 && word <= 0xFEFC))

CPVT_WordRange CPWL_Edit::GetSameWordsRange(const CPVT_WordPlace & place, FX_BOOL bLatin, FX_BOOL bArabic) const
{
	CPVT_WordRange range;

	if (IFX_Edit_Iterator* pIterator = m_pEdit->GetIterator())
	{
		CPVT_Word wordinfo;	
		CPVT_WordPlace wpStart(place),wpEnd(place);			
		pIterator->SetAt(place);			
		
		if (bLatin)
		{
			while (pIterator->NextWord())
			{
				if (pIterator->GetWord(wordinfo) && FX_EDIT_ISLATINWORD(wordinfo.Word))
				{
					wpEnd = pIterator->GetAt();
					continue;
				}
				else 
					break;
			};
		}
		else if (bArabic)
		{
			while (pIterator->NextWord())
			{
				if (pIterator->GetWord(wordinfo) && PWL_ISARABICWORD(wordinfo.Word))
				{
					wpEnd = pIterator->GetAt();
					continue;
				}
				else 
					break;
			};
		}

		pIterator->SetAt(place);

		if (bLatin)
		{
			do
			{
				if (pIterator->GetWord(wordinfo) && FX_EDIT_ISLATINWORD(wordinfo.Word))
				{					
					continue;
				}
				else
				{
					wpStart = pIterator->GetAt();
					break;
				}
			}
			while (pIterator->PrevWord());
		}
		else if (bArabic)
		{
			do
			{
				if (pIterator->GetWord(wordinfo) && PWL_ISARABICWORD(wordinfo.Word))
				{					
					continue;
				}
				else
				{
					wpStart = pIterator->GetAt();
					break;
				}
			}
			while (pIterator->PrevWord());
		}

		range.Set(wpStart,wpEnd);
	}	

	return range;
}

void CPWL_Edit::AjustArabicWords(const CPVT_WordRange& wr)
{
}

void CPWL_Edit::GeneratePageObjects(CPDF_PageObjects* pPageObjects, 
										const CPDF_Point& ptOffset, CFX_ArrayTemplate<CPDF_TextObject*>& ObjArray)
{
	IFX_Edit::GeneratePageObjects(pPageObjects, m_pEdit, ptOffset, NULL, CPWL_Utils::PWLColorToFXColor(GetTextColor(),GetTransparency()), ObjArray);
}

void CPWL_Edit::GeneratePageObjects(CPDF_PageObjects* pPageObjects, 
									const CPDF_Point& ptOffset)
{
	CFX_ArrayTemplate<CPDF_TextObject*> ObjArray;
	IFX_Edit::GeneratePageObjects(pPageObjects, m_pEdit, ptOffset, NULL, CPWL_Utils::PWLColorToFXColor(GetTextColor(),GetTransparency()), ObjArray);
}

