diff options
author | Vadim Dashevskiy <watcherhd@gmail.com> | 2012-05-15 10:38:20 +0000 |
---|---|---|
committer | Vadim Dashevskiy <watcherhd@gmail.com> | 2012-05-15 10:38:20 +0000 |
commit | 48540940b6c28bb4378abfeb500ec45a625b37b6 (patch) | |
tree | 2ef294c0763e802f91d868bdef4229b6868527de /plugins/mTextControl/src/FormattedTextDraw.cpp | |
parent | 5c350913f011e119127baeb32a6aedeb4f0d33bc (diff) |
initial commit
git-svn-id: http://svn.miranda-ng.org/main/trunk@2 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c
Diffstat (limited to 'plugins/mTextControl/src/FormattedTextDraw.cpp')
-rw-r--r-- | plugins/mTextControl/src/FormattedTextDraw.cpp | 551 |
1 files changed, 551 insertions, 0 deletions
diff --git a/plugins/mTextControl/src/FormattedTextDraw.cpp b/plugins/mTextControl/src/FormattedTextDraw.cpp new file mode 100644 index 0000000000..0762e779e9 --- /dev/null +++ b/plugins/mTextControl/src/FormattedTextDraw.cpp @@ -0,0 +1,551 @@ +// Feel free to use this code in your own applications.
+// The Author does not guarantee anything about this code.
+// Author : Yves Maurer
+
+// FormattedTextDraw.cpp : Implementation of CFormattedTextDraw
+
+#include "headers.h"
+
+
+const IID IID_ITextServices = { // 8d33f740-cf58-11ce-a89d-00aa006cadc5
+ 0x8d33f740,
+ 0xcf58,
+ 0x11ce,
+ {0xa8, 0x9d, 0x00, 0xaa, 0x00, 0x6c, 0xad, 0xc5}
+ };
+
+const IID IID_ITextHost = { // c5bdd8d0-d26e-11ce-a89e-00aa006cadc5
+ 0xc5bdd8d0,
+ 0xd26e,
+ 0x11ce,
+ {0xa8, 0x9e, 0x00, 0xaa, 0x00, 0x6c, 0xad, 0xc5}
+ };
+
+static const IID IID_ITextDocument = {
+ 0x8CC497C0,
+ 0xA1DF,
+ 0x11CE,
+ {0x80,0x98,0x00,0xAA,0x00,0x47,0xBE,0x5D}
+ };
+
+/////////////////////////////////////////////////////////////////////////////
+// CallBack functions
+DWORD CALLBACK EditStreamInCallback(DWORD_PTR dwCookie, LPBYTE pbBuff, LONG cb, LONG *pcb)
+{
+ PCOOKIE pCookie = (PCOOKIE) dwCookie;
+ if (pCookie->isUnicode)
+ {
+ if((pCookie->dwSize - pCookie->dwCount)*sizeof(WCHAR) < (DWORD)cb)
+ *pcb = (pCookie->dwSize - pCookie->dwCount)*sizeof(WCHAR);
+ else
+ *pcb = cb&~1UL;
+ CopyMemory(pbBuff, pCookie->unicode+pCookie->dwCount, *pcb);
+ pCookie->dwCount += *pcb/sizeof(WCHAR);
+ } else
+ {
+ if(pCookie->dwSize - pCookie->dwCount < (DWORD)cb)
+ *pcb = pCookie->dwSize - pCookie->dwCount;
+ else
+ *pcb = cb;
+ CopyMemory(pbBuff, pCookie->ansi+pCookie->dwCount, *pcb);
+ pCookie->dwCount += *pcb;
+ }
+
+ return 0; // callback succeeded - no errors
+}
+
+/////////////////////////////////////////////////////////////////////////////
+// CFormattedTextDraw
+HRESULT CFormattedTextDraw::putRTFTextA(char *newVal)
+{
+ HRESULT hr;
+ LRESULT lResult = 0;
+ EDITSTREAM editStream;
+
+ if (!m_spTextServices)
+ return S_FALSE;
+
+ m_editCookie.isUnicode = false;
+ m_editCookie.ansi = newVal;
+ m_editCookie.dwSize = lstrlenA(m_editCookie.ansi);
+ m_editCookie.dwCount = 0;
+ editStream.dwCookie = (DWORD_PTR) &m_editCookie;
+ editStream.dwError = 0;
+ editStream.pfnCallback = (EDITSTREAMCALLBACK)EditStreamInCallback;
+ hr = m_spTextServices->TxSendMessage(EM_STREAMIN, (WPARAM)(SF_RTF), (LPARAM)&editStream, &lResult);
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::putRTFTextW(WCHAR *newVal)
+{
+#ifdef UNICODE
+ HRESULT hr;
+ LRESULT lResult = 0;
+ EDITSTREAM editStream;
+
+ if (!m_spTextServices)
+ return S_FALSE;
+
+ m_editCookie.isUnicode = true;
+ m_editCookie.unicode = newVal;
+ m_editCookie.dwSize = lstrlenW(m_editCookie.unicode);
+ m_editCookie.dwCount = 0;
+ editStream.dwCookie = (DWORD_PTR) &m_editCookie;
+ editStream.dwError = 0;
+ editStream.pfnCallback = (EDITSTREAMCALLBACK)EditStreamInCallback;
+ hr = m_spTextServices->TxSendMessage(EM_STREAMIN, (WPARAM)(SF_RTF|SF_UNICODE), (LPARAM)&editStream, &lResult);
+ return S_OK;
+#else
+ return E_FAIL;
+#endif
+}
+
+HRESULT CFormattedTextDraw::putTextA(char *newVal)
+{
+ HRESULT hr;
+ LRESULT lResult = 0;
+ EDITSTREAM editStream;
+
+ if (!m_spTextServices)
+ return S_FALSE;
+
+ m_editCookie.isUnicode = false;
+ m_editCookie.ansi = newVal;
+ m_editCookie.dwSize = lstrlenA(m_editCookie.ansi);
+ m_editCookie.dwCount = 0;
+ editStream.dwCookie = (DWORD_PTR) &m_editCookie;
+ editStream.dwError = 0;
+ editStream.pfnCallback = (EDITSTREAMCALLBACK)EditStreamInCallback;
+ hr = m_spTextServices->TxSendMessage(EM_STREAMIN, (WPARAM)(SF_TEXT), (LPARAM)&editStream, &lResult);
+
+ CHARFORMAT cf;
+ cf.cbSize = sizeof(cf);
+ cf.dwMask = CFM_FACE|CFM_BOLD;
+ cf.dwEffects = 0;
+ wsprintf(cf.szFaceName, _T("MS Shell Dlg"));
+ m_spTextServices->TxSendMessage(EM_SETCHARFORMAT, (WPARAM)(SCF_ALL), (LPARAM)&cf, &lResult);
+
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::putTextW(WCHAR *newVal)
+{
+#ifdef UNICODE
+ HRESULT hr;
+ LRESULT lResult = 0;
+ EDITSTREAM editStream;
+
+ if (!m_spTextServices)
+ return S_FALSE;
+
+ m_editCookie.isUnicode = true;
+ m_editCookie.unicode = newVal;
+ m_editCookie.dwSize = lstrlenW(m_editCookie.unicode);
+ m_editCookie.dwCount = 0;
+ editStream.dwCookie = (DWORD_PTR) &m_editCookie;
+ editStream.dwError = 0;
+ editStream.pfnCallback = (EDITSTREAMCALLBACK)EditStreamInCallback;
+ hr = m_spTextServices->TxSendMessage(EM_STREAMIN, (WPARAM)(SF_TEXT|SF_UNICODE), (LPARAM)&editStream, &lResult);
+
+ CHARFORMAT cf;
+ cf.cbSize = sizeof(cf);
+ cf.dwMask = CFM_FACE|CFM_BOLD;
+ cf.dwEffects = 0;
+ wsprintf(cf.szFaceName, _T("MS Shell Dlg"));
+ m_spTextServices->TxSendMessage(EM_SETCHARFORMAT, (WPARAM)(SCF_ALL), (LPARAM)&cf, &lResult);
+
+ return S_OK;
+#else
+ return E_FAIL;
+#endif
+}
+
+HRESULT CFormattedTextDraw::Draw(void *hdcDraw, RECT *prc)
+{
+ LOGFONT lf;
+ GetObject(GetCurrentObject((HDC)hdcDraw, OBJ_FONT), sizeof(lf), &lf);
+
+ LRESULT lResult;
+ CHARFORMAT cf;
+ cf.cbSize = sizeof(cf);
+ cf.dwMask = CFM_FACE/*|CFM_COLOR*/|CFM_CHARSET|CFM_SIZE|
+ (lf.lfWeight>=FW_BOLD?CFM_BOLD:0)|
+ (lf.lfItalic?CFM_ITALIC:0)|
+ (lf.lfUnderline?CFM_UNDERLINE:0)|
+ (lf.lfStrikeOut?CFM_STRIKEOUT:0);
+ cf.dwEffects = CFE_BOLD|CFE_ITALIC|CFE_STRIKEOUT|CFE_UNDERLINE;
+ cf.crTextColor = GetTextColor((HDC)hdcDraw);
+ cf.bCharSet = lf.lfCharSet;
+ cf.yHeight = 1440 * abs(lf.lfHeight) / GetDeviceCaps((HDC)hdcDraw, LOGPIXELSY);
+ wsprintf(cf.szFaceName, lf.lfFaceName);
+ m_spTextServices->TxSendMessage(EM_SETCHARFORMAT, (WPARAM)(SCF_ALL), (LPARAM)&cf, &lResult);
+
+ m_spTextServices->TxDraw(
+ DVASPECT_CONTENT, // Draw Aspect
+ 0, // Lindex
+ NULL, // Info for drawing optimization
+ NULL, // target device information
+ (HDC) hdcDraw, // Draw device HDC
+ NULL, // Target device HDC
+ (RECTL *) prc, // Bounding client rectangle
+ NULL, // Clipping rectangle for metafiles
+ (RECT *) NULL, // Update rectangle
+ NULL, // Call back function
+ NULL, // Call back parameter
+ TXTVIEW_INACTIVE); // What view of the object could be TXTVIEW_ACTIVE
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::Create()
+{
+ return CreateTextServicesObject();
+}
+
+HRESULT CFormattedTextDraw::get_NaturalSize(void *hdcDraw, long *Width, long *Height)
+{
+ LOGFONT lf;
+ GetObject(GetCurrentObject((HDC)hdcDraw, OBJ_FONT), sizeof(lf), &lf);
+
+ LRESULT lResult;
+ CHARFORMAT cf;
+ cf.cbSize = sizeof(cf);
+ cf.dwMask = CFM_FACE/*|CFM_COLOR*/|CFM_CHARSET|CFM_SIZE|
+ (lf.lfWeight>=FW_BOLD?CFM_BOLD:0)|
+ (lf.lfItalic?CFM_ITALIC:0)|
+ (lf.lfUnderline?CFM_UNDERLINE:0)|
+ (lf.lfStrikeOut?CFM_STRIKEOUT:0);
+ cf.dwEffects = CFE_BOLD|CFE_ITALIC|CFE_STRIKEOUT|CFE_UNDERLINE;
+ cf.crTextColor = GetTextColor((HDC)hdcDraw);
+ cf.bCharSet = lf.lfCharSet;
+ cf.yHeight = 1440 * abs(lf.lfHeight) / GetDeviceCaps((HDC)hdcDraw, LOGPIXELSY);
+ wsprintf(cf.szFaceName, lf.lfFaceName);
+ m_spTextServices->TxSendMessage(EM_SETCHARFORMAT, (WPARAM)(SCF_ALL), (LPARAM)&cf, &lResult);
+
+ SIZEL szExtent;
+// HDC hdcDraw;
+
+ if (!m_spTextServices)
+ return S_FALSE;
+
+// hdcDraw = GetDC(NULL);
+ *Height = 1;
+ szExtent.cx = *Width;
+ szExtent.cy = *Height;
+ if (m_spTextServices->TxGetNaturalSize(DVASPECT_CONTENT, (HDC)hdcDraw, NULL, NULL, TXTNS_FITTOCONTENT, &szExtent, Width, Height) != S_OK)
+ {
+// ReleaseDC(NULL, hdcDraw);
+ return S_FALSE;
+ }
+
+// ReleaseDC(NULL, hdcDraw);
+ return S_OK;
+}
+
+/////////////////////////////////////////////////////////////////////////////
+// ITextHost functions
+HDC CFormattedTextDraw::TxGetDC()
+{
+ return NULL;
+}
+
+INT CFormattedTextDraw::TxReleaseDC(HDC hdc)
+{
+ return 1;
+}
+
+BOOL CFormattedTextDraw::TxShowScrollBar(INT fnBar, BOOL fShow)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxEnableScrollBar(INT fuSBFlags, INT fuArrowflags)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxSetScrollRange(INT fnBar, LONG nMinPos, INT nMaxPos, BOOL fRedraw)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxSetScrollPos(INT fnBar, INT nPos, BOOL fRedraw)
+{
+ return FALSE;
+}
+
+void CFormattedTextDraw::TxInvalidateRect(LPCRECT prc, BOOL fMode)
+{
+}
+
+void CFormattedTextDraw::TxViewChange(BOOL fUpdate)
+{
+}
+
+BOOL CFormattedTextDraw::TxCreateCaret(HBITMAP hbmp, INT xWidth, INT yHeight)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxShowCaret(BOOL fShow)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxSetCaretPos(INT x, INT y)
+{
+ return FALSE;
+}
+
+BOOL CFormattedTextDraw::TxSetTimer(UINT idTimer, UINT uTimeout)
+{
+ return FALSE;
+}
+
+void CFormattedTextDraw::TxKillTimer(UINT idTimer)
+{
+}
+
+void CFormattedTextDraw::TxScrollWindowEx(INT dx, INT dy, LPCRECT lprcScroll, LPCRECT lprcClip, HRGN hrgnUpdate, LPRECT lprcUpdate, UINT fuScroll)
+{
+}
+
+void CFormattedTextDraw::TxSetCapture(BOOL fCapture)
+{
+}
+
+void CFormattedTextDraw::TxSetFocus()
+{
+}
+
+
+void CFormattedTextDraw::TxSetCursor(HCURSOR hcur, BOOL fText)
+{
+ if (fText)
+ {
+ SetCursor(LoadCursor(NULL, MAKEINTRESOURCE(IDC_ARROW)));
+ } else
+ {
+ SetCursor(hcur);
+ }
+}
+
+BOOL CFormattedTextDraw::TxScreenToClient(LPPOINT lppt)
+{
+ if (!m_hwndParent) return FALSE;
+// BOOL result = ScreenToClient(m_hwndParent, lppt);
+// lppt->x -= m_rcClient.left;
+// lppt->y -= m_rcClient.left;
+ return ScreenToClient(m_hwndParent, lppt);
+}
+
+BOOL CFormattedTextDraw::TxClientToScreen(LPPOINT lppt)
+{
+ if (!m_hwndParent) return FALSE;
+// BOOL result = ;
+// lppt->x -= m_rcClient.left;
+// lppt->y -= m_rcClient.left;
+ return ClientToScreen(m_hwndParent, lppt);
+}
+
+HRESULT CFormattedTextDraw::TxActivate(LONG * plOldState)
+{
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxDeactivate(LONG lNewState)
+{
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetClientRect(LPRECT prc)
+{
+ *prc = m_rcClient;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetViewInset(LPRECT prc)
+{
+ *prc = m_rcViewInset;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetCharFormat(const CHARFORMATW **ppCF)
+{
+ *ppCF = m_pCF;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetParaFormat(const PARAFORMAT **ppPF)
+{
+ *ppPF = &m_PF;
+ return S_OK;
+}
+
+COLORREF CFormattedTextDraw::TxGetSysColor(int nIndex)
+{
+ return GetSysColor(nIndex);
+}
+
+HRESULT CFormattedTextDraw::TxGetBackStyle(TXTBACKSTYLE *pstyle)
+{
+ *pstyle = TXTBACK_TRANSPARENT;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetMaxLength(DWORD *plength)
+{
+ *plength = m_dwMaxLength;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetScrollBars(DWORD *pdwScrollBar)
+{
+ *pdwScrollBar = m_dwScrollbar;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetPasswordChar(TCHAR *pch)
+{
+ return S_FALSE;
+}
+
+HRESULT CFormattedTextDraw::TxGetAcceleratorPos(LONG *pcp)
+{
+ *pcp = -1;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetExtent(LPSIZEL lpExtent)
+{
+ return E_NOTIMPL;
+}
+
+HRESULT CFormattedTextDraw::OnTxCharFormatChange(const CHARFORMATW * pcf)
+{
+ memcpy(m_pCF, pcf, pcf->cbSize);
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::OnTxParaFormatChange(const PARAFORMAT * ppf)
+{
+ memcpy(&m_PF, ppf, ppf->cbSize);
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxGetPropertyBits(DWORD dwMask, DWORD *pdwBits)
+{
+ *pdwBits = m_dwPropertyBits;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::TxNotify(DWORD iNotify, void *pv)
+{
+ return S_OK;
+}
+
+HIMC CFormattedTextDraw::TxImmGetContext()
+{
+ return NULL;
+}
+
+void CFormattedTextDraw::TxImmReleaseContext(HIMC himc)
+{
+}
+
+HRESULT CFormattedTextDraw::TxGetSelectionBarWidth(LONG *lSelBarWidth)
+{
+ *lSelBarWidth = 100;
+ return S_OK;
+}
+
+/////////////////////////////////////////////////////////////////////////////
+// custom functions
+
+HRESULT CFormattedTextDraw::CharFormatFromHFONT(CHARFORMAT2W* pCF, HFONT hFont)
+// Takes an HFONT and fills in a CHARFORMAT2W structure with the corresponding info
+{
+
+ HWND hWnd;
+ LOGFONT lf;
+ HDC hDC;
+ LONG yPixPerInch;
+
+ // Get LOGFONT for default font
+ if (!hFont)
+ hFont = (HFONT) GetStockObject(SYSTEM_FONT);
+
+ // Get LOGFONT for passed hfont
+ if (!GetObject(hFont, sizeof(LOGFONT), &lf))
+ return E_FAIL;
+
+ // Set CHARFORMAT structure
+ memset(pCF, 0, sizeof(CHARFORMAT2W));
+ pCF->cbSize = sizeof(CHARFORMAT2W);
+
+ hWnd = GetDesktopWindow();
+ hDC = GetDC(hWnd);
+ yPixPerInch = GetDeviceCaps(hDC, LOGPIXELSY);
+ pCF->yHeight = -lf.lfHeight * LY_PER_INCH / yPixPerInch;
+ ReleaseDC(hWnd, hDC);
+
+ pCF->yOffset = 0;
+ pCF->crTextColor = 0;
+
+ pCF->dwEffects = CFM_EFFECTS | CFE_AUTOBACKCOLOR;
+ pCF->dwEffects &= ~(CFE_PROTECTED | CFE_LINK | CFE_AUTOCOLOR);
+
+ if(lf.lfWeight < FW_BOLD)
+ pCF->dwEffects &= ~CFE_BOLD;
+
+ if(!lf.lfItalic)
+ pCF->dwEffects &= ~CFE_ITALIC;
+
+ if(!lf.lfUnderline)
+ pCF->dwEffects &= ~CFE_UNDERLINE;
+
+ if(!lf.lfStrikeOut)
+ pCF->dwEffects &= ~CFE_STRIKEOUT;
+
+ pCF->dwMask = CFM_ALL | CFM_BACKCOLOR | CFM_STYLE;
+ pCF->bCharSet = lf.lfCharSet;
+ pCF->bPitchAndFamily = lf.lfPitchAndFamily;
+
+#ifdef UNICODE
+ lstrcpyW(pCF->szFaceName, lf.lfFaceName);
+#else
+ MultiByteToWideChar(CP_ACP, 0, lf.lfFaceName, LF_FACESIZE, pCF->szFaceName, LF_FACESIZE);
+#endif
+
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::InitDefaultCharFormat()
+{
+ return CharFormatFromHFONT(m_pCF, NULL);
+}
+
+HRESULT CFormattedTextDraw::InitDefaultParaFormat()
+{
+ memset(&m_PF, 0, sizeof(PARAFORMAT2));
+ m_PF.cbSize = sizeof(PARAFORMAT2);
+ m_PF.dwMask = PFM_ALL;
+ m_PF.wAlignment = PFA_LEFT;
+ m_PF.cTabCount = 1;
+ m_PF.rgxTabs[0] = lDefaultTab;
+ return S_OK;
+}
+
+HRESULT CFormattedTextDraw::CreateTextServicesObject()
+{
+ HRESULT hr;
+ IUnknown *spUnk;
+
+ hr = MyCreateTextServices(NULL, static_cast<ITextHost*>(this), &spUnk);
+ if (hr == S_OK) {
+ hr = spUnk->QueryInterface(IID_ITextServices, (void**)&m_spTextServices);
+ hr = spUnk->QueryInterface(IID_ITextDocument, (void**)&m_spTextDocument);
+ spUnk->Release();
+ }
+ return hr;
+}
+
|