⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 viewedit.cpp

📁 vc6.0完整版
💻 CPP
📖 第 1 页 / 共 3 页
字号:
// This is a part of the Microsoft Foundation Classes C++ library.
// Copyright (C) 1992-1998 Microsoft Corporation
// All rights reserved.
//
// This source code is only intended as a supplement to the
// Microsoft Foundation Classes Reference and related
// electronic documentation provided with the library.
// See these sources for detailed information regarding the
// Microsoft Foundation Classes product.

#include "stdafx.h"
#include <ctype.h>

#ifdef AFX_CORE4_SEG
#pragma code_seg(AFX_CORE4_SEG)
#endif

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// CEditView

#define new DEBUG_NEW

AFX_STATIC const UINT _afxMsgFindReplace = ::RegisterWindowMessage(FINDMSGSTRING);

#ifdef _UNICODE

AFX_STATIC_DATA HFONT _afxUnicodeFont = 0;

void AFX_CDECL AfxEditviewTerm()
{
	AfxDeleteObject((HGDIOBJ*)&_afxUnicodeFont);
}
char _afxEditviewTerm = (char)atexit(&AfxEditviewTerm);

#endif //_UNICODE

BEGIN_MESSAGE_MAP(CEditView, CCtrlView)
	//{{AFX_MSG_MAP(CEditView)
	ON_UPDATE_COMMAND_UI(ID_EDIT_CUT, OnUpdateNeedSel)
	ON_UPDATE_COMMAND_UI(ID_EDIT_PASTE, OnUpdateNeedClip)
	ON_UPDATE_COMMAND_UI(ID_EDIT_SELECT_ALL, OnUpdateNeedText)
	ON_UPDATE_COMMAND_UI(ID_EDIT_UNDO, OnUpdateEditUndo)
	ON_UPDATE_COMMAND_UI(ID_EDIT_FIND, OnUpdateNeedText)
	ON_UPDATE_COMMAND_UI(ID_EDIT_REPLACE, OnUpdateNeedText)
	ON_UPDATE_COMMAND_UI(ID_EDIT_REPEAT, OnUpdateNeedFind)
	ON_UPDATE_COMMAND_UI(ID_EDIT_COPY, OnUpdateNeedSel)
	ON_UPDATE_COMMAND_UI(ID_EDIT_CLEAR, OnUpdateNeedSel)
	ON_CONTROL_REFLECT_EX(EN_CHANGE, OnEditChange)
	ON_WM_CREATE()
	ON_MESSAGE(WM_SETFONT, OnSetFont)
	ON_COMMAND(ID_EDIT_CUT, OnEditCut)
	ON_COMMAND(ID_EDIT_COPY, OnEditCopy)
	ON_COMMAND(ID_EDIT_PASTE, OnEditPaste)
	ON_COMMAND(ID_EDIT_CLEAR, OnEditClear)
	ON_COMMAND(ID_EDIT_UNDO, OnEditUndo)
	ON_COMMAND(ID_EDIT_SELECT_ALL, OnEditSelectAll)
	ON_COMMAND(ID_EDIT_FIND, OnEditFind)
	ON_COMMAND(ID_EDIT_REPLACE, OnEditReplace)
	ON_COMMAND(ID_EDIT_REPEAT, OnEditRepeat)
	ON_WM_DESTROY()
	//}}AFX_MSG_MAP
	// Special registered message for Find and Replace
	ON_REGISTERED_MESSAGE(_afxMsgFindReplace, OnFindReplaceCmd)
	// Standard Print commands (print only - not preview)
	ON_COMMAND(ID_FILE_PRINT, CCtrlView::OnFilePrint)
	ON_COMMAND(ID_FILE_PRINT_DIRECT, CCtrlView::OnFilePrint)
END_MESSAGE_MAP()

const AFX_DATADEF DWORD CEditView::dwStyleDefault =
	AFX_WS_DEFAULT_VIEW |
	WS_HSCROLL | WS_VSCROLL |
	ES_AUTOHSCROLL | ES_AUTOVSCROLL |
	ES_MULTILINE | ES_NOHIDESEL;

// Operating system specific maximum buffer limit
const AFX_DATADEF UINT CEditView::nMaxSize = 1024U*1024U-1;

