home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 October: Mac OS SDK / Dev.CD Oct 96 SDK / Dev.CD Oct 96 SDK2.toast / Development Kits (Disc 2) / OpenDoc / OpenDoc Development / Debugging Support / OpenDoc Source Code / UI / WinStat.cpp < prev    next >
Encoding:
Text File  |  1996-04-22  |  60.4 KB  |  2,312 lines  |  [TEXT/MPS ]

  1. /*
  2.     File:        WinStat.cpp
  3.  
  4.     Contains:    Definition of ODWindowState class
  5.  
  6.     Owned by:    Richard Rodseth
  7.  
  8.     Copyright:    © 1994 - 1996 by Apple Computer, Inc., all rights reserved.
  9.  
  10.     Change History (most recent first):
  11.  
  12.          <2>     1/15/96    TJ        Cleaned Up
  13.         <82>     11/2/95    RR        #1298525, 1298642 Internalize now uses a
  14.                                     SUView on the draftsProperties, and checks
  15.                                     for reference validity
  16.         <81>    10/26/95    eeh        1296308: deal with non-persistant frames in
  17.                                     Internalize
  18.         <80>    10/24/95    RR        #1295596 OpenWindows no longer calls
  19.                                     select() during normal document open.
  20.         <79>    10/18/95    RR        1289153: Recover from exceptions creating /
  21.                                                                         internalizing / registering
  22.                                     windows. Added TRY/CATCH in CATCH block of
  23.                                     ::INnternalize
  24.         <78>    10/17/95    jpa        1289153: Recover from exceptions creating /
  25.                                     internalizing / registering windows.
  26.         <77>    10/16/95    RR        #1293067 Pass shouldDispose to
  27.                                     RegisterWindow
  28.         <76>     10/8/95    TJ        Fixes Recomended by Refball
  29.         <75>     10/3/95    eeh        1287095: use ReleaseObject in
  30.                                     RegisterWindow
  31.         <74>     10/3/95    TJ        Changes done by RefBall Team
  32.         <73>     9/21/95    RR        # 1285189 AcquireFrontWindow calls
  33.                                     FrontWindow() rather than
  34.                                     GetFrontNonFloatingWindow
  35.         <72>     9/13/95    TÇ        1282067 FB3:  UI temp var before SOM_TRY
  36.         <71>     9/12/95    RR        #1274439 Don't activate/deactivate windows
  37.                                     when in background
  38.         <70>      9/6/95    RR        #(1236387) Deactivate before suspend.
  39.                                     Reactivate after Resume
  40.         <69>      9/1/95    RR        # 1279100/1280338 Added IsActive test to
  41.                                     SelectODWindow
  42.         <68>     8/26/95    TÇ        1274606 FB2: Patching Remarks
  43.         <67>     8/25/95    JBS        1263078 FB: fix part editor swapping
  44.         <66>     8/15/95    RR        # 1233767 Use window iterator in
  45.                                     SuspendResume
  46.         <65>     8/12/95    TÇ        1276812 Need to use TempObjs and TempRefs
  47.                                     for exception safety and to avoid TRY
  48.                                     blocks, 1276807 Opt./Bug: use StdTypIO
  49.                                     routines for portable streaming & smaller
  50.                                     footprint, 1276806 Optimization: use
  51.                                     kODFalse instead of kODTrue in comparisons
  52.         <64>      8/3/95    RR        #1257260: Collapse B classes. Remove
  53.                                     somInit methods. Don't call IsInitialized
  54.                                     or SubclassResponsibility
  55.         <63>      8/2/95    VL        1270320: Correct refcounting in
  56.                                     SetCurrentMenuBar and SetBaseMenuBar.
  57.         <62>     6/30/95    RR        1242642 BB Ref counting fixes in
  58.                                     HideODWindow.
  59.         <61>     6/28/95    RR        1242642 BB Mostly ref counting. AddWindow
  60.                                     and RemoveWindow adjust ref counts. Window
  61.                                     iterator skips items marked for lazy
  62.                                     deletion.
  63.         <60>     6/26/95    TÇ        1242642 BB:Fix refcounting bugs
  64.         <59>     6/25/95    TÇ        1242642 BB: Turn on ODDebug warning if
  65.                                     refcount is wrong in
  66.                                     ODRefCntObjectsomUninit.
  67.         <58>     6/22/95    RR        #1245283 Undoable frame deletion
  68.                                     #1209427 Changed private api between
  69.                                     iterator and iteratee. Allow deletion while
  70.                                     iterating
  71.         <57>     6/19/95    jpa        Added hook to check for path pop-up
  72.                                     (cmd-click title bar) [1259398]
  73.         <56>     6/15/95    RR        #1256879 Get->AcquireCurrentMenuBar
  74.         <55>      6/8/95    RR        #1257260 Collapse base classes. #1214898
  75.                                     StdTypes.r -> ODTypes.r
  76.         <54>     5/31/95    RR        #1251403 Release after AcquirePart #1251980
  77.                                     Missing release in GetFrontRootWindow
  78.         <53>     5/26/95    RR        #1251403: Multithreading naming support
  79.         <52>     5/25/95    jpa        List.h --> LinkList.h [1253324]
  80.         <51>     5/17/95    RR        #1250135/1250137/1250143 Getters increment
  81.                                     refcount
  82.         <50>     5/10/95    RR        # 1234319. Check for rootFrameList before
  83.                                     internalizing
  84.         <49>      5/4/95    eeh        1242889: get drafts string from resource
  85.         <48>      5/2/95    RR        # 1244133 Fixed SetDefaultWindowTitles to
  86.                                     avoid extra bogus characters
  87.         <47>     4/28/95    RR        1211085 Remove 5$ comments
  88.         <46>     4/14/95    TÇ        With RR & CG: #1194507 DR/BB:title bar of a
  89.                                     draft window doesn't reveal it is a draft
  90.                                     or which draft it is
  91.         <45>     4/13/95    RR        #1216618 Added ODVolatile
  92.         <44>      4/7/95    RR        #1216618 Added SOM_TRY etc.
  93.         <43>      4/6/95    RR        # 1236361 Call Deactivate in HideODWindow.
  94.                                     Remove redundant code to prevent
  95.                                     deadstripping of PlatformFile
  96.         <42>      4/4/95    RR        # 1220104 Use ODObjectsAreEqual
  97.         <41>     3/22/95    RR        #1225420, 1227993 Parts internalize
  98.                                     windows. Modified OpenWindow, Externalize,
  99.                                     Internalize. Added RegisterWindowForFrame
  100.         <40>     3/10/95    RR        # 1225861 Send Suspend/resume to invisible
  101.                                     windows
  102.         <39>      3/7/95    RR        # 1151165 Cleaned up AdjustPartMenus #
  103.                                     1220929 Added fMenuFocus
  104.         <38>      3/3/95    CC        # 1205622: Ensure activate event is
  105.                                     delivered after modal dialog is dismissed.
  106.         <37>      3/1/95    RR        # 1205622 ::OpenWindows now supports
  107.                                     re-opening an open draft by bringing its
  108.                                     windows to the front.
  109.         <36>     2/24/95    jpa        Use ODNewRgn. [1220810]
  110.         <35>     2/22/95    RR        # 1213850 Call AdjustMenus for root part of
  111.                                     active window before calling it for menu
  112.                                     focus
  113.         <34>     2/20/95    TÇ        #1221861 BB: Incomplete AOCE support needs
  114.                                     to be removed from OpenDoc
  115.         <33>     1/31/95    RR        # 1209165 Rewrote HandleAOCEEvent. #1209552
  116.                                     Call SendBehind in HideODWindow
  117.         <31>     1/26/95    VL        #???: Use updated Storage Unit Ref API.
  118.         <30>     1/25/95    RR        #1211853 Removed session parameter from
  119.                                     CreateMenuBar. Pass _fSession to
  120.                                     InitMenuBar
  121.         <29>     1/23/95    RR        # 1211853 Added CreateMenuBar
  122.         <28>      1/4/95    eeh        1209165: added test to
  123.                                     HandleAOCEMailerEvent
  124.         <27>    12/20/94    VL        1195012: Make Storage calls be
  125.                                     marshallable.
  126.         <26>    12/19/94    eeh        1192626: change ::Internalize not to
  127.                                     duplicate windows already open
  128.         <25>    11/28/94    RR        Check for AOCE presence
  129.         <24>     11/1/94    RR        #1196761 Don't exit HandleAOCEMailerEvent
  130.                                     without handling updates in inactive mailer
  131.                                     windows
  132.         <23>    10/18/94    RR        Used AcquireWindow(id) to validate windows in
  133.                                     CLoseWindows, in case part closed
  134.                                     subsidiary windows
  135.         <22>     9/29/94    RA        1189812: Mods for 68K build.
  136.         <21>     9/23/94    VL        1155579, 1184272: Use StorUtil to
  137.                                     create/get container and its file.
  138.         <20>     9/22/94    eeh        #1154961 AddAOCEMailer takes additional
  139.                                     param.
  140.         <19>     9/19/94    eeh        #1164891: check for userCanceledErr after
  141.                                     SMPMailerEvent call.
  142.         <18>      9/1/94    RR        #1176805 Release old base menu bar
  143.         <17>      9/1/94    CC        RADAR #1181971 - missing factory methods
  144.                                     (for JBS)
  145.         <16>     8/29/94    RR        #1171772 DOn't call SelectWindow
  146.         <15>     8/26/94    TÇ        #1181761 rename obsolete kOD IDs to correct
  147.                                     kODStrong/WeakStorageUnitRefs
  148.         <14>     8/26/94    VL        1183174: Use updated cloning APIs.
  149.         <13>     8/25/94    RR        Added private AcquireBaseMenuBar. Set
  150.                                     generation of menubar in SetBaseMenuBar
  151.         <12>     8/19/94    TÇ        #1180922 Need to Stop using obsolete types
  152.                                     (kOD ID)
  153.         <11>     8/18/94    jpa        Filled in CreateCanvas [1180387]
  154.         <10>     8/16/94    JBS        1180387: add CreateCanvas()
  155.          <9>     8/15/94    JBS        1181138: add frameType to CreateFrame();
  156.                                     1181156: UI API Cleanup
  157.          <8>      8/3/94    VL        1153123: Storage to ODStor.
  158.          <7>     7/27/94    eeh        fix use of Point and Rect (honesty to SOM…)
  159.          <6>     7/21/94    eeh        fix FixUpMailerWindow
  160.          <5>     7/15/94    TÇ        make sure PlatformFile code is not
  161.                                     deadstripped
  162.          <4>      7/8/94    RR        Converted HandleAOCEMailerEvent
  163.          <3>     6/27/94    eeh        add Environment* parameters to
  164.                                     AOCEHelperObj method calls
  165.          <2>     9/27/94    RR        Call InitBaseWindowState
  166.          <1>     9/26/94    RR        first checked in
  167.  
  168.     To Do:
  169.     In Progress:
  170.         
  171. */
  172.  
  173.  
  174. #define ODWindowState_Class_Source
  175. #define VARIABLE_MACROS
  176. #include <WinStat.xih>
  177.  
  178. #ifndef SOM_ODWindowIterator_xh
  179. #include <WinIter.xh>
  180. #endif
  181.  
  182. #ifndef _WINUTILM_
  183. #include "WinUtilM.h" 
  184. #endif
  185.  
  186. #ifndef _UIDEFS_
  187. #include "UIDefs.h"
  188. #endif
  189.  
  190. #ifndef _TEMPOBJ_
  191. #include <TempObj.h>
  192. #endif
  193.  
  194. #ifndef _STDTYPIO_
  195. #include <StdTypIO.h>
  196. #endif
  197.  
  198. #ifndef SOM_ODSession_xh
  199. #include <ODSessn.xh>
  200. #endif
  201.  
  202. #ifndef SOM_ODWindow_xh
  203. #include <Window.xh>
  204. #endif
  205.  
  206. #ifndef SOM_ODMenuBar_xh
  207. #include <MenuBar.xh>
  208. #endif
  209.  
  210. #ifndef SOM_ODArbitrator_xh
  211. #include <Arbitrat.xh>
  212. #endif
  213.  
  214. #ifndef SOM_Module_Apple_defined
  215. #include <Part.xh>
  216. #endif
  217.  
  218. #ifndef SOM_ODFrame_xh
  219. #include <Frame.xh>
  220. #endif
  221.  
  222. #ifndef SOM_ODFacet_xh
  223. #include <Facet.xh>
  224. #endif
  225.  
  226. #ifndef SOM_ODCanvas_xh
  227. #include <Canvas.xh>
  228. #endif
  229.  
  230. #ifndef SOM_ODDraft_xh
  231. #include <Draft.xh>
  232. #endif
  233.  
  234. #ifndef SOM_ODDocument_xh
  235. #include <Document.xh>
  236. #endif
  237.  
  238. #ifndef SOM_ODContainer_xh
  239. #include <ODCtr.xh>
  240. #endif
  241.  
  242. #ifndef SOM_ODStorageSystem_xh
  243. #include <ODStor.xh>
  244. #endif
  245.  
  246. #ifndef SOM_ODStorageUnit_xh
  247. #include <StorageU.xh>
  248. #endif
  249.  
  250. #ifndef SOM_Module_OpenDoc_Commands_defined
  251. #include <CmdDefs.xh>
  252. #endif
  253.  
  254. #ifndef __GESTALTEQU__
  255. #include <GestaltEqu.h>
  256. #endif
  257.  
  258. #ifndef _DLOGUTIL_
  259. #include <DlogUtil.h>
  260. #endif
  261.  
  262. #ifndef _USERSRCM_
  263. #include <UseRsrcM.h>
  264. #endif
  265.  
  266. #ifndef _PLFMFILE_
  267. #include <PlfmFile.h>
  268. #endif
  269.  
  270. #ifndef _PASCLSTR_
  271. #include "PasclStr.h"
  272. #endif
  273.  
  274. #ifndef _LINKLIST_
  275. #include <LinkList.h>
  276. #endif
  277.  
  278. #ifndef _ORDCOLL_
  279. #include "OrdColl.h"
  280. #endif
  281.  
  282. #ifndef _EXCEPT_
  283. #include "Except.h"
  284. #endif
  285.  
  286. #ifndef SOM_Module_OpenDoc_StdTypes_defined
  287. #include <StdTypes.xh>
  288. #endif
  289.  
  290. #ifndef SOM_Module_OpenDoc_StdProps_defined
  291. #include <StdProps.xh>
  292. #endif
  293.  
  294. #ifndef SOM_Module_OpenDoc_Foci_defined
  295. #include <Foci.xh>
  296. #endif
  297.  
  298. #ifndef _ODUTILS_
  299. #include <ODUtils.h>
  300. #endif
  301.  
  302. #ifndef _STORUTIL
  303. #include <StorUtil.h>
  304. #endif
  305.  
  306. #ifndef __LOWMEM__
  307. #include <LowMem.h> // For WindowList global
  308. #endif
  309.  
  310. #ifndef __TOOLUTILS__
  311. #include <ToolUtils.h>
  312. #endif
  313.  
  314. #ifndef _ODDEBUG_
  315. #include "ODDebug.h"    // Adkins -- added
  316. #endif
  317.  
  318. #ifndef _WINPOPM_
  319. #include "WinPopM.h"
  320. #endif
  321.  
  322.  
  323. // New Window API uses a new "WindowRef" type as an opaque window type. So that we can compile
  324. // with or without the new Windows.h, define WindowRef if it's not already defined:      --jpa
  325. #ifndef STRICT_WINDOWS
  326. #define WindowRef WindowPeek
  327. #endif
  328.  
  329. #define ODDebugActivates 0
  330.  
  331. #pragma segment ODWindowState
  332.  
  333. #include "WinStatB.cpp"    // Platform-independent methods, if any
  334.  
  335. static ODBoolean IsFrontProcess()
  336. {
  337.     ProcessSerialNumber    currentPSN;
  338.     ProcessSerialNumber    frontPSN;
  339.     OSErr                getFrontProcessResult;
  340.     OSErr                getCurrentProcessResult;
  341.     ODBoolean                isSameProcess = kODFalse;
  342.     
  343.     // Compare this process and the front process
  344.     getFrontProcessResult = GetFrontProcess(&frontPSN);
  345.     getCurrentProcessResult = GetCurrentProcess(¤tPSN);
  346.     
  347.     if ((getFrontProcessResult == noErr) && (getCurrentProcessResult == noErr))
  348.         SameProcess(&frontPSN, ¤tPSN, &isSameProcess);
  349.         
  350.     return isSameProcess;
  351. }
  352.  
  353.  
  354. SOM_Scope void  SOMLINK ODWindowStateDeactivateFrontWindows(ODWindowState *somSelf, Environment *ev)
  355. {
  356.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  357.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateDeactivateFrontWindows");
  358.     
  359.     SOM_TRY
  360.  
  361.         WindowPtr            firstDocWindow;
  362.         WindowPtr            secondDocWindow;
  363.         WindowPtr            window;
  364.         WindowListIterator    iter;
  365.     
  366.         firstDocWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  367.         if (firstDocWindow != kODNULL)
  368.             secondDocWindow = GetNextWindow(firstDocWindow);
  369.         
  370.         window = iter.First();
  371.         while (iter.IsNotComplete() && (window != secondDocWindow)) 
  372.         {
  373.             if (GetWindowVisible(window) != kODFalse) 
  374.             {
  375.                 somSelf->DeactivateWindow(ev,window);
  376.             }
  377.             window = iter.Next();
  378.         }
  379.         
  380.     SOM_CATCH_ALL
  381.     SOM_ENDTRY
  382. }
  383.  
  384. SOM_Scope void  SOMLINK ODWindowStateActivateFrontWindows(ODWindowState *somSelf, Environment *ev)
  385. {
  386.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  387.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateActivateFrontWindows");
  388.  
  389.     SOM_TRY
  390.     
  391.         WindowPtr            firstDocWindow;
  392.         WindowPtr            secondDocWindow;
  393.         WindowPtr            window;
  394.         WindowListIterator    iter;
  395.         
  396.         firstDocWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  397.         if (firstDocWindow != kODNULL)
  398.             secondDocWindow = GetNextWindow(firstDocWindow);
  399.         
  400.         window = iter.First();
  401.         while (iter.IsNotComplete() && (window != secondDocWindow)) 
  402.         {
  403.             if (GetWindowVisible(window) != kODFalse) 
  404.             {
  405.                 somSelf->ActivateWindow(ev,window);
  406.             }
  407.             window = iter.Next();
  408.         }
  409.  
  410.     SOM_CATCH_ALL
  411.     SOM_ENDTRY
  412. }
  413.  
  414. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireFrontWindow(ODWindowState *somSelf, Environment *ev)
  415. {
  416.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  417.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireFrontWindow");
  418.  
  419.     ODWindow*    odWindow = kODNULL;
  420.  
  421.     SOM_TRY
  422.  
  423.         WindowPtr window = FrontWindow();
  424.         
  425.         if (window != kODNULL) 
  426.         {
  427.             if (somSelf->IsODWindow(ev,window))
  428.                 odWindow = somSelf->AcquireODWindow(ev,window);
  429.         }
  430.  
  431.     SOM_CATCH_ALL
  432.     SOM_ENDTRY
  433.         
  434.     // AcquireODWindow increments ref count
  435.     //if (odWindow)
  436.     //    odWindow->Acquire(ev);    
  437.     return odWindow;
  438. }
  439.  
  440. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireFrontFloatingWindow(ODWindowState *somSelf, Environment *ev)
  441. {
  442.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  443.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireFrontFloatingWindow");
  444.  
  445.     ODWindow* frontFloatingWindow = kODNULL;
  446.     
  447.     SOM_TRY
  448.     
  449.         WindowListIterator    iter;
  450.         
  451.         WindowPtr    platformWindow = iter.First();
  452.         while (iter.IsNotComplete() && (frontFloatingWindow == kODNULL)) 
  453.         {
  454.             ODWindow*    odWindow = somSelf->AcquireODWindow(ev,platformWindow);
  455.             if (odWindow != kODNULL) 
  456.             {
  457.                 if (odWindow->IsFloating(ev) != kODFalse) 
  458.                 {
  459.                     frontFloatingWindow = odWindow;
  460.                 }
  461.                 else
  462.                 {
  463.                     ODReleaseObject(ev, odWindow);    // -- TÇ: released only if we don't want it.
  464.                 }
  465.             }
  466.         }
  467.  
  468.     SOM_CATCH_ALL
  469.     
  470.         frontFloatingWindow = kODNULL;
  471.         
  472.     SOM_ENDTRY
  473.  
  474.     // AcquireODWindow increments ref count
  475.     //if (frontFloatingWindow)
  476.     //    frontFloatingWindow->Acquire(ev);
  477.     return frontFloatingWindow;
  478. }
  479.  
  480. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireFrontRootWindow(ODWindowState *somSelf, Environment *ev)
  481. {
  482.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  483.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireFrontRootWindow");
  484.  
  485.     ODWindow* odWindow = kODNULL;
  486.  
  487.     SOM_TRY
  488.  
  489.         WindowListIterator    iter;
  490.         
  491.         for (WindowPtr platformWindow = iter.First(); 
  492.             iter.IsNotComplete(); 
  493.             platformWindow = iter.Next())
  494.         {
  495.             odWindow = somSelf->AcquireODWindow(ev,platformWindow);
  496.             if (odWindow && odWindow->IsRootWindow(ev))
  497.                 break;
  498.             else
  499.                 ODReleaseObject(ev, odWindow);                
  500.         }
  501.  
  502.     SOM_CATCH_ALL
  503.     
  504.         odWindow = kODNULL;
  505.         
  506.     SOM_ENDTRY
  507.  
  508.     // AcquireODWindow increments ref count
  509.     //if (odWindow)
  510.     //    odWindow->Acquire(ev);
  511.     return odWindow;    // -- TÇ: was acquired in the for loop above.
  512. }
  513.  
  514. SOM_Scope void  SOMLINK ODWindowStateInitWindowState(ODWindowState *somSelf, Environment *ev,
  515.         ODSession* session)
  516. {
  517.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  518.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateInitWindowState");
  519.  
  520.     LinkedList* linkedList = kODNULL; ODVolatile(linkedList);
  521.     
  522.     SOM_TRY
  523.     
  524.         /* Moved from somInit. SOM itself sets fields to zero
  525.         _fWindowList = kODNULL;
  526.         _fSession = kODNULL;
  527.         _fBaseMenuBar = kODNULL;
  528.         _fCurrentMenuBar = kODNULL;
  529.         _fNextID = 0;
  530.         _fMenuFocus = 0;
  531.         _fIteratorCount = 0;
  532.         */
  533.         
  534.         somSelf->InitObject(ev);    
  535.         _fSession = session;
  536.         _fMenuFocus = _fSession->Tokenize(ev,kODMenuFocus);
  537.         linkedList = new LinkedList;
  538.         _fWindowList = linkedList;
  539.     
  540.     SOM_CATCH_ALL
  541.     
  542.         ODDeleteObject(linkedList);
  543.         
  544.     SOM_ENDTRY
  545. }
  546.  
  547. SOM_Scope void  SOMLINK ODWindowStateSetCurrentMenuBar(ODWindowState *somSelf, Environment *ev,
  548.         ODMenuBar* theMenuBar)
  549. {
  550.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  551.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateSetCurrentMenuBar");
  552.  
  553.     SOM_TRY
  554.  
  555.         if (!ODObjectsAreEqual(ev, _fCurrentMenuBar, theMenuBar))
  556.         {
  557.             ODReleaseObject(ev, _fCurrentMenuBar);
  558.             if (theMenuBar)
  559.                 theMenuBar->Acquire(ev);
  560.             _fCurrentMenuBar = theMenuBar;
  561.         }
  562.  
  563.     SOM_CATCH_ALL
  564.     SOM_ENDTRY
  565. }
  566.  
  567. SOM_Scope ODMenuBar*  SOMLINK ODWindowStateAcquireCurrentMenuBar(ODWindowState *somSelf, Environment *ev)
  568. {
  569.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  570.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetCurrentMenuBar");
  571.  
  572.     SOM_TRY
  573.     
  574.     if (_fCurrentMenuBar)
  575.         _fCurrentMenuBar->Acquire(ev);
  576.     
  577.     SOM_CATCH_ALL
  578.     SOM_ENDTRY
  579.     return _fCurrentMenuBar;
  580. }
  581.  
  582. SOM_Scope ODMenuBar*  SOMLINK ODWindowStateAcquireBaseMenuBar(ODWindowState *somSelf, Environment *ev)
  583. {
  584.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  585.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireBaseMenuBar");
  586.  
  587.     SOM_TRY
  588.     
  589.     if (_fBaseMenuBar)
  590.         _fBaseMenuBar->Acquire(ev);
  591.     
  592.     SOM_CATCH_ALL
  593.     SOM_ENDTRY
  594.     
  595.     return _fBaseMenuBar;
  596. }
  597.  
  598. SOM_Scope ODWindow*  SOMLINK ODWindowStateAddWindow(ODWindowState *somSelf, Environment *ev,
  599.         ODWindow* window)
  600. {
  601.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  602.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAddWindow");
  603.  
  604.     SOM_TRY
  605.  
  606.         if (window)
  607.         {
  608.             ODBoolean found = kODFalse;
  609.             WindowLink* foundLink = kODNULL;
  610.         
  611.             LinkedListIterator iter(_fWindowList);
  612.             
  613.             for ( WindowLink* link = (WindowLink*) iter.First();
  614.                     iter.IsNotComplete(); 
  615.                     link = (WindowLink*) iter.Next())
  616.             {
  617.                 if (!link->ShouldRemove() && ODObjectsAreEqual(ev, link->fWindow, window))
  618.                 {
  619.                     found = kODTrue;
  620.                     foundLink = link;
  621.                     break;                
  622.                 }
  623.             }
  624.             if (!found)
  625.             {
  626.                 // There is a problem here. We assume that the window is always going to be
  627.                 // in front. We may need to change the Window API to handle the case when
  628.                 // someone actually wants a window at the back.
  629.                 
  630.                 WindowPtr    platformWindow = window->GetPlatformWindow(ev);
  631.                 WindowPtr    lastFloatingWindow = somSelf->GetLastFloatingPlatformWindow(ev);
  632.                 if (lastFloatingWindow != kODNULL) {
  633.                     SendBehind(platformWindow, lastFloatingWindow);
  634.                 }
  635.                 else {
  636.                     BringToFront(platformWindow);
  637.                 }
  638.                 
  639.                 window->Acquire(ev);
  640.                 _fNextID++;
  641.                 WindowLink* link = new WindowLink(_fNextID, window);
  642.                 window->SetID(ev,_fNextID);
  643.                 THROW_IF_NULL(link);
  644.                 _fWindowList->AddLast(link);
  645.             }
  646.         }
  647.  
  648.     SOM_CATCH_ALL
  649.     
  650.         window = kODNULL;
  651.         
  652.     SOM_ENDTRY
  653.  
  654.     return window;
  655. }
  656.  
  657. SOM_Scope void  SOMLINK ODWindowStateRemoveWindow(ODWindowState *somSelf, Environment *ev,
  658.         ODWindow* oldWindow)
  659. {
  660.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  661.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateRemoveWindow");
  662.  
  663.     SOM_TRY
  664.     
  665.         ODBoolean found = kODFalse;
  666.         WindowLink* foundLink = kODNULL;
  667.     
  668.         LinkedListIterator iter(_fWindowList);
  669.         
  670.         for ( WindowLink* link = (WindowLink*) iter.First();
  671.                 iter.IsNotComplete(); 
  672.                 link = (WindowLink*) iter.Next())
  673.         {
  674.             if (!link->ShouldRemove() && ODObjectsAreEqual(ev, link->fWindow, oldWindow))
  675.             {
  676.                 found = kODTrue;
  677.                 foundLink = link;
  678.                 break;                
  679.             }
  680.         }
  681.         if (found)
  682.         {
  683.             ODWindow* window = foundLink->fWindow;
  684.             ODReleaseObject(ev, window);
  685.             if (_fIteratorCount > 0)
  686.             {
  687.                 foundLink->fRemove = kODTrue;
  688.             }
  689.             else
  690.             {
  691.                 _fWindowList->Remove(*foundLink);
  692.                 ODDeleteObject(foundLink);
  693.             }
  694.         }
  695.         
  696.     SOM_CATCH_ALL
  697.     SOM_ENDTRY
  698. }
  699.  
  700. SOM_Scope ODWindow*  SOMLINK ODWindowStateFindODWindow(ODWindowState *somSelf, Environment *ev,
  701.         Point* globalPoint)
  702. {
  703.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  704.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateFindODWindow");
  705.  
  706.     ODWindow* odWindow = kODNULL;
  707.     
  708.     SOM_TRY
  709.     
  710.         WindowPtr window;
  711.         FindWindow(*globalPoint, &window);
  712.         if (window)
  713.             odWindow = somSelf->AcquireODWindow(ev,window);
  714.  
  715.     SOM_CATCH_ALL
  716.     SOM_ENDTRY
  717.     
  718.     return odWindow;    // -- TÇ: ODWindowStateFindODWindow is an 'acquire' function
  719. }
  720.  
  721. SOM_Scope void  SOMLINK ODWindowStateReleaseWindow(ODWindowState *somSelf, Environment *ev,
  722.         ODWindow* window)
  723. {
  724.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  725.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateReleaseWindow");
  726.  
  727.     SOM_TRY
  728.  
  729.         ODDeleteObject(window);
  730.  
  731.     SOM_CATCH_ALL
  732.     SOM_ENDTRY
  733. }
  734.  
  735. SOM_Scope void  SOMLINK ODWindowStateSuspendResume(ODWindowState *somSelf, Environment *ev,
  736.         ODEventData* event)
  737. {
  738.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  739.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateSuspendResume");
  740.  
  741.     SOM_TRY
  742.     
  743.         const short kResumeMask = 0x01;    // High byte suspend/resume event 
  744.         
  745.         ODBoolean    goingToBackground = (event->message & kResumeMask) == 0;
  746.         // WindowPtr    frontWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  747.         //ODWindow* odWindow = kODNULL;
  748.  
  749.     #if ODDebug && ODDebugActivates
  750.         somPrintf("WindowState Suspend/Resume %d\n", !goingToBackground);
  751.     #endif
  752.             
  753.         ODWindowIterator* iter = somSelf->CreateWindowIterator(ev);
  754.         
  755.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev); window = iter->Next(ev))
  756.         {
  757.             window->SuspendResume(ev,event);
  758.         }
  759.         ODDeleteObject(iter);
  760.         
  761.         // Deactivate the front doc window and any floaters that haven't been hidden. 
  762.         // The system only unhilites the frontmost window
  763.  
  764.         if (goingToBackground)
  765.         {
  766.     #if ODDebug && ODDebugActivates
  767.         somPrintf("WindowState Suspend Event - deactivate front windows\n");
  768.     #endif
  769.             somSelf->DeactivateFrontWindows(ev);
  770.         }
  771.         else
  772.         {
  773.     #if ODDebug && ODDebugActivates
  774.         somPrintf("WindowState Resume Event - activate front windows\n");
  775.     #endif
  776.             somSelf->ActivateFrontWindows(ev);
  777.         }
  778.  
  779.     SOM_CATCH_ALL
  780.     SOM_ENDTRY
  781. }
  782.  
  783. SOM_Scope void  SOMLINK ODWindowStateSelectODWindow(ODWindowState *somSelf, Environment *ev,
  784.         ODWindow* window)
  785. {
  786.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  787.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateSelectODWindow");
  788.  
  789.     SOM_TRY
  790.     
  791.         WindowPtr            currentFrontWindow;
  792.         WindowPtr            lastFloatingWindow;
  793.         Boolean                isFloatingWindow;
  794.         Boolean                isFrontProcess;
  795.         WindowPtr            windowToSelect = window->GetPlatformWindow(ev);
  796.  
  797.         isFrontProcess = IsFrontProcess();
  798.     
  799.         if (window->IsFloating(ev) != kODFalse) 
  800.         {
  801.             isFloatingWindow = kODTrue;
  802.             currentFrontWindow = (WindowPtr) FrontWindow();
  803.         }
  804.         else 
  805.         {
  806.             isFloatingWindow = kODFalse;
  807.             currentFrontWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  808.             lastFloatingWindow = somSelf->GetLastFloatingPlatformWindow(ev);
  809.         }
  810.     
  811.         // Be fast (and lazy) and do nothing if we don’t have to.
  812.         // The !IsActive test was added because this method might get called when
  813.         // in the background during a Drop.
  814.     
  815.         if ((currentFrontWindow != windowToSelect) || (!window->IsActive(ev)))
  816.         {
  817.     
  818.         // Selecting floating windows are easy, since they’re always active
  819.     
  820.             if (isFloatingWindow) 
  821.             {
  822.                 BringToFront(windowToSelect);
  823.             }
  824.             else 
  825.             {
  826.                 // This replaces the code below.
  827.                 // In order to facilitate a predictable flow of events,
  828.                 // we must use Macintosh Toolbox calls that don't generate activate
  829.                 // events themselves (ie. BringToFront, SendBehind). 
  830.                 
  831.                 if (isFrontProcess)
  832.                     somSelf->DeactivateWindow(ev, currentFrontWindow);
  833.                 
  834.                 if (lastFloatingWindow == kODNULL)
  835.                     BringToFront(windowToSelect);
  836.                 else
  837.                     SendBehind(windowToSelect, lastFloatingWindow);
  838.                     
  839.                 //if (isFrontProcess) // Must allow activates for Drop in inactive window 
  840.                     somSelf->ActivateWindow(ev,windowToSelect);    
  841.     
  842.             }
  843.         }
  844.  
  845.     SOM_CATCH_ALL
  846.     SOM_ENDTRY
  847. } // SelectODWindow
  848.  
  849.  
  850. SOM_Scope void  SOMLINK ODWindowStateDragODWindow(ODWindowState *somSelf, Environment *ev,
  851.         ODWindow* window,
  852.         Point* startPoint,
  853.         Rect* draggingBounds)
  854. {
  855.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  856.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateDragODWindow");
  857.  
  858.     SOM_TRY
  859.     
  860.         // Check for command-click on window title:
  861.         if( TrackWindowPathPopUp(ev,window,*startPoint) )
  862.             return;
  863.     
  864.         WindowPtr    windowToDrag = window->GetPlatformWindow(ev);
  865.         Rect        dragRect;
  866.         KeyMap        keyMap;
  867.         GrafPtr        savePort;
  868.         GrafPtr        windowManagerPort;
  869.         RgnHandle    dragRegion;
  870.         RgnHandle    windowContentRegion;
  871.         long        dragResult;
  872.         short        topLimit;
  873.         short        newHorizontalWindowPosition;
  874.         short        newVerticalWindowPosition;
  875.         short        horizontalOffset;
  876.         short        verticalOffset;
  877.         Boolean        commandKeyDown = kODFalse;
  878.         
  879.         if (WaitMouseUp()) {
  880.         
  881.             // Adjust the top of the dragging rectangle so that it’s below the menu bar
  882.         
  883.             topLimit = LMGetMBarHeight() + 4;
  884.             dragRect = *draggingBounds;
  885.             if (dragRect.top < topLimit)
  886.                 dragRect.top = topLimit;
  887.         
  888.         // Set up the Window Manager port.
  889.         
  890.             GetPort(&savePort);
  891.             GetWMgrPort(&windowManagerPort);
  892.             SetPort(windowManagerPort);
  893.             SetClip(GetGrayRgn());
  894.             
  895.             // Check to see if the command key is down.  If it is, don’t bring the window to the
  896.             // front after the move.
  897.         
  898.             GetKeys(keyMap);
  899.             if (keyMap[1] & 0x8000)
  900.                 commandKeyDown = kODTrue;
  901.         
  902.             if ((commandKeyDown != kODFalse) || (window->IsFloating(ev) == kODFalse)) {
  903.                 
  904.                 if (commandKeyDown == kODFalse)
  905.         
  906.                 // If there are floating windows, clip the dragging outline to draw behind the floaters.
  907.         
  908.                     /* Adkins -- changed WindowPeek to WindowRef */
  909.                     ClipAbove((WindowRef) somSelf->GetFrontNonFloatingPlatformWindow(ev));
  910.                 else
  911.                 
  912.                 // If the command key was down, clip the outline to draw behind any windows above
  913.                 // the window being dragged.
  914.         
  915.                     ClipAbove((WindowRef) windowToDrag); /* Adkins -- changed WindowPeek to WindowRef */
  916.     
  917.             }
  918.                 
  919.             // Create a region to drag
  920.         
  921.             dragRegion = ODNewRgn();
  922.             CopyRgn(GetStructureRegion(windowToDrag), dragRegion);
  923.             
  924.             // Drag the window around
  925.         
  926.             dragResult = DragGrayRgn(dragRegion, *startPoint, &dragRect, &dragRect, noConstraint, nil);
  927.         
  928.             // Restore the port for coordinate conversion.
  929.         
  930.             SetPort(savePort);
  931.     
  932.             if (dragResult != 0) {
  933.                 horizontalOffset = (ODSShort) (dragResult & 0xFFFF);
  934.                 verticalOffset = (ODSShort) (dragResult >> 16);
  935.         
  936.                 // Only move it if it stayed inside the dragging box.
  937.         
  938.                 if (verticalOffset != -32768) {
  939.                     windowContentRegion = GetContentRegion(windowToDrag);
  940.                     newHorizontalWindowPosition = (**windowContentRegion).rgnBBox.left + horizontalOffset;
  941.                     newVerticalWindowPosition = (**windowContentRegion).rgnBBox.top + verticalOffset;
  942.                     
  943.                     MoveWindow((WindowPtr) windowToDrag, newHorizontalWindowPosition, newVerticalWindowPosition, kODFalse);
  944.                     
  945.                 }
  946.             }
  947.         
  948.             // Bring the window forward if the command key wasn’t down
  949.         
  950.             if (commandKeyDown == kODFalse)
  951.                 somSelf->SelectODWindow(ev, window);
  952.         
  953.             // Get rid of the dragging region
  954.         
  955.             DisposeRgn(dragRegion);
  956.         }
  957.  
  958.     SOM_CATCH_ALL
  959.     SOM_ENDTRY
  960. }
  961.  
  962. SOM_Scope void  SOMLINK ODWindowStateShowODWindow(ODWindowState *somSelf, Environment *ev,
  963.         ODWindow* window)
  964. {
  965.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  966.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateShowODWindow");
  967.  
  968.     SOM_TRY
  969.     
  970.         WindowPtr            windowToShow = window->GetPlatformWindow(ev);
  971.         WindowPtr            windowBehind;
  972.         ODBoolean            windowIsInFront = kODFalse;
  973.         
  974.         if (GetWindowVisible(windowToShow) == kODFalse) 
  975.         {
  976.                     
  977.             // If the window behind the window to show is currently the frontmost document window,
  978.             // unhighlight it, and highlight the new front window.
  979.             
  980.             if (window->IsFloating(ev) == kODFalse) 
  981.             {
  982.                 WindowPtr    frontPlatformWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev); 
  983.                 if (frontPlatformWindow == kODNULL)
  984.                     windowIsInFront = kODTrue;
  985.                 else {
  986.                     windowBehind = GetNextWindow(windowToShow);
  987.                     if (windowBehind == frontPlatformWindow) 
  988.                     {
  989.                         if (windowBehind != kODNULL)
  990.                             somSelf->DeactivateWindow(ev,windowBehind);
  991.                         windowIsInFront = kODTrue;
  992.                     }
  993.                 }
  994.             }
  995.             else 
  996.             {
  997.             
  998.                 // A floating window is being shown.  Should check to see if a modal window is up before
  999.                 // trying to highlight it.
  1000.             
  1001.                 windowIsInFront = kODTrue;
  1002.             }
  1003.             
  1004.             if (windowIsInFront)
  1005.                 SetWindowHilite(windowToShow, kODTrue);
  1006.             else
  1007.                 SetWindowHilite(windowToShow, kODFalse);
  1008.     
  1009.             // Show the window
  1010.             
  1011.             ShowHide(windowToShow, kODTrue);
  1012.             
  1013.             // If this is the new frontmost document window or a floating window, send it an activate event
  1014.             
  1015.             if (windowIsInFront &&     IsFrontProcess())
  1016.             {
  1017.     #if ODDebug && ODDebugActivates
  1018.                     somPrintf("Activate in ShowODWindow for root frame %x\n", window->GetRootFrame(ev));
  1019.     #endif
  1020.                 window->Activate(ev);
  1021.             }
  1022.         }
  1023.  
  1024.     SOM_CATCH_ALL
  1025.     SOM_ENDTRY
  1026. }
  1027.  
  1028. // ref-count-neutral static function used in workaround in HideODWindow below
  1029. static ODBoolean IsFloating(Environment* ev, ODWindowState* windowState, ODPlatformWindow win)
  1030. {
  1031.     ODBoolean isFloating = kODFalse;
  1032.     ODWindow* window = windowState->AcquireODWindow(ev,win);
  1033.     if (window)
  1034.         isFloating = window->IsFloating(ev);
  1035.     ODReleaseObject(ev, window);
  1036.     return isFloating;
  1037. }
  1038.  
  1039. SOM_Scope void  SOMLINK ODWindowStateHideODWindow(ODWindowState *somSelf, Environment *ev,
  1040.         ODWindow* window)
  1041. {
  1042.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1043.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateHideODWindow");
  1044.  
  1045.     SOM_TRY
  1046.     
  1047.         WindowPtr            windowToHide = window->GetPlatformWindow(ev);
  1048.         WindowPtr            frontFloater;
  1049.         WindowPtr            frontPlatformWindow;
  1050.         WindowPtr            windowBehind;
  1051.         
  1052.             
  1053.         if (GetWindowVisible(windowToHide) != kODFalse) 
  1054.         {
  1055.         
  1056.             // Get the first visible floating window, if any.
  1057.             
  1058.             frontFloater = (WindowPtr) FrontWindow();
  1059.             
  1060.             TempODWindow ODFrontFloater = somSelf->AcquireODWindow(ev,frontFloater);
  1061.             if ((ODFrontFloater != kODNULL) && (ODFrontFloater->IsFloating(ev) == kODFalse))
  1062.                 frontFloater = nil;
  1063.             
  1064.             // Get the first visible document window, if any.
  1065.             
  1066.             frontPlatformWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  1067.             
  1068.             // Deactivate and Hide the window.
  1069.             somSelf->DeactivateWindow(ev,windowToHide);
  1070.             
  1071.             ShowHide(windowToHide, kODFalse);
  1072.             
  1073.             // If the frontmost floating window is being hidden, move it behind the floating window
  1074.             // behind it, if there is one.
  1075.             
  1076.             if (windowToHide == frontFloater) 
  1077.             {
  1078.                 windowBehind = GetNextWindow(windowToHide);
  1079.                 
  1080.             // Only do the rearrangement if there’s another floating window.
  1081.     
  1082.     //            if ((windowBehind != kODNULL) &&
  1083.     //                (((ODWindowBehind = somSelf->AcquireODWindow(ev,windowBehind)) != kODNULL) &&
  1084.     //                    (ODWindowBehind->IsFloating() != kODFalse))) {
  1085.     //                SetNextWindow(windowToHide, GetNextWindow(windowBehind));
  1086.     //                SetNextWindow(windowBehind, windowToHide);
  1087.     //                SetWindowList(windowBehind);
  1088.     //            }
  1089.             }
  1090.             else 
  1091.             {
  1092.             
  1093.             // If the frontmost document window is behind hidden, send it behind the window
  1094.             // behind it.
  1095.                 TempODWindow        ODWindowBehind = kODNULL;
  1096.             
  1097.                 if (windowToHide == frontPlatformWindow) 
  1098.                 {                
  1099.                     windowBehind = windowToHide;
  1100.                     /* $$$$$ Need to find out why this doesn't work, ref count wise
  1101.                     do 
  1102.                     {
  1103.                         windowBehind = GetNextWindow(windowBehind);
  1104.                         if (somSelf->IsODWindow(ev,windowBehind))
  1105.                         {
  1106.                             ODReleaseObject(ev, ODWindowBehind); // Swapping references inside loop
  1107.                             ODWindowBehind = somSelf->AcquireODWindow(ev,windowBehind);
  1108.                         }
  1109.                         else
  1110.                             ODWindowBehind = kODNULL;
  1111.                     } 
  1112.                     while (windowBehind && 
  1113.                             (((ODWindowBehind == kODNULL) || (ODWindowBehind->IsFloating(ev))) ||
  1114.                               (GetWindowVisible(windowBehind) == kODFalse)));
  1115.                     */
  1116.                     
  1117.                     // Workaround for above loop, to avoid refcounted variable in loop
  1118.                     // Is Floating is an rc-neutral static function above this method
  1119.                     ODBoolean isODWindow = kODFalse;
  1120.                     do 
  1121.                     {
  1122.                         windowBehind = GetNextWindow(windowBehind);
  1123.                         isODWindow = somSelf->IsODWindow(ev,windowBehind);
  1124.                     } 
  1125.                     while (windowBehind && 
  1126.                             (((isODWindow == kODFalse) || (IsFloating(ev, somSelf, windowBehind))) ||
  1127.                               (GetWindowVisible(windowBehind) == kODFalse)));
  1128.                     // End workaround
  1129.                     if (windowBehind != kODNULL) 
  1130.                     {
  1131.                         // Note: Experiment to fix #1209552. Using GetNextVisible instead of GetNext
  1132.                         // might be better
  1133.                         
  1134.                         SendBehind(windowToHide, windowBehind);
  1135.                     
  1136.                         // The window behind it is now the front document window.  Highlight it and send it
  1137.                         // and activate event.
  1138.                         
  1139.                         if (IsFrontProcess())
  1140.                             somSelf->ActivateWindow(ev,windowBehind);
  1141.                     }
  1142.                 }
  1143.  
  1144.             }
  1145.         }
  1146.  
  1147.     SOM_CATCH_ALL
  1148.     SOM_ENDTRY
  1149. }
  1150.  
  1151. /*
  1152.  *  for ODWindowIterator
  1153.  */
  1154.  
  1155. SOM_Scope ODULong  SOMLINK ODWindowStateAddIterator(ODWindowState *somSelf, Environment *ev,
  1156.         ODWindowIterator* iterator)
  1157. {
  1158.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1159.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAddIterator");
  1160.  
  1161.     LinkedListIterator* iter = kODNULL; ODVolatile(iter);
  1162.  
  1163.     SOM_TRY
  1164.     
  1165.         iter = new LinkedListIterator(_fWindowList);
  1166.         _fIteratorCount++;
  1167.             
  1168.     SOM_CATCH_ALL
  1169.     
  1170.         ODDeleteObject(iter);
  1171.         
  1172.     SOM_ENDTRY
  1173.  
  1174.     return (ODULong) iter;
  1175. }
  1176.  
  1177. SOM_Scope ODWindow*  SOMLINK ODWindowStateFirst(ODWindowState *somSelf, Environment *ev,
  1178.         ODULong iteratorID)
  1179. {
  1180.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1181.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateFirst");
  1182.  
  1183.     ODWindow* window = kODNULL;
  1184.  
  1185.     SOM_TRY
  1186.     
  1187.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1188.         WindowLink* link = (WindowLink*) iterator->First();
  1189.         
  1190.         while (link && link->ShouldRemove())
  1191.             link = (WindowLink*) iterator->Next();
  1192.             
  1193.         if (link)
  1194.             window = link->fWindow;
  1195.  
  1196.     SOM_CATCH_ALL
  1197.     SOM_ENDTRY
  1198.     
  1199.     return window;
  1200. }
  1201.  
  1202. SOM_Scope ODWindow*  SOMLINK ODWindowStateNext(ODWindowState *somSelf, Environment *ev,
  1203.         ODULong iteratorID)
  1204. {
  1205.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1206.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateNext");
  1207.  
  1208.     ODWindow* window = kODNULL;
  1209.  
  1210.     SOM_TRY
  1211.     
  1212.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1213.         WindowLink* link = (WindowLink*) iterator->Next();
  1214.  
  1215.         while (link && link->ShouldRemove())
  1216.             link = (WindowLink*) iterator->Next();
  1217.  
  1218.         if (link)
  1219.             window = link->fWindow;
  1220.  
  1221.     SOM_CATCH_ALL
  1222.     SOM_ENDTRY
  1223.     
  1224.     return window;
  1225. }
  1226.  
  1227. SOM_Scope ODWindow*  SOMLINK ODWindowStateLast(ODWindowState *somSelf, Environment *ev,
  1228.         ODULong iteratorID)
  1229. {
  1230.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1231.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateLast");
  1232.  
  1233.     ODWindow* window = kODNULL;
  1234.  
  1235.     SOM_TRY
  1236.     
  1237.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1238.         WindowLink* link = (WindowLink*) iterator->Last();
  1239.  
  1240.         while (link && link->ShouldRemove())
  1241.             link = (WindowLink*) iterator->Previous();
  1242.  
  1243.         if (link)
  1244.             window = link->fWindow;
  1245.  
  1246.     SOM_CATCH_ALL
  1247.     SOM_ENDTRY
  1248.     
  1249.     return window;
  1250. }
  1251.  
  1252. SOM_Scope ODWindow*  SOMLINK ODWindowStatePrevious(ODWindowState *somSelf, Environment *ev,
  1253.         ODULong iteratorID)
  1254. {
  1255.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1256.     ODWindowStateMethodDebug("ODWindowState","ODWindowStatePrevious");
  1257.  
  1258.     ODWindow* window = kODNULL;
  1259.  
  1260.     SOM_TRY
  1261.     
  1262.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1263.         WindowLink* link = (WindowLink*) iterator->Previous();
  1264.  
  1265.         while (link && link->ShouldRemove())
  1266.             link = (WindowLink*) iterator->Previous();
  1267.  
  1268.         if (link)
  1269.             window = link->fWindow;
  1270.  
  1271.     SOM_CATCH_ALL
  1272.     SOM_ENDTRY
  1273.     
  1274.     return window;
  1275. }
  1276.  
  1277. SOM_Scope ODBoolean  SOMLINK ODWindowStateIsNotComplete(ODWindowState *somSelf, Environment *ev,
  1278.         ODULong iteratorID)
  1279. {
  1280.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1281.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateIsNotComplete");
  1282.     
  1283.     ODBoolean isNotComplete = kODFalse;
  1284.  
  1285.     SOM_TRY
  1286.  
  1287.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1288.         isNotComplete = iterator->IsNotComplete();
  1289.     
  1290.     SOM_CATCH_ALL
  1291.     SOM_ENDTRY
  1292.  
  1293.     return isNotComplete;
  1294. }
  1295.  
  1296. SOM_Scope void  SOMLINK ODWindowStateRemoveIterator(ODWindowState *somSelf, Environment *ev,
  1297.         ODULong iteratorID)
  1298. {
  1299.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1300.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateRemoveIterator");
  1301.  
  1302.     SOM_TRY
  1303.     
  1304.         LinkedListIterator* iterator = (LinkedListIterator*) iteratorID; 
  1305.         ODDeleteObject(iterator);
  1306.         _fIteratorCount--;
  1307.         
  1308.         if (_fIteratorCount == 0) // Clear items marked for deletion during iteration
  1309.         {
  1310.             LinkedListIterator iter(_fWindowList);
  1311.             for ( WindowLink* link = (WindowLink*) iter.First();
  1312.                     iter.IsNotComplete(); 
  1313.                     link = (WindowLink*) iter.Next())
  1314.             {
  1315.                 if (link->ShouldRemove())
  1316.                 {
  1317.                     iter.RemoveCurrent();
  1318.                     delete link;
  1319.                 }
  1320.             }
  1321.         }
  1322.  
  1323.     SOM_CATCH_ALL
  1324.     SOM_ENDTRY
  1325. }
  1326.  
  1327.  
  1328. SOM_Scope void  SOMLINK ODWindowStateActivateWindow(ODWindowState *somSelf, Environment *ev,
  1329.         ODPlatformWindow platformWindow)
  1330. {
  1331.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1332.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateActivateWindow");
  1333.  
  1334.     SOM_TRY
  1335.     
  1336.         somSelf->HighlightAndActivateWindow(ev, platformWindow, kODTrue);
  1337.  
  1338.     SOM_CATCH_ALL
  1339.     SOM_ENDTRY
  1340. }
  1341.  
  1342. SOM_Scope void  SOMLINK ODWindowStateDeactivateWindow(ODWindowState *somSelf, Environment *ev,
  1343.         ODPlatformWindow platformWindow)
  1344. {
  1345.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1346.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateDeactivateWindow");
  1347.  
  1348.     SOM_TRY
  1349.  
  1350.         somSelf->HighlightAndActivateWindow(ev, platformWindow, kODFalse);
  1351.  
  1352.     SOM_CATCH_ALL
  1353.     SOM_ENDTRY
  1354. }
  1355.  
  1356. SOM_Scope void  SOMLINK ODWindowStateHighlightAndActivateWindow(ODWindowState *somSelf, Environment *ev,
  1357.         ODPlatformWindow platformWindow,
  1358.         ODBoolean activate)
  1359. {
  1360.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1361.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateHighlightAndActivateWindow");
  1362.  
  1363.     SOM_TRY
  1364.     
  1365. #if ODDebug && ODDebugActivates
  1366.     somPrintf("Activate/Deactivate message from OpenDoc\n");
  1367. #endif
  1368.  
  1369.         // Note: This optimization doesn't work if we don't dispatch
  1370.         // activate events from the Toolbox. eg. if you dismiss a modal dialog
  1371.         // the activate calls below don't get made because the Toolbox must have already
  1372.         // tweaked the highlighting.
  1373.     
  1374.         //if (AcquireWindowHilite(platformWindow) != activate) 
  1375.         {
  1376.             HiliteWindow(platformWindow, activate);
  1377.             
  1378.             if (somSelf->IsODWindow(ev,platformWindow) != kODFalse) 
  1379.             {
  1380.             
  1381.                 TempODWindow odWindow = somSelf->AcquireODWindow(ev,platformWindow);
  1382.                 if (activate == kODFalse)
  1383.                 {
  1384.     #if ODDebug && ODDebugActivates
  1385.                     somPrintf("Deactivate message from OpenDoc for root frame %x\n", odWindow->GetRootFrame(ev));
  1386.     #endif
  1387.                     odWindow->Deactivate(ev);
  1388.                 }
  1389.                 else
  1390.                 {
  1391.     #if ODDebug && ODDebugActivates
  1392.                     somPrintf("Activate message from OpenDoc for root frame %x\n", odWindow->GetRootFrame(ev));
  1393.     #endif
  1394.                     odWindow->Activate(ev);
  1395.                 }
  1396.             }
  1397.         }
  1398.  
  1399.     SOM_CATCH_ALL
  1400.     SOM_ENDTRY
  1401. }
  1402.  
  1403. SOM_Scope ODPlatformWindow  SOMLINK ODWindowStateGetLastFloatingPlatformWindow(ODWindowState *somSelf, Environment *ev)
  1404. {
  1405.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1406.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetLastFloatingPlatformWindow");
  1407.  
  1408.     WindowPtr    lastFloatingWindow = kODNULL;
  1409.  
  1410.     SOM_TRY
  1411.     
  1412.         WindowPtr    theWindow;
  1413.         ODWindow*    odWindow;
  1414.         
  1415.         theWindow = ::GetWindowList();
  1416.         lastFloatingWindow = kODNULL;
  1417.         
  1418.         // We have to search the entire window list because we don’t know what the windowKind
  1419.         // of other windows in the list might be, and we have account for the fact that a modal
  1420.         // dialog is up.
  1421.         
  1422.         while (theWindow != kODNULL) 
  1423.         {
  1424.             if (somSelf->IsODWindow(ev,theWindow) != kODFalse) 
  1425.             {
  1426.                 odWindow = somSelf->AcquireODWindow(ev,theWindow);
  1427.                 if (odWindow->IsFloating(ev) != kODFalse)
  1428.                     lastFloatingWindow = theWindow;
  1429.                 ODReleaseObject(ev, odWindow);
  1430.             }
  1431.             theWindow = GetNextWindow(theWindow);
  1432.         }
  1433.         
  1434.     SOM_CATCH_ALL
  1435.     
  1436.         lastFloatingWindow = kODNULL;
  1437.         
  1438.     SOM_ENDTRY
  1439.  
  1440.     return lastFloatingWindow;
  1441. }
  1442.  
  1443. SOM_Scope ODPlatformWindow  SOMLINK ODWindowStateGetFrontNonFloatingPlatformWindow(ODWindowState *somSelf, Environment *ev)
  1444. {
  1445.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1446.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetFrontNonFloatingPlatformWindow");
  1447.  
  1448.     
  1449.     WindowPtr    theWindow = kODNULL;
  1450.     ODVolatile(theWindow);
  1451.     
  1452.     SOM_TRY
  1453.     
  1454.         TempODWindow    odWindow = kODNULL;
  1455.         
  1456.         // Get the first visible window in the window list.
  1457.         
  1458.         theWindow = FrontWindow();
  1459.         
  1460.         // Keep searching until a visible window whose windowKind is not
  1461.         // kApplicationFloaterKind is found, or the end of the window list is reached.
  1462.         
  1463.         while ((theWindow != kODNULL) && 
  1464.                 (((odWindow = somSelf->AcquireODWindow(ev,theWindow)) != kODNULL) &&  /* -- TÇ:released down below */
  1465.                      (odWindow->IsFloating(ev) != kODFalse))) 
  1466.         {
  1467.             ODReleaseObject(ev, odWindow); // -- TÇ: to balance the above acquire
  1468.             do 
  1469.             {
  1470.                 theWindow = GetNextWindow(theWindow);
  1471.             } 
  1472.             while ((theWindow != kODNULL) && (GetWindowVisible(theWindow) == kODFalse));
  1473.         }
  1474.     
  1475.  
  1476.     SOM_CATCH_ALL
  1477.     
  1478.         theWindow = kODNULL;
  1479.             
  1480.     SOM_ENDTRY
  1481.  
  1482.     // odWindow is released here on destruction of the TempODWindow, if not in the loop above
  1483.     return theWindow;
  1484.  
  1485. }
  1486.  
  1487. SOM_Scope void  SOMLINK ODWindowStatesomUninit(ODWindowState *somSelf)
  1488. {
  1489.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1490.     ODWindowStateMethodDebug("ODWindowState","ODWindowStatesomUninit");
  1491.  
  1492.     Environment* ev = somGetGlobalEnvironment();
  1493.  
  1494.     ODDeleteObject(_fWindowList);
  1495.     ODSafeReleaseObject(_fBaseMenuBar);        _fBaseMenuBar = kODNULL;
  1496.     ODSafeReleaseObject(_fCurrentMenuBar);    _fCurrentMenuBar = kODNULL;
  1497. }
  1498.  
  1499. SOM_Scope ODSize  SOMLINK ODWindowStatePurge(ODWindowState *somSelf, Environment *ev,
  1500.         ODSize size)
  1501. {
  1502.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1503.     ODWindowStateMethodDebug("ODWindowState","ODWindowStatePurge");
  1504.  
  1505.     return 0;
  1506. }
  1507.  
  1508. SOM_Scope ODWindow*  SOMLINK ODWindowStateRegisterWindow(ODWindowState *somSelf, Environment *ev,
  1509.         ODPlatformWindow newWindow,
  1510.         ODType frameType,
  1511.         ODBoolean isRootWindow,
  1512.         ODBoolean isResizable,
  1513.         ODBoolean isFloating,
  1514.         ODBoolean shouldSave,
  1515.         ODBoolean shouldDispose,
  1516.         ODPart* rootPart,
  1517.         ODTypeToken viewType,
  1518.         ODTypeToken presentation,
  1519.         ODFrame* sourceFrame)
  1520. {
  1521.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1522.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCreateWindow");
  1523.  
  1524.     ODWindow* window = kODNULL; ODVolatile(window);
  1525.  
  1526.     SOM_TRY
  1527.         
  1528.         window = new ODWindow();
  1529.         if (window == kODNULL)
  1530.             THROW(kODErrCannotCreateWindow); // Note: Should we just use kODErrOutOfMemory?
  1531.             
  1532.         window->InitWindow(ev, newWindow, frameType,
  1533.                             isRootWindow, isResizable, isFloating, shouldSave, shouldDispose,
  1534.                             rootPart, viewType, presentation, sourceFrame);
  1535.         somSelf->AddWindow(ev,window);
  1536.         
  1537.     SOM_CATCH_ALL
  1538.     
  1539.         if (window)
  1540.         {
  1541.             TRY
  1542.                 window->CloseAndRemove(ev);
  1543.             CATCH_ALL
  1544.             ENDTRY
  1545.             window = kODNULL;
  1546.         }
  1547.                     
  1548.     SOM_ENDTRY
  1549.  
  1550.     return window;
  1551. }
  1552.  
  1553. SOM_Scope ODWindow*  SOMLINK ODWindowStateRegisterWindowForFrame(ODWindowState *somSelf, Environment *ev,
  1554.         ODPlatformWindow newWindow,
  1555.         ODFrame* frame,
  1556.         ODBoolean isRootWindow,
  1557.         ODBoolean isResizable,
  1558.         ODBoolean isFloating,
  1559.         ODBoolean shouldSave,
  1560.         ODBoolean shouldDispose,
  1561.         ODFrame* sourceFrame)
  1562. {
  1563.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1564.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCreateWindow");
  1565.  
  1566.     ODWindow* window = kODNULL; ODVolatile(window);
  1567.  
  1568.     SOM_TRY
  1569.     
  1570.         window = new ODWindow();
  1571.         if (window == kODNULL)
  1572.             THROW(kODErrCannotCreateWindow); // Note: Should we just use kODErrOutOfMemory?
  1573.             
  1574.         window->InitWindowForFrame(ev, newWindow, frame,
  1575.                             isRootWindow, isResizable, isFloating, shouldSave,  shouldDispose, sourceFrame);
  1576.         somSelf->AddWindow(ev,window);
  1577.  
  1578.     SOM_CATCH_ALL
  1579.         
  1580.         if (window)
  1581.         {
  1582.             TRY
  1583.                 window->Close(ev);
  1584.             CATCH_ALL
  1585.             ENDTRY
  1586.             window = kODNULL;
  1587.         }
  1588.             
  1589.     SOM_ENDTRY
  1590.  
  1591.     return window;
  1592. }
  1593.  
  1594. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireWindow(ODWindowState *somSelf, Environment *ev,
  1595.         ODID id)
  1596. {
  1597.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1598.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireWindow");
  1599.  
  1600.     ODWindow* window = kODNULL;
  1601.     
  1602.     SOM_TRY
  1603.     
  1604. /*        LinkedListIterator iter(_fWindowList);
  1605.         
  1606.         for ( WindowLink* link = (WindowLink*) iter.First();
  1607.                 iter.IsNotComplete(); 
  1608.                 link = (WindowLink*) iter.Next())
  1609.         {
  1610.             if (!link->ShouldRemove() && (link->fID == id))
  1611.             {
  1612.                 window = link->fWindow;
  1613.                 break;
  1614.             }
  1615.         }
  1616. */
  1617.             ODWindowIterator* iter = kODNULL; 
  1618.  
  1619.             iter = somSelf->CreateWindowIterator(ev);
  1620.         
  1621.             for (ODWindow* win = iter->First(ev); iter->IsNotComplete(ev);
  1622.                     win = iter->Next(ev))
  1623.             {
  1624.                 if (win->GetID(ev) == id)
  1625.                 {
  1626.                     window = win; 
  1627.                     break;
  1628.                 }
  1629.             }
  1630.             ODDeleteObject(iter);
  1631.  
  1632.             if (window)
  1633.                 window->Acquire(ev);
  1634.  
  1635.     SOM_CATCH_ALL
  1636.         
  1637.         window = kODNULL;
  1638.             
  1639.     SOM_ENDTRY
  1640.  
  1641.     return window;
  1642. }
  1643.  
  1644. SOM_Scope void  SOMLINK ODWindowStateInternalize(ODWindowState *somSelf, Environment *ev,
  1645.         ODDraft* draft)
  1646. {
  1647.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1648.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateInternalize");
  1649.     
  1650.     OrderedCollection* wsuIDCollection = kODNULL; ODVolatile(wsuIDCollection);
  1651.     
  1652.     SOM_TRY
  1653.     
  1654.         // To avoid calling Select in OpenWindows, we use this piece of cross-method state
  1655.         // A better solution might be to change ODOpenDraft to distinguish between the
  1656.         // opendraft and activateopendraft (from the dialog) cases. See also #1295739
  1657.         
  1658.         _fActivateOnOpen = (somSelf->GetRootWindowCount(ev, draft) > 0);
  1659.  
  1660.         ODULong offset, offsetLimit;
  1661.         ODStorageUnitRef suRef;
  1662.         
  1663.         TempODStorageUnit draftProps = draft->AcquireDraftProperties(ev); // -- TÇ tempobj'd
  1664.         
  1665.         if (ODSUExistsThenFocus(ev, draftProps,kODPropRootFrameList, kODStrongStorageUnitRefs))
  1666.         {
  1667.             offsetLimit = draftProps->GetSize(ev);
  1668.     
  1669.             // Get collection of windowstorageunit ids belonging to the draft here.  We'll
  1670.             // use it below to ensure that we don't reopen open windows.
  1671.         
  1672.             wsuIDCollection = new OrderedCollection;
  1673.             WindowPtr theWindow = ::GetWindowList();    
  1674.             while (theWindow != kODNULL)
  1675.             {
  1676.                 if (somSelf->IsODWindow(ev,theWindow) != kODFalse)
  1677.                 {
  1678.                     TempODWindow odWindow = somSelf->AcquireODWindow(ev,theWindow);
  1679.                     if ( ODObjectsAreEqual(ev, odWindow->GetDraft(ev) , draft) )
  1680.                     {
  1681.                         ODStorageUnit* storageU = odWindow->GetRootFrame(ev)->GetStorageUnit(ev);
  1682.                         if ( storageU )
  1683.                             wsuIDCollection->AddLast( (ElementType)(storageU->GetID(ev)) );
  1684.                     }
  1685.                 }
  1686.                 theWindow = GetNextWindow(theWindow);
  1687.             }
  1688.         
  1689.             TempODStorageUnitView draftPropsView = draftProps->CreateView(ev);
  1690.             for (offset = 0; offset < offsetLimit; offset += sizeof(ODStorageUnitRef))
  1691.             {
  1692.                 draftPropsView->SetOffset(ev,offset);
  1693.                 StorageUnitViewGetValue(draftPropsView,ev,sizeof(ODStorageUnitRef), (ODValue)&suRef);
  1694.                 if (draftPropsView->IsValidStorageUnitRef(ev, suRef))
  1695.                 {
  1696.                     ODStorageUnitID wsuID = draftPropsView->GetIDFromStorageUnitRef(ev,suRef);
  1697.                     if ( !wsuIDCollection->Contains((ElementType)wsuID) )
  1698.                     {
  1699.                         ODFrame *rootFrame = draft->AcquireFrame(ev, wsuID);
  1700.                         if (rootFrame)
  1701.                         {
  1702.                             TRY{
  1703.                                 TempODPart rootPart = rootFrame->AcquirePart(ev);
  1704.                                 rootPart->Open(ev, rootFrame);
  1705.                             }CATCH_ALL{
  1706.                                     TRY
  1707.                                         rootFrame->Close(ev);
  1708.                                     CATCH_ALL
  1709.                                     ENDTRY
  1710.                                 RERAISE;
  1711.                             }ENDTRY
  1712.                             rootFrame->Release(ev);
  1713.                         }
  1714.                     }
  1715.                 }
  1716.             }    
  1717.             ODDeleteObject(wsuIDCollection);
  1718.             
  1719.             somSelf->SetDefaultWindowTitles(ev,draft);
  1720.         }
  1721.         
  1722.     SOM_CATCH_ALL
  1723.     
  1724.         ODDeleteObject(wsuIDCollection);
  1725.         
  1726.     SOM_ENDTRY
  1727. }
  1728.  
  1729. SOM_Scope void  SOMLINK ODWindowStateExternalize(ODWindowState *somSelf, Environment *ev,
  1730.         ODDraft* draft)
  1731. {
  1732.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1733.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateExternalize");
  1734.  
  1735.     SOM_TRY
  1736.     
  1737.         somSelf->SetDefaultWindowTitles(ev,draft);
  1738.     
  1739.         ODULong offset, offsetLimit;
  1740.         ODFrame* rootFrame = kODNULL;
  1741.         
  1742.         TempODStorageUnit draftProps = draft->AcquireDraftProperties(ev);
  1743.         
  1744.         ODSUForceFocus(ev, draftProps, kODPropRootFrameList, kODStrongStorageUnitRefs);
  1745.         
  1746.         offset = 0;
  1747.         offsetLimit = draftProps->GetSize(ev);
  1748.     
  1749.         // Use the Window Manager list, since it's ordered
  1750.         // Note: we write the windows out back to front, since we create them in internalize
  1751.         // with the "behind" pointer -1. This only works because ShowODWindow does not bring
  1752.         // the newly shown window in front of the other invisible ones, as does ShowWindow.
  1753.  
  1754.         WindowListIterator iter;
  1755.         
  1756.         for (WindowPtr window = iter.Last(); iter.IsNotComplete(); window = iter.Previous())
  1757.         {
  1758.             if (somSelf->IsODWindow(ev,window))
  1759.             {
  1760.                 TempODWindow odWindow = somSelf->AcquireODWindow(ev,window); // DMc refcount - make temp
  1761.                 if (odWindow 
  1762.                     && (odWindow->ShouldSave(ev)) 
  1763.                     && (ODObjectsAreEqual(ev, odWindow->GetDraft(ev), draft)))
  1764.                 {
  1765.                     if (odWindow->GetStorageUnit(ev) == kODNULL) 
  1766.                     {
  1767.                         TempODStorageUnit    su = draft->CreateStorageUnit(ev);
  1768.                         odWindow->SetStorageUnit(ev, su);
  1769.                     }
  1770.                     odWindow->Externalize(ev);
  1771.     
  1772.                     rootFrame = odWindow->GetRootFrame(ev);
  1773.                     draftProps->SetOffset(ev,offset);    // $opt: Won't the offset be correct automatically? -TC
  1774.                     ODSetStrongSURefProp(ev, draftProps, kODNULL, kODNULL, rootFrame->GetStorageUnit(ev)->GetID(ev));
  1775.                     offset += sizeof(ODStorageUnitRef); // $opt: Won't the offset be correct automatically? -TC
  1776.                 }
  1777.             }
  1778.         }
  1779.         
  1780.         if (offset < offsetLimit)
  1781.             draftProps->DeleteValue(ev,offsetLimit - offset);
  1782.                     
  1783.     SOM_CATCH_ALL
  1784.     SOM_ENDTRY
  1785. }
  1786.  
  1787. SOM_Scope void  SOMLINK ODWindowStateSetDefaultWindowTitles(ODWindowState *somSelf, Environment *ev,
  1788.         ODDraft* draft)
  1789. {
  1790.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1791.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateSetDefaultWindowTitles");
  1792.  
  1793.     //!!! Needs work. Should add counter
  1794.     // Sets default window titles for all root windows of the given draft,
  1795.     // based on the file name.
  1796.  
  1797.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  1798.     PlatformFile* file = kODNULL; ODVolatile(file);
  1799.         
  1800.     SOM_TRY
  1801.         
  1802.         ODContainer* container = draft->GetDocument(ev)->GetContainer(ev);
  1803.         
  1804.         file = GetPlatformFileFromContainer(ev, container);
  1805.  
  1806.         char    windowName[256];
  1807.     
  1808.         iter = somSelf->CreateWindowIterator(ev);
  1809.     
  1810.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  1811.                 window = iter->Next(ev))
  1812.         {
  1813.             if ( (ODObjectsAreEqual(ev, window->GetDraft(ev), draft)) && window->IsRootWindow(ev) )
  1814.             {
  1815.                 file->GetAsciiName(windowName,235);
  1816.                 
  1817.                 ODULong draftNum = 0;
  1818.                 
  1819.                 TRY
  1820.                     draftNum = GetDraftNumFromDraft(ev, draft);
  1821.                 CATCH_ALL
  1822.                 ENDTRY
  1823.                 
  1824.                 if (draftNum != 0)
  1825.                 {
  1826.                     CToPascalString(windowName);
  1827.  
  1828.                     const ODSShort kMaxNumberSuffixLength = 10;                    
  1829.                     char theNum[kMaxNumberSuffixLength];
  1830.                     NumToString(draftNum, (StringPtr)theNum); // Macintosh Specific
  1831.  
  1832.                     ODSLong savedRefNum;
  1833.                     BeginUsingLibraryResources(savedRefNum);
  1834.                     ReplaceIntoString( kODDraftTextResID, (StringPtr)windowName,
  1835.                             (StringPtr)theNum, (StringPtr)windowName );
  1836.                     EndUsingLibraryResources(savedRefNum);
  1837.                     PascalToCString((StringPtr)windowName);
  1838.                 }
  1839.     
  1840.                 window->SetWindowTitle(ev, windowName);
  1841.             }
  1842.         }
  1843.         ODDeleteObject(iter);
  1844.         ODDeleteObject(file);
  1845.  
  1846.     SOM_CATCH_ALL
  1847.  
  1848.         ODDeleteObject(iter);
  1849.         ODDeleteObject(file);
  1850.  
  1851.     SOM_ENDTRY
  1852. }
  1853.  
  1854. SOM_Scope void  SOMLINK ODWindowStateOpenWindows(ODWindowState *somSelf, Environment *ev,
  1855.         ODDraft* draft)
  1856. {
  1857.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1858.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateOpenWindows");
  1859.  
  1860.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  1861.  
  1862.     SOM_TRY
  1863.  
  1864.         if (draft)
  1865.         {
  1866.             iter = somSelf->CreateWindowIterator(ev);
  1867.         
  1868.             // Windows were externalize/internalized back to front
  1869.             for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  1870.                     window = iter->Next(ev))
  1871.             {
  1872.                 if (ODObjectsAreEqual(ev, window->GetDraft(ev) , draft))
  1873.                 {
  1874.                     window->Open(ev); // A no-op if its already open
  1875.                     if (_fActivateOnOpen && window->IsShown(ev)) // The draft is already open
  1876.                         window->Select(ev);
  1877.                 }
  1878.             }
  1879.             ODDeleteObject(iter);
  1880.         }
  1881.         _fActivateOnOpen = kODFalse;
  1882.         
  1883.     SOM_CATCH_ALL
  1884.  
  1885.         _fActivateOnOpen = kODFalse;
  1886.         ODDeleteObject(iter);
  1887.  
  1888.     SOM_ENDTRY
  1889.     
  1890. }
  1891.  
  1892. SOM_Scope void  SOMLINK ODWindowStateCloseWindows(ODWindowState *somSelf, Environment *ev,
  1893.         ODDraft* draft)
  1894. {
  1895.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1896.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCloseWindows");
  1897.  
  1898.     SOM_TRY
  1899.     
  1900.         // For now, since we can't delete while iterating, we make a copy of the list. Yuck.
  1901.     
  1902. /*        LinkedList windowListCopy;    
  1903.     
  1904.         {
  1905.             LinkedListIterator iter(_fWindowList);
  1906.             
  1907.             for ( WindowLink* link = (WindowLink*) iter.First();
  1908.                     iter.IsNotComplete(); 
  1909.                     link = (WindowLink*) iter.Next())
  1910.             {
  1911.                 WindowLink* linkCopy = new WindowLink(link->fID, link->fWindow);
  1912.                 THROW_IF_NULL(linkCopy);
  1913.                 windowListCopy.AddLast(linkCopy);
  1914.             }
  1915.         }
  1916.     
  1917.         LinkedListIterator citer(&windowListCopy);
  1918.         for ( WindowLink* clink = (WindowLink*) citer.First();
  1919.                 citer.IsNotComplete(); 
  1920.                 clink = (WindowLink*) citer.Next())
  1921.         {
  1922.             // Note: Use ID check in case Part closed a subsidiary window
  1923.             // This works now because this is a copy of the list. 
  1924.             // Should probably do a deferred close scheme instead
  1925.             
  1926.             ODWindow* window = somSelf->AcquireWindow(ev, clink->fID);
  1927.             // ODWindow* window = link->fWindow;
  1928.             if (window && (ODObjectsAreEqual(ev, window->GetDraft(ev), draft )))
  1929.             {
  1930.                 window->Close(ev);
  1931.             }
  1932.             ODReleaseObject(ev, window);
  1933.         }
  1934.         windowListCopy.DeleteAllLinks();
  1935. */        
  1936.         
  1937.         ODWindowIterator* iter = somSelf->CreateWindowIterator(ev);
  1938.         
  1939.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev); window = iter->Next(ev))
  1940.         {
  1941.             if (ODObjectsAreEqual(ev, window->GetDraft(ev), draft ))
  1942.             {
  1943.                 window->Acquire(ev); // Close Releases
  1944.                 window->Close(ev);
  1945.             }
  1946.         }
  1947.         ODDeleteObject(iter);
  1948.  
  1949.     
  1950.     SOM_CATCH_ALL
  1951.     SOM_ENDTRY
  1952. }
  1953.  
  1954. SOM_Scope ODUShort  SOMLINK ODWindowStateGetWindowCount(ODWindowState *somSelf, Environment *ev)
  1955. {
  1956.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1957.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetWindowCount");
  1958.  
  1959.     ODUShort count = 0;
  1960.  
  1961.     SOM_TRY
  1962.     
  1963.         if (_fWindowList)
  1964.             count = _fWindowList->Count();
  1965.         
  1966.     SOM_CATCH_ALL
  1967.     SOM_ENDTRY
  1968.     
  1969.     return count;
  1970. }
  1971.  
  1972. SOM_Scope ODUShort  SOMLINK ODWindowStateGetRootWindowCount(ODWindowState *somSelf, Environment *ev,
  1973.         ODDraft* draft)
  1974. {
  1975.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  1976.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetRootWindowCount");
  1977.  
  1978.     ODUShort count = 0;
  1979.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  1980.     
  1981.     SOM_TRY
  1982.     
  1983.         if (draft)
  1984.         {
  1985.             iter = somSelf->CreateWindowIterator(ev);
  1986.         
  1987.             for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  1988.                     window = iter->Next(ev))
  1989.             {
  1990.                 if (window->IsRootWindow(ev) && (ODObjectsAreEqual(ev, window->GetDraft(ev), draft)))
  1991.                 {
  1992.                     count++;
  1993.                 }
  1994.             }
  1995.             ODDeleteObject(iter);
  1996.         }
  1997.     
  1998.     SOM_CATCH_ALL
  1999.  
  2000.             ODDeleteObject(iter);
  2001.  
  2002.     SOM_ENDTRY
  2003.     
  2004.     return count;
  2005. }
  2006.  
  2007. SOM_Scope ODUShort  SOMLINK ODWindowStateGetTotalRootWindowCount(ODWindowState *somSelf, Environment *ev)
  2008. {
  2009.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2010.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateGetTotalRootWindowCount");
  2011.  
  2012.     //!!! Should get count directly from collection
  2013.     
  2014.     ODUShort count = 0;
  2015.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  2016.     
  2017.     SOM_TRY
  2018.  
  2019.         iter = somSelf->CreateWindowIterator(ev);
  2020.     
  2021.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  2022.                 window = iter->Next(ev))
  2023.         {
  2024.             if (window->IsRootWindow(ev))
  2025.                 count++;
  2026.         }
  2027.         ODDeleteObject(iter);
  2028.         
  2029.     SOM_CATCH_ALL
  2030.  
  2031.         ODDeleteObject(iter);
  2032.  
  2033.     SOM_ENDTRY
  2034.     
  2035.     return count;
  2036. }
  2037.  
  2038. SOM_Scope ODBoolean  SOMLINK ODWindowStateIsODWindow(ODWindowState *somSelf, Environment *ev,
  2039.         ODPlatformWindow aWindow)
  2040. {
  2041.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2042.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateIsODWindow");
  2043.  
  2044.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  2045.     ODBoolean isODWindow = kODFalse;
  2046.         
  2047.     SOM_TRY
  2048.  
  2049.         iter = somSelf->CreateWindowIterator(ev);
  2050.     
  2051.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  2052.                 window = iter->Next(ev))
  2053.         {
  2054.             if (window && (aWindow == window->GetPlatformWindow(ev)))
  2055.             {
  2056.                 isODWindow = kODTrue;
  2057.                 break;
  2058.             }
  2059.         }
  2060.         ODDeleteObject(iter);
  2061.  
  2062.     
  2063.     SOM_CATCH_ALL
  2064.  
  2065.         ODDeleteObject(iter);
  2066.  
  2067.     SOM_ENDTRY
  2068.     
  2069.     return isODWindow;
  2070. }
  2071.  
  2072. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireODWindow(ODWindowState *somSelf, Environment *ev,
  2073.         ODPlatformWindow aWindow)
  2074. {
  2075.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2076.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireODWindow");
  2077.  
  2078.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  2079.     ODWindow* odWindow = kODNULL;
  2080.         
  2081.     SOM_TRY
  2082.     
  2083.         iter = somSelf->CreateWindowIterator(ev);
  2084.     
  2085.         for (ODWindow* window = iter->First(ev); iter->IsNotComplete(ev);
  2086.                 window = iter->Next(ev))
  2087.         {
  2088.             if (window && (aWindow == window->GetPlatformWindow(ev)))
  2089.             {
  2090.                 odWindow = window;
  2091.                 break;
  2092.             }
  2093.         }
  2094.         ODDeleteObject(iter);
  2095.         
  2096.         if (odWindow)
  2097.             odWindow->Acquire(ev);
  2098.  
  2099.     SOM_CATCH_ALL
  2100.  
  2101.         ODDeleteObject(iter);
  2102.         odWindow = kODNULL;
  2103.  
  2104.     SOM_ENDTRY
  2105.     
  2106.     return odWindow;
  2107. }
  2108.  
  2109. SOM_Scope ODWindowIterator*  SOMLINK ODWindowStateCreateWindowIterator(ODWindowState *somSelf, Environment *ev)
  2110. {
  2111.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2112.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCreateWindowIterator");
  2113.  
  2114.     ODWindowIterator* iter = kODNULL; ODVolatile(iter);
  2115.     
  2116.     SOM_TRY
  2117.  
  2118.         iter = new ODWindowIterator;
  2119.         THROW_IF_NULL(iter); // "new" does not throw for SOM objects
  2120.         iter->InitWindowIterator(ev, somSelf);
  2121.         
  2122.     SOM_CATCH_ALL
  2123.     
  2124.         ODDeleteObject(iter);
  2125.         
  2126.     SOM_ENDTRY
  2127.     
  2128.     return iter;
  2129. }
  2130.  
  2131. SOM_Scope ODWindow*  SOMLINK ODWindowStateAcquireActiveWindow(ODWindowState *somSelf, Environment *ev)
  2132. {
  2133.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2134.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAcquireActiveWindow");
  2135.  
  2136.     ODWindow* aWindow = kODNULL;
  2137.  
  2138.     SOM_TRY
  2139.  
  2140.         WindowPtr platformWindow = kODNULL;
  2141.         
  2142.         //    • First we need to find out the frontmost window
  2143.         platformWindow = somSelf->GetFrontNonFloatingPlatformWindow(ev);
  2144.         
  2145.         if (platformWindow)
  2146.             aWindow = somSelf->AcquireODWindow(ev,platformWindow);
  2147.         
  2148.     SOM_CATCH_ALL
  2149.     SOM_ENDTRY
  2150.     
  2151.     // Not necessary to increment ref count, because AcquireODWindow has done it
  2152.     //if (aWindow)
  2153.     //    aWindow->Acquire(ev);
  2154.     return aWindow;
  2155. }
  2156.  
  2157. SOM_Scope void  SOMLINK ODWindowStateSetBaseMenuBar(ODWindowState *somSelf, Environment *ev,
  2158.         ODMenuBar* theMenuBar)
  2159. {
  2160.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2161.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateSetBaseMenuBar");
  2162.  
  2163.     SOM_TRY
  2164.         
  2165.         // $$$$$ Change this error code to be more explicit. -VL
  2166.         ASSERT(theMenuBar, kODErrIllegalNullInput);
  2167.     
  2168.         if (!ODObjectsAreEqual(ev, theMenuBar, _fBaseMenuBar))
  2169.         {
  2170.             ODULong generation;
  2171.             if (_fBaseMenuBar)
  2172.                 generation = _fBaseMenuBar->GetGeneration(ev) + 1;
  2173.             else
  2174.                 generation = 1;
  2175.             ODReleaseObject(ev, _fBaseMenuBar);
  2176.             theMenuBar->Acquire(ev);
  2177.             _fBaseMenuBar = theMenuBar;
  2178.             _fBaseMenuBar->SetGeneration(ev,generation);
  2179.         }
  2180.  
  2181.     SOM_CATCH_ALL
  2182.     SOM_ENDTRY
  2183. }
  2184.  
  2185. SOM_Scope ODMenuBar*  SOMLINK ODWindowStateCopyBaseMenuBar(ODWindowState *somSelf, Environment *ev)
  2186. {
  2187.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2188.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCopyBaseMenuBar");
  2189.     
  2190.     ODMenuBar* menuBar = kODNULL;
  2191.     
  2192.     SOM_TRY
  2193.  
  2194.         if (_fBaseMenuBar)
  2195.             menuBar = _fBaseMenuBar->Copy(ev);
  2196.     
  2197.     SOM_CATCH_ALL
  2198.     SOM_ENDTRY
  2199.     
  2200.     return menuBar;    // -- TÇ: CopyBaseMenuBar is an 'acquire' function.
  2201. }
  2202.  
  2203. SOM_Scope void  SOMLINK ODWindowStateAdjustPartMenus(ODWindowState *somSelf, Environment *ev)
  2204. {
  2205.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2206.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateAdjustPartMenus");
  2207.  
  2208.     SOM_TRY
  2209.  
  2210.         TempODFrame targetFrame 
  2211.             = _fSession->GetArbitrator(ev)->AcquireFocusOwner(ev,_fMenuFocus);
  2212.             
  2213.         // To support root menu items like Print. 
  2214.         // Other platforms may choose to add a new focus for this
  2215.         
  2216.         ODFrame* rootFrame;
  2217.         { TempODWindow window = somSelf->AcquireActiveWindow(ev) ;    
  2218.           rootFrame = window ? window->GetRootFrame(ev) : kODNULL;
  2219.         }
  2220.         
  2221.         if (rootFrame)
  2222.         {
  2223.             TempODPart targetPart = rootFrame->AcquirePart(ev); // -- TÇ tempobj'd
  2224.             targetPart->AdjustMenus(ev,rootFrame);
  2225.         }    
  2226.             
  2227.         if (targetFrame && (targetFrame != rootFrame))
  2228.         {
  2229.             TempODPart targetPart = targetFrame->AcquirePart(ev); // -- TÇ tempobj'd
  2230.             targetPart->AdjustMenus(ev,targetFrame);
  2231.         }
  2232.         
  2233.     SOM_CATCH_ALL
  2234.     SOM_ENDTRY
  2235. }
  2236.  
  2237. SOM_Scope ODMenuBar*  SOMLINK ODWindowStateCreateMenuBar(ODWindowState *somSelf, Environment *ev,
  2238.         ODPlatformMenuBar menuBar)
  2239. {
  2240.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2241.     ODWindowStateMethodDebug("ODWindowState","ODWindowStateCreateMenuBar");
  2242.  
  2243.     ODMenuBar* mb = kODNULL;  ODVolatile(mb);
  2244.  
  2245.     SOM_TRY
  2246.     
  2247.         mb = new ODMenuBar;
  2248.         THROW_IF_NULL(mb);    // "new" does not THROW for SOM objects
  2249.         mb->InitMenuBar(ev, _fSession, menuBar);
  2250.     
  2251.     SOM_CATCH_ALL
  2252.  
  2253.         ODDeleteObject(mb);
  2254.  
  2255.     SOM_ENDTRY
  2256.         
  2257.     return mb;
  2258. }
  2259.  
  2260. SOM_Scope ODCanvas*  SOMLINK ODWindowStateCreateCanvas(ODWindowState *somSelf, Environment *ev,
  2261.         ODGraphicsSystem graphicsSystem,
  2262.         ODPlatformCanvas platformCanvas,
  2263.         ODBoolean isDynamic,
  2264.         ODBoolean isOffscreen)
  2265. {
  2266.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2267.     ODWindowStateMethodDebug("ODWindowState","CreateCanvas");
  2268.  
  2269.     ODCanvas* canvas = kODNULL;  ODVolatile(canvas);
  2270.  
  2271.     SOM_TRY
  2272.  
  2273.         canvas = new ODCanvas;
  2274.         THROW_IF_NULL(canvas);    // "new" does not THROW for SOM objects
  2275.         canvas->InitCanvas(ev, graphicsSystem,platformCanvas,isDynamic,isOffscreen);
  2276.         
  2277.     SOM_CATCH_ALL
  2278.     
  2279.         ODDeleteObject(canvas);
  2280.         
  2281.     SOM_ENDTRY
  2282.     
  2283.     return canvas;
  2284. }
  2285.  
  2286. SOM_Scope ODFacet*  SOMLINK ODWindowStateCreateFacet(ODWindowState *somSelf, Environment *ev,
  2287.         ODFrame* frame,
  2288.         ODShape* clipShape,
  2289.         ODTransform* externalTransform,
  2290.         ODCanvas* canvas,
  2291.         ODCanvas* biasCanvas)
  2292. {
  2293.     ODWindowStateData *somThis = ODWindowStateGetData(somSelf);
  2294.     ODWindowStateMethodDebug("ODWindowState","CreateFacet");
  2295.  
  2296.     ODFacet* facet = kODNULL;  ODVolatile(facet);
  2297.     
  2298.     SOM_TRY
  2299.  
  2300.         facet = new ODFacet;
  2301.         THROW_IF_NULL(facet);    // "new" does not THROW for SOM objects
  2302.         facet->InitFacet(ev, frame, clipShape, externalTransform, canvas, biasCanvas);
  2303.     
  2304.     SOM_CATCH_ALL
  2305.     
  2306.         ODDeleteObject(facet);
  2307.         
  2308.     SOM_ENDTRY
  2309.     
  2310.     return facet;
  2311. }
  2312.