|
|
1.1 root 1: /*
2: * utility.c - general purpose utility routines
3: *
4: * Created by Microsoft Corporation.
5: * (c) Copyright Microsoft Corp. 1990 - 1992 All Rights Reserved
6: *
7: */
8:
9: //*** INCLUDES ****
10:
11: #include <windows.h>
12: #include <ole.h>
13:
14: #include "global.h"
15: #include "demorc.h"
16: #include "utility.h"
17: #include "object.h"
18: #include "dialog.h"
19:
20: static INT iTimerID = 0;
21: static APPITEMPTR lpaItemHold;
22:
23:
24: /****************************************************************************
25: * ErrorMessage()
26: *
27: * Display a message box containing the specified string from the table.
28: *
29: * id WORD - Index into string table.
30: ***************************************************************************/
31:
32: VOID FAR ErrorMessage( //* ENTRY:
33: DWORD id //* message ID
34: ){ //* LOCAL:
35: CHAR sz[CBMESSAGEMAX]; //* string
36: HWND hwnd; //* parent window handle
37:
38: if (IsWindow(hwndProp))
39: hwnd = hwndProp;
40: else if (IsWindow(hwndFrame))
41: hwnd = hwndFrame;
42: else
43: return;
44:
45: LoadString(hInst, id, sz, CBMESSAGEMAX);
46: MessageBox(hwnd, sz, szAppName, MB_OK | MB_ICONEXCLAMATION);
47:
48: }
49:
50:
51: /****************************************************************************
52: * Hourglass()
53: *
54: * Put up or takes down the hourglass cursor as needed.
55: *
56: * int bToggle - TRUE turns the hour glass on
57: * HG_OFF turn it off
58: ***************************************************************************/
59:
60: VOID FAR Hourglass( //* ENTRY:
61: BOOL bOn //* hourglass on/off
62: ){ //* LOCAL:
63: static HCURSOR hcurWait = NULL; //* hourglass cursor
64: static HCURSOR hcurSaved; //* old cursor
65: static iCount = 0;
66:
67:
68: if (bOn)
69: {
70: iCount++;
71: if (!hcurWait)
72: hcurWait = LoadCursor(NULL, IDC_WAIT);
73: if (!hcurSaved)
74: hcurSaved = SetCursor(hcurWait);
75: }
76: else if (!bOn)
77: {
78: if (--iCount < 0 )
79: iCount = 0;
80: else if (!iCount)
81: {
82: SetCursor(hcurSaved);
83: hcurSaved = NULL;
84: }
85: }
86:
87: }
88:
89: /***************************************************************************
90: * WaitForObject()
91: *
92: * Dispatch messagee until the specified object is not busy.
93: * This allows asynchronous processing to occur.
94: *
95: * lpObject LPOLEOBJECT - pointer to object
96: **************************************************************************/
97:
98: void FAR WaitForObject( //* ENTRY:
99: APPITEMPTR paItem //* pointer to OLE object
100: ){ //* LOCAL
101: BOOL bTimerOn = FALSE;
102:
103: while (OleQueryReleaseStatus(paItem->lpObject) == OLE_BUSY)
104: {
105: lpaItemHold = paItem;
106: if (!bTimerOn)
107: bTimerOn = ToggleBlockTimer(TRUE);//* set timer
108: ProcessMessage(hwndFrame, hAccTable);
109: }
110:
111: if (bTimerOn)
112: ToggleBlockTimer(FALSE);//* toggle timer off
113: }
114:
115: /***************************************************************************
116: * WaitForAllObjects()
117: *
118: * Wait for all asynchronous operations to complete.
119: **************************************************************************/
120:
121: VOID FAR WaitForAllObjects(VOID)
122: {
123: BOOL bTimerOn = FALSE;
124:
125: while (cOleWait)
126: {
127: if (!bTimerOn)
128: bTimerOn = ToggleBlockTimer(TRUE);//* set timer
129:
130: ProcessMessage(hwndFrame, hAccTable) ;
131: }
132:
133: if (bTimerOn)
134: ToggleBlockTimer(FALSE);//* toggle timer off
135:
136: }
137:
138: /****************************************************************************
139: * ProcessMessage()
140: *
141: * Obtain and dispatch a message. Used when in a message dispatch loop.
142: *
143: * Returns BOOL - TRUE if message other than WM_QUIT retrieved
144: * FALSE if WM_QUIT retrieved.
145: ***************************************************************************/
146:
147: BOOL FAR ProcessMessage( //* ENTRY:
148: HWND hwndFrame, //* main window handle
149: HANDLE hAccTable //* accelerator table handle
150: ){ //* LOCAL:
151: BOOL fReturn; //* return value
152: MSG msg; //* message
153:
154: if (fReturn = GetMessage(&msg, NULL, NULL, NULL))
155: {
156: if (cOleWait || !TranslateAccelerator(hwndFrame, hAccTable, &msg))
157: {
158: TranslateMessage(&msg);
159: DispatchMessage(&msg);
160: }
161: }
162: return fReturn;
163:
164: }
165:
166:
167: /****************************************************************************
168: * Dirty()
169: *
170: * Keep track of weather modifications have been made
171: * to the document or not.
172: *
173: * iAction - action type:
174: * DOC_CLEAN set document clean flag true
175: * DOC_DIRTY the opposite
176: * DOC_UNDIRTY undo one dirty op
177: * DOC_QUERY return present state
178: *
179: * Returs int - present value of fDirty; 0 is clean.
180: ***************************************************************************/
181:
182: INT FAR Dirty( //* ENTRY:
183: INT iAction //* see above comment
184: ){ //* LOCAL:
185: static INT iDirty = 0; //* dirty state >0 is dirty
186:
187: switch (iAction)
188: {
189: case DOC_CLEAN:
190: iDirty = 0;
191: break;
192: case DOC_DIRTY:
193: iDirty++;
194: break;
195: case DOC_UNDIRTY:
196: iDirty--;
197: break;
198: case DOC_QUERY:
199: break;
200: }
201: return(iDirty);
202:
203: }
204:
205: /***************************************************************************
206: * ObjectsBusy()
207: *
208: * This function enumerates the OLE objects in the current document
209: * and displays a message box stating whether an object is busy.
210: * This function calls the DisplayBusyMessage() function which
211: * performs most of the work. This function is only used by the macro
212: * BUSY_CHECK(), defined in object.h.
213: *
214: * fSelectionOnly BOOL -NOT USED?
215: *
216: * BOOL - TRUE if one or more objects found to be busy
217: * FALSE otherwise
218: *
219: ***************************************************************************/
220:
221: BOOL FAR ObjectsBusy ()
222: {
223: APPITEMPTR pItem;
224:
225: if (iTimerID)
226: {
227: RetryMessage(NULL,RD_CANCEL);
228: return TRUE;
229: }
230:
231: for (pItem = GetTopItem(); pItem; pItem = GetNextItem(pItem))
232: if (DisplayBusyMessage(pItem))
233: return TRUE;
234:
235: return FALSE;
236:
237: }
238:
239: /***************************************************************************
240: * DisplayBusyMessage()
241: *
242: * This function determines if an object is busy and displays
243: * a message box stating this status.
244: *
245: * Returns BOOL - TRUE if object is busy
246: **************************************************************************/
247:
248: BOOL FAR DisplayBusyMessage ( //* ENTRY:
249: APPITEMPTR paItem //* application item pointer
250: ){ //* LOCAL:
251:
252: if (OleQueryReleaseStatus(paItem->lpObject) == OLE_BUSY)
253: {
254: RetryMessage(paItem,RD_CANCEL);
255: return TRUE;
256: }
257: return FALSE;
258:
259: }
260:
261: /***************************************************************************
262: * CreateNewUniqueName()
263: *
264: * Create a string name unique to this document. This is done by using the
265: * prefix string("OleDemo #") and appending a counter to the end of the
266: * prefix string. The counter is incremented whenever a new object is added.
267: * String will be 14 bytes long.
268: *
269: * Return LPSTR - pointer to unique object name.
270: ***************************************************************************/
271:
272: LPSTR FAR CreateNewUniqueName( //* ENTRY:
273: LPSTR lpstr //* destination pointer
274: ){
275:
276: wsprintf( lpstr, "%s%04d", OBJPREFIX, iObjectNumber++ );
277: return( lpstr );
278:
279: }
280:
281: /***************************************************************************
282: * ValidateName()
283: *
284: * This function ensures that the given object name is valid and unique.
285: *
286: * Returns: BOOL - TRUE if object name valid
287: **************************************************************************/
288:
289: BOOL FAR ValidateName( //* ENTRY:
290: LPSTR lpstr //* pointer to object name
291: ){ //* LOCAL:
292: LPSTR lp; //* worker string
293: INT n;
294: //* check for "OleDemo #" prefix
295: lp = OBJPREFIX;
296:
297: while( *lp )
298: {
299: if( *lpstr != *lp )
300: return( FALSE );
301:
302: lpstr++; lp++;
303: }
304: //* convert string number to int
305: for (n = 0 ; *lpstr ; n = n*10 + (*lpstr - '0'),lpstr++);
306:
307: if( n > 9999 ) //* 9999 is largest legal number
308: return FALSE;
309:
310: if( iObjectNumber <= n) //* Make count > than any current
311: iObjectNumber = n + 1; //* object to ensure uniqueness
312:
313: return TRUE;
314: }
315:
316: /***************************************************************************
317: * FreeAppItem()
318: *
319: * Free application item structure and destroy the associated structure.
320: **************************************************************************/
321:
322: VOID FAR FreeAppItem( //* ENTRY:
323: APPITEMPTR pItem //* pointer to application item
324: ){ //* LOCAL:
325: HANDLE hWork; //* handle used to free
326:
327: if (pItem)
328: { //* destroy the window
329: if (pItem->hwnd)
330: DestroyWindow(pItem->hwnd);
331:
332: hWork = LocalHandle((LPSTR)pItem);//* get handle from pointer
333:
334: if (pItem->aLinkName)
335: DeleteAtom(pItem->aLinkName);
336:
337: if (pItem->aServer)
338: DeleteAtom(pItem->aServer);
339:
340: LocalUnlock(hWork);
341: LocalFree(hWork);
342: }
343:
344: }
345:
346: /***************************************************************************
347: * SizeOfLinkData()
348: *
349: * Find the size of a linkdata string.
350: **************************************************************************/
351:
352: LONG FAR SizeOfLinkData( //* ENTRY:
353: LPSTR lpData //* pointer to link data
354: ){ //* LOCAL:
355: LONG lSize; //* total size
356:
357: lSize = (LONG)lstrlen(lpData)+1; //* get size of classname
358: lSize += (LONG)lstrlen(lpData+lSize)+1; //* get size of doc.
359: lSize += (LONG)lstrlen(lpData+lSize)+2;//* get size of item
360: return lSize;
361:
362: }
363:
364: /****************************************************************************
365: * ShowDoc()
366: *
367: * Display all the child windows associated with a document, or make all the
368: * child windows hidden.
369: ***************************************************************************/
370:
371: VOID FAR ShowDoc( //* ENTRY:
372: LHCLIENTDOC lhcDoc, //* document handle
373: INT iShow //* show/hide
374: ){ //* LOCAL:
375: APPITEMPTR pItem; //* application item pointer
376: APPITEMPTR pItemTop = NULL;
377:
378: for (pItem = GetTopItem(); pItem; pItem = GetNextItem(pItem))
379: {
380: if (pItem->lhcDoc == lhcDoc)
381: {
382: if (!pItemTop)
383: pItemTop = pItem;
384: ShowWindow(pItem->hwnd,(iShow ? SW_SHOW : SW_HIDE));
385: pItem->fVisible = (BOOL)iShow;
386: }
387: }
388:
389: if (pItemTop)
390: SetTopItem(pItemTop);
391:
392: }
393:
394: /****************************************************************************
395: * GetNextActiveItem()
396: *
397: * Returns HWND - the next visible window.
398: ***************************************************************************/
399:
400: APPITEMPTR FAR GetNextActiveItem()
401: { //* LOCAL:
402: APPITEMPTR pItem; //* application item pointer
403:
404: for (pItem = GetTopItem(); pItem; pItem = GetNextItem(pItem))
405: if (pItem->fVisible)
406: break;
407:
408: return pItem;
409:
410: }
411:
412: /****************************************************************************
413: * GetTopItem()
414: ***************************************************************************/
415:
416: APPITEMPTR FAR GetTopItem()
417: {
418: HWND hwnd;
419:
420: if (hwnd = GetTopWindow(hwndFrame))
421: return ((APPITEMPTR)GetWindowLong(hwnd,0));
422: else
423: return NULL;
424:
425: }
426: /****************************************************************************
427: * GetNextItem()
428: ***************************************************************************/
429:
430: APPITEMPTR FAR GetNextItem( //* ENTRY:
431: APPITEMPTR pItem //* application item pointer
432: ){ //* LOCAL:
433: HWND hwnd; //* next item window handle
434:
435: if (hwnd = GetNextWindow(pItem->hwnd, GW_HWNDNEXT))
436: return((APPITEMPTR)GetWindowLong(hwnd,0));
437: else
438: return NULL;
439:
440: }
441:
442: /****************************************************************************
443: * SetTopItem()
444: ***************************************************************************/
445:
446: VOID FAR SetTopItem(
447: APPITEMPTR pItem
448: ){
449: APPITEMPTR pLastItem;
450:
451: pLastItem = GetTopItem();
452: if (pLastItem && pLastItem != pItem)
453: SendMessage(pLastItem->hwnd,WM_NCACTIVATE, 0, 0L);
454:
455: if (!pItem)
456: return;
457:
458: if (pItem->fVisible)
459: {
460: BringWindowToTop(pItem->hwnd);
461: SendMessage(pItem->hwnd,WM_NCACTIVATE, 1, 0L);
462: }
463:
464: }
465:
466: /***************************************************************************
467: * ReallocLinkData()
468: *
469: * Reallocate link data in order to avoid creating lots and lots of global
470: * memory thunks.
471: **************************************************************************/
472:
473: BOOL FAR ReallocLinkData( //* ENTRY:
474: APPITEMPTR pItem, //* application item pointer
475: LONG lSize //* new link data size
476: ){ //* LOCAL:
477: HANDLE handle; //* temporary memory handle
478:
479: handle = GlobalHandle(pItem->lpLinkData);
480: GlobalUnlock(handle);
481:
482: if (!(pItem->lpLinkData = GlobalLock(GlobalReAlloc(handle, lSize, NULL))))
483: {
484: ErrorMessage(E_FAILED_TO_ALLOC);
485: return FALSE;
486: }
487:
488: return TRUE;
489:
490: }
491:
492: /***************************************************************************
493: * AllocLinkData()
494: *
495: * Allocate link data space.
496: **************************************************************************/
497:
498: BOOL FAR AllocLinkData( //* ENTRY:
499: APPITEMPTR pItem, //* application item pointer
500: LONG lSize //* link data size
501: ){
502:
503: if (!(pItem->lpLinkData = GlobalLock(
504: GlobalAlloc(GMEM_DDESHARE | GMEM_ZEROINIT ,lSize)
505: )))
506: {
507: ErrorMessage(E_FAILED_TO_ALLOC);
508: return FALSE;
509: }
510:
511: return TRUE;
512: }
513:
514: /***************************************************************************
515: * FreeLinkData()
516: *
517: * Free the space associated with a linkdata pointer.
518: **************************************************************************/
519:
520: VOID FAR FreeLinkData( //* ENTRY:
521: LPSTR lpLinkData //* pointer to linkdata
522: ){ //* LOCAL:
523: HANDLE handle; //* temporary memory handle
524:
525: if (lpLinkData)
526: {
527: handle = GlobalHandle(lpLinkData);
528: GlobalUnlock(handle);
529: GlobalFree(handle);
530: }
531: }
532:
533: /****************************************************************************
534: * ShowNewWindow()
535: *
536: * Show a new application item window.
537: ***************************************************************************/
538:
539: VOID FAR ShowNewWindow( //* ENTRY:
540: APPITEMPTR pItem
541: ){
542:
543: if (pItem->fVisible)
544: {
545: pItem->fNew = TRUE;
546: SetTopItem(pItem);
547: ShowWindow(pItem->hwnd,SW_SHOW);
548: }
549: else
550: ObjDelete(pItem,OLE_OBJ_DELETE);
551:
552: }
553:
554: /****************************************************************************
555: * UnqualifyPath()
556: *
557: * return pointer to unqualified path name.
558: ***************************************************************************/
559:
560: PSTR FAR UnqualifyPath(PSTR pPath)
561: {
562: PSTR pReturn;
563:
564: for (pReturn = pPath; *pPath; pPath++)
565: if (*pPath == ':' || *pPath == '\\')
566: pReturn = pPath+1;
567:
568: return pReturn;
569:
570: }
571:
572: /****************************************************************************
573: * ToggleBlockTimer()
574: *
575: * Toggle a timer used to check for blocked servers.
576: ***************************************************************************/
577:
578: BOOL FAR ToggleBlockTimer(BOOL bSet)
579: {
580: if (bSet && !iTimerID)
581: {
1.1.1.2 ! root 582: if (iTimerID = SetTimer(hwndFrame,1, 3000, (TIMERPROC) fnTimerBlockProc))
1.1 root 583: return TRUE;
584: }
585: else if (iTimerID)
586: {
587: KillTimer(hwndFrame,1);
588: iTimerID = 0;
589: return TRUE;
590: }
591:
592: return FALSE;
593: }
594:
595: /****************************************************************************
596: * fnTimerBlockProc()
597: *
598: * Timer callback procedure
599: ***************************************************************************/
600:
1.1.1.2 ! root 601: VOID CALLBACK fnTimerBlockProc( //* ENTRY:
1.1 root 602: HWND hWnd,
603: UINT wMsg,
604: UINT iTimerID,
605: DWORD dwTime
606: ){
607:
608: if (!hRetry)
609: RetryMessage(lpaItemHold, RD_RETRY | RD_CANCEL);
610:
611: }
612:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.