/////////////////////////////////////////////////////////////////////////////
// _AFX_EDIT_STATE

_AFX_EDIT_STATE::_AFX_EDIT_STATE()
{
	// Note: it is only necessary to initialize non-zero data.

	bNext = TRUE;
}

_AFX_EDIT_STATE::~_AFX_EDIT_STATE()
{
}

EXTERN_PROCESS_LOCAL(_AFX_EDIT_STATE, _afxEditState)

/////////////////////////////////////////////////////////////////////////////
// CEditView construction/destruction

// pass a NULL style because dwStyleDefault stays for backward compatibility
CEditView::CEditView() : CCtrlView(_T("EDIT"), NULL)
{
	m_nTabStops = 8*4;  // default 8 character positions
	m_hPrinterFont = NULL;
	m_hMirrorFont = NULL;
	m_pShadowBuffer = NULL;
	m_nShadowSize = 0;
}

CEditView::~CEditView()
{
	ASSERT(m_hWnd == NULL);
	ASSERT(m_pShadowBuffer == NULL || afxData.bWin95);
	delete[] m_pShadowBuffer;
}

BOOL CEditView::PreCreateWindow(CREATESTRUCT& cs)
{
	m_dwDefaultStyle = dwStyleDefault;
	return CCtrlView::PreCreateWindow(cs);
}

int CEditView::OnCreate(LPCREATESTRUCT lpcs)
{
	if (CCtrlView::OnCreate(lpcs) != 0)
		return -1;

#ifdef _UNICODE
	AfxLockGlobals(CRIT_EDITVIEW);
	if (_afxUnicodeFont == NULL)
	{
		// get unicode font same size as system font
		HFONT hSystemFont = (HFONT)GetStockObject(SYSTEM_FONT);
		LOGFONT systemFont;
		VERIFY(::GetObject(hSystemFont, sizeof(LOGFONT), (void*)&systemFont));

		// default size and facename, but allow customization
		LOGFONT logFont; memset(&logFont, 0, sizeof(LOGFONT));
		logFont.lfHeight = systemFont.lfHeight;
		logFont.lfWeight = systemFont.lfWeight;
		logFont.lfCharSet = DEFAULT_CHARSET;
		lstrcpy(logFont.lfFaceName, _T("Lucida Sans Unicode"));
		AfxCustomLogFont(AFX_IDS_UNICODE_FONT, &logFont);

		// attempt to create the font
		_afxUnicodeFont = ::CreateFontIndirect(&logFont);
		if (_afxUnicodeFont == NULL)
			TRACE1("Unable to create unicode font '%s'.\n", logFont.lfFaceName);
	}
	AfxUnlockGlobals(CRIT_EDITVIEW);
	// set unicode font instead of using system font
	if (_afxUnicodeFont != NULL)
		SendMessage(WM_SETFONT, (WPARAM)_afxUnicodeFont);
#endif

	GetEditCtrl().LimitText(nMaxSize);
	GetEditCtrl().SetTabStops(m_nTabStops);

	return 0;
}

void CEditView::OnDestroy()
{
	_AFX_EDIT_STATE* pEditState = _afxEditState;
	pEditState->pFindReplaceDlg = NULL;

	CView::OnDestroy();
}

// EDIT controls always turn off WS_BORDER and draw it themselves
void CEditView::CalcWindowRect(LPRECT lpClientRect, UINT nAdjustType)
{
	if (nAdjustType != 0)
	{
		// default behavior for in-place editing handles scrollbars
		DWORD dwStyle = GetStyle();
		if (dwStyle & WS_VSCROLL)
			lpClientRect->right += afxData.cxVScroll - CX_BORDER;
		if (dwStyle & WS_HSCROLL)
			lpClientRect->bottom += afxData.cyHScroll - CY_BORDER;
		return;
	}

	::AdjustWindowRectEx(lpClientRect, GetStyle() | WS_BORDER, FALSE,
		GetExStyle() & ~(WS_EX_CLIENTEDGE));
}

/////////////////////////////////////////////////////////////////////////////
// CEditView document like functions

