|
|
1.1 root 1: /*************************************************************************
2: **
3: ** OLE 2 Sample Code
4: **
5: ** outltxtl.c
6: **
7: ** This file contains TextLine methods and related support functions.
8: **
9: ** (c) Copyright Microsoft Corp. 1992 - 1993 All Rights Reserved
10: **
11: *************************************************************************/
12:
13:
14: #include "outline.h"
15:
16: OLEDBGDATA
17:
18: extern LPOUTLINEAPP g_lpApp;
19:
20:
21: /* TextLine_Create
22: * ---------------
23: *
24: * Create a text line object and return the pointer
25: */
26: LPTEXTLINE TextLine_Create(HDC hDC, UINT nTab, LPSTR lpszText)
27: {
28: LPTEXTLINE lpTextLine;
29:
30: lpTextLine=(LPTEXTLINE) New((DWORD)sizeof(TEXTLINE));
31: if (lpTextLine == NULL) {
32: OleDbgAssertSz(lpTextLine!=NULL,"Error allocating TextLine");
33: return NULL;
34: }
35:
36: TextLine_Init(lpTextLine, nTab, hDC);
37:
38: if (lpszText) {
39: lpTextLine->m_nLength = lstrlen(lpszText);
40: lstrcpy((LPSTR)lpTextLine->m_szText, lpszText);
41: } else {
42: lpTextLine->m_nLength = 0;
43: lpTextLine->m_szText[0] = '\0';
44: }
45:
46: TextLine_CalcExtents(lpTextLine, hDC);
47:
48: return(lpTextLine);
49: }
50:
51:
52: /* TextLine_Init
53: * -------------
54: *
55: * Calculate the width/height of a text line object.
56: */
57: void TextLine_Init(LPTEXTLINE lpTextLine, int nTab, HDC hDC)
58: {
59: Line_Init((LPLINE)lpTextLine, nTab, hDC); // init the base class fields
60:
61: ((LPLINE)lpTextLine)->m_lineType = TEXTLINETYPE;
62: lpTextLine->m_nLength = 0;
63: lpTextLine->m_szText[0] = '\0';
64: }
65:
66:
67: /* TextLine_Delete
68: * ---------------
69: *
70: * Delete the TextLine structure
71: */
72: void TextLine_Delete(LPTEXTLINE lpTextLine)
73: {
74: Delete((LPVOID)lpTextLine);
75: }
76:
77:
78: /* TextLine_Edit
79: * -------------
80: *
81: * Edit the text line object.
82: *
83: * Returns TRUE if line was changed
84: * FALSE if the line was NOT changed
85: */
86: BOOL TextLine_Edit(LPTEXTLINE lpLine, HWND hWndDoc, HDC hDC)
87: {
88: #if defined( USE_FRAMETOOLS )
89: LPFRAMETOOLS lptb = OutlineApp_GetFrameTools(g_lpApp);
90: #endif
91: BOOL fStatus = FALSE;
92:
93: #if defined( USE_FRAMETOOLS )
94: FrameTools_FB_GetEditText(lptb, lpLine->m_szText, sizeof(lpLine->m_szText));
95: #else
96: if (! InputTextDlg(hWndDoc, lpLine->m_szText, "Edit Line"))
97: return FALSE;
98: #endif
99:
100: lpLine->m_nLength = lstrlen(lpLine->m_szText);
101: TextLine_CalcExtents(lpLine, hDC);
102: fStatus = TRUE;
103:
104: return fStatus;
105: }
106:
107:
108: /* TextLine_CalcExtents
109: * --------------------
110: *
111: * Calculate the width/height of a text line object.
112: */
113: void TextLine_CalcExtents(LPTEXTLINE lpTextLine, HDC hDC)
114: {
115: SIZE size;
116: LPLINE lpLine = (LPLINE)lpTextLine;
117:
118: if (lpTextLine->m_nLength) {
119: GetTextExtentPoint(hDC, lpTextLine->m_szText,
120: lpTextLine->m_nLength, &size);
121: lpLine->m_nWidthInHimetric=size.cx;
122: lpLine->m_nHeightInHimetric=size.cy;
123: } else {
124: // we still need to calculate proper height even for NULL string
125: TEXTMETRIC tm;
126: GetTextMetrics(hDC, &tm);
127:
128: // required to set height
129: lpLine->m_nHeightInHimetric = tm.tmHeight;
130: lpLine->m_nWidthInHimetric = 0;
131: }
132:
133: // Allow size for boundary space
134: lpLine->m_nHeightInHimetric += 2 *
135: XformHeightInPixelsToHimetric(hDC, LINE_BOUNDARY_WIDTH);
136: lpLine->m_nWidthInHimetric += 2 *
137: XformWidthInPixelsToHimetric(hDC, LINE_BOUNDARY_WIDTH);
138:
139:
140: #if defined( _DEBUG )
141: {
142: RECT rc;
143: rc.left = 0;
144: rc.top = 0;
145: rc.right = XformWidthInHimetricToPixels(hDC,
146: lpLine->m_nWidthInHimetric);
147: rc.bottom = XformHeightInHimetricToPixels(hDC,
148: lpLine->m_nHeightInHimetric);
149:
150: OleDbgOutRect3("TextLine_CalcExtents", (LPRECT)&rc);
151: }
152: #endif
153: }
154:
155:
156:
157: /* TextLine_SetHeightInHimetric
158: * ----------------------------
159: *
160: * Set the height of a textline object.
161: */
162: void TextLine_SetHeightInHimetric(LPTEXTLINE lpTextLine, int nHeight)
163: {
164: if (!lpTextLine)
165: return;
166:
167: ((LPLINE)lpTextLine)->m_nHeightInHimetric = nHeight;
168: }
169:
170:
171:
172: /* TextLine_GetTextLen
173: * -------------------
174: *
175: * Return length of string of the TextLine (not considering the tab level).
176: */
177: int TextLine_GetTextLen(LPTEXTLINE lpTextLine)
178: {
179: return lstrlen((LPSTR)lpTextLine->m_szText);
180: }
181:
182:
183: /* TextLine_GetTextData
184: * --------------------
185: *
186: * Return the string of the TextLine (not considering the tab level).
187: */
188: void TextLine_GetTextData(LPTEXTLINE lpTextLine, LPSTR lpszBuf)
189: {
190: lstrcpy(lpszBuf, (LPSTR)lpTextLine->m_szText);
191: }
192:
193:
194: /* TextLine_GetOutlineData
195: * -----------------------
196: *
197: * Return the CF_OUTLINE format data for the TextLine.
198: */
199: BOOL TextLine_GetOutlineData(LPTEXTLINE lpTextLine, LPTEXTLINE lpBuf)
200: {
201: TextLine_Copy((LPTEXTLINE)lpTextLine, lpBuf);
202: return TRUE;
203: }
204:
205:
206: /* TextLine_Draw
207: * -------------
208: *
209: * Draw a text line object on a DC.
210: * Parameters:
211: * hDC - DC to which the line will be drawn
212: * lpRect - the object rectangle in logical coordinates
213: */
214: void TextLine_Draw(LPTEXTLINE lpTextLine, HDC hDC, LPRECT lpRect)
215: {
216: RECT rc;
217:
218: if (!lpTextLine)
219: return;
220:
221: rc = *lpRect;
222: rc.left += ((LPLINE)lpTextLine)->m_nTabWidthInHimetric;
223: rc.right += ((LPLINE)lpTextLine)->m_nTabWidthInHimetric;
224:
225: ExtTextOut(
226: hDC,
227: rc.left,
228: rc.top,
229: ETO_CLIPPED | ETO_OPAQUE,
230: (LPRECT)&rc,
231: lpTextLine->m_szText,
232: lpTextLine->m_nLength,
233: (LPINT) NULL /* default char spacing */
234: );
235:
236: #if defined( WONT_WORK_IN_METAFILE )
237: SaveDC(hDC);
238: IntersectClipRect(
239: hDC,
240: lpRect->left,
241: lpRect->top,
242: lpRect->right,
243: lpRect->bottom
244: );
245: TabbedTextOut(
246: hDC,
247: lpRect->left+((LPLINE)lpTextLine)->m_nTabWidthInHimetric +
248: XformWidthInPixelsToHimetric(NULL, 1),
249: lpRect->top + XformHeightInPixelsToHimetric(NULL, 1),
250: lpTextLine->m_szText,
251: lpTextLine->m_nLength,
252: 0,
253: NULL,
254: 0
255: );
256: RestoreDC(hDC, -1);
257: #endif
258:
259: }
260:
261: /* TextLine_DrawSelHilight
262: * -----------------------
263: *
264: * Handles selection of textline
265: */
266: void TextLine_DrawSelHilight(LPTEXTLINE lpTextLine, HDC hDC, LPRECT lpRect, UINT itemAction, UINT itemState)
267: {
268: if (itemAction & ODA_SELECT) {
269: // check if there is a selection state change, ==> invert rect
270: if (itemState & ODS_SELECTED) {
271: if (!((LPLINE)lpTextLine)->m_fSelected) {
272: ((LPLINE)lpTextLine)->m_fSelected = TRUE;
273: InvertRect(hDC, (LPRECT)lpRect);
274: }
275: } else {
276: if (((LPLINE)lpTextLine)->m_fSelected) {
277: ((LPLINE)lpTextLine)->m_fSelected = FALSE;
278: InvertRect(hDC, lpRect);
279: }
280: }
281: } else if (itemAction & ODA_DRAWENTIRE) {
282: ((LPLINE)lpTextLine)->m_fSelected=((itemState & ODS_SELECTED) ? TRUE : FALSE);
283: InvertRect(hDC, lpRect);
284: }
285: }
286:
287: /* TextLine_Copy
288: * -------------
289: *
290: * Duplicate a textline
291: */
292: BOOL TextLine_Copy(LPTEXTLINE lpSrcLine, LPTEXTLINE lpDestLine)
293: {
294: _fmemcpy(lpDestLine, lpSrcLine, sizeof(TEXTLINE));
295: return TRUE;
296: }
297:
298:
299: /* TextLine_CopyToDoc
300: * ------------------
301: *
302: * Copy a textline to another Document (usually ClipboardDoc)
303: */
304: BOOL TextLine_CopyToDoc(LPTEXTLINE lpSrcLine, LPOUTLINEDOC lpDestDoc, int nIndex)
305: {
306: LPTEXTLINE lpDestLine;
307: BOOL fStatus = FALSE;
308:
309: lpDestLine = (LPTEXTLINE) New((DWORD)sizeof(TEXTLINE));
310: if (lpDestLine == NULL) {
311: OleDbgAssertSz(lpDestLine!=NULL,"Error allocating TextLine");
312: return FALSE;
313: }
314:
315: if (TextLine_Copy(lpSrcLine, lpDestLine)) {
316: OutlineDoc_AddLine(lpDestDoc, (LPLINE)lpDestLine, nIndex);
317: fStatus = TRUE;
318: }
319:
320: return fStatus;
321: }
322:
323:
324: /* TextLine_SaveToStg
325: * ------------------
326: *
327: * Save a textline into a storage
328: *
329: * Return TRUE if successful, FALSE otherwise
330: */
331: BOOL TextLine_SaveToStg(LPTEXTLINE lpTextLine, UINT uFormat, LPSTORAGE lpSrcStg, LPSTORAGE lpDestStg, LPSTREAM lpLLStm, BOOL fRemember)
332: {
333: HRESULT hrErr;
334: ULONG nWritten;
335:
336: hrErr = lpLLStm->lpVtbl->Write(
337: lpLLStm,
338: (LPVOID)&lpTextLine->m_nLength,
339: sizeof(lpTextLine->m_nLength),
340: &nWritten
341: );
342: if (! OleDbgVerifySz(hrErr == NOERROR, "Error writing TextLine data"))
343: return FALSE;
344:
345: hrErr = lpLLStm->lpVtbl->Write(
346: lpLLStm,
347: (LPVOID)lpTextLine->m_szText,
348: lpTextLine->m_nLength,
349: &nWritten
350: );
351: if (! OleDbgVerifySz(hrErr == NOERROR, "Error writing TextLine data"))
352: return FALSE;
353:
354: return TRUE;
355: }
356:
357:
358: /* TextLine_LoadFromStg
359: * --------------------
360: *
361: * Load a textline from storage
362: */
363: LPLINE TextLine_LoadFromStg(LPSTORAGE lpSrcStg, LPSTREAM lpLLStm, LPOUTLINEDOC lpDestDoc)
364: {
365: HRESULT hrErr;
366: ULONG nRead;
367: LPTEXTLINE lpTextLine;
368:
369: lpTextLine=(LPTEXTLINE) New((DWORD)sizeof(TEXTLINE));
370: if (lpTextLine == NULL) {
371: OleDbgAssertSz(lpTextLine!=NULL,"Error allocating TextLine");
372: return NULL;
373: }
374:
375: TextLine_Init(lpTextLine, 0, NULL);
376:
377: hrErr = lpLLStm->lpVtbl->Read(
378: lpLLStm,
379: (LPVOID)&lpTextLine->m_nLength,
380: sizeof(lpTextLine->m_nLength),
381: &nRead
382: );
383: if (! OleDbgVerifySz(hrErr == NOERROR, "Error reading TextLine data"))
384: return NULL;
385:
386: OleDbgAssert(lpTextLine->m_nLength < sizeof(lpTextLine->m_szText));
387:
388: hrErr = lpLLStm->lpVtbl->Read(
389: lpLLStm,
390: (LPVOID)&lpTextLine->m_szText,
391: lpTextLine->m_nLength,
392: &nRead
393: );
394: if (! OleDbgVerifySz(hrErr == NOERROR, "Error reading TextLine data"))
395: return NULL;
396:
397: lpTextLine->m_szText[lpTextLine->m_nLength] = '\0'; // add str terminator
398:
399: return (LPLINE)lpTextLine;
400: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.