// $Id: module.cpp 1464 2006-07-18 12:32:26Z gerry $ /* @@tag:xara-cn@@ DO NOT MODIFY THIS LINE ================================XARAHEADERSTART=========================== Xara LX, a vector drawing and manipulation program. Copyright (C) 1993-2006 Xara Group Ltd. Copyright on certain contributions may be held in joint with their respective authors. See AUTHORS file for details. LICENSE TO USE AND MODIFY SOFTWARE ---------------------------------- This file is part of Xara LX. Xara LX is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License version 2 as published by the Free Software Foundation. Xara LX and its component source files are distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Xara LX (see the file GPL in the root directory of the distribution); if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA ADDITIONAL RIGHTS ----------------- Conditional upon your continuing compliance with the GNU General Public License described above, Xara Group Ltd grants to you certain additional rights. The additional rights are to use, modify, and distribute the software together with the wxWidgets library, the wxXtra library, and the "CDraw" library and any other such library that any version of Xara LX relased by Xara Group Ltd requires in order to compile and execute, including the static linking of that library to XaraLX. In the case of the "CDraw" library, you may satisfy obligation under the GNU General Public License to provide source code by providing a binary copy of the library concerned and a copy of the license accompanying it. Nothing in this section restricts any of the rights you have under the GNU General Public License. SCOPE OF LICENSE ---------------- This license applies to this program (XaraLX) and its constituent source files only, and does not necessarily apply to other Xara products which may in part share the same code base, and are subject to their own licensing terms. This license does not apply to files in the wxXtra directory, which are built into a separate library, and are subject to the wxWindows license contained within that directory in the file "WXXTRA-LICENSE". This license does not apply to the binary libraries (if any) within the "libs" directory, which are subject to a separate license contained within that directory in the file "LIBS-LICENSE". ARRANGEMENTS FOR CONTRIBUTION OF MODIFICATIONS ---------------------------------------------- Subject to the terms of the GNU Public License (see above), you are free to do whatever you like with your modifications. However, you may (at your option) wish contribute them to Xara's source tree. You can find details of how to do this at: http://www.xaraxtreme.org/developers/ Prior to contributing your modifications, you will need to complete our contributor agreement. This can be found at: http://www.xaraxtreme.org/developers/contribute/ Please note that Xara will not accept modifications which modify any of the text between the start and end of this header (marked XARAHEADERSTART and XARAHEADEREND). MARKS ----- Xara, Xara LX, Xara X, Xara X/Xtreme, Xara Xtreme, the Xtreme and Xara designs are registered or unregistered trademarks, design-marks, and/or service marks of Xara Group Ltd. All rights in these marks are reserved. Xara Group Ltd, Gaddesden Place, Hemel Hempstead, HP2 6EX, UK. http://www.xara.com/ =================================XARAHEADEREND============================ */ /* */ #include "camtypes.h" #include "oilmods.h" #include "module.h" #include "modlist.h" //#include "tool.h" - in camtypes.h [AUTOMATICALLY REMOVED] //#include "ensure.h" - in camtypes.h [AUTOMATICALLY REMOVED] //#include "viewrc.h" //#include "errors.h" - in camtypes.h [AUTOMATICALLY REMOVED] #include "zoomtool.h" //#include "pushtool.h" DECLARE_SOURCE("$Revision: 1464 $"); ModuleList *Module::Modules = NULL; CC_IMPLEMENT_MEMDUMP(ModInfo_v1, CCObject) CC_IMPLEMENT_MEMDUMP(ModInfo, ModInfo_v1) CC_IMPLEMENT_MEMDUMP(Module_v1, CCObject) CC_IMPLEMENT_MEMDUMP(Module, Module_v1) // Declare smart memory handling in Debug builds #define new CAM_DEBUG_NEW /******************************************************************************************** > void Module::InitModules() Author: Tim_Browse (Xara Group Ltd) Created: 30/6/93 Inputs: - Outputs: - Returns: TRUE if OK, FALSE for catastrophic failure Purpose: Called at the end of initialisation (as it may well need all other initialisations to have been done) to add Tools and Modules to the Kernel's knowledgebase. Errors: None Scope: Public ********************************************************************************************/ BOOL Module::InitModules() { // Initialise the list of Modules. Modules = new ModuleList; if (!Modules) return FALSE; if (!OILModule::Init()) // get OIL's list of modules. This works return FALSE; // by calling back to DescribeModule. // NB. OILModule::Init does it own error BOOL Finished; // reporting do { // All the modules have been 'new'ed now. We can now ask them to initialise themselves. // If they don't want to, they get 'delete'ed. ModuleListItem *Item = (ModuleListItem *) Modules->GetHead(); Finished = TRUE; while (Item != NULL) { Module *Module = Item->m_pModule; // If this module exists and has not been initialised yet, then try to // initialise it. If it initialises ok, set the item's flag, and force // another scan of the remaining modules in case one of them depends on // this module being present. if ((Module != NULL) && (!Item->m_Initialised) && (Module->Init())) { Item->m_Initialised = TRUE; // Tool initialised ok. Finished = FALSE; // At least one more loop to try } // Try the next module Item = (ModuleListItem *) Modules->GetNext(Item); } } while (!Finished); // Delete any un-initialised modules ModuleListItem *Item = (ModuleListItem *) Modules->GetHead(); while (Item != NULL) { if ((Item->m_pModule != NULL) && (!Item->m_Initialised)) { delete Item->m_pModule; Item->m_pModule = NULL; } // Try the next module Item = (ModuleListItem *) Modules->GetNext(Item); } // Scan all the modules and create (but do not initialise) any tools they provide. if (!Tool::InitToolList() || !CreateTools()) return FALSE; return TRUE; } /******************************************************************************************** > ModuleListItem *Module::Declare(Module *NewModule) Author: Andy_Pennell (Xara Group Ltd) Created: 21/6/93 Inputs: NewModule - pointer to a new Tool and its ID pOILModule - pointer to the OILModule object to be associated with this module. Outputs: None Returns: Pointer to new module list item if module. Purpose: Called by OIL code to declare new modules. Errors: Will return NULL if invalid ID or same module ID used twice, and NewModule will have been deleted. ********************************************************************************************/ ModuleListItem *Module::Declare(Module *NewModule, OILModule *pOILModule) { // Try to add the module to the kernel's list. ModuleListItem *NewItem = Modules->Add(NewModule, pOILModule); if (NewItem == NULL) { // Either out of memory or Module has invalid ID - print error message and // destroy module. #ifdef _DEBUG ModInfo Info; NewModule->Describe(&Info); TRACE( _T("Module %u is invalid or has no memory to initialise with.\n"), Info.ID ); #endif delete NewModule; } return NewItem; } /******************************************************************************************** > ModuleListItem *Module::Find(UINT32 ModuleID) Author: Tim_Browse (Xara Group Ltd) Created: 30/6/93 Inputs: Module ID Outputs: None Returns: Pointer to list item of the required module, or NULL if not found. Purpose: Anyone can ask about a module's presence by its ID. Errors: None. ********************************************************************************************/ ModuleListItem *Module::Find(UINT32 ModuleID) { // Simple search of list for ID ModuleListItem *Item = (ModuleListItem *) Modules->GetHead(); while (Item != NULL) { if (Item->m_ModInfo.ID == ModuleID) // Found ID - return pointer to this list item. return Item; Item = (ModuleListItem *) Modules->GetNext(Item); } // Not found return NULL; } /******************************************************************************************** > void Module::DeinitModules() Author: Andy_Pennell (Xara Group Ltd) Created: 21/6/93 Inputs: None Outputs: None Returns: None Purpose: Deletes all allocated modules (and hence tools), then asks OIL to tidy up. Safe to call more than once. Do NOT try to use any tools or modules after calling this. Errors: None ********************************************************************************************/ void Module::DeinitModules() { if (Modules != NULL) { // Delete the list itself. delete Modules; Modules = NULL; // Perform any clean-up required by the OIL layer. PORTNOTE("other","Removed OILModule usage") #ifndef EXCLUDE_FROM_XARALX OILModule::Deinit(); #endif } } /******************************************************************************************** > BOOL Module::CreateTools() Author: Tim_Browse (Xara Group Ltd) Created: 1/7/93 Inputs: - Outputs: - Returns: TRUE => Tools created OK. Purpose: Scan all modules known to the kernel, and try to create an instance of each tool they contain, and add this tool to the kernel's list. Errors: - SeeAlso: - ********************************************************************************************/ BOOL Module::CreateTools() { // Scan the list of modules ModuleListItem *Item = (ModuleListItem *) Modules->GetHead(); while (Item != NULL) { // Interrogate module ModInfo Info; Item->m_pModule->Describe(&Info); // Try to create an instance of each tool in this module for (unsigned tool = 1; tool <= Info.NumTools; tool++) { Tool *NewTool = (Tool *) Item->m_pModule->CreateTool(tool); if (NewTool != NULL) { // Tool was created - add it to the list Tool::Declare(NewTool, Info.ID); } } // Try the next module in the list. Item = (ModuleListItem *) Modules->GetNext(Item); } // Tool* NewTool ; // NewTool = (Tool*)new ZoomTool; if ( NewTool ) Tool::Declare(NewTool,1); // NewTool = (Tool*)new PushTool; if ( NewTool ) Tool::Declare(NewTool,Info.ID); // No error codes yet return TRUE; } // Empty functions for the default module. /******************************************************************************************** > BOOL Module_v1::Init() Author: Andy_Pennell (Xara Group Ltd) Created: 21/6/93 Inputs: - Outputs: - Returns: TRUE if OK, FALSE if module doesn't want to initialise. Purpose: Called after module's constructor to ask it whether it wants to exist or not. Each module is asked in two passes, so that its existence can depend on another module. If a module does not want to exist, it should return FALSE, whereupon it will be deleted. Errors: None ********************************************************************************************/ BOOL Module_v1::Init() { return FALSE; // Should never try to instantiate a module base class } /******************************************************************************************** > Module_v1::~Module_v1() Author: Tim_Browse (Xara Group Ltd) Created: 7/7/93 Inputs: - Outputs: - Returns: - Purpose: Destroys the module, performing any cleanup necessary. Errors: - SeeAlso: - ********************************************************************************************/ Module_v1::~Module_v1() { // Null destructor } /******************************************************************************************** > BOOL Module_v1::Describe(void *Infoptr) Author: Andy_Pennell (Xara Group Ltd) Created: 21/6/93 Inputs: Pointer to area to recieve info Outputs: Info area is updated Returns: None Purpose: Asks a module for more information. The pointer points to a struct such as ModInfo_v1 which the module should fill in. All fields should be filled (NULL is OK for char* variables). The type of the pointer is not explicitly defined so the structure can evolve while keeping backward compatibility. Errors: None ********************************************************************************************/ void Module_v1::Describe(void *InfoPtr) { // Cast structure into the latest one we understand. ModInfo_v1 *Info = (ModInfo_v1 *) InfoPtr; Info->InterfaceVersion = GetInterfaceVersion(); // You should always have this line. // These are all garbage as we should never try to create one of these... Info->Version = 1; Info->ID = MODULEID_INVALID; // so we never get instantiated Info->NumTools = 0; Info->Name = Info->Purpose = Info->Author = NULL; } /******************************************************************************************** > void *Module_v1::CreateTool(UINT32 ToolNumber) Author: Tim_Browse (Xara Group Ltd) Created: 30/6/93 Inputs: ToolNumber - The number of the tool to create (1 to NumTools) Outputs: - Returns: Pointer to the new instantiation of the desired tool. Purpose: Provide a clean interface from module to kernel code for the creation of tools. Errors: - ********************************************************************************************/ void *Module_v1::CreateTool(UINT32) { return NULL; // Should never call this for the base class }