00001 // $Id: cmxibits.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 // bits for CMX import... 00099 00100 #include "camtypes.h" 00101 #include "layer.h" 00102 //#include "group.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00103 //#include "colmodel.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00104 #include "combshps.h" 00105 //#include "app.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00106 #include "fontman.h" 00107 00108 #include "cmxform.h" 00109 #include "cmxifltr.h" 00110 #include "cmxidata.h" 00111 #include "cmxibits.h" 00112 #include "cmxistut.h" 00113 00114 CC_IMPLEMENT_DYNAMIC(CMXImportLayer, ListItem); 00115 CC_IMPLEMENT_DYNAMIC(CMXImportStack, List); 00116 CC_IMPLEMENT_DYNAMIC(CMXImportStackableItem, ListItem); 00117 CC_IMPLEMENT_DYNAMIC(CMXImportTransform, CMXImportStackableItem); 00118 CC_IMPLEMENT_DYNAMIC(CMXImportClipper, CMXImportStackableItem); 00119 CC_IMPLEMENT_DYNAMIC(CMXImportColourList, List); 00120 CC_IMPLEMENT_DYNAMIC(CMXImportColourListItem, ListItem); 00121 00122 #define new CAM_DEBUG_NEW 00123 00124 00125 /******************************************************************************************** 00126 00127 > CMXImportLayer::CMXImportLayer() 00128 00129 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00130 Created: 09/08/96 00131 Inputs: none 00132 Returns: none 00133 Purpose: constructor 00134 00135 ********************************************************************************************/ 00136 00137 CMXImportLayer::CMXImportLayer() 00138 { 00139 // set up things to a nice initial state 00140 pSubTree = NULL; 00141 pLastNodeAdded = NULL; 00142 pGroup = NULL; 00143 00144 GroupLevel = 0; 00145 00146 Used = FALSE; 00147 } 00148 00149 00150 /******************************************************************************************** 00151 00152 > CMXImportLayer::~CMXImportLayer() 00153 00154 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00155 Created: 09/08/96 00156 Inputs: none 00157 Returns: none 00158 Purpose: destructor -- will delete all objects enclosed by it if they aren't marked 00159 as used. 00160 00161 ********************************************************************************************/ 00162 00163 CMXImportLayer::~CMXImportLayer() 00164 { 00165 if(!Used) 00166 { 00167 // stuff wasn't used... delete it 00168 Node *This = pSubTree, *Next; 00169 00170 while(This != 0) 00171 { 00172 Next = This->FindNext(); 00173 00174 This->CascadeDelete(); 00175 00176 delete This; 00177 00178 This = Next; 00179 } 00180 } 00181 } 00182 00183 00184 /******************************************************************************************** 00185 00186 > BOOL CMXImportLayer::AddNode(Node *pNode) 00187 00188 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00189 Created: 09/08/96 00190 Inputs: node to add 00191 Returns: success flag thingy 00192 Purpose: adds a node to the subtree for the layer 00193 00194 ********************************************************************************************/ 00195 00196 BOOL CMXImportLayer::AddNode(Node *pNode) 00197 { 00198 // pNode can be NULL, just in case it's the result of a clipping operation 00199 // which actually resulted in nothing 00200 if(pNode == NULL) 00201 return TRUE; 00202 00203 // right then, where do we want to put this thing? 00204 if(pGroup != 0) 00205 { 00206 // bung it on the end of this group 00207 pNode->AttachNode(pGroup, LASTCHILD, FALSE); // don't check for transparency 00208 } 00209 else 00210 { 00211 // have we added something before? 00212 if(pSubTree == NULL) 00213 { 00214 // nope 00215 pSubTree = pNode; 00216 } 00217 else 00218 { 00219 // bung it on the end of the subtree list 00220 Node *pTarget = pSubTree; 00221 while(pTarget->FindNext() != 0) 00222 pTarget = pTarget->FindNext(); 00223 00224 // pTarget is the last node in the top level of the subtree 00225 pNode->AttachNode(pTarget, NEXT, FALSE); // don't check transparency 00226 } 00227 } 00228 00229 pLastNodeAdded = pNode; 00230 00231 return TRUE; 00232 } 00233 00234 00235 /******************************************************************************************** 00236 00237 > BOOL CMXImportLayer::StartGroup(void) 00238 00239 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00240 Created: 09/08/96 00241 Inputs: none 00242 Returns: success flag thingy 00243 Purpose: starts a group in the layer 00244 00245 ********************************************************************************************/ 00246 00247 BOOL CMXImportLayer::StartGroup(void) 00248 { 00249 // create a new group node 00250 NodeGroup *pNewGroup = new NodeGroup; 00251 if(pNewGroup == NULL) 00252 return FALSE; 00253 00254 // add it to the tree (but don't let it modify the last node thingy) 00255 Node *pTheLastNode = pLastNodeAdded; 00256 AddNode(pNewGroup); 00257 pLastNodeAdded = pTheLastNode; 00258 00259 // put group level up a bit 00260 GroupLevel++; 00261 00262 // point the thingy to this group node 00263 pGroup = pNewGroup; 00264 00265 return TRUE; 00266 } 00267 00268 00269 /******************************************************************************************** 00270 00271 > BOOL CMXImportLayer::EndGroup(void) 00272 00273 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00274 Created: 09/08/96 00275 Inputs: none 00276 Returns: success flag thingy 00277 Purpose: ends a group in the layer 00278 00279 ********************************************************************************************/ 00280 00281 BOOL CMXImportLayer::EndGroup(void) 00282 { 00283 if(GroupLevel < 1) // no start group... 00284 CMXFORMATERROR(FALSE) 00285 00286 // now, we need to wander up a level 00287 if(GroupLevel == 1) 00288 { 00289 // this is a top level node -- just set the group pointer to zero and we're done 00290 pGroup = NULL; 00291 } 00292 else 00293 { 00294 // OK, this isn't a top level one -- we need to find it's parent group... easy! 00295 Node *pParent = pGroup->FindParent(); 00296 00297 // check it's what we expect 00298 ERROR2IF(!IS_A(pParent, NodeGroup), FALSE, "Parent of the group isn't a group, and it jolly well should be. <sulk>"); 00299 00300 // set the new group pointer as the new group 00301 pGroup = pParent; 00302 } 00303 00304 // make a note of our nice group level thing 00305 GroupLevel--; 00306 00307 return TRUE; 00308 } 00309 00310 00311 /******************************************************************************************** 00312 00313 > Layer *CMXImportLayer::UseSubTreeAsLayer(void) 00314 00315 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00316 Created: 09/08/96 00317 Inputs: none 00318 Returns: layer node or NULL 00319 Purpose: creates a layer node, bungs the subtree under it, and returns it, 00320 marking the subtree as used 00321 00322 ********************************************************************************************/ 00323 00324 Layer *CMXImportLayer::UseSubTreeAsLayer(void) 00325 { 00326 Layer *pLayer = new Layer; 00327 if(pLayer == NULL) 00328 return NULL; 00329 00330 // set up some stuff 00331 pLayer->SetLayerID(LayerName); 00332 pLayer->SetVisible(TRUE); 00333 pLayer->SetLocked(FALSE); 00334 pLayer->SetActive(FALSE); 00335 pLayer->SetPrintable(TRUE); 00336 pLayer->SetBackground(FALSE); 00337 pLayer->SetOutline(FALSE); 00338 00339 // stick the objects under it, if we have any (blank layers are allowed) 00340 if(pSubTree != 0) 00341 pSubTree->InsertChainSimple(pLayer, FIRSTCHILD); 00342 00343 // mark as used -- we don't want to go deleting things which are 00344 // in the tree, do we? 00345 Used = TRUE; 00346 00347 return pLayer; 00348 } 00349 00350 00351 00352 /******************************************************************************************** 00353 00354 > CMXImportStack::~CMXImportStack() 00355 00356 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00357 Created: 13/08/96 00358 Inputs: none 00359 Returns: none 00360 Purpose: destructor for the stack 00361 00362 ********************************************************************************************/ 00363 00364 CMXImportStack::~CMXImportStack() 00365 { 00366 #ifdef _DEBUG 00367 if(GetCount() != 0) 00368 TRACEUSER( "Ben", _T("\n\n****************** cmx stack not empty when deleted\n\n\n")); 00369 #endif 00370 00371 // get rid of anything left on the stack 00372 DeleteAll(); 00373 } 00374 00375 00376 00377 /******************************************************************************************** 00378 00379 > BOOL CMXImportStack::Push(CMXImportStackableItem *pItem) 00380 00381 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00382 Created: 13/08/96 00383 Inputs: none 00384 Returns: none 00385 Purpose: push an item onto the stack. It will be activated. It must be the 00386 right kind of item for this stack, by the way. 00387 00388 ********************************************************************************************/ 00389 00390 BOOL CMXImportStack::Push(CMXImportStackableItem *pItem) 00391 { 00392 ERROR2IF(pItem == NULL, FALSE, "no item"); 00393 00394 // get the last item on at the moment 00395 CMXImportStackableItem *pPreviousTail = (CMXImportStackableItem *)GetTail(); 00396 00397 // put the item on the stack 00398 AddTail(pItem); 00399 00400 // tell the item it's been added 00401 if(!pItem->PlacedOnStack(this)) 00402 return FALSE; 00403 00404 // deactivate the previous item, if we have one 00405 if(pPreviousTail != 0) 00406 pPreviousTail->Deactivate(this, FALSE); 00407 00408 // activate this item 00409 return pItem->Activate(this); 00410 } 00411 00412 00413 /******************************************************************************************** 00414 00415 > CMXImportStackableItem *CMXImportStack::Pop(void) 00416 00417 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00418 Created: 13/08/96 00419 Inputs: none 00420 Returns: none 00421 Purpose: pop an item from the stack. It will be deactivated, and the previous one 00422 activated. 00423 00424 ********************************************************************************************/ 00425 00426 CMXImportStackableItem *CMXImportStack::Pop(void) 00427 { 00428 // check we've got something 00429 if(GetCount() == 0) 00430 return 0; 00431 00432 // right then, we need to get the last item by removing from the stack 00433 CMXImportStackableItem *pPopped = (CMXImportStackableItem *)RemoveTail(); 00434 ERROR2IF(pPopped == NULL, 0, "oh no, not item here when the list said there was"); 00435 00436 // deactivate it 00437 pPopped->Deactivate(this, (GetCount() != 0)?FALSE:TRUE); 00438 00439 // activate anything which is left 00440 CMXImportStackableItem *pLast = (CMXImportStackableItem *)GetTail(); 00441 if(pLast != 0) 00442 pLast->Activate(this); 00443 00444 // return the popped item for the caller to use or dispose of 00445 return pPopped; 00446 } 00447 00448 00449 00450 /******************************************************************************************** 00451 00452 > BOOL CMXImportTransform::PlacedOnStack(CMXImportStack *pStack) 00453 00454 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00455 Created: 13/08/96 00456 Inputs: none 00457 Returns: none 00458 Purpose: called when the transform is placed on the stack. It will wander through 00459 the stack creating it's transform matrices and generally set itself up niecly. 00460 00461 ********************************************************************************************/ 00462 00463 BOOL CMXImportTransform::PlacedOnStack(CMXImportStack *pStack) 00464 { 00465 CMXImportFilter *pFilter = pStack->GetFilter(); 00466 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00467 00468 CMXImportTransform *pTrans = (CMXImportTransform *)pStack->GetHead(); 00469 Matrix Sarah; // identity matrix 00470 00471 // run through the previous entries doing fancy stuff 00472 // note that we're on the stack at this point so we include 00473 // ourselves automagically 00474 while(pTrans != 0) 00475 { 00476 // what we do with this thing depends on whether the thingy is 00477 // concatenated to the previous ones or not 00478 if(pTrans->Concatenate) 00479 { 00480 // transform our compound thing by the one in the object 00481 Sarah *= pTrans->TheMatrix; 00482 } 00483 else 00484 { 00485 // just make our current compound one the one in the object 00486 Sarah = pTrans->TheMatrix; 00487 } 00488 00489 // get the next item 00490 pTrans = (CMXImportTransform *)pStack->GetNext(pTrans); 00491 } 00492 00493 // transform it by the filter's base matrix 00494 Matrix *pBase = pFilter->GetBaseMatrix(); 00495 ERROR2IF(pBase == NULL, FALSE, "no base matrix"); 00496 Sarah *= (*pBase); 00497 00498 // set the compound matrix here ready for activation 00499 CompoundMatrix = Sarah; 00500 00501 return TRUE; 00502 } 00503 00504 00505 /******************************************************************************************** 00506 00507 > BOOL CMXImportTransform::Activate(CMXImportStack *pStack) 00508 00509 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00510 Created: 13/08/96 00511 Inputs: none 00512 Returns: none 00513 Purpose: called to set this transform as the current transform 00514 00515 ********************************************************************************************/ 00516 00517 BOOL CMXImportTransform::Activate(CMXImportStack *pStack) 00518 { 00519 CMXImportFilter *pFilter = pStack->GetFilter(); 00520 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00521 00522 // set the matrix in the file to the compound of the previous transforms 00523 // and the base matrix 00524 pFilter->SetMatrix(&CompoundMatrix); 00525 00526 return TRUE; 00527 } 00528 00529 00530 /******************************************************************************************** 00531 00532 > BOOL CMXImportTransform::Deactivate(CMXImportStack *pStack, BOOL IsLastItemOnStack) 00533 00534 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00535 Created: 13/08/96 00536 Inputs: none 00537 Returns: none 00538 Purpose: called to stop this being the active transform. It sets the matrix back 00539 to being the base transform thingy. 00540 00541 ********************************************************************************************/ 00542 00543 BOOL CMXImportTransform::Deactivate(CMXImportStack *pStack, BOOL IsLastItemOnStack) 00544 { 00545 CMXImportFilter *pFilter = pStack->GetFilter(); 00546 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00547 00548 // set the matrix to the base matrix -- this will either be replaced by the 00549 // previous matrix in the stack, or stay as the base matrix which is just 00550 // what we wanted anyway. 00551 pFilter->SetMatrix(pFilter->GetBaseMatrix()); 00552 00553 return TRUE; 00554 } 00555 00556 00557 /******************************************************************************************** 00558 00559 > BOOL CMXImportClipper::PlacedOnStack(CMXImportStack *pStack) 00560 00561 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00562 Created: 22/08/96 00563 Inputs: none 00564 Returns: none 00565 Purpose: called when the clipper is placed on the stack. It will intersect itself 00566 with the previous item if it's required to do so. 00567 00568 ********************************************************************************************/ 00569 00570 BOOL CMXImportClipper::PlacedOnStack(CMXImportStack *pStack) 00571 { 00572 ERROR2IF(pClipPath == NULL, FALSE, "no clip path"); 00573 CMXImportFilter *pFilter = pStack->GetFilter(); 00574 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00575 00576 // first, transform the happy chappy with the currently active matrix 00577 Matrix *pSarah = pFilter->GetCurrentMatrix(); 00578 ERROR2IF(pSarah == NULL, FALSE, "no matrix to transform with"); 00579 pSarah->transform(pClipPath->GetCoordArray(), pClipPath->GetNumCoords()); 00580 00581 if(Intersect) 00582 { 00583 // find previous item 00584 CMXImportClipper *pLastClip = (CMXImportClipper *)pStack->GetPrev(this); 00585 00586 if(pLastClip != 0) // there was actually a previous path to clip 00587 { 00588 // right then, we need to create one of those things 00589 Path *pClippedClipPath = new Path; 00590 if(pClippedClipPath == NULL || !pClippedClipPath->Initialise()) 00591 return FALSE; // something went wrong getting a pathything 00592 00593 // clip this new path to the previous item 00594 ERROR2IF(pLastClip->pClipPath == NULL, FALSE, "no clip path in previous thing"); 00595 if(!pLastClip->pClipPath->ClipPathToPath(*pClipPath, pClippedClipPath, CLIP_STYLE_INTERSECT)) 00596 return FALSE; 00597 00598 // set the clipped path to this new one, deleteing the old one 00599 delete pClipPath; 00600 pClipPath = pClippedClipPath; 00601 } 00602 } 00603 00604 return TRUE; 00605 } 00606 00607 00608 /******************************************************************************************** 00609 00610 > BOOL CMXImportClipper::Activate(CMXImportStack *pStack) 00611 00612 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00613 Created: 22/08/96 00614 Inputs: none 00615 Returns: none 00616 Purpose: called to set this clipper as the current transform 00617 00618 ********************************************************************************************/ 00619 00620 BOOL CMXImportClipper::Activate(CMXImportStack *pStack) 00621 { 00622 CMXImportFilter *pFilter = pStack->GetFilter(); 00623 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00624 00625 // set the clipping path in the thingy 00626 pFilter->SetClippingPath(pClipPath); 00627 00628 return TRUE; 00629 } 00630 00631 00632 /******************************************************************************************** 00633 00634 > BOOL CMXImportClipper::Deactivate(CMXImportStack *pStack, BOOL IsLastItemOnStack) 00635 00636 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00637 Created: 13/08/96 00638 Inputs: none 00639 Returns: none 00640 Purpose: called to stop this being the active clipper. It sets the clipping 00641 path to nothing 00642 00643 ********************************************************************************************/ 00644 00645 BOOL CMXImportClipper::Deactivate(CMXImportStack *pStack, BOOL IsLastItemOnStack) 00646 { 00647 CMXImportFilter *pFilter = pStack->GetFilter(); 00648 ERROR2IF(pFilter == NULL, FALSE, "no filter"); 00649 00650 // set to no clipping 00651 pFilter->SetClippingPath(); 00652 00653 return TRUE; 00654 } 00655 00656 00657 /******************************************************************************************** 00658 00659 > BOOL CMXImportColour::Convert(cmxiColour *pCol) 00660 00661 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00662 Created: 13/08/96 00663 Inputs: pointer to the raw data structure returned by the read data routine 00664 Returns: error flag 00665 Purpose: converts a colour from the data supplied by the file to a nice indexed 00666 colour we can use in our document 00667 00668 ********************************************************************************************/ 00669 00670 #define CVAL(n, max) (FIXED24)(((double)n) / ((double)max)) 00671 00672 BOOL CMXImportColour::Convert(/*cmxiColour*/ void *pvCol) 00673 { 00674 // to get around compiler difficulties (see header file) 00675 cmxiColour *pCol = (cmxiColour *)pvCol; 00676 00677 // OK, get some stuff... 00678 ColourModel Model; 00679 ColourGeneric ColDef; 00680 ColourCMYK *pCMYK = (ColourCMYK *)&ColDef; 00681 ColourRGBT *pRGBT = (ColourRGBT *)&ColDef; 00682 ColourHSVT *pHSVT = (ColourHSVT *)&ColDef; 00683 ColourGreyT *pGreyT = (ColourGreyT *)&ColDef; 00684 00685 switch(pCol->ColourModel) 00686 { 00687 case cmxCOLMODEL_CMYK: 00688 Model = COLOURMODEL_CMYK; 00689 pCMYK->Cyan = CVAL(pCol->Spec.CMYK.Cyan, 100); 00690 pCMYK->Magenta = CVAL(pCol->Spec.CMYK.Magenta, 100); 00691 pCMYK->Yellow = CVAL(pCol->Spec.CMYK.Yellow, 100); 00692 pCMYK->Key = CVAL(pCol->Spec.CMYK.Key, 100); 00693 break; 00694 00695 case cmxCOLMODEL_CMYK255: 00696 Model = COLOURMODEL_CMYK; 00697 pCMYK->Cyan = CVAL(pCol->Spec.CMYK.Cyan, 255); 00698 pCMYK->Magenta = CVAL(pCol->Spec.CMYK.Magenta, 255); 00699 pCMYK->Yellow = CVAL(pCol->Spec.CMYK.Yellow, 255); 00700 pCMYK->Key = CVAL(pCol->Spec.CMYK.Key, 255); 00701 break; 00702 00703 case cmxCOLMODEL_CMY: 00704 Model = COLOURMODEL_CMYK; 00705 pCMYK->Cyan = CVAL(pCol->Spec.CMYK.Cyan, 100); 00706 pCMYK->Magenta = CVAL(pCol->Spec.CMYK.Magenta, 100); 00707 pCMYK->Yellow = CVAL(pCol->Spec.CMYK.Yellow, 100); 00708 pCMYK->Key = 0; 00709 break; 00710 00711 case cmxCOLMODEL_RGB: 00712 Model = COLOURMODEL_RGBT; 00713 pRGBT->Red = CVAL(pCol->Spec.RGB.Red, 255); 00714 pRGBT->Green = CVAL(pCol->Spec.RGB.Green, 255); 00715 pRGBT->Blue = CVAL(pCol->Spec.RGB.Blue, 255); 00716 pRGBT->Transparent = 0; 00717 break; 00718 00719 case cmxCOLMODEL_HSB: 00720 case cmxCOLMODEL_HLS: 00721 Model = COLOURMODEL_HSVT; 00722 pHSVT->Hue = CVAL(pCol->Spec.HSV.Hue, 360); 00723 pHSVT->Saturation = CVAL(pCol->Spec.HSV.Saturation, 255); 00724 pHSVT->Value = CVAL(pCol->Spec.HSV.Value, 255); 00725 pHSVT->Transparent = 0; 00726 break; 00727 00728 case cmxCOLMODEL_GREY: 00729 Model = COLOURMODEL_GREYT; 00730 pGreyT->Intensity = CVAL(pCol->Spec.Grey.Grey, 255); 00731 pGreyT->Reserved1 = 0; 00732 pGreyT->Reserved2 = 0; 00733 pGreyT->Transparent = 0; 00734 break; 00735 00736 default: 00737 TRACEUSER( "Ben", _T("unknown colour type encountered")); 00738 // don't know about this -- make up black and use that instead 00739 Model = COLOURMODEL_CMYK; 00740 pCMYK->Cyan = 1; 00741 pCMYK->Magenta = 1; 00742 pCMYK->Yellow = 1; 00743 pCMYK->Key = 1; 00744 break; 00745 } 00746 00747 // make an index colour, and a DocColour which refers to it 00748 pIndexedColour = new IndexedColour(Model, &ColDef); 00749 pColour = new DocColour; 00750 if(pIndexedColour == NULL || pColour == NULL) 00751 return FALSE; 00752 00753 pColour->MakeRefToIndexedColour(pIndexedColour); 00754 00755 return TRUE; 00756 } 00757 00758 00759 00760 /******************************************************************************************** 00761 00762 > BOOL CMXImportOutline::Convert(cmxiOutline *pOut, CMXImportFilterDataSet *Data) 00763 00764 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00765 Created: 14/08/96 00766 Inputs: pointer to the raw data structure returned by the read data routine 00767 Returns: error flag 00768 Purpose: converts an outline description to a thingy we can use 00769 00770 ********************************************************************************************/ 00771 00772 BOOL CMXImportOutline::Convert(/*cmxiOutline*/ void *pvOut, CMXImportFilterDataSet *Data) 00773 { 00774 // to get around compiler difficulties (see header file) 00775 cmxiOutline *pOut = (cmxiOutline *)pvOut; 00776 00777 // do the colour ref 00778 ColourReference = pOut->ColourRef; 00779 00780 // get the line width 00781 if(pOut->PenRef <= 0 || pOut->PenRef > Data->NumPens) 00782 CMXFORMATERROR(FALSE) // pen ref out of range 00783 00784 Width = Data->Pens[pOut->PenRef - 1].Width; 00785 00786 // get the line style 00787 if(pOut->LineStyleRef <= 0 || pOut->LineStyleRef > Data->NumLineStyles) 00788 CMXFORMATERROR(FALSE) // line style ref out of range 00789 00790 Join = Data->LineStyles[pOut->LineStyleRef - 1].Join; 00791 Cap = Data->LineStyles[pOut->LineStyleRef - 1].Cap; 00792 NoStroke = Data->LineStyles[pOut->LineStyleRef - 1].NoStroke; 00793 00794 // think about dot dash patterns for a while. 00795 // 00796 // 00797 // 00798 // nope, they're not very interesting, are they? 00799 // 00800 // anyway, I suppose we better see if this outline style has one 00801 // of the silly things attached to it. 00802 pDots = NULL; 00803 if(Data->LineStyles[pOut->LineStyleRef - 1].DotDash) 00804 { 00805 // right then, a dot dash pattern is applied. Test this theory. 00806 if(pOut->DotDashRef > 0 && pOut->DotDashRef <= Data->NumDotDashes) 00807 { 00808 // ref valid. Check it out. 00809 if(Data->DotDashes[pOut->DotDashRef - 1].NDots >= 1) 00810 pDots = &Data->DotDashes[pOut->DotDashRef - 1]; 00811 } 00812 } 00813 00814 // what about arrowheads...? 00815 pArrowheads = NULL; 00816 if(pOut->ArrowheadsRef > 0 && pOut->ArrowheadsRef <= Data->NumArrowheads) 00817 { 00818 pArrowheads = &Data->Arrowheads[pOut->ArrowheadsRef - 1]; 00819 } 00820 00821 // that'll do for now 00822 00823 return TRUE; 00824 } 00825 00826 00827 /******************************************************************************************** 00828 00829 > BOOL CMXImportPen::Convert(cmxiPen *pPen) 00830 00831 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00832 Created: 14/08/96 00833 Inputs: pointer to the raw data structure returned by the read data routine 00834 Returns: error flag 00835 Purpose: converts a pen description 00836 00837 ********************************************************************************************/ 00838 00839 BOOL CMXImportPen::Convert(/*cmxiPen*/ void *pvPen) 00840 { 00841 // to get around compiler difficulties (see header file) 00842 cmxiPen *pPen = (cmxiPen *)pvPen; 00843 00844 // store the width -- that's all we can use 00845 Width = pPen->Width; 00846 if(Width < 0) Width = 0 - Width; 00847 00848 return TRUE; 00849 } 00850 00851 00852 /******************************************************************************************** 00853 00854 > BOOL CMXImportFont::Convert( void *pvFont) 00855 00856 Author: Claude_Quemerais (Xara Group Ltd) <camelotdev@xara.com> 00857 Created: 22/08/96 00858 Inputs: pointer to the raw data structure returned by the read data routine 00859 Returns: error flag 00860 Purpose: converts a font description 00861 00862 ********************************************************************************************/ 00863 00864 BOOL CMXImportFont::Convert(/*cmxiFont*/ void *pvFont) 00865 { 00866 // to get around compiler difficulties (see header file) 00867 cmxiFontRecord *pFont = (cmxiFontRecord *)pvFont; 00868 00869 mIsItalic = FALSE; 00870 mIsBold = FALSE; 00871 mFont = pFont->FontName; 00872 String_64 name((TCHAR*)*mFont); 00873 00874 (GetApplication()->GetFontManager())->CacheNamedFont(&name, FC_TRUETYPE); 00875 00876 if((pFont->FontStyle == cmxTEXTATTR_THIN_ITALIC) || 00877 (pFont->FontStyle == cmxTEXTATTR_EXTRA_LIGHT_ITALIC) || 00878 (pFont->FontStyle == cmxTEXTATTR_LIGHT_ITALIC) || 00879 (pFont->FontStyle == cmxTEXTATTR_NORMAL_ITALIC) || 00880 (pFont->FontStyle == cmxTEXTATTR_MEDIUM_ITALIC) || 00881 (pFont->FontStyle == cmxTEXTATTR_SEMI_BOLD_ITALIC) || 00882 (pFont->FontStyle == cmxTEXTATTR_BOLD_ITALIC) || 00883 (pFont->FontStyle == cmxTEXTATTR_EXTRA_BOLD_ITALIC) || 00884 (pFont->FontStyle == cmxTEXTATTR_BLACK_ITALIC)) 00885 mIsItalic = TRUE; 00886 00887 if((pFont->FontStyle == cmxTEXTATTR_BOLD) || 00888 (pFont->FontStyle == cmxTEXTATTR_EXTRA_BOLD) || 00889 (pFont->FontStyle == cmxTEXTATTR_SEMI_BOLD) || 00890 (pFont->FontStyle == cmxTEXTATTR_SEMI_BOLD_ITALIC) || 00891 (pFont->FontStyle == cmxTEXTATTR_BOLD_ITALIC) || 00892 (pFont->FontStyle == cmxTEXTATTR_EXTRA_BOLD_ITALIC)) 00893 mIsBold = TRUE; 00894 00895 return TRUE; 00896 } 00897 00898 00899 /******************************************************************************************** 00900 00901 > BOOL CMXImportPen::Convert(cmxiPen *pPen) 00902 00903 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00904 Created: 15/08/96 00905 Inputs: pointer to the raw data structure returned by the read data routine 00906 Returns: error flag 00907 Purpose: converts a line style description 00908 00909 ********************************************************************************************/ 00910 00911 BOOL CMXImportLineStyle::Convert(/*cmxiLineStyle*/ void *pvStyle) 00912 { 00913 // to get around compiler difficulties (see header file) 00914 cmxiLineStyle *pStyle = (cmxiLineStyle *)pvStyle; 00915 00916 // do spec thingy 00917 if((pStyle->Spec & cmxLINESPEC_DOTDASH) != 0) 00918 DotDash = TRUE; 00919 else 00920 DotDash = FALSE; 00921 00922 // do cap and join types 00923 switch(pStyle->CapAndJoin & cmxCAPJOIN_JOINMASK) 00924 { 00925 case cmxCAPJOIN_ROUNDJOIN: Join = RoundJoin; break; 00926 case cmxCAPJOIN_BEVELJOIN: Join = BevelledJoin; break; 00927 default: Join = MitreJoin; break; 00928 } 00929 switch(pStyle->CapAndJoin & cmxCAPJOIN_CAPMASK) 00930 { 00931 case cmxCAPJOIN_ROUNDCAP: Cap = LineCapRound; break; 00932 case cmxCAPJOIN_SQUARECAP: Cap = LineCapSquare; break; 00933 default: Cap = LineCapButt; break; 00934 } 00935 00936 NoStroke = FALSE; 00937 if((pStyle->Spec & cmxLINESPEC_NONE) != 0) 00938 NoStroke = TRUE; 00939 00940 00941 return TRUE; 00942 } 00943 00944 00945 /******************************************************************************************** 00946 00947 > BOOL CMXImportDotDash::Convert(cmxiDotDash *pvDotDash) 00948 00949 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00950 Created: 22/08/96 00951 Inputs: pointer to the raw data structure returned by the read data routine 00952 Returns: error flag 00953 Purpose: converts a dot dash description 00954 00955 ********************************************************************************************/ 00956 00957 BOOL CMXImportDotDash::Convert(/*cmxiDotDash*/ void *pvDotDash) 00958 { 00959 // to get around compiler difficulties (see header file) 00960 cmxiDotDash *pDotDash = (cmxiDotDash *)pvDotDash; 00961 00962 // copy in the dots INT32 array 00963 NDots = pDotDash->Dots.NumElements; 00964 pElements = (DashElement *)pDotDash->Dots.pElements; 00965 00966 return TRUE; 00967 } 00968 00969 00970 /******************************************************************************************** 00971 00972 > BOOL CMXImportArrowShape::Convert(cmxiArrowShape *pvArrowShape, BOOL Is32Bit) 00973 00974 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 00975 Created: 26/08/96 00976 Inputs: pointer to the raw data structure returned by the read data routine 00977 Returns: error flag 00978 Purpose: converts an arrow shape description 00979 00980 ********************************************************************************************/ 00981 00982 BOOL CMXImportArrowShape::Convert(/*cmxiArrowShape*/ void *pvArrowShape, BOOL Is32Bit) 00983 { 00984 // to get around compiler difficulties (see header file) 00985 cmxiArrowShape *pArrowShape = (cmxiArrowShape *)pvArrowShape; 00986 00987 // set up the arrow rec thingy 00988 Arrow.ArrowShape = pArrowShape->pShape; 00989 Arrow.LineWidth = (Is32Bit)?(360000):(1400); 00990 Arrow.IsNull = FALSE; 00991 00992 // record the line offset 00993 LineOffset = pArrowShape->LineOffset; 00994 TRACEUSER( "Ben", _T("LineOffset = %d\n"), LineOffset); 00995 00996 return TRUE; 00997 } 00998 00999 01000 /******************************************************************************************** 01001 01002 > BOOL CMXImportArrowShape::Convert(cmxiArrowheads *pvArrowShape, CMXImportFilterDataSet *Data) 01003 01004 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 01005 Created: 26/08/96 01006 Inputs: pointer to the raw data structure returned by the read data routine 01007 Returns: error flag 01008 Purpose: converts an arrow shape description 01009 01010 ********************************************************************************************/ 01011 01012 BOOL CMXImportArrowheads::Convert(/*cmxiArrowheads*/ void *pvArrowheads, CMXImportFilterDataSet *Data) 01013 { 01014 // to get around compiler difficulties (see header file) 01015 cmxiArrowheads *pArrowheads = (cmxiArrowheads *)pvArrowheads; 01016 01017 // record the start and end thingsy 01018 if(pArrowheads->StartRef > 0 && pArrowheads->StartRef <= Data->NumArrowShapes) 01019 pStart = &Data->ArrowShapes[pArrowheads->StartRef - 1]; 01020 01021 if(pArrowheads->EndRef > 0 && pArrowheads->EndRef <= Data->NumArrowShapes) 01022 pEnd = &Data->ArrowShapes[pArrowheads->EndRef - 1]; 01023 01024 return TRUE; 01025 } 01026 01027 01028 /******************************************************************************************** 01029 01030 > BOOL CMXImportColourList::AddColour(INT32 Reference, INT32 Position) 01031 01032 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 01033 Created: 14/08/96 01034 Inputs: reference of colour, position of colour 01035 Returns: error flag 01036 Purpose: adds a colour to the list 01037 01038 ********************************************************************************************/ 01039 01040 BOOL CMXImportColourList::AddColour(INT32 Reference, INT32 Position) 01041 { 01042 // get new item 01043 CMXImportColourListItem *pNewItem = new CMXImportColourListItem; 01044 if(pNewItem == NULL) 01045 return FALSE; 01046 01047 // set the data in the item 01048 pNewItem->Reference = Reference; 01049 pNewItem->Position = Position; 01050 01051 // add it to the list 01052 AddTail(pNewItem); 01053 01054 return TRUE; 01055 } 01056 01057 01058 01059 /******************************************************************************************** 01060 01061 > INT32 CMXImportColourList::GetColourRefClosestToPosition(INT32 Position) 01062 01063 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 01064 Created: 14/08/96 01065 Inputs: Position 01066 Returns: reference of colour closest to this position 01067 Purpose: finds the colour closest to a given position 01068 01069 ********************************************************************************************/ 01070 01071 INT32 CMXImportColourList::GetColourRefClosestToPosition(INT32 Position) 01072 { 01073 // variable things 01074 INT32 Ref = 1; 01075 INT32 Distance = 10000; 01076 01077 // run through the list 01078 CMXImportColourListItem *pEn = (CMXImportColourListItem *)GetHead(); 01079 while(pEn != 0) 01080 { 01081 // see if this is closer 01082 INT32 d = ABS(pEn->Position - Position); 01083 if(d < Distance) 01084 { 01085 Ref = pEn->Reference; 01086 Distance = d; 01087 } 01088 01089 // next! 01090 pEn = (CMXImportColourListItem *)GetNext(pEn); 01091 } 01092 01093 return Ref; 01094 } 01095 01096 01097 01098 /******************************************************************************************** 01099 01100 > BOOL CMXImportProcedure::Read(cmxiProcedureIndexEntry *pEn); 01101 01102 Author: Ben_Summers (Xara Group Ltd) <camelotdev@xara.com> 01103 Created: 19/08/96 01104 Inputs: entry of index 01105 Returns: error flag 01106 Purpose: converts an entry type thing 01107 01108 ********************************************************************************************/ 01109 01110 BOOL CMXImportProcedure::Read(/*cmxiProcedureIndexEntry*/ void *pvEn) 01111 { 01112 cmxiProcedureIndexEntry *pEn = (cmxiProcedureIndexEntry *)pvEn; 01113 01114 Position = pEn->Position; 01115 01116 return TRUE; 01117 } 01118