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 Development Framework / ODFDev / Container / Sources / Content.cpp < prev    next >
Encoding:
Text File  |  1996-08-16  |  20.1 KB  |  667 lines  |  [TEXT/MPS ]

  1. //========================================================================================
  2. //
  3. //    File:                Content.cpp
  4. //    Release Version:    $ ODF 1 $
  5. //
  6. //    Copyright:            (c) 1993 - 1996 by Apple Computer, Inc., all rights reserved.
  7. //
  8. //========================================================================================
  9.  
  10. #include "Container.hpp"
  11.  
  12. #ifndef CONTENT_H
  13. #include "Content.h"
  14. #endif
  15.  
  16. #ifndef PART_H
  17. #include "Part.h"
  18. #endif
  19.  
  20. #ifndef SELECT_H
  21. #include "Select.h"
  22. #endif
  23.  
  24. // ----- Part Layer -----
  25.  
  26. #ifndef FWUTIL_H
  27. #include "FWUtil.h"
  28. #endif
  29.  
  30. #ifndef FWPRESEN_H
  31. #include "FWPresen.h"
  32. #endif
  33.  
  34. #ifndef FWFCTCLP_H
  35. #include "FWFctClp.h"
  36. #endif
  37.  
  38. // ----- OS Layer -----
  39.  
  40. #ifndef FWRECT_H
  41. #include "FWRect.h"
  42. #endif
  43.  
  44. #ifndef FWODGEOM_H
  45. #include "FWODGeom.h"
  46. #endif
  47.  
  48. #ifndef FWSUSINK_H
  49. #include "FWSUSink.h"
  50. #endif
  51.  
  52. #ifndef FWBARRAY_H
  53. #include "FWBArray.h"
  54. #endif
  55.  
  56. // ----- Foundation Layer -----
  57.  
  58. #ifndef FWSTREAM_H
  59. #include "FWStream.h"
  60. #endif
  61.  
  62. #ifndef FWSUSINK_H
  63. #include "FWSUSink.h"
  64. #endif
  65.  
  66. #ifndef FWMEMORY_H
  67. #include "FWMemory.h"
  68. #endif
  69.  
  70. // ----- OpenDoc Includes -----
  71.  
  72. #ifndef SOM_Module_OpenDoc_StdProps_defined
  73. #include <StdProps.xh>
  74. #endif
  75.  
  76. #ifndef SOM_ODShape_xh
  77. #include <Shape.xh>
  78. #endif
  79.  
  80. #ifndef SOM_ODStorageUnit_xh
  81. #include <StorageU.xh>
  82. #endif
  83.  
  84. //========================================================================================
  85. // Runtime Information
  86. //========================================================================================
  87.  
  88. #ifdef FW_BUILD_MAC
  89. #pragma segment odfcontainer
  90. #endif
  91.  
  92. FW_DEFINE_AUTO(CBaseContent)
  93. FW_DEFINE_AUTO(CPartContent)
  94. FW_DEFINE_AUTO(CSelectionContent)
  95. FW_DEFINE_AUTO(CUndoContent)
  96. FW_DEFINE_AUTO(CContentProxyIterator)
  97.  
  98. //========================================================================================
  99. //    class CBaseContent
  100. //========================================================================================
  101.  
  102. //----------------------------------------------------------------------------------------
  103. //    CBaseContent::CBaseContent
  104. //----------------------------------------------------------------------------------------
  105. //    CBaseContent constructor
  106.  
  107. CBaseContent::CBaseContent(Environment* ev, CContainerPart* part) :
  108.     FW_CEmbeddingContent(ev, part),
  109.     fProxyList(NULL),
  110.     fContainerPart(part)
  111. {
  112.     fProxyList = FW_NEW(CProxyCollection, ());
  113.     
  114.     FW_END_CONSTRUCTOR
  115. }
  116.  
  117. //----------------------------------------------------------------------------------------
  118. //    CBaseContent::CBaseContent
  119. //----------------------------------------------------------------------------------------
  120.  
  121. CBaseContent::CBaseContent(Environment* ev, CBaseContent* other) :
  122.     FW_CEmbeddingContent(ev, other->fContainerPart),
  123.     fProxyList(NULL),
  124.     fContainerPart(other->fContainerPart)
  125. {
  126.     fProxyList = FW_NEW(CProxyCollection, ());
  127.  
  128.     CContentProxyIterator ite(other);
  129.     for (CProxy* proxy = ite.First(); ite.IsNotComplete(); proxy = ite.Next())
  130.     {
  131.         this->AddProxy(ev, proxy);
  132.     }
  133.  
  134.     FW_END_CONSTRUCTOR
  135. }
  136.  
  137. //----------------------------------------------------------------------------------------
  138. //    CBaseContent::~CBaseContent
  139. //----------------------------------------------------------------------------------------
  140. //    CBaseContent destructor
  141.  
  142. CBaseContent::~CBaseContent()
  143. {
  144.     FW_START_DESTRUCTOR
  145.     delete fProxyList;
  146. }
  147.  
  148. //----------------------------------------------------------------------------------------
  149. //    CBaseContent::AddProxy
  150. //----------------------------------------------------------------------------------------
  151.  
  152. void CBaseContent::AddProxy(Environment* ev, CProxy* proxy)
  153. {
  154.     fProxyList->AddLast(proxy);
  155. }
  156.  
  157. //----------------------------------------------------------------------------------------
  158. //    CBaseContent::RemoveProxy
  159. //----------------------------------------------------------------------------------------
  160.  
  161. void CBaseContent::RemoveProxy(Environment* ev, CProxy* proxy)
  162. {
  163.     fProxyList->Remove(proxy);
  164. }
  165.  
  166. //----------------------------------------------------------------------------------------
  167. //    CBaseContent::CountProxies
  168. //----------------------------------------------------------------------------------------
  169.  
  170. unsigned long CBaseContent::CountProxies() const
  171. {
  172.     return fProxyList->Count();
  173. }
  174.  
  175. //----------------------------------------------------------------------------------------
  176. //    CBaseContent::GetFirstProxy
  177. //----------------------------------------------------------------------------------------
  178.  
  179. CProxy* CBaseContent::GetFirstProxy() const
  180. {
  181.     return fProxyList->First();
  182. }
  183.  
  184. //----------------------------------------------------------------------------------------
  185. //    CBaseContent::IsEmpty
  186. //----------------------------------------------------------------------------------------
  187.  
  188. FW_Boolean CBaseContent::IsEmpty() const
  189. {
  190.     return (fProxyList->Count() == 0);
  191. }
  192.  
  193. //----------------------------------------------------------------------------------------
  194. //    CBaseContent::CalcUpdateShape
  195. //----------------------------------------------------------------------------------------
  196.  
  197. ODShape* CBaseContent::CalcUpdateShape(Environment* ev)
  198. {
  199.     if (this->IsEmpty())
  200.         return NULL;
  201.  
  202.     ODShape* updateShape = ::FW_NewODShape(ev);
  203.  
  204.     FW_CAcquiredODShape aqTempShape = ::FW_NewODShape(ev);
  205.     FW_Boolean first = TRUE;
  206.  
  207.     CContentProxyIterator ite(this);
  208.     for (CProxy* proxy = ite.First(); ite.IsNotComplete(); proxy = ite.Next())
  209.     {
  210.         proxy->GetUpdateBox(ev, aqTempShape);
  211.         if (first)
  212.             updateShape->CopyFrom(ev, aqTempShape);
  213.         else
  214.             updateShape->Union(ev, aqTempShape);
  215.                         
  216.         first = FALSE;
  217.     }
  218.  
  219.     return updateShape;
  220. }
  221.  
  222. //----------------------------------------------------------------------------------------
  223. //    CBaseContent::RedrawProxies
  224. //----------------------------------------------------------------------------------------
  225.  
  226. void CBaseContent::RedrawProxies(Environment* ev)
  227. {
  228.     // Calculate the update shape and invalidate it
  229.     FW_CAcquiredODShape updateShape = CalcUpdateShape(ev);
  230.     if (updateShape != NULL)
  231.     {
  232.         // Invalidate the update shape
  233.         FW_CPresentation* presentation = fContainerPart->GetMainPresentation();
  234.         FW_CFacetClipper facetClipper(ev, fContainerPart);
  235.         facetClipper.Clip(ev, presentation, updateShape);
  236.         presentation->Invalidate(ev, updateShape);
  237.     }
  238. }
  239.  
  240. //----------------------------------------------------------------------------------------
  241. //    CBaseContent::PostInternalizeProxy
  242. //----------------------------------------------------------------------------------------
  243.  
  244. void CBaseContent::PostInternalizeProxy(Environment* ev, const FW_CPoint& offset, CProxy* /*proxy*/)
  245. {
  246.     // Default is to do nothing
  247. }
  248.  
  249. //----------------------------------------------------------------------------------------
  250. //    CBaseContent::ExternalizeProxyList
  251. //----------------------------------------------------------------------------------------
  252.  
  253. void CBaseContent::ExternalizeProxyList(Environment* ev,
  254.                                         ODStorageUnit* storageUnit, 
  255.                                         FW_CCloneInfo* cloneInfo,
  256.                                         FW_Fixed offsetX,
  257.                                         FW_Fixed offsetY)
  258. {
  259.     // ----- Create an archive for our proxies -----
  260.     FW_PStorageUnitSink suSink(ev, storageUnit, kODPropContents, fContainerPart->GetPartKind(ev));
  261.     FW_CWritableStream archive(suSink);
  262.     
  263.     // ----- Write number of proxies -----
  264.     unsigned long count = fProxyList->Count();
  265.     archive << count;
  266.     
  267.     // ----- Write top, left offsets -----
  268.     archive << offsetX;
  269.     archive << offsetY;
  270.  
  271.     // ----- Write proxies -----
  272.     CProxyCollectionIterator ite(fProxyList);
  273.     FW_CRect frameRect;
  274.     for (CProxy* proxy = ite.First(); ite.IsNotComplete(); proxy = ite.Next())
  275.     {
  276.         FW_CRect bounds = proxy->GetBounds(ev);
  277.         archive << bounds;
  278.         proxy->Externalize(ev, suSink->GetStorageUnitView(ev), cloneInfo);
  279.     }    
  280. }
  281.  
  282. //----------------------------------------------------------------------------------------
  283. //    CBaseContent::InternalizeProxyList
  284. //----------------------------------------------------------------------------------------
  285.  
  286. void CBaseContent::InternalizeProxyList(Environment* ev,
  287.                                         ODStorageUnit* storageUnit, 
  288.                                         FW_CCloneInfo* cloneInfo)
  289. {
  290.     // ----- Create an archive for our proxies -----
  291.     FW_PStorageUnitSink suSink(ev, storageUnit, kODPropContents, fContainerPart->GetPartKind(ev));
  292.     FW_CReadableStream archive(suSink);
  293.     
  294.     // ----- Read number of proxies -----
  295.     unsigned long count;
  296.     archive >> count;
  297.  
  298.     // ----- Read top left offset -----
  299.     FW_CPoint offset;
  300.     archive >> offset.x;
  301.     archive >> offset.y;
  302.  
  303.     FW_CRect frameRect;
  304.     CProxy* proxy;
  305.     for (short i = 0; i<count; i++)
  306.     {
  307.         archive >> frameRect;
  308.         proxy = new CProxy(ev, frameRect, fContainerPart);
  309.         proxy->Internalize(ev, suSink->GetStorageUnitView(ev), cloneInfo);
  310.         
  311.         // ----- Add the proxy to the proxy list -----
  312.         this->AddProxy(ev, proxy);
  313.  
  314.         // ----- Do whatever else needs to be done to the proxy -----
  315.         this->PostInternalizeProxy(ev, offset, proxy);
  316.     }
  317. }
  318.  
  319. //----------------------------------------------------------------------------------------
  320. //    CBaseContent::IsDataOnlyOneProxy
  321. //----------------------------------------------------------------------------------------
  322.  
  323. FW_MProxy* CBaseContent::IsDataOnlyOneProxy(Environment* ev) const
  324. {
  325.     if (CountProxies() == 1)
  326.     {
  327.         return (CProxy*)GetFirstProxy();
  328.     }
  329.     
  330.     return NULL;
  331. }
  332.  
  333. //----------------------------------------------------------------------------------------
  334. //    CBaseContent::AddSingleEmbeddedFrame
  335. //----------------------------------------------------------------------------------------
  336.  
  337. CProxy* CBaseContent::AddSingleEmbeddedFrame(Environment* ev, 
  338.                                                   FW_CEmbeddingFrame* scopeFrame,
  339.                                                   ODPart* embeddedPart, 
  340.                                                   ODFrame* embeddedFrame,
  341.                                                   ODShape* suggestedShape,
  342.                                                   ODTypeToken viewType)
  343. {
  344.     // ----- Calculate the default proxy rect -----
  345.     FW_CRect proxyRect;
  346.     if (suggestedShape)
  347.     {
  348.         proxyRect = FW_GetShapeBoundingBox(ev, suggestedShape);
  349.         proxyRect.Offset(-proxyRect.left, -proxyRect.top);
  350.     }
  351.     else
  352.     {
  353.         proxyRect.SetInt(0, 0, 80, 80);
  354.     }
  355.  
  356.     // ----- Calculate the shape of the embedded frame -----    
  357.     FW_CAcquiredODShape aqFrameShape = ::FW_NewODShape(ev, proxyRect);
  358.     
  359.     // ----- Calculate the position of the embedded frame -----
  360.     // ----- We place it in the middle of the content view -----
  361.     FW_CRect frameBounds = scopeFrame->GetContentView(ev)->GetBoundsInContent(ev);
  362.     proxyRect.PlaceInCenter(frameBounds);
  363.     
  364.     // ----- Create the proxy -----
  365.     CProxy* proxy = new CProxy(ev, proxyRect, fContainerPart);
  366.  
  367.     // Make sure that if an exception occurs before we complete this method,
  368.     // we dispose of the proxy
  369.     FW_TRY
  370.     {
  371.         scopeFrame->GetPresentation(ev)->Embed(ev, 
  372.                                                 embeddedPart, 
  373.                                                 embeddedFrame,
  374.                                                 kODFrameObject,    // I want persistent frames
  375.                                                 proxy,
  376.                                                 aqFrameShape,
  377.                                                 viewType,
  378.                                                 NULL,        // no presentation
  379.                                                 0,            // group id
  380.                                                 FALSE,        // IsOverlaid
  381.                                                 FALSE);        // sub-frame
  382.     }
  383.     FW_CATCH_BEGIN
  384.     FW_CATCH_EVERYTHING () {
  385.         // cleanup in case the Embed failed
  386.         delete proxy;
  387.         FW_THROW_SAME ();
  388.     }
  389.     FW_CATCH_END
  390.  
  391.     // ----- Add the proxy to our list -----
  392.     this->AddProxy(ev, proxy);
  393.     
  394.     return proxy;
  395. }
  396.  
  397. //========================================================================================
  398. //    class CContentProxyIterator
  399. //========================================================================================
  400.  
  401. //----------------------------------------------------------------------------------------
  402. //    CContentProxyIterator::CContentProxyIterator
  403. //----------------------------------------------------------------------------------------
  404.  
  405. CContentProxyIterator::CContentProxyIterator(CBaseContent* content) :
  406.     CProxyCollectionIterator(content->fProxyList)
  407. {
  408.     FW_END_CONSTRUCTOR
  409. }
  410.  
  411. //----------------------------------------------------------------------------------------
  412. //    CContentProxyIterator::~CContentProxyIterator
  413. //----------------------------------------------------------------------------------------
  414.  
  415. CContentProxyIterator::~CContentProxyIterator()
  416. {
  417.     FW_START_DESTRUCTOR
  418. }
  419.  
  420. //========================================================================================
  421. //    class CPartContent
  422. //========================================================================================
  423.  
  424. //----------------------------------------------------------------------------------------
  425. //    CPartContent::CPartContent
  426. //----------------------------------------------------------------------------------------
  427. //    CPartContent constructor
  428.  
  429. CPartContent::CPartContent(Environment* ev, CContainerPart* part)
  430. :    CBaseContent(ev, part)
  431. {
  432. }
  433.  
  434. //----------------------------------------------------------------------------------------
  435. //    CPartContent::~CPartContent
  436. //----------------------------------------------------------------------------------------
  437. //    CPartContent destructor
  438.  
  439. CPartContent::~CPartContent()
  440. {
  441.     if (fProxyList)
  442.     {
  443.         CProxy* proxy;
  444.         while ((proxy = fProxyList->First()) != NULL)
  445.         {
  446.             fProxyList->Remove(proxy);
  447.             delete proxy;
  448.         }
  449.     }
  450. }
  451.  
  452. //----------------------------------------------------------------------------------------
  453. //    CPartContent::Externalize
  454. //----------------------------------------------------------------------------------------
  455.  
  456. void CPartContent::Externalize (Environment* ev,
  457.                                 ODStorageUnit* storageUnit, 
  458.                                 FW_EStorageKinds storageKind,
  459.                                 FW_CCloneInfo* cloneInfo)
  460. {
  461.     ExternalizeProxyList(ev, storageUnit, cloneInfo, FW_kFixed0, FW_kFixed0);
  462. }
  463.  
  464. //----------------------------------------------------------------------------------------
  465. //    CPartContent::Internalize
  466. //----------------------------------------------------------------------------------------
  467.  
  468. FW_Boolean CPartContent::Internalize(Environment* ev,
  469.                                      ODStorageUnit* storageUnit, 
  470.                                      FW_EStorageKinds storageKind,
  471.                                      FW_CCloneInfo* cloneInfo)
  472. {    
  473.     InternalizeProxyList(ev, storageUnit, cloneInfo);
  474.     return true;
  475. }
  476.  
  477. //----------------------------------------------------------------------------------------
  478. //    CPartContent::PostInternalizeProxy
  479. //----------------------------------------------------------------------------------------
  480.  
  481. void CPartContent::PostInternalizeProxy(Environment* ev, const FW_CPoint& offset, CProxy* proxy)
  482. {
  483.     proxy->OffsetProxy(ev, -offset.x, -offset.y);
  484. }
  485.  
  486. //========================================================================================
  487. //    class CSelectionContent
  488. //========================================================================================
  489.  
  490. //----------------------------------------------------------------------------------------
  491. //    CSelectionContent::CSelectionContent
  492. //----------------------------------------------------------------------------------------
  493. //    CSelectionContent constructor
  494.  
  495. CSelectionContent::CSelectionContent(Environment* ev, CContainerPart* part, CContainerSelection* selection)
  496. :    CBaseContent(ev, part),
  497.     fContainerSelection(selection)
  498. {
  499. }
  500.  
  501. //----------------------------------------------------------------------------------------
  502. //    CSelectionContent::~CSelectionContent
  503. //----------------------------------------------------------------------------------------
  504. //    CSelectionContent destructor
  505.  
  506. CSelectionContent::~CSelectionContent()
  507. {
  508. }
  509.  
  510. //----------------------------------------------------------------------------------------
  511. //    CSelectionContent::Internalize
  512. //----------------------------------------------------------------------------------------
  513.  
  514. FW_Boolean CSelectionContent::Internalize(Environment* ev,
  515.                                           ODStorageUnit* storageUnit, 
  516.                                           FW_EStorageKinds storageKind,
  517.                                           FW_CCloneInfo* cloneInfo)
  518. {
  519.     if (!storageUnit->Exists(ev, kODPropContents, fContainerPart->GetPartKind(ev), 0))
  520.         return false;
  521.         
  522.     // ----- Read in the proxies -----
  523.     InternalizeProxyList(ev, storageUnit, cloneInfo);
  524.     return true;
  525. }
  526.  
  527. //----------------------------------------------------------------------------------------
  528. //    CSelectionContent::Externalize
  529. //----------------------------------------------------------------------------------------
  530.  
  531. void CSelectionContent::Externalize(Environment* ev,
  532.                                     ODStorageUnit* storageUnit, 
  533.                                     FW_EStorageKinds storageKind,
  534.                                     FW_CCloneInfo* cloneInfo)
  535. {
  536.     FW_CRect selectRect;
  537.     fContainerSelection->GetDragRect(selectRect);
  538.  
  539.     ExternalizeProxyList(ev, storageUnit, cloneInfo, selectRect.left, selectRect.top);
  540. }
  541.  
  542. //----------------------------------------------------------------------------------------
  543. //    CSelectionContent::SingleEmbeddedFrameInternalized
  544. //----------------------------------------------------------------------------------------
  545.  
  546. void CSelectionContent::SingleEmbeddedFrameInternalized(Environment* ev, 
  547.                                                         FW_CEmbeddingFrame* scopeFrame,
  548.                                                         ODPart* embeddedPart, 
  549.                                                         ODFrame* embeddedFrame,
  550.                                                         ODShape* suggestedShape,
  551.                                                         ODTypeToken viewType)
  552. {
  553.     CProxy* insertedProxy = AddSingleEmbeddedFrame(ev, 
  554.                                                         scopeFrame, 
  555.                                                         embeddedPart, 
  556.                                                         embeddedFrame, 
  557.                                                         suggestedShape, 
  558.                                                         viewType);    
  559.     PostInternalizeProxy(ev, FW_kZeroPoint, insertedProxy);                                        
  560. }
  561.  
  562. //----------------------------------------------------------------------------------------
  563. //    CSelectionContent::PostInternalizeProxy
  564. //----------------------------------------------------------------------------------------
  565.  
  566. void CSelectionContent::PostInternalizeProxy(Environment* ev, const FW_CPoint& offset, CProxy* proxy)
  567. {
  568.     // ----- Add the proxy to the right places -----
  569.     fContainerPart->AddProxyToPart(ev, proxy);    // Add to the part data
  570.     
  571.     // ----- Proxy has already been added to the selection list (fProxyList)
  572.     fContainerSelection->ProxyAdded(ev, proxy);
  573. }
  574.  
  575. //----------------------------------------------------------------------------------------
  576. //    CSelectionContent::CreateDataFrameShape
  577. //----------------------------------------------------------------------------------------
  578.  
  579. ODShape* CSelectionContent::CreateDataFrameShape(Environment* ev) const
  580. {
  581.     FW_CRect selectionRect;
  582.     fContainerSelection->GetDragRect(selectionRect);
  583.     selectionRect.Place(FW_kZeroPoint);
  584.     
  585.     ODShape* selectionShape = ::FW_NewODShape(ev, selectionRect);
  586.     return selectionShape;
  587. }
  588.  
  589. //========================================================================================
  590. //    class CUndoContent
  591. //========================================================================================
  592.  
  593. //----------------------------------------------------------------------------------------
  594. //    CUndoContent::CUndoContent
  595. //----------------------------------------------------------------------------------------
  596. //    CUndoContent constructor
  597.  
  598. CUndoContent::CUndoContent(Environment* ev, CContainerSelection* selection) :
  599.     CBaseContent(ev, selection->GetSelectionContent(ev)),
  600.     fContainerSelection(selection)
  601. {
  602. }
  603.  
  604. //----------------------------------------------------------------------------------------
  605. //    CUndoContent::~CUndoContent
  606. //----------------------------------------------------------------------------------------
  607. //    CUndoContent destructor
  608.  
  609. CUndoContent::~CUndoContent()
  610. {
  611. }
  612.  
  613. //----------------------------------------------------------------------------------------
  614. //    CUndoContent::RemoveProxySelection
  615. //----------------------------------------------------------------------------------------
  616.  
  617. void CUndoContent::RemoveProxySelection(Environment* ev)
  618. {
  619.     // Select the saved proxies
  620.     fContainerSelection->SelectContent(ev, this);
  621.  
  622.     // Clear the selected proxies
  623.     fContainerSelection->ClearSelection(ev);
  624.  
  625.     // Notify everybody
  626.     fContainerSelection->SelectionChanged(ev);
  627. }
  628.  
  629. //----------------------------------------------------------------------------------------
  630. //    CUndoContent::RestoreProxySelection
  631. //----------------------------------------------------------------------------------------
  632.  
  633. void CUndoContent::RestoreProxySelection(Environment* ev)
  634. {
  635.     // Add the saved proxies back into the part
  636.     CContentProxyIterator ite(this);
  637.     for (CProxy* proxy = ite.First(); ite.IsNotComplete(); proxy = ite.Next())
  638.     {
  639.         fContainerPart->AttachProxy(ev, proxy);
  640.     }
  641.  
  642.     // Redraw the restored proxies
  643.     RedrawProxies(ev);
  644.  
  645.     // Select the saved proxies
  646.     fContainerSelection->SelectContent(ev, this);
  647.  
  648.     // Notify everybody
  649.     fContainerSelection->SelectionChanged(ev);
  650. }
  651.  
  652. //----------------------------------------------------------------------------------------
  653. //    CUndoContent::DeleteSavedProxies
  654. //----------------------------------------------------------------------------------------
  655.  
  656. void CUndoContent::DeleteSavedProxies(Environment* ev)
  657. {
  658.     // ----- Delete all the saved proxies -----
  659.     CProxy* proxy;
  660.     while ((proxy = GetFirstProxy()) != NULL)
  661.     {
  662.         RemoveProxy(ev, proxy);
  663.         delete proxy;
  664.     }        
  665. }
  666.  
  667.