void CEditView::DeleteContents()
{
	ASSERT_VALID(this);
	ASSERT(m_hWnd != NULL);
	SetWindowText(NULL);
	ASSERT_VALID(this);
}

void CEditView::Serialize(CArchive& ar)
	// Read and write CEditView object to archive, with length prefix.
{
	ASSERT_VALID(this);
	ASSERT(m_hWnd != NULL);
	if (ar.IsStoring())
	{
		UINT nLen = GetBufferLength();
		ar << (DWORD)nLen;
		WriteToArchive(ar);
	}
	else
	{
		DWORD dwLen;
		ar >> dwLen;
		if (dwLen > nMaxSize)
			AfxThrowArchiveException(CArchiveException::badIndex);
		UINT nLen = (UINT)dwLen;
		ReadFromArchive(ar, nLen);
	}
	ASSERT_VALID(this);
}

void CEditView::ReadFromArchive(CArchive& ar, UINT nLen)
	// Read certain amount of text from the file, assume at least nLen
	// characters (not bytes) are in the file.
{
	ASSERT_VALID(this);

	LPVOID hText = LocalAlloc(LMEM_MOVEABLE, (nLen+1)*sizeof(TCHAR));
	if (hText == NULL)
		AfxThrowMemoryException();

	LPTSTR lpszText = (LPTSTR)LocalLock(hText);
	ASSERT(lpszText != NULL);
	if (ar.Read(lpszText, nLen*sizeof(TCHAR)) != nLen*sizeof(TCHAR))
	{
		LocalUnlock(hText);
		LocalFree(hText);
		AfxThrowArchiveException(CArchiveException::endOfFile);
	}
	// Replace the editing edit buffer with the newly loaded data
	lpszText[nLen] = '\0';
#ifndef _UNICODE
	if (afxData.bWin95)
	{
		// set the text with SetWindowText, then free
		BOOL bResult = ::SetWindowText(m_hWnd, lpszText);
		LocalUnlock(hText);
		LocalFree(hText);

		// make sure that SetWindowText was successful
		if (!bResult || ::GetWindowTextLength(m_hWnd) < (int)nLen)
			AfxThrowMemoryException();

		// remove old shadow buffer
		delete[] m_pShadowBuffer;
		m_pShadowBuffer = NULL;
		m_nShadowSize = 0;

		ASSERT_VALID(this);
		return;
	}
#endif
	LocalUnlock(hText);
	HLOCAL hOldText = GetEditCtrl().GetHandle();
	ASSERT(hOldText != NULL);
	LocalFree(hOldText);
	GetEditCtrl().SetHandle((HLOCAL)(UINT)(DWORD)hText);
	Invalidate();
	ASSERT_VALID(this);
}

void CEditView::WriteToArchive(CArchive& ar)
	// Write just the text to an archive, no length prefix.
{
	ASSERT_VALID(this);
	LPCTSTR lpszText = LockBuffer();
	ASSERT(lpszText != NULL);
	UINT nLen = GetBufferLength();
	TRY
	{
		ar.Write(lpszText, nLen*sizeof(TCHAR));
	}
	CATCH_ALL(e)
	{
		UnlockBuffer();
		THROW_LAST();
	}
	END_CATCH_ALL
	UnlockBuffer();
	ASSERT_VALID(this);
}

void CEditView::SerializeRaw(CArchive& ar)
	// Read/Write object as stand-alone file.
{
	ASSERT_VALID(this);
	if (ar.IsStoring())
	{
		WriteToArchive(ar);
	}
	else
	{
		CFile* pFile = ar.GetFile();
		ASSERT(pFile->GetPosition() == 0);
		DWORD nFileSize = pFile->GetLength();
		if (nFileSize/sizeof(TCHAR) > nMaxSize)
		{
			AfxMessageBox(AFX_IDP_FILE_TOO_LARGE);
			AfxThrowUserException();
		}
		// ReadFromArchive takes the number of characters as argument
		ReadFromArchive(ar, (UINT)nFileSize/sizeof(TCHAR));
	}
	ASSERT_VALID(this);
}

/////////////////////////////////////////////////////////////////////////////
// CEditView Printing Helpers

