00001 // $Id: sgname.cpp 1282 2006-06-09 09:46:49Z alex $ 00002 /* @@tag:xara-cn@@ DO NOT MODIFY THIS LINE 00003 ================================XARAHEADERSTART=========================== 00004 00005 Xara LX, a vector drawing and manipulation program. 00006 Copyright (C) 1993-2006 Xara Group Ltd. 00007 Copyright on certain contributions may be held in joint with their 00008 respective authors. See AUTHORS file for details. 00009 00010 LICENSE TO USE AND MODIFY SOFTWARE 00011 ---------------------------------- 00012 00013 This file is part of Xara LX. 00014 00015 Xara LX is free software; you can redistribute it and/or modify it 00016 under the terms of the GNU General Public License version 2 as published 00017 by the Free Software Foundation. 00018 00019 Xara LX and its component source files are distributed in the hope 00020 that it will be useful, but WITHOUT ANY WARRANTY; without even the 00021 implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 00022 See the GNU General Public License for more details. 00023 00024 You should have received a copy of the GNU General Public License along 00025 with Xara LX (see the file GPL in the root directory of the 00026 distribution); if not, write to the Free Software Foundation, Inc., 51 00027 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 00028 00029 00030 ADDITIONAL RIGHTS 00031 ----------------- 00032 00033 Conditional upon your continuing compliance with the GNU General Public 00034 License described above, Xara Group Ltd grants to you certain additional 00035 rights. 00036 00037 The additional rights are to use, modify, and distribute the software 00038 together with the wxWidgets library, the wxXtra library, and the "CDraw" 00039 library and any other such library that any version of Xara LX relased 00040 by Xara Group Ltd requires in order to compile and execute, including 00041 the static linking of that library to XaraLX. In the case of the 00042 "CDraw" library, you may satisfy obligation under the GNU General Public 00043 License to provide source code by providing a binary copy of the library 00044 concerned and a copy of the license accompanying it. 00045 00046 Nothing in this section restricts any of the rights you have under 00047 the GNU General Public License. 00048 00049 00050 SCOPE OF LICENSE 00051 ---------------- 00052 00053 This license applies to this program (XaraLX) and its constituent source 00054 files only, and does not necessarily apply to other Xara products which may 00055 in part share the same code base, and are subject to their own licensing 00056 terms. 00057 00058 This license does not apply to files in the wxXtra directory, which 00059 are built into a separate library, and are subject to the wxWindows 00060 license contained within that directory in the file "WXXTRA-LICENSE". 00061 00062 This license does not apply to the binary libraries (if any) within 00063 the "libs" directory, which are subject to a separate license contained 00064 within that directory in the file "LIBS-LICENSE". 00065 00066 00067 ARRANGEMENTS FOR CONTRIBUTION OF MODIFICATIONS 00068 ---------------------------------------------- 00069 00070 Subject to the terms of the GNU Public License (see above), you are 00071 free to do whatever you like with your modifications. However, you may 00072 (at your option) wish contribute them to Xara's source tree. You can 00073 find details of how to do this at: 00074 http://www.xaraxtreme.org/developers/ 00075 00076 Prior to contributing your modifications, you will need to complete our 00077 contributor agreement. This can be found at: 00078 http://www.xaraxtreme.org/developers/contribute/ 00079 00080 Please note that Xara will not accept modifications which modify any of 00081 the text between the start and end of this header (marked 00082 XARAHEADERSTART and XARAHEADEREND). 00083 00084 00085 MARKS 00086 ----- 00087 00088 Xara, Xara LX, Xara X, Xara X/Xtreme, Xara Xtreme, the Xtreme and Xara 00089 designs are registered or unregistered trademarks, design-marks, and/or 00090 service marks of Xara Group Ltd. All rights in these marks are reserved. 00091 00092 00093 Xara Group Ltd, Gaddesden Place, Hemel Hempstead, HP2 6EX, UK. 00094 http://www.xara.com/ 00095 00096 =================================XARAHEADEREND============================ 00097 */ 00098 // sgname.cpp - the NameGallery implementation. 00099 00100 /* 00101 $Log: /Camelot/kernel/sgname.cpp $ 00102 * 00103 * 2 11/02/04 10:58a Alex 00104 * Support for HTML Help 00105 * 00106 * 2 16/07/99 18:06 Justinf 00107 * Now shows little circular blobs for adding sets to / subtracting sets 00108 * from the selection. 00109 * 00110 * 1 24/06/99 16:23 Justinf 00111 * Name Gallery 00112 */ 00113 00114 #include "camtypes.h" 00115 00116 //#include "app.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00117 //#include "ink.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00118 //#include "attrmgr.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00119 #include "ccdc.h" 00120 //#include "fillval.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00121 #include "grnddib.h" 00122 00123 //#include "cxfrech.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00124 //#include "attrval.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00125 #include "userattr.h" 00126 #include "tmpltatr.h" 00127 00128 #include "grndbmp.h" 00129 //#include "wbitmap.h" 00130 #include "dragmgr.h" 00131 //#include "scrvw.h" 00132 //#include "docview.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00133 00134 //#include "resource.h" 00135 //#include "galstr.h" 00136 //#include "galres.h" 00137 #include "sgmenu.h" 00138 //#include "barsdlgs.h" 00139 //#include "mario.h" 00140 //#include "justin3.h" 00141 //#include "richard2.h" 00142 00143 //#include "xshelpid.h" 00144 #include "helpuser.h" 00145 00146 #include "sginit.h" 00147 #include "sgname.h" 00148 00149 DECLARE_SOURCE("$Revision: 1282 $"); 00150 00151 // Implement the dynamic class bits... 00152 CC_IMPLEMENT_DYNCREATE(NameGallery, SuperGallery) 00153 CC_IMPLEMENT_DYNAMIC(SGNameItem, SGDisplayItem) 00154 CC_IMPLEMENT_DYNCREATE(OpDisplayNameGallery, Operation); 00155 CC_IMPLEMENT_DYNAMIC(GalleryNameDragInfo, BitmapDragInformation); 00156 CC_IMPLEMENT_DYNAMIC(SGNameDragTarget, SGListDragTarget); 00157 CC_IMPLEMENT_DYNCREATE(NameObjectsDlg, DialogOp) 00158 00159 // This line mustn't go before any CC_IMPLEMENT_... macros 00160 #define new CAM_DEBUG_NEW 00161 00162 00163 00164 /*********************************************************************************************** 00165 > SGNameItem::SGNameItem(const String_256& strName) 00166 00167 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00168 Created: 27/1/95 (base generated in sgbase.cpp) 00169 Inputs: NameItemToDisplay - The NameItem this item will display 00170 Purpose: SGNameItem constructor 00171 ***********************************************************************************************/ 00172 00173 SGNameItem::SGNameItem(const String_256& strName) 00174 : m_strSetName(strName), 00175 m_eIntersect(AttributeSets::Intersect::NONE) 00176 { 00177 // TRACEUSER( "JustinF", _T("SGNameItem %s\n"), (LPCTSTR) m_strSetName); 00178 } 00179 00180 00181 00182 /*********************************************************************************************** 00183 > virtual void SGNameItem::CalculateMyRect(SGFormatInfo* pFormatInfo, SGMiscInfo* pMiscInfo) 00184 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00185 Created: 27/1/95 (base generated in sgbase.cpp) 00186 Inputs: FormatInfo - The formatting info from which to calculate my position/size 00187 MiscInfo - As usual, the useful misc info struct 00188 Outputs: member variable FormatRect - is returned filled in with the size/position of 00189 this NameItem item's display area. This is dependent upon the current display 00190 mode and format state. FormatInfo will be updated as a result of the formatting 00191 operation. 00192 Purpose: Shared code for NameItem items to calculate where they will appear in the 00193 grand scheme of things 00194 Notes: NameItems supply only one display mode ("full info") 00195 ***********************************************************************************************/ 00196 00197 void SGNameItem::CalculateMyRect(SGFormatInfo* pFormatInfo, SGMiscInfo* pMiscInfo) 00198 { 00199 CalculateFormatRect(pFormatInfo, pMiscInfo, SG_InfiniteWidth, SG_DefaultSmallIcon); 00200 } 00201 00202 00203 00204 /******************************************************************************************** 00205 > virtual void SGNameItem::GetNameText(String_256* pResult) 00206 00207 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00208 Created: 9/3/95 (base generated in sgbase.cpp) 00209 Outputs: On exit, the string pointed at by Result will contain either a blank 00210 string, or the name text associated with this item (if any) 00211 Purpose: To determine a name string for this node. Generally, this is used for 00212 a simple mechanism which searches for display items whose names match 00213 given search parameters in some way. It is also used in libraries to 00214 provide default redraw methods. 00215 Notes: **** TO DO **** 00216 Modify this method to return the correct text. You may also want to 00217 add an override for the GetFullInfoText() method if you can provide 00218 a full-info display mode. 00219 SeeAlso: SGDisplayNode::GetNameText 00220 ********************************************************************************************/ 00221 00222 void SGNameItem::GetNameText(String_256* pResult) 00223 { 00224 ERROR3IF(pResult == 0, "SGNameItem::GetNameText: illegal null param"); 00225 *pResult = m_strSetName; 00226 } 00227 00228 00229 00230 /******************************************************************************************** 00231 > virtual BOOL SGNameItem::GetBubbleHelp(DocCoord *pMousePos, String_256 *pResult) 00232 00233 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00234 Created: 16/4/95 00235 Inputs: pMousePos - The current mouse position. This will generally be expected 00236 to lie inside this item's FormatRect. With it, this item can provide 00237 help on specific areas of an item. 00238 Outputs: On exit, if the return value is TRUE, the string pointed at by Result 00239 will contain a bubble help string for this item 00240 Returns: TRUE if it filled in the string, FALSE if it did not 00241 Purpose: Called by the parent gallery when bubble help is needed. The parent 00242 gallery will do a hit test to determine which node contains the pointer, 00243 and will then ask that node to supply bubble/status-line help. 00244 Notes: The base class returns FALSE (i.e. provides no help) 00245 If you can provide help, then override the base class method to do so. 00246 SeeAlso: SGDisplayNode::GetStatusLineHelp 00247 ********************************************************************************************/ 00248 00249 BOOL SGNameItem::GetBubbleHelp(DocCoord*, String_256* pResult) 00250 { 00251 ERROR3IF(pResult == 0, "SGNameItem::GetBubbleHelp: invalid null params"); 00252 00253 // Work out the intersection with the user selection. 00254 AttributeSets::Intersect eState = 00255 GetDocument()->GetAttributeSets()->IntersectSelectedObj(m_strSetName); 00256 00257 // Create the bubble help text. 00258 String_256 strName; 00259 GetNameText(&strName); 00260 return pResult->MakeMsg(_R(IDBBL_NAMEGAL_ITEM), 00261 &String_32(_R(IDBBL_NAMEGAL_NONE) + INT32(eState)), &strName); 00262 } 00263 00264 00265 00266 /******************************************************************************************** 00267 > virtual BOOL SGNameItem::GetStatusLineHelp(DocCoord* pMousePos, String_256* pResult) 00268 00269 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00270 Created: 16/4/95 00271 Inputs: pMousePos - The current mouse position. This will generally be expected 00272 to lie inside this item's FormatRect. With it, this item can provide 00273 help on specific areas of an item. 00274 Outputs: On exit, if the return value is TRUE, the string pointed at by Result 00275 will contain a status line help string for this item 00276 Returns: TRUE if it filled in the string, FALSE if it did not 00277 Purpose: Called by the parent gallery when status line help is needed. The parent 00278 gallery will do a hit test to determine which node contains the pointer, 00279 and will then ask that node to supply bubble/status-line help. 00280 Notes: The base class returns FALSE (i.e. provides no help) 00281 If you can provide help, then override the base class method to do so. 00282 SeeAlso: SGDisplayNode::GetBubbleHelp 00283 ********************************************************************************************/ 00284 00285 BOOL SGNameItem::GetStatusLineHelp(DocCoord* pMousePos, String_256* pResult) 00286 { 00287 // Work out the intersection with the user selection. 00288 AttributeSets::Intersect eState = 00289 GetDocument()->GetAttributeSets()->IntersectSelectedObj(m_strSetName); 00290 00291 // Create the bubble help text. 00292 String_256 strName; 00293 GetNameText(&strName); 00294 return pResult->MakeMsg(_R(IDS_NAMEGAL_ITEM_STATUS), 00295 &String_32(_R(IDBBL_NAMEGAL_NONE) + INT32(eState)), 00296 &strName); 00297 } 00298 00299 00300 00301 /*********************************************************************************************** 00302 > virtual void SGNameItem::HandleRedraw(SGRedrawInfo* pRedrawInfo, 00303 SGFormatInfo* pFormatInfo) 00304 00305 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00306 Created: 27/1/95 (base generated in sgbase.cpp) 00307 Inputs: RedrawInfo - The information on the kernel-rendered redraw area 00308 FormatInfo - The formatting information structure 00309 member variable FormatRect should be set up (before calling this method) 00310 to be the rectangle in which to draw this item 00311 Purpose: SGNameItem item redraw method - removed from the main HandleEvent 00312 method merely to make the code tidier. 00313 ***********************************************************************************************/ 00314 00315 void SGNameItem::HandleRedraw(SGRedrawInfo* pRedrawInfo, SGMiscInfo* pMiscInfo) 00316 { 00317 // Intersect the item's set with the user selection. 00318 String_256 strName; 00319 GetNameText(&strName); 00320 00321 // Set the foreground and background colours according to whether this item is 00322 // gallery selected or not. 00323 RenderRegion* pRenderer = pRedrawInfo->Renderer; 00324 DocColour dcolForegnd, dcolBackgnd; 00325 if (Flags.Selected) 00326 { 00327 dcolForegnd = pRedrawInfo->SelForeground; 00328 dcolBackgnd = pRedrawInfo->SelBackground; 00329 } 00330 else 00331 { 00332 // Unselected items are in the 'selected' colour if the user selection includes 00333 // any of their members. 00334 dcolBackgnd = pRedrawInfo->Background; 00335 dcolForegnd = pRedrawInfo->Foreground; 00336 } 00337 00338 // Work out the bounds of the bitmap and the label. 00339 DocRect drBmp(FormatRect), drTxt(FormatRect); 00340 drBmp.hi.x = drBmp.lo.x + SG_DefaultSmallIcon; 00341 drTxt.lo.x = drBmp.hi.x + SG_GapBeforeText; 00342 GridLockRect(pMiscInfo, &drBmp); 00343 GridLockRect(pMiscInfo, &drTxt); 00344 00345 // Render the background. 00346 pRenderer->SetLineWidth(0); 00347 pRenderer->SetLineColour(pRedrawInfo->Transparent); 00348 pRenderer->SetFillColour(pRedrawInfo->Background); 00349 pRenderer->DrawRect(&drBmp); 00350 pRenderer->SetFillColour(dcolBackgnd); 00351 pRenderer->DrawRect(&drTxt); 00352 00353 // Render the foreground. 00354 pRenderer->SetFixedSystemTextColours(&dcolForegnd, &dcolBackgnd); 00355 pRenderer->DrawFixedSystemText(&strName, drTxt); 00356 00357 // Work out which bitmap to render beside it. 00358 UINT32 idBmp; 00359 m_eIntersect = GetDocument()->GetAttributeSets()->IntersectSelectedObj(strName); 00360 switch (m_eIntersect) 00361 { 00362 case AttributeSets::Intersect::NONE: 00363 idBmp = _R(IDB_NAMEGAL_NONESEL); 00364 break; 00365 00366 case AttributeSets::Intersect::SOME: 00367 idBmp = _R(IDB_NAMEGAL_SOMESEL); 00368 break; 00369 00370 case AttributeSets::Intersect::ALL: 00371 idBmp = _R(IDB_NAMEGAL_ALLSEL); 00372 break; 00373 } 00374 00375 // Render the bitmap. 00376 DrawBitmap(pRenderer, &drBmp, idBmp); 00377 } 00378 00379 00380 00381 /*********************************************************************************************** 00382 > virtual BOOL SGNameItem::HandleEvent(SGEventType nEventType, void* pEventInfo, 00383 SGMiscInfo* pMiscInfo) 00384 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00385 Created: 17/4/99 00386 Inputs: nEventType - An enumerated value describing what type of event is to be processed 00387 pEventInfo - A structure describing the event (may be 0). The exact thing 00388 pointed at by this pointer depends upon the event type: 00389 00390 SGEVENT_FORMAT 0 00391 SGEVENT_REDRAW (SGRedrawInfo*) 00392 SGEVENT_BGREDRAW 0 00393 SGEVENT_BGFLUSH 0 - May have 0 MiscInfo 00394 SGEVENT_MOUSECLICK (SGMouseInfo*) 00395 SGEVENT_DRAGSTARTED (DragMessage*) 00396 SGEVENT_CLAIMPOINT (SGMouseInfo*) 00397 SGEVENT_THUMBMSG (ThumbMessage*) - May have 0 MiscInfo 00398 00399 Use the provided SGDisplayNode::Get[Format]Info() inlines to retrieve this 00400 information - they provide useful error/type checking, and hide the cast 00401 00402 pMiscInfo - almost always provided. Contains a few useful bits of info that may be 00403 needed for all event types. This may be 0 for special event types (see sgtree.h 00404 for the enum and information on which ones may pass 0 MiscInfo - currently 00405 this is _THUMBMSG and _BGFLUSH, neither of which should concern you - so as long 00406 as you only reference MiscInfo once you know the event type, you will be safe) 00407 00408 Outputs: FormatInfo is updated as appropriate 00409 Returns: TRUE if the event was handled successfully 00410 FALSE if it was not 00411 Purpose: Handles a SuperGallery DisplayTree event 00412 Notes: VERY IMPORTANT: The rendering must be enclosed by calls to StartRendering 00413 and StopRendering, to ensure that rendering works properly (in the future 00414 we may change the redraw system to use a GRenderRegion for each individual 00415 item, rather than one global one for the window, for which these calls will 00416 be essential) 00417 SeeAlso: SGDisplayNode::HandleEvent; SGDisplayItem::HandleEvent 00418 ***********************************************************************************************/ 00419 00420 BOOL SGNameItem::HandleEvent(SGEventType nEventType, void* pEventInfo, SGMiscInfo* pMiscInfo) 00421 { 00422 switch (nEventType) 00423 { 00424 case SGEVENT_FORMAT: 00425 { 00426 SGFormatInfo* pFormatInfo = GetFormatInfo(nEventType, pEventInfo); 00427 CalculateMyRect(pFormatInfo, pMiscInfo); 00428 break; 00429 } 00430 case SGEVENT_REDRAW: 00431 { 00432 DocRect MyRect(FormatRect); // Rely on FormatRect being cached from above 00433 SGRedrawInfo* pRedrawInfo = GetRedrawInfo(nEventType, pEventInfo); 00434 if (IMustRedraw(pRedrawInfo)) 00435 { 00436 StartRendering(pRedrawInfo, pMiscInfo); 00437 HandleRedraw(pRedrawInfo, pMiscInfo); 00438 StopRendering(pRedrawInfo, pMiscInfo); 00439 } 00440 break; 00441 } 00442 case SGEVENT_MOUSECLICK: 00443 { 00444 // Work out the bounds of the bitmap and the label. 00445 DocRect drBmp(FormatRect), drTxt(FormatRect); 00446 drBmp.hi.x = drBmp.lo.x + SG_DefaultSmallIcon; 00447 drTxt.lo.x = drBmp.hi.x + SG_GapBeforeText; 00448 GridLockRect(pMiscInfo, &drBmp); 00449 GridLockRect(pMiscInfo, &drTxt); 00450 00451 // Check if the click is on the text label or the bitmap button beside it. 00452 SGMouseInfo* pMouse = GetMouseInfo(nEventType, pEventInfo); 00453 if (drTxt.ContainsCoord(pMouse->Position)) 00454 { 00455 // It's a click on the text label. Work out what to do. 00456 // No drag, so move on to selection click handling. Note that 00457 // Adjust-Double-Click does _not_ close the Name gallery. 00458 if (pMouse->DoubleClick) 00459 DefaultClickHandler(pMouse, pMiscInfo, FALSE, FALSE); 00460 else 00461 { 00462 // See if the base class can handle the mouse event. 00463 DefaultPreDragHandler(pMouse, pMiscInfo); 00464 00465 // Make an appropriate attribute and try to start a drag. 00466 String_256 strName; 00467 GetNameText(&strName); 00468 TemplateAttribute* pAttrib = 00469 new TemplateAttribute(String_256(TEXT("ObjectName")), 00470 NullString, strName); 00471 if (pAttrib != 0) 00472 { 00473 GalleryNameDragInfo* pInfo = 00474 new GalleryNameDragInfo(this, pMouse, pMiscInfo, pAttrib, 00475 pMouse->MenuClick); 00476 if (pInfo != 0) DragManagerOp::StartDrag(pInfo, GetListWindow()); 00477 } 00478 } 00479 00480 // Claim this event - nobody else can own this click. 00481 return TRUE; 00482 } 00483 else if (drBmp.ContainsCoord(pMouse->Position)) 00484 { 00485 // It's a click on the selection bitmap button. 00486 String_256 strName; 00487 GetNameText(&strName); 00488 INT32 nChanged = 0; 00489 switch (m_eIntersect) 00490 { 00491 case AttributeSets::Intersect::NONE: 00492 case AttributeSets::Intersect::SOME: 00493 nChanged = GetDocument()->GetAttributeSets()->ChangeObjSelect(strName, TRUE); 00494 break; 00495 00496 case AttributeSets::Intersect::ALL: 00497 nChanged = GetDocument()->GetAttributeSets()->ChangeObjSelect(strName, FALSE); 00498 break; 00499 } 00500 00501 // Make sure the selection is updated if something happened. 00502 if (nChanged != 0) GetApplication()->FindSelection()->Update(TRUE); 00503 00504 // Claim the event. 00505 return TRUE; 00506 } 00507 break; 00508 } 00509 default: 00510 // Let the base class handle any events we don't know about. 00511 // This includes things like hit testing (CLAIMPOINT) etc 00512 return SGDisplayItem::HandleEvent(nEventType, pEventInfo, pMiscInfo); 00513 } 00514 00515 // Default return value: we do not claim this event, so it will be passed on to others. 00516 return FALSE; 00517 } 00518 00519 00520 00521 /******************************************************************************************** 00522 > NameGallery::NameGallery() 00523 00524 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00525 Created: 27/1/95 (base generated in sgbase.cpp) 00526 Purpose: Initialises a NameGallery object, registering an idle processor for it. 00527 ********************************************************************************************/ 00528 00529 NameGallery::NameGallery() 00530 : m_fMenusCreated(FALSE), 00531 m_fIdleProc(FALSE) 00532 { 00533 // Empty. 00534 } 00535 00536 00537 00538 /******************************************************************************************** 00539 > NameGallery::~NameGallery() 00540 00541 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00542 Created: 27/1/95 (base generated in sgbase.cpp) 00543 Purpose: Destroys a NameGallery object, deregistering its idle processor. 00544 ********************************************************************************************/ 00545 00546 NameGallery::~NameGallery() 00547 { 00548 // Stop sending idle events if we are still claiming them. 00549 if (m_fIdleProc) GetApplication()->RemoveIdleProcessor(IDLEPRIORITY_HIGH, this); 00550 } 00551 00552 00553 00554 /******************************************************************************************** 00555 > BOOL NameGallery::PreCreate() 00556 00557 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00558 Created: 27/1/95 (base generated in sgbase.cpp) 00559 Returns: TRUE if the Gallery initialised successfully 00560 FALSE if it should not be opened due to a failure to initialise 00561 Purpose: The NameGallery PreCreate handler. This overrides the base class 00562 PreCreate function. It is called at the very beginning of the 00563 SuperGallery::Create method, before the window has been created. 00564 Notes: As this is called before the window is open, it must not attempt to touch 00565 any of the button gadgets in the window, or force redraws, etc. Also, 00566 events cannot be passed to the tree, as the tree formatting relies on 00567 knowing the window size - however, the tree will be reformatted and 00568 redrawn automatically when the window is opened - this will happen shortly. 00569 ********************************************************************************************/ 00570 00571 BOOL NameGallery::PreCreate() 00572 { 00573 // If there isn't already one, create a DisplayTree. 00574 if (GetDisplayTree() == 0) 00575 { 00576 DisplayTree = new SGDisplayRootScroll(this); 00577 ERRORIF(DisplayTree == 0, _R(IDE_NOMORE_MEMORY), FALSE); 00578 } 00579 00580 // For each document already present, create a display subtree (possibly replacing 00581 // a previous displaytree for it if we had one earlier) 00582 Document* pDoc = (Document*) GetApplication()->Documents.GetTail(); 00583 while (pDoc != 0) 00584 { 00585 // Find the existing subtree, if any, and create the items for it. 00586 SGNameGroup* pGroup = (SGNameGroup*) GetDisplayTree()->FindSubtree(this, pDoc, 0); 00587 if (!CreateItems(pDoc, pGroup)) return FALSE; 00588 pDoc = (Document*) GetApplication()->Documents.GetPrev(pDoc); 00589 } 00590 00591 // Success. 00592 return TRUE; 00593 } 00594 00595 00596 00597 /******************************************************************************************** 00598 > virtual SGNameGroup* NameGallery::CreateItems(Document* pParentDoc, SGNameGroup* pGroup) 00599 00600 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00601 Created: 27/1/95 (base generated in sgbase.cpp) 00602 Inputs: pParentDoc - The document to create a display subtree for 00603 pGroup - NULL (creates a new group for this document), or 00604 a pointer to the existing group-node for this document (in which case 00605 it clears all displayitems from the group and rebuilds it in place - this 00606 stops the display group moving around the tree at random!) 00607 Returns: Pointer to the group the items were created in, or null if it fails. 00608 Purpose: Internal call. This takes the NameItem list of the given document and 00609 creates a DisplayTree subtree from it. This subtree is then added to 00610 the DisplayTree. Note that this does not force a redraw of the list - 00611 after making this call, you should also call ForceRedrawOfList 00612 Notes: Passing in a NULL parent document pointer results in an ERROR3 - 00613 the function returns without doing anything in retail builds 00614 SeeAlso: SuperGallery::ForceRedrawOfList 00615 ********************************************************************************************/ 00616 00617 SGNameGroup* NameGallery::CreateItems(Document* pParentDoc, SGNameGroup* pGroup) 00618 { 00619 ERROR3IF(pParentDoc == 0, "NameSGallery::CreateNewSubtree: no document"); 00620 00621 // If there isn't already one, create a DisplayTree. 00622 if (GetDisplayTree() == 0) 00623 { 00624 DisplayTree = new SGDisplayRootScroll(this); 00625 ERRORIF(DisplayTree == 0, _R(IDE_NOMORE_MEMORY), 0); 00626 } 00627 00628 // Set up a sort key ("by name") for both items and groups. 00629 SGSortKey sk[2] = { { SGSORTKEY_BYNAME, FALSE }, { SGSORTKEY_NONE, FALSE } }; 00630 00631 // Use either the provided group or create a new one. 00632 if (pGroup != 0) 00633 { 00634 ERROR3IF(pGroup->GetParentDocument() != pParentDoc, 00635 "NameGallery::CreateItems: Group/Document mismatch"); 00636 pGroup->DestroySubtree(FALSE); 00637 } 00638 else 00639 { 00640 pGroup = new SGNameGroup(this, pParentDoc); 00641 ERRORIF(pGroup == 0, _R(IDE_NOMORE_MEMORY), 0); 00642 GetDisplayTree()->AddItem(pGroup, sk); 00643 } 00644 00645 // Iterate over all the name in the set, creating a DisplayItem for 00646 // each one and inserting it in the DisplayGroup. 00647 String_256 strName; 00648 AttributeSets* pSets = pParentDoc->GetAttributeSets(); 00649 BOOL fOK = pSets->GetFirstSet(&strName); 00650 while (fOK) 00651 { 00652 SGNameItem* pNewItem = new SGNameItem(strName); 00653 ERRORIF(pNewItem == 0, _R(IDE_NOMORE_MEMORY), 0); 00654 pGroup->AddItem(pNewItem, sk); 00655 fOK = pSets->GetNextSet(&strName); 00656 } 00657 00658 // Success. 00659 return pGroup; 00660 } 00661 00662 00663 00664 /******************************************************************************************** 00665 > virtual MsgResult NameGallery::Message(Msg* pMessage) 00666 00667 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00668 Created: 27/1/95 (base generated in sgbase.cpp) 00669 Inputs: pMessage - The message to handle 00670 Purpose: A standard message handler, really. 00671 Notes: Any messages that this does not handle must be passed down to the 00672 SuperGallery base class message handler. 00673 00674 NOTE WELL that the SuperGallery base class handler does some funky things 00675 for us - see SuperGallery::Message - such as deleting our display subtree 00676 for any document which dies (which, uncannily, would explain why they go 00677 away like that when you close documents ;-), and shading the gallery when 00678 there are no documents present. [To override this behaviour in these cases, 00679 you should respond to the message, and return OK rather than calling the 00680 base class message handler] 00681 00682 SeeAlso: SuperGallery::Message; NameGallery::UpdateList 00683 ********************************************************************************************/ 00684 00685 MsgResult NameGallery::Message(Msg* pMessage) 00686 { 00687 // User interface? 00688 if (IS_OUR_DIALOG_MSG(pMessage)) 00689 { 00690 DialogMsg* pMsg = (DialogMsg*) pMessage; 00691 switch (pMsg->DlgMsg) 00692 { 00693 case DIM_CREATE: 00694 SGInit::UpdateGalleryButton(OPTOKEN_DISPLAY_NAME_GALLERY, TRUE); 00695 break; 00696 00697 case DIM_CANCEL: 00698 SGInit::UpdateGalleryButton(OPTOKEN_DISPLAY_NAME_GALLERY, FALSE); 00699 break; 00700 00701 // Handle custom buttons. 00702 case DIM_LFT_BN_CLICKED: 00703 switch(pMsg->GadgetID) 00704 { 00705 case _R(IDC_NAMEGAL_RENAME): 00706 ApplyAction(SGACTION_EDIT); 00707 break; 00708 00709 case _R(IDC_NAMEGAL_UNNAME): 00710 ApplyAction((SGActionType) SGACTION_UNNAME); 00711 break; 00712 00713 case _R(IDC_GALLERY_HELP): 00714 HelpUserTopic(_R(IDS_HELPPATH_Gallery_Name)); 00715 break; 00716 } 00717 break; 00718 } 00719 } 00720 00721 // A new document or a change in focus? 00722 else if (MESSAGE_IS_A(pMessage, DocChangingMsg)) 00723 { 00724 DocChangingMsg* pMsg = (DocChangingMsg*) pMessage; 00725 switch (pMsg->State) 00726 { 00727 case DocChangingMsg::DocState::BORNANDSTABLE: 00728 { 00729 // A new document has been opened, create a new group and items for it. 00730 MILLIPOINT nExtent = GetDisplayExtent(); 00731 if (!CreateItems(pMsg->pChangingDoc, 0)) return FAIL; 00732 ShadeGallery(FALSE); 00733 InvalidateCachedFormat(); 00734 RedrawEverythingBelow(-nExtent); 00735 } 00736 break; 00737 00738 case DocChangingMsg::DocState::SELCHANGED: 00739 // Unhighlight all the items in the old document's group. 00740 if (pMsg->pOldDoc != 0) SelectItems(FALSE, FALSE, pMsg->pOldDoc); 00741 break; 00742 } 00743 00744 // Make sure the button states are updated. 00745 SelectionHasChanged(); 00746 } 00747 00748 // New intersection to show? 00749 else if (MESSAGE_IS_A(pMessage, SelChangingMsg)) 00750 { 00751 SelChangingMsg* pMsg = (SelChangingMsg*) pMessage; 00752 if (pMsg->State == SelChangingMsg::SelectionState::SELECTIONCHANGED) 00753 RefreshDocument(Document::GetCurrent()); 00754 } 00755 00756 // An message that a Document's AttributeSets has changed? 00757 else if (MESSAGE_IS_A(pMessage, AttrSetChangeMsg)) 00758 { 00759 AttrSetChangeMsg* pMsg = (AttrSetChangeMsg*) pMessage; 00760 RefreshDocument(pMsg->GetDocument()); 00761 } 00762 00763 // Always pass messages on for base class handling. 00764 return SuperGallery::Message(pMessage); 00765 } 00766 00767 00768 00769 /******************************************************************************************** 00770 > virtual void NameGallery::RefreshDocument(Document* pDoc) 00771 00772 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00773 Created: 27/1/95 (base generated in sgbase.cpp) 00774 Inputs: pDoc --- the Document whose gallery items should be refreshed 00775 on the next idle event. 00776 Purpose: Marks a gallery as needing to be refreshed/redrawn on the next idle 00777 event sent to the NameGallery. 00778 SeeAlso: NameGallery::Message; NameGallery::OnIdleEvent; SGNameGroup::SetRefresh 00779 ********************************************************************************************/ 00780 00781 void NameGallery::RefreshDocument(Document* pDoc) 00782 { 00783 // Ignore messages sent before there's a DisplayTree, or for Documents which don't 00784 // have an associated group. 00785 if (GetDisplayTree() == 0) return; 00786 SGNameGroup* pGroup = (SGNameGroup*) GetDisplayTree()->FindSubtree(this, pDoc, 0); 00787 if (pGroup != 0) 00788 { 00789 // Mark the group as needing to be refreshed and if there isn't one already, 00790 // register an idle event handler for this gallery. 00791 pGroup->SetRefresh(); 00792 if (!m_fIdleProc) 00793 { 00794 // Set at high priority so the gallery UI is quick. The proc will be 00795 // deregistered after one event so it won't hog the idle time. 00796 GetApplication()->RegisterIdleProcessor(IDLEPRIORITY_HIGH, this); 00797 m_fIdleProc = TRUE; 00798 } 00799 } 00800 } 00801 00802 00803 00804 /******************************************************************************************** 00805 > virtual BOOL NameGallery::OnIdleEvent() 00806 00807 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00808 Created: 27/1/95 (base generated in sgbase.cpp) 00809 Purpose: Called on idle events. Updates the selection if it's been changed, and 00810 recreates and redraws SGNameGroups if the named objects in their 00811 associated Documents have been changed. 00812 Notes: We bypass the standard SuperGallery OnIdleEvent background redraw code as 00813 we may have to destroy SGNameItems during the refresh operation, which 00814 cannot be done during the HandleEvent processing. 00815 SeeAlso: NameGallery::Message; NameGallery::OnIdleEvent; SGNameGroup::SetRefresh; 00816 Application::RegisterIdleProcessor 00817 ********************************************************************************************/ 00818 00819 BOOL NameGallery::OnIdleEvent() 00820 { 00821 // If there's no display tree or we're shaded or closed then there's nothing 00822 // more to do. 00823 BOOL fChanged = FALSE; 00824 if (GetDisplayTree() != 0 && !AmShaded && IsVisible()) 00825 { 00826 // Iterate over all the groups, recreating and redrawing each that is marked 00827 // for refresh. 00828 SGNameGroup* pGroup = (SGNameGroup*) GetDisplayTree()->GetChild(); 00829 while (pGroup != 0) 00830 { 00831 if (pGroup->NeedsRefresh()) 00832 { 00833 // Recreate the items in this group and redraw everything. 00834 CreateItems(pGroup->GetParentDocument(), pGroup); 00835 fChanged = TRUE; 00836 } 00837 00838 pGroup = (SGNameGroup*) pGroup->GetNext(); 00839 } 00840 } 00841 00842 // If we changed something then update the buttons and the display. 00843 if (fChanged) 00844 { 00845 SelectionHasChanged(); 00846 ForceRedrawOfList(); 00847 } 00848 00849 // Kill the idle event now the update has been done. 00850 ERROR3IF(!m_fIdleProc, "NameGallery::OnIdleEvent: lost track of idle event proc"); 00851 GetApplication()->RemoveIdleProcessor(IDLEPRIORITY_HIGH, this); 00852 m_fIdleProc = FALSE; 00853 00854 // Don't call the SuperGallery handler as this gallery doesn't use the 00855 // background redraw facility and works on a lower priority level. 00856 return TRUE; 00857 } 00858 00859 00860 00861 /******************************************************************************************** 00862 > virtual void NameGallery::SelectionHasChanged() 00863 00864 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00865 Created: 7/4/95 00866 Purpose: Called by the base-class SuperGallery whenever the user clicks on an item. 00867 This version overrides the default bahaviour so that selecting more than 00868 one item does NOT grey the "Apply" button. 00869 ********************************************************************************************/ 00870 00871 void NameGallery::SelectionHasChanged() 00872 { 00873 // Nothing to do if we are unavailable. 00874 if (AmShaded || !IsVisible()) return; 00875 00876 // Work out if the user has selected any objects in the selected Document. 00877 BOOL fSelectionExists = Document::GetSelected() != 0 && 00878 !GetApplication()->FindSelection()->IsEmpty(); 00879 00880 // Work out how items are highlighted in the gallery. 00881 INT32 n = GetSelectedItemCount(); 00882 00883 // New button available when there is something selected in the Document. 00884 EnableGadget(_R(IDC_GALLERY_NEW), fSelectionExists); 00885 00886 // Apply and Delete buttons available when at least one item is highlighted. 00887 EnableGadget(_R(IDC_GALLERY_APPLY), n >= 1); 00888 EnableGadget(_R(IDC_GALLERY_DELETE), n >= 1); 00889 00890 // Rename button available when only one item is highlighted. 00891 EnableGadget(_R(IDC_NAMEGAL_RENAME), n == 1); 00892 00893 // Redefine button available when at least one item is highlighted and something 00894 // is selected in the Document. 00895 EnableGadget(_R(IDC_GALLERY_REDEFINE), n >= 1 && fSelectionExists); 00896 00897 // Unname button available when at least one item is highlighted and something 00898 // is selected in the Document. 00899 EnableGadget(_R(IDC_NAMEGAL_UNNAME), n >= 1 && fSelectionExists); 00900 } 00901 00902 00903 00904 /******************************************************************************************** 00905 > virtual BOOL NameGallery::ApplyAction(SGActionType nAction) 00906 00907 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00908 Created: 27/1/95 (base generated in sgbase.cpp) 00909 Inputs: nAction - Indicates what action to apply 00910 Returns: TRUE to indicate successful handling of the action, or 00911 FALSE to indicate failure 00912 Purpose: Applies certain conventional gallery actions (usually associated with 00913 gallery buttons, for new, edit, delete, etc) 00914 SeeAlso: SGActionType 00915 ********************************************************************************************/ 00916 00917 BOOL NameGallery::ApplyAction(SGActionType nAction) 00918 { 00919 // No display tree? Better forget about it then! 00920 if (GetDisplayTree() == 0) return FALSE; 00921 00922 // Determine useful info - this is usually needed for most actions, so always get it 00923 Document* pDoc = Document::GetSelected(); 00924 ERROR3IF(pDoc == 0, "NameGallery::ApplyAction: no selected Document"); 00925 SGNameGroup* pGroup = (SGNameGroup*) GetDisplayTree()->FindSubtree(this, pDoc, 0); 00926 ERROR3IF(pGroup == 0, "NameGallery::ApplyAction: no Group for selected Document"); 00927 00928 // Call the appropriate handler. 00929 switch (nAction) 00930 { 00931 case SGACTION_APPLY: 00932 return OnApply(pGroup, FALSE); 00933 00934 case SGACTION_APPLYADJUST: 00935 return OnApply(pGroup, TRUE); 00936 00937 case SGACTION_CREATE: 00938 return OnCreate(pGroup); 00939 00940 case SGACTION_EDIT: 00941 return OnRename(pGroup); 00942 00943 case SGACTION_DELETE: 00944 return OnDelete(pGroup); 00945 00946 case SGACTION_REDEFINE: 00947 return OnRedefine(pGroup); 00948 00949 case SGACTION_UNNAME: 00950 return OnUnname(pGroup); 00951 00952 default: 00953 TRACEUSER( "JustinF", _T("NameGallery::ApplyAction: unimplemented action\n")); 00954 break; 00955 } 00956 00957 // Successful processing. 00958 return TRUE; 00959 } 00960 00961 00962 00963 /*********************************************************************************************** 00964 > virtual BOOL NameGallery::OnApply(SGNameGroup* pGroup, BOOL fIsAdjust) 00965 00966 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 00967 Created: 17/4/99 00968 Inputs: pGroup --- the group whose items are being applied 00969 fIsAdjust --- if TRUE then this is an "adjust" action, eg. the 00970 user ran the action with the Control button as a 00971 click modifier. 00972 Returns: TRUE if successful. 00973 Purpose: Selects (not "adjust") or toggles ("adjust") the selection status of all 00974 the objects in the associated attribute set of each highlighted 00975 SGNameItem. 00976 Notes: The Application's SelRange object is updated _after_ the SuperGallery 00977 event has been processed, as calling SelRange::Update during an SG event 00978 may destroy the SGNameItems which are processing it. 00979 SeeAlso: NameGallery::ApplyAction; AttributeSets::ChangeObjSelect 00980 ***********************************************************************************************/ 00981 00982 BOOL NameGallery::OnApply(SGNameGroup* pGroup, BOOL fIsAdjust) 00983 { 00984 // If not Adjust then deselect all other objects first. If Adjust then _don't_ change 00985 // the selection of other objects. Don't broadcast a SelChangingMsg or the items will 00986 // be deleted before the iteration. 00987 if (!fIsAdjust) NodeRenderableInk::DeselectAll(TRUE, FALSE); 00988 00989 // Work out what the new selection status of the objects will be. If Adjust then 00990 // toggle the selection states, otherwise set the selection states. 00991 BOOL fState = (fIsAdjust) ? -1 : TRUE; 00992 00993 // Iterate over all the SGNameItems in pGroup which are selected. 00994 INT32 nChanged = 0; 00995 SGNameItem* pItem = (SGNameItem*) pGroup->FindNextSelectedItem(0); 00996 while (pItem != 0) 00997 { 00998 SGNameItem* pNextItem = (SGNameItem*) pGroup->FindNextSelectedItem(pItem); 00999 01000 // Change the selection status of every object in the sets. Afterwards 01001 // NameGallery::Message will update the app's object selection. 01002 String_256 strName; 01003 pItem->GetNameText(&strName); 01004 nChanged += pItem->GetDocument()->GetAttributeSets()->ChangeObjSelect(strName, fState); 01005 01006 pItem = pNextItem; 01007 } 01008 01009 // Inform the application that the selection has changed if any objects were affected. 01010 if (nChanged != 0) GetApplication()->FindSelection()->Update(TRUE); 01011 return TRUE; 01012 } 01013 01014 01015 01016 /*********************************************************************************************** 01017 > virtual BOOL NameGallery::GetNewName(SGNameGroup* pGroup, UINT32 nDialogTemplateID, 01018 String_256* pstrName) 01019 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 01020 Created: 17/4/99 01021 Inputs: pGroup --- the group that a new name is being prompted for 01022 nDialogTemplateID --- the template ID to use, ie. _R(IDD_NAMEOBJ_NAMEDLG) 01023 or _R(IDD_NAMEOBJ_RENAMEDLG) 01024 Outputs: 01025 Returns: TRUE if successful and *pstrName is valid, FALSE if the user cancelled the 01026 dialog or something else went wrong. 01027 Purpose: Runs either the "Name selected objects" or "Rename objects" dialogs, 01028 returning a new, unique name chosen by the user. 01029 SeeAlso: NameGallery::OnCreate; NameGallery::OnRename; class NameObjectsDlg 01030 ***********************************************************************************************/ 01031 01032 BOOL NameGallery::GetNewName(SGNameGroup* pGroup, UINT32 nDialogTemplateID, String_256* pstrName) 01033 { 01034 // Nightmarish pointer gubbins. 01035 ERROR3IF(pstrName == 0, "NameGallery::GetNewName: no output parameter"); 01036 ERROR3IF(pGroup == 0 || pGroup->GetParentDocument() == 0, 01037 "NameGallery::GetNewName: no Group or Document"); 01038 01039 AttributeSets* pSets = pGroup->GetParentDocument()->GetAttributeSets(); 01040 OpDescriptor* pDesc = OpDescriptor::FindOpDescriptor(OPTOKEN_NAME_OBJECTS_DLG); 01041 ERROR3IF(pDesc == 0, "NameGallery::OnCreate: can't find OPTOKEN_NAME_OBJECTS_DLG"); 01042 01043 // Prompt the user until successfully ok-ed or cancelled. 01044 for (;;) 01045 { 01046 // Run the given dialog and get its result. 01047 BOOL fOk; 01048 pDesc->Invoke(&OpParam((INT32) pstrName, (INT32) nDialogTemplateID, &fOk)); 01049 01050 // Did the user cancel the dialog or OK it with a valid entry? 01051 if (!fOk) return FALSE; 01052 if (!pSets->IsSet(*pstrName)) break; 01053 01054 // Explain to the user that new names must be different and prompt again. 01055 InformError(_R(IDE_NAMEOBJ_NAME_EXISTS)); 01056 } 01057 01058 // Success. 01059 return TRUE; 01060 } 01061 01062 01063 01064 /*********************************************************************************************** 01065 > virtual BOOL NameGallery::OnCreate(SGNameGroup* pGroup) 01066 01067 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 01068 Created: 17/4/99 01069 Inputs: pGroup --- the group in which a new name is to be created 01070 Purpose: Prompts the user for a new name for the selected objects in the 01071 group's associated document and creates a new attribute set with 01072 that name. 01073 Returns: TRUE if successful. 01074 SeeAlso: NameGallery::ApplyAction; NameGallery::GetNewName; 01075 AttributeSets::CreateSetOfSelectedObj 01076 ***********************************************************************************************/ 01077 01078 BOOL NameGallery::OnCreate(SGNameGroup* pGroup) 01079 { 01080 ERROR3IF(pGroup == 0 || pGroup->GetParentDocument() == 0, 01081 "NameGallery::OnCreate: no Group or Document"); 01082 01083 // Run the "Name selected objects" dialog and get its result back. If the user 01084 // cancels the dialog we've nothing more to do. 01085 String_256 strName = GetApplication()->FindSelection()->Describe(STATUS_BAR); 01086 if (!GetNewName(pGroup, _R(IDD_NAMEOBJ_NAMEDLG), &strName)) return TRUE; 01087 01088 // Ask the Document's AttributeSets object to make a set of the given name of all 01089 // the selected objects. 01090 ERROR3IF(pGroup->GetParentDocument() != Document::GetSelected(), 01091 "NameGallery::OnCreate: can't CreateSetOfSelectedObj as Document not selected"); 01092 return pGroup->GetParentDocument()->GetAttributeSets()->CreateSetOfSelectedObj(strName); 01093 } 01094 01095 01096 01097 /*********************************************************************************************** 01098 > virtual BOOL NameGallery::OnRename(SGNameGroup* pGroup) 01099 01100 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 01101 Created: 17/4/99 01102 Inputs: pGroup --- the group containing the item to be renamed 01103 Returns: TRUE if successful. 01104 Purpose: Changes the existing name of objects. 01105 SeeAlso: NameGallery::ApplyAction; NameGallery::GetNewName; AttributeSets::RenameSet 01106 ***********************************************************************************************/ 01107 01108 BOOL NameGallery::OnRename(SGNameGroup* pGroup) 01109 { 01110 ERROR3IF(pGroup == 0 || pGroup->GetParentDocument() == 0, 01111 "NameGallery::OnRename: no Group or Document"); 01112 01113 // Extract the old name from the item. 01114 String_256 strName; 01115 SGNameItem* pItem = (SGNameItem*) pGroup->FindNextSelectedItem(0); 01116 pItem->GetNameText(&strName); 01117 01118 // Run the "Name selected objects" dialog and get its result back. If the user 01119 // cancels the dialog we've nothing more to do. 01120 String_256 strNewName = strName; 01121 if (!GetNewName(pGroup, _R(IDD_NAMEOBJ_RENAMEDLG), &strNewName)) return TRUE; 01122 01123 // Ask the Document's AttributeSets object to make a set of the given name of all 01124 // the selected objects. 01125 return pGroup->GetParentDocument()->GetAttributeSets()->RenameSet(strName, strNewName); 01126 } 01127 01128 01129 01130 /*********************************************************************************************** 01131 > virtual BOOL NameGallery::OnDelete(SGNameGroup* pGroup) 01132 01133 Author: Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> 01134 Created: 17/4/99 01135 Inputs: pGroup --- the group containing the items to be deleted 01136 Returns: TRUE if successful. 01137 Purpose: Deletes the given set from the group's document's AttributeSets. 01138 SeeAlso: NameGallery::ApplyAction 01139 ***********************************************************************************************/ 01140 01141 BOOL NameGallery::OnDelete(SGNameGroup* pGroup) 01142 { 01143 ERROR3IF(pGroup == 0 || pGroup->GetParentDocument() == 0, 01144 "NameGallery::OnDelete: no Group or Document"); 01145 01146 // Allocate an array of name parameters at least as big as all the number of 01147 // selected items. Set the last entry to null. 01148 INT32 nEntries = GetSelectedItemCount(); 01149 typedef const StringBase* PSTRBASE; 01150 PSTRBASE* pstrNames = new PSTRBASE[nEntries + 1]; 01151 ERRORIF(pstrNames == 0, _R(IDE_NOMORE_MEMORY), FALSE); 01152 pstrNames[nEntries] = 0; 01153 01154 // Iterate over all the SGNameItems in pGroup which are selected, extracting their 01155 // names and allocating a copy for them. 01156 PSTRBASE* pstrIter = pstrNames; 01157 SGNameItem* pItem = (SGNameItem*) pGroup->FindNextSelectedItem(0); 01158 while (pItem != 0) 01159 { 01160 SGNameItem* pNextItem = (SGNameItem*) pGroup->FindNextSelectedItem(pItem); 01161 01162 String_256 strName; 01163 pItem->GetNameText(&strName); 01164 *pstrIter = new String_256(strName); 01165 if (*pstrIter++ == 0) 01166 { 01167 delete[] pstrNames; 01168 Error::SetError(_R(IDE_NOMORE_MEMORY), 0); 01169 return FALSE; 01170 } 01171 01172 pItem = pNextItem; 01173 } 01174 01175 // Destroy the attribute sets. 01176 BOOL fResult = pGroup->GetParentDocument()->GetAttributeSets()->DestroySets(pstrNames); 01177 01178 // Deallocate the parameter array and return the result. 01179 pstrIter = pstrNames; 01180 while (*pstrIter != 0) delete *pstrIter++; 01181 delete[] pstrNames; 01182 return fResult; 01183 } 0