1 : /**********************************************************************
2 : * $Id: mitab_tooldef.cpp,v 1.6 2004/06/30 20:29:04 dmorissette Exp $
3 : *
4 : * Name: mitab_tooldef.cpp
5 : * Project: MapInfo TAB Read/Write library
6 : * Language: C++
7 : * Purpose: Implementation of the TABToolDefTable class used to handle
8 : * a dataset's table of drawing tool blocks
9 : * Author: Daniel Morissette, dmorissette@dmsolutions.ca
10 : *
11 : **********************************************************************
12 : * Copyright (c) 1999, 2000, Daniel Morissette
13 : *
14 : * Permission is hereby granted, free of charge, to any person obtaining a
15 : * copy of this software and associated documentation files (the "Software"),
16 : * to deal in the Software without restriction, including without limitation
17 : * the rights to use, copy, modify, merge, publish, distribute, sublicense,
18 : * and/or sell copies of the Software, and to permit persons to whom the
19 : * Software is furnished to do so, subject to the following conditions:
20 : *
21 : * The above copyright notice and this permission notice shall be included
22 : * in all copies or substantial portions of the Software.
23 : *
24 : * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
25 : * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
26 : * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
27 : * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
28 : * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
29 : * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
30 : * DEALINGS IN THE SOFTWARE.
31 : **********************************************************************
32 : *
33 : * $Log: mitab_tooldef.cpp,v $
34 : * Revision 1.6 2004/06/30 20:29:04 dmorissette
35 : * Fixed refs to old address danmo@videotron.ca
36 : *
37 : * Revision 1.5 2000/11/15 04:13:50 daniel
38 : * Fixed writing of TABMAPToolBlock to allocate a new block when full
39 : *
40 : * Revision 1.4 2000/02/28 17:06:54 daniel
41 : * Support pen width in points and V450 check
42 : *
43 : * Revision 1.3 2000/01/15 22:30:45 daniel
44 : * Switch to MIT/X-Consortium OpenSource license
45 : *
46 : * Revision 1.2 1999/10/18 15:39:21 daniel
47 : * Handle case of "no pen" or "no brush" in AddPen/BrushRef()
48 : *
49 : * Revision 1.1 1999/09/26 14:59:37 daniel
50 : * Implemented write support
51 : *
52 : **********************************************************************/
53 :
54 : #include "mitab.h"
55 : #include "mitab_utils.h"
56 :
57 : /*=====================================================================
58 : * class TABToolDefTable
59 : *====================================================================*/
60 :
61 : /**********************************************************************
62 : * TABToolDefTable::TABToolDefTable()
63 : *
64 : * Constructor.
65 : **********************************************************************/
66 4 : TABToolDefTable::TABToolDefTable()
67 : {
68 4 : m_papsPen = NULL;
69 4 : m_papsBrush = NULL;
70 4 : m_papsFont = NULL;
71 4 : m_papsSymbol = NULL;
72 4 : m_numPen = 0;
73 4 : m_numBrushes = 0;
74 4 : m_numFonts = 0;
75 4 : m_numSymbols = 0;
76 4 : m_numAllocatedPen = 0;
77 4 : m_numAllocatedBrushes = 0;
78 4 : m_numAllocatedFonts = 0;
79 4 : m_numAllocatedSymbols = 0;
80 :
81 4 : }
82 :
83 : /**********************************************************************
84 : * TABToolDefTable::~TABToolDefTable()
85 : *
86 : * Destructor.
87 : **********************************************************************/
88 4 : TABToolDefTable::~TABToolDefTable()
89 : {
90 : int i;
91 :
92 8 : for(i=0; m_papsPen && i < m_numPen; i++)
93 4 : CPLFree(m_papsPen[i]);
94 4 : CPLFree(m_papsPen);
95 :
96 8 : for(i=0; m_papsBrush && i < m_numBrushes; i++)
97 4 : CPLFree(m_papsBrush[i]);
98 4 : CPLFree(m_papsBrush);
99 :
100 4 : for(i=0; m_papsFont && i < m_numFonts; i++)
101 0 : CPLFree(m_papsFont[i]);
102 4 : CPLFree(m_papsFont);
103 :
104 4 : for(i=0; m_papsSymbol && i < m_numSymbols; i++)
105 0 : CPLFree(m_papsSymbol[i]);
106 4 : CPLFree(m_papsSymbol);
107 :
108 4 : }
109 :
110 :
111 : /**********************************************************************
112 : * TABToolDefTable::ReadAllToolDefs()
113 : *
114 : * Read all tool definition blocks until we reach the end of the chain.
115 : * This function will be called only once per dataset, after that
116 : * we keep all the tool definitions in memory.
117 : *
118 : * Returns 0 on success, -1 on error.
119 : **********************************************************************/
120 2 : int TABToolDefTable::ReadAllToolDefs(TABMAPToolBlock *poBlock)
121 : {
122 2 : int nStatus = 0;
123 : int nDefType;
124 :
125 : /*-----------------------------------------------------------------
126 : * Loop until we reach the end of the chain of blocks... we assume
127 : * that the first block of data is already pre-loaded.
128 : *----------------------------------------------------------------*/
129 8 : while( ! poBlock->EndOfChain() )
130 : {
131 4 : nDefType = poBlock->ReadByte();
132 4 : switch(nDefType)
133 : {
134 : case TABMAP_TOOL_PEN: // PEN
135 2 : if (m_numPen >= m_numAllocatedPen)
136 : {
137 : // Realloc array by blocks of 20 items
138 2 : m_numAllocatedPen += 20;
139 : m_papsPen = (TABPenDef**)CPLRealloc(m_papsPen,
140 2 : m_numAllocatedPen*sizeof(TABPenDef*));
141 : }
142 2 : m_papsPen[m_numPen] = (TABPenDef*)CPLCalloc(1, sizeof(TABPenDef));
143 :
144 2 : m_papsPen[m_numPen]->nRefCount = poBlock->ReadInt32();
145 2 : m_papsPen[m_numPen]->nPixelWidth = poBlock->ReadByte();
146 2 : m_papsPen[m_numPen]->nLinePattern = poBlock->ReadByte();
147 2 : m_papsPen[m_numPen]->nPointWidth = poBlock->ReadByte();
148 : m_papsPen[m_numPen]->rgbColor = poBlock->ReadByte()*256*256+
149 : poBlock->ReadByte()*256 +
150 2 : poBlock->ReadByte();
151 :
152 : // Adjust width value...
153 : // High bits for point width values > 255 are stored in the
154 : // pixel width byte
155 2 : if (m_papsPen[m_numPen]->nPixelWidth > 7)
156 : {
157 : m_papsPen[m_numPen]->nPointWidth +=
158 0 : (m_papsPen[m_numPen]->nPixelWidth-8)*0x100;
159 0 : m_papsPen[m_numPen]->nPixelWidth = 1;
160 : }
161 :
162 2 : m_numPen++;
163 :
164 2 : break;
165 : case TABMAP_TOOL_BRUSH: // BRUSH
166 2 : if (m_numBrushes >= m_numAllocatedBrushes)
167 : {
168 : // Realloc array by blocks of 20 items
169 2 : m_numAllocatedBrushes += 20;
170 : m_papsBrush = (TABBrushDef**)CPLRealloc(m_papsBrush,
171 2 : m_numAllocatedBrushes*sizeof(TABBrushDef*));
172 : }
173 : m_papsBrush[m_numBrushes] =
174 2 : (TABBrushDef*)CPLCalloc(1,sizeof(TABBrushDef));
175 :
176 2 : m_papsBrush[m_numBrushes]->nRefCount = poBlock->ReadInt32();
177 2 : m_papsBrush[m_numBrushes]->nFillPattern = poBlock->ReadByte();
178 2 : m_papsBrush[m_numBrushes]->bTransparentFill = poBlock->ReadByte();
179 : m_papsBrush[m_numBrushes]->rgbFGColor =poBlock->ReadByte()*256*256+
180 : poBlock->ReadByte()*256 +
181 2 : poBlock->ReadByte();
182 : m_papsBrush[m_numBrushes]->rgbBGColor =poBlock->ReadByte()*256*256+
183 : poBlock->ReadByte()*256 +
184 2 : poBlock->ReadByte();
185 :
186 2 : m_numBrushes++;
187 :
188 2 : break;
189 : case TABMAP_TOOL_FONT: // FONT NAME
190 0 : if (m_numFonts >= m_numAllocatedFonts)
191 : {
192 : // Realloc array by blocks of 20 items
193 0 : m_numAllocatedFonts += 20;
194 : m_papsFont = (TABFontDef**)CPLRealloc(m_papsFont,
195 0 : m_numAllocatedFonts*sizeof(TABFontDef*));
196 : }
197 : m_papsFont[m_numFonts] =
198 0 : (TABFontDef*)CPLCalloc(1,sizeof(TABFontDef));
199 :
200 0 : m_papsFont[m_numFonts]->nRefCount = poBlock->ReadInt32();
201 0 : poBlock->ReadBytes(32, (GByte*)m_papsFont[m_numFonts]->szFontName);
202 0 : m_papsFont[m_numFonts]->szFontName[32] = '\0';
203 :
204 0 : m_numFonts++;
205 :
206 0 : break;
207 : case TABMAP_TOOL_SYMBOL: // SYMBOL
208 0 : if (m_numSymbols >= m_numAllocatedSymbols)
209 : {
210 : // Realloc array by blocks of 20 items
211 0 : m_numAllocatedSymbols += 20;
212 : m_papsSymbol = (TABSymbolDef**)CPLRealloc(m_papsSymbol,
213 0 : m_numAllocatedSymbols*sizeof(TABSymbolDef*));
214 : }
215 : m_papsSymbol[m_numSymbols] =
216 0 : (TABSymbolDef*)CPLCalloc(1,sizeof(TABSymbolDef));
217 :
218 0 : m_papsSymbol[m_numSymbols]->nRefCount = poBlock->ReadInt32();
219 0 : m_papsSymbol[m_numSymbols]->nSymbolNo = poBlock->ReadInt16();
220 0 : m_papsSymbol[m_numSymbols]->nPointSize = poBlock->ReadInt16();
221 0 : m_papsSymbol[m_numSymbols]->_nUnknownValue_ = poBlock->ReadByte();
222 : m_papsSymbol[m_numSymbols]->rgbColor = poBlock->ReadByte()*256*256+
223 : poBlock->ReadByte()*256 +
224 0 : poBlock->ReadByte();
225 :
226 0 : m_numSymbols++;
227 :
228 0 : break;
229 : default:
230 : /* Unsupported Tool type!!! */
231 : CPLError(CE_Failure, CPLE_NotSupported,
232 0 : "Unsupported drawing tool type: `%d'", nDefType);
233 0 : nStatus = -1;
234 : }
235 :
236 4 : if (CPLGetLastErrorNo() != 0)
237 : {
238 : // An error happened reading this tool definition... stop now.
239 0 : nStatus = -1;
240 : }
241 : }
242 :
243 2 : return nStatus;
244 : }
245 :
246 :
247 : /**********************************************************************
248 : * TABToolDefTable::WriteAllToolDefs()
249 : *
250 : * Write all tool definition structures to the TABMAPToolBlock.
251 : *
252 : * Note that at the end of this call, poBlock->CommitToFile() will have
253 : * been called.
254 : *
255 : * Returns 0 on success, -1 on error.
256 : **********************************************************************/
257 2 : int TABToolDefTable::WriteAllToolDefs(TABMAPToolBlock *poBlock)
258 : {
259 2 : int i, nStatus = 0;
260 :
261 : /*-----------------------------------------------------------------
262 : * Write Pen Defs
263 : *----------------------------------------------------------------*/
264 4 : for(i=0; nStatus == 0 && i< m_numPen; i++)
265 : {
266 : // The pen width is encoded over 2 bytes
267 2 : GByte byPixelWidth=1, byPointWidth=0;
268 2 : if (m_papsPen[i]->nPointWidth > 0)
269 : {
270 0 : byPointWidth = (GByte)(m_papsPen[i]->nPointWidth & 0xff);
271 0 : if (m_papsPen[i]->nPointWidth > 255)
272 0 : byPixelWidth = 8 + (GByte)(m_papsPen[i]->nPointWidth/0x100);
273 : }
274 : else
275 2 : byPixelWidth = MIN(MAX(m_papsPen[i]->nPixelWidth, 1), 7);
276 :
277 2 : poBlock->CheckAvailableSpace(TABMAP_TOOL_PEN);
278 2 : poBlock->WriteByte(TABMAP_TOOL_PEN); // Def Type = Pen
279 2 : poBlock->WriteInt32(m_papsPen[i]->nRefCount);
280 :
281 2 : poBlock->WriteByte(byPixelWidth);
282 2 : poBlock->WriteByte(m_papsPen[i]->nLinePattern);
283 2 : poBlock->WriteByte(byPointWidth);
284 2 : poBlock->WriteByte(COLOR_R(m_papsPen[i]->rgbColor));
285 2 : poBlock->WriteByte(COLOR_G(m_papsPen[i]->rgbColor));
286 2 : poBlock->WriteByte(COLOR_B(m_papsPen[i]->rgbColor));
287 :
288 2 : if (CPLGetLastErrorNo() != 0)
289 : {
290 : // An error happened reading this tool definition... stop now.
291 0 : nStatus = -1;
292 : }
293 : }
294 :
295 : /*-----------------------------------------------------------------
296 : * Write Brush Defs
297 : *----------------------------------------------------------------*/
298 4 : for(i=0; nStatus == 0 && i< m_numBrushes; i++)
299 : {
300 2 : poBlock->CheckAvailableSpace(TABMAP_TOOL_BRUSH);
301 :
302 2 : poBlock->WriteByte(TABMAP_TOOL_BRUSH); // Def Type = Brush
303 2 : poBlock->WriteInt32(m_papsBrush[i]->nRefCount);
304 :
305 2 : poBlock->WriteByte(m_papsBrush[i]->nFillPattern);
306 2 : poBlock->WriteByte(m_papsBrush[i]->bTransparentFill);
307 2 : poBlock->WriteByte(COLOR_R(m_papsBrush[i]->rgbFGColor));
308 2 : poBlock->WriteByte(COLOR_G(m_papsBrush[i]->rgbFGColor));
309 2 : poBlock->WriteByte(COLOR_B(m_papsBrush[i]->rgbFGColor));
310 2 : poBlock->WriteByte(COLOR_R(m_papsBrush[i]->rgbBGColor));
311 2 : poBlock->WriteByte(COLOR_G(m_papsBrush[i]->rgbBGColor));
312 2 : poBlock->WriteByte(COLOR_B(m_papsBrush[i]->rgbBGColor));
313 :
314 2 : if (CPLGetLastErrorNo() != 0)
315 : {
316 : // An error happened reading this tool definition... stop now.
317 0 : nStatus = -1;
318 : }
319 : }
320 :
321 : /*-----------------------------------------------------------------
322 : * Write Font Defs
323 : *----------------------------------------------------------------*/
324 2 : for(i=0; nStatus == 0 && i< m_numFonts; i++)
325 : {
326 0 : poBlock->CheckAvailableSpace(TABMAP_TOOL_FONT);
327 :
328 0 : poBlock->WriteByte(TABMAP_TOOL_FONT); // Def Type = Font name
329 0 : poBlock->WriteInt32(m_papsFont[i]->nRefCount);
330 :
331 0 : poBlock->WriteBytes(32, (GByte*)m_papsFont[i]->szFontName);
332 :
333 0 : if (CPLGetLastErrorNo() != 0)
334 : {
335 : // An error happened reading this tool definition... stop now.
336 0 : nStatus = -1;
337 : }
338 : }
339 :
340 : /*-----------------------------------------------------------------
341 : * Write Symbol Defs
342 : *----------------------------------------------------------------*/
343 2 : for(i=0; nStatus == 0 && i< m_numSymbols; i++)
344 : {
345 0 : poBlock->CheckAvailableSpace(TABMAP_TOOL_SYMBOL);
346 :
347 0 : poBlock->WriteByte(TABMAP_TOOL_SYMBOL); // Def Type = Symbol
348 0 : poBlock->WriteInt32(m_papsSymbol[i]->nRefCount);
349 :
350 0 : poBlock->WriteInt16(m_papsSymbol[i]->nSymbolNo);
351 0 : poBlock->WriteInt16(m_papsSymbol[i]->nPointSize);
352 0 : poBlock->WriteByte(m_papsSymbol[i]->_nUnknownValue_);
353 0 : poBlock->WriteByte(COLOR_R(m_papsSymbol[i]->rgbColor));
354 0 : poBlock->WriteByte(COLOR_G(m_papsSymbol[i]->rgbColor));
355 0 : poBlock->WriteByte(COLOR_B(m_papsSymbol[i]->rgbColor));
356 :
357 0 : if (CPLGetLastErrorNo() != 0)
358 : {
359 : // An error happened reading this tool definition... stop now.
360 0 : nStatus = -1;
361 : }
362 : }
363 :
364 2 : if (nStatus == 0)
365 2 : nStatus = poBlock->CommitToFile();
366 :
367 2 : return nStatus;
368 : }
369 :
370 :
371 :
372 : /**********************************************************************
373 : * TABToolDefTable::GetNumPen()
374 : *
375 : * Return the number of valid pen indexes for this .MAP file
376 : **********************************************************************/
377 4 : int TABToolDefTable::GetNumPen()
378 : {
379 4 : return m_numPen;
380 : }
381 :
382 : /**********************************************************************
383 : * TABToolDefTable::GetPenDefRef()
384 : *
385 : * Return a reference to the specified Pen tool definition, or NULL if
386 : * specified index is invalid.
387 : *
388 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
389 : * in MapInfo.
390 : **********************************************************************/
391 52 : TABPenDef *TABToolDefTable::GetPenDefRef(int nIndex)
392 : {
393 52 : if (nIndex >0 && nIndex <= m_numPen)
394 52 : return m_papsPen[nIndex-1];
395 :
396 0 : return NULL;
397 : }
398 :
399 : /**********************************************************************
400 : * TABToolDefTable::AddPenDefRef()
401 : *
402 : * Either create a new PenDefRef or add a reference to an existing one.
403 : *
404 : * Return the pen index that has been attributed to this Pen tool
405 : * definition, or -1 if something went wrong
406 : *
407 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
408 : * in MapInfo.
409 : **********************************************************************/
410 12 : int TABToolDefTable::AddPenDefRef(TABPenDef *poNewPenDef)
411 : {
412 12 : int i, nNewPenIndex = 0;
413 : TABPenDef *poDef;
414 :
415 12 : if (poNewPenDef == NULL)
416 0 : return -1;
417 :
418 : /*-----------------------------------------------------------------
419 : * Check for "none" case: pattern = 0 (pattern 0 does not exist!)
420 : *----------------------------------------------------------------*/
421 12 : if (poNewPenDef->nLinePattern < 1)
422 0 : return 0;
423 :
424 : /*-----------------------------------------------------------------
425 : * Start by searching the list of existing pens
426 : *----------------------------------------------------------------*/
427 22 : for (i=0; nNewPenIndex == 0 && i<m_numPen; i++)
428 : {
429 10 : poDef = m_papsPen[i];
430 10 : if (poDef->nPixelWidth == poNewPenDef->nPixelWidth &&
431 : poDef->nLinePattern == poNewPenDef->nLinePattern &&
432 : poDef->nPointWidth == poNewPenDef->nPointWidth &&
433 : poDef->rgbColor == poNewPenDef->rgbColor)
434 : {
435 10 : nNewPenIndex = i+1; // Fount it!
436 10 : poDef->nRefCount++;
437 : }
438 : }
439 :
440 : /*-----------------------------------------------------------------
441 : * OK, we did not find a match, then create a new entry
442 : *----------------------------------------------------------------*/
443 12 : if (nNewPenIndex == 0)
444 : {
445 2 : if (m_numPen >= m_numAllocatedPen)
446 : {
447 : // Realloc array by blocks of 20 items
448 2 : m_numAllocatedPen += 20;
449 : m_papsPen = (TABPenDef**)CPLRealloc(m_papsPen,
450 2 : m_numAllocatedPen*sizeof(TABPenDef*));
451 : }
452 2 : m_papsPen[m_numPen] = (TABPenDef*)CPLCalloc(1, sizeof(TABPenDef));
453 :
454 2 : *m_papsPen[m_numPen] = *poNewPenDef;
455 2 : m_papsPen[m_numPen]->nRefCount = 1;
456 2 : nNewPenIndex = ++m_numPen;
457 : }
458 :
459 12 : return nNewPenIndex;
460 : }
461 :
462 : /**********************************************************************
463 : * TABToolDefTable::GetNumBrushes()
464 : *
465 : * Return the number of valid Brush indexes for this .MAP file
466 : **********************************************************************/
467 4 : int TABToolDefTable::GetNumBrushes()
468 : {
469 4 : return m_numBrushes;
470 : }
471 :
472 : /**********************************************************************
473 : * TABToolDefTable::GetBrushDefRef()
474 : *
475 : * Return a reference to the specified Brush tool definition, or NULL if
476 : * specified index is invalid.
477 : *
478 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
479 : * in MapInfo.
480 : **********************************************************************/
481 51 : TABBrushDef *TABToolDefTable::GetBrushDefRef(int nIndex)
482 : {
483 51 : if (nIndex >0 && nIndex <= m_numBrushes)
484 51 : return m_papsBrush[nIndex-1];
485 :
486 0 : return NULL;
487 : }
488 :
489 : /**********************************************************************
490 : * TABToolDefTable::AddBrushDefRef()
491 : *
492 : * Either create a new BrushDefRef or add a reference to an existing one.
493 : *
494 : * Return the Brush index that has been attributed to this Brush tool
495 : * definition, or -1 if something went wrong
496 : *
497 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
498 : * in MapInfo.
499 : **********************************************************************/
500 11 : int TABToolDefTable::AddBrushDefRef(TABBrushDef *poNewBrushDef)
501 : {
502 11 : int i, nNewBrushIndex = 0;
503 : TABBrushDef *poDef;
504 :
505 11 : if (poNewBrushDef == NULL)
506 0 : return -1;
507 :
508 : /*-----------------------------------------------------------------
509 : * Check for "none" case: pattern = 0 (pattern 0 does not exist!)
510 : *----------------------------------------------------------------*/
511 11 : if (poNewBrushDef->nFillPattern < 1)
512 0 : return 0;
513 :
514 : /*-----------------------------------------------------------------
515 : * Start by searching the list of existing Brushs
516 : *----------------------------------------------------------------*/
517 20 : for (i=0; nNewBrushIndex == 0 && i<m_numBrushes; i++)
518 : {
519 9 : poDef = m_papsBrush[i];
520 9 : if (poDef->nFillPattern == poNewBrushDef->nFillPattern &&
521 : poDef->bTransparentFill == poNewBrushDef->bTransparentFill &&
522 : poDef->rgbFGColor == poNewBrushDef->rgbFGColor &&
523 : poDef->rgbBGColor == poNewBrushDef->rgbBGColor)
524 : {
525 9 : nNewBrushIndex = i+1; // Fount it!
526 9 : poDef->nRefCount++;
527 : }
528 : }
529 :
530 : /*-----------------------------------------------------------------
531 : * OK, we did not find a match, then create a new entry
532 : *----------------------------------------------------------------*/
533 11 : if (nNewBrushIndex == 0)
534 : {
535 2 : if (m_numBrushes >= m_numAllocatedBrushes)
536 : {
537 : // Realloc array by blocks of 20 items
538 2 : m_numAllocatedBrushes += 20;
539 : m_papsBrush = (TABBrushDef**)CPLRealloc(m_papsBrush,
540 2 : m_numAllocatedBrushes*sizeof(TABBrushDef*));
541 : }
542 : m_papsBrush[m_numBrushes]=(TABBrushDef*)CPLCalloc(1,
543 2 : sizeof(TABBrushDef));
544 :
545 2 : *m_papsBrush[m_numBrushes] = *poNewBrushDef;
546 2 : m_papsBrush[m_numBrushes]->nRefCount = 1;
547 2 : nNewBrushIndex = ++m_numBrushes;
548 : }
549 :
550 11 : return nNewBrushIndex;
551 : }
552 :
553 : /**********************************************************************
554 : * TABToolDefTable::GetNumFonts()
555 : *
556 : * Return the number of valid Font indexes for this .MAP file
557 : **********************************************************************/
558 4 : int TABToolDefTable::GetNumFonts()
559 : {
560 4 : return m_numFonts;
561 : }
562 :
563 : /**********************************************************************
564 : * TABToolDefTable::GetFontDefRef()
565 : *
566 : * Return a reference to the specified Font tool definition, or NULL if
567 : * specified index is invalid.
568 : *
569 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
570 : * in MapInfo.
571 : **********************************************************************/
572 0 : TABFontDef *TABToolDefTable::GetFontDefRef(int nIndex)
573 : {
574 0 : if (nIndex >0 && nIndex <= m_numFonts)
575 0 : return m_papsFont[nIndex-1];
576 :
577 0 : return NULL;
578 : }
579 :
580 : /**********************************************************************
581 : * TABToolDefTable::AddFontDefRef()
582 : *
583 : * Either create a new FontDefRef or add a reference to an existing one.
584 : *
585 : * Return the Font index that has been attributed to this Font tool
586 : * definition, or -1 if something went wrong
587 : *
588 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
589 : * in MapInfo.
590 : **********************************************************************/
591 0 : int TABToolDefTable::AddFontDefRef(TABFontDef *poNewFontDef)
592 : {
593 0 : int i, nNewFontIndex = 0;
594 : TABFontDef *poDef;
595 :
596 0 : if (poNewFontDef == NULL)
597 0 : return -1;
598 :
599 : /*-----------------------------------------------------------------
600 : * Start by searching the list of existing Fonts
601 : *----------------------------------------------------------------*/
602 0 : for (i=0; nNewFontIndex == 0 && i<m_numFonts; i++)
603 : {
604 0 : poDef = m_papsFont[i];
605 0 : if (EQUAL(poDef->szFontName, poNewFontDef->szFontName))
606 : {
607 0 : nNewFontIndex = i+1; // Fount it!
608 0 : poDef->nRefCount++;
609 : }
610 : }
611 :
612 : /*-----------------------------------------------------------------
613 : * OK, we did not find a match, then create a new entry
614 : *----------------------------------------------------------------*/
615 0 : if (nNewFontIndex == 0)
616 : {
617 0 : if (m_numFonts >= m_numAllocatedFonts)
618 : {
619 : // Realloc array by blocks of 20 items
620 0 : m_numAllocatedFonts += 20;
621 : m_papsFont = (TABFontDef**)CPLRealloc(m_papsFont,
622 0 : m_numAllocatedFonts*sizeof(TABFontDef*));
623 : }
624 : m_papsFont[m_numFonts]=(TABFontDef*)CPLCalloc(1,
625 0 : sizeof(TABFontDef));
626 :
627 0 : *m_papsFont[m_numFonts] = *poNewFontDef;
628 0 : m_papsFont[m_numFonts]->nRefCount = 1;
629 0 : nNewFontIndex = ++m_numFonts;
630 : }
631 :
632 0 : return nNewFontIndex;
633 : }
634 :
635 : /**********************************************************************
636 : * TABToolDefTable::GetNumSymbols()
637 : *
638 : * Return the number of valid Symbol indexes for this .MAP file
639 : **********************************************************************/
640 4 : int TABToolDefTable::GetNumSymbols()
641 : {
642 4 : return m_numSymbols;
643 : }
644 :
645 : /**********************************************************************
646 : * TABToolDefTable::GetSymbolDefRef()
647 : *
648 : * Return a reference to the specified Symbol tool definition, or NULL if
649 : * specified index is invalid.
650 : *
651 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
652 : * in MapInfo.
653 : **********************************************************************/
654 0 : TABSymbolDef *TABToolDefTable::GetSymbolDefRef(int nIndex)
655 : {
656 0 : if (nIndex >0 && nIndex <= m_numSymbols)
657 0 : return m_papsSymbol[nIndex-1];
658 :
659 0 : return NULL;
660 : }
661 :
662 :
663 : /**********************************************************************
664 : * TABToolDefTable::AddSymbolDefRef()
665 : *
666 : * Either create a new SymbolDefRef or add a reference to an existing one.
667 : *
668 : * Return the Symbol index that has been attributed to this Symbol tool
669 : * definition, or -1 if something went wrong
670 : *
671 : * Note that nIndex is a 1-based index. A value of 0 indicates "none"
672 : * in MapInfo.
673 : **********************************************************************/
674 0 : int TABToolDefTable::AddSymbolDefRef(TABSymbolDef *poNewSymbolDef)
675 : {
676 0 : int i, nNewSymbolIndex = 0;
677 : TABSymbolDef *poDef;
678 :
679 0 : if (poNewSymbolDef == NULL)
680 0 : return -1;
681 :
682 : /*-----------------------------------------------------------------
683 : * Start by searching the list of existing Symbols
684 : *----------------------------------------------------------------*/
685 0 : for (i=0; nNewSymbolIndex == 0 && i<m_numSymbols; i++)
686 : {
687 0 : poDef = m_papsSymbol[i];
688 0 : if (poDef->nSymbolNo == poNewSymbolDef->nSymbolNo &&
689 : poDef->nPointSize == poNewSymbolDef->nPointSize &&
690 : poDef->_nUnknownValue_ == poNewSymbolDef->_nUnknownValue_ &&
691 : poDef->rgbColor == poNewSymbolDef->rgbColor )
692 : {
693 0 : nNewSymbolIndex = i+1; // Fount it!
694 0 : poDef->nRefCount++;
695 : }
696 : }
697 :
698 : /*-----------------------------------------------------------------
699 : * OK, we did not find a match, then create a new entry
700 : *----------------------------------------------------------------*/
701 0 : if (nNewSymbolIndex == 0)
702 : {
703 0 : if (m_numSymbols >= m_numAllocatedSymbols)
704 : {
705 : // Realloc array by blocks of 20 items
706 0 : m_numAllocatedSymbols += 20;
707 : m_papsSymbol = (TABSymbolDef**)CPLRealloc(m_papsSymbol,
708 0 : m_numAllocatedSymbols*sizeof(TABSymbolDef*));
709 : }
710 : m_papsSymbol[m_numSymbols]=(TABSymbolDef*)CPLCalloc(1,
711 0 : sizeof(TABSymbolDef));
712 :
713 0 : *m_papsSymbol[m_numSymbols] = *poNewSymbolDef;
714 0 : m_papsSymbol[m_numSymbols]->nRefCount = 1;
715 0 : nNewSymbolIndex = ++m_numSymbols;
716 : }
717 :
718 0 : return nNewSymbolIndex;
719 : }
720 :
721 :
722 : /**********************************************************************
723 : * TABToolDefTable::GetMinVersionNumber()
724 : *
725 : * Returns the minimum file version number that can accept all the
726 : * tool objects currently defined.
727 : *
728 : * Default is 300, and currently 450 can be returned if file contains
729 : * pen widths defined in points.
730 : **********************************************************************/
731 2 : int TABToolDefTable::GetMinVersionNumber()
732 : {
733 2 : int i, nVersion = 300;
734 :
735 : /*-----------------------------------------------------------------
736 : * Scan Pen Defs
737 : *----------------------------------------------------------------*/
738 4 : for(i=0; i< m_numPen; i++)
739 : {
740 2 : if (m_papsPen[i]->nPointWidth > 0 )
741 : {
742 0 : nVersion = MAX(nVersion, 450); // Raise version to 450
743 : }
744 : }
745 :
746 2 : return nVersion;
747 : }
748 :
|