AFX_STATIC UINT AFXAPI _AfxEndOfLine(LPCTSTR lpszText, UINT nLen, UINT nIndex)
{
	ASSERT(AfxIsValidAddress(lpszText, nLen, FALSE));
	LPCTSTR lpsz = lpszText + nIndex;
	LPCTSTR lpszStop = lpszText + nLen;
	while (lpsz < lpszStop && *lpsz != '\r')
		++lpsz;
	return lpsz - lpszText;
}

AFX_STATIC UINT AFXAPI _AfxNextLine(LPCTSTR lpszText, UINT nLen, UINT nIndex)
{
	ASSERT(AfxIsValidAddress(lpszText, nLen, FALSE));
	LPCTSTR lpsz = lpszText + nIndex;
	LPCTSTR lpszStop = lpszText + nLen;
	while (lpsz < lpszStop && *lpsz == '\r')
		++lpsz;
	if (lpsz < lpszStop && *lpsz == '\n')
		++lpsz;
	return lpsz - lpszText;
}

AFX_STATIC UINT AFXAPI
_AfxClipLine(CDC* pDC, int aCharWidths[256], int cxLine, int nTabStop,
	LPCTSTR lpszText, UINT nIndex, UINT nIndexEnd)
{
	ASSERT_VALID(pDC);
	ASSERT(nIndex < nIndexEnd);
	ASSERT(AfxIsValidAddress(lpszText, nIndexEnd, FALSE));

	TEXTMETRIC tm;
	::GetTextMetrics(pDC->m_hDC, &tm);

	// make an initial guess on the number of characters that will fit
	int cx = 0;
	LPCTSTR lpszStart = lpszText + nIndex;
	LPCTSTR lpszStop = lpszText + nIndexEnd;
	LPCTSTR lpsz = lpszStart;
	while (lpsz < lpszStop)
	{
		if (*lpsz == '\t')
			cx += nTabStop - (cx % nTabStop);
		else
		{
#ifdef _UNICODE
			if (*lpsz <= 0xFF)
				cx += aCharWidths[(BYTE)*lpsz];
			else
				cx += tm.tmAveCharWidth;
#else //_UNICODE
			if (_afxDBCS && _istlead(*lpsz))
			{
				++lpsz;
				cx += tm.tmAveCharWidth;
			}
			else
				cx += aCharWidths[(BYTE)*lpsz];
#endif //!_UNICODE
		}
		++lpsz;
		if (cx > cxLine)
			break;
	}

	// adjust for errors in the guess
	cx = pDC->GetTabbedTextExtent(lpszStart, lpsz-lpszStart, 1, &nTabStop).cx;
	if (cx > cxLine)
	{
		// remove characters until it fits
		do
		{
			ASSERT(lpsz != lpszStart);
			if (_afxDBCS)
				lpsz = _tcsdec(lpszStart, lpsz);
			else
				--lpsz;
			cx = pDC->GetTabbedTextExtent(lpszStart, lpsz-lpszStart, 1, &nTabStop).cx;
		} while (cx > cxLine);
	}
	else if (cx < cxLine)
	{
		// add characters until it doesn't fit
		while (lpsz < lpszStop)
		{
			lpsz = _tcsinc(lpsz);
			ASSERT(lpsz <= lpszStop);
			cx = pDC->GetTabbedTextExtent(lpszStart, lpsz-lpszStart, 1, &nTabStop).cx;
			if (cx > cxLine)
			{
				if (_afxDBCS)
					lpsz = _tcsdec(lpszStart, lpsz);
				else
					--lpsz;
				break;
			}
		}
	}

	// return index of character just past the last that would fit
	return lpsz - lpszText;
}

/////////////////////////////////////////////////////////////////////////////
// CEditView Printing support

BOOL CEditView::OnPreparePrinting(CPrintInfo* pInfo)
{
	return DoPreparePrinting(pInfo);
}

void CEditView::OnBeginPrinting(CDC* pDC, CPrintInfo*)
{
	ASSERT_VALID(this);
	ASSERT_VALID(pDC);
	// initialize page start vector
	ASSERT(m_aPageStart.GetSize() == 0);
	m_aPageStart.Add(0);
	ASSERT(m_aPageStart.GetSize() > 0);

	if (m_hPrinterFont == NULL)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -