KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > jxl > biff > DVParser


1 /*********************************************************************
2 *
3 * Copyright (C) 2004 Andrew Khan
4 *
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later version.
9 *
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
14 *
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 ***************************************************************************/

19
20 package jxl.biff;
21
22 import common.Logger;
23 import jxl.WorkbookSettings;
24 import jxl.biff.formula.ExternalSheet;
25 import jxl.biff.formula.FormulaParser;
26 import jxl.biff.formula.FormulaException;
27
28 /**
29  * Class which parses the binary data associated with Data Validity (DV)
30  * setting
31  */

32 public class DVParser
33 {
34   /**
35    * The logger
36    */

37   private static Logger logger = Logger.getLogger(DVParser.class);
38
39   // DV Type
40
public static class DVType
41   {
42     private int value;
43     
44     private static DVType[] types = new DVType[0];
45    
46     DVType(int v)
47     {
48       value = v;
49       DVType[] oldtypes = types;
50       types = new DVType[oldtypes.length+1];
51       System.arraycopy(oldtypes, 0, types, 0, oldtypes.length);
52       types[oldtypes.length] = this;
53     }
54
55     static DVType getType(int v)
56     {
57       DVType found = null;
58       for (int i = 0 ; i < types.length && found == null ; i++)
59       {
60         if (types[i].value == v)
61         {
62           found = types[i];
63         }
64       }
65       return found;
66     }
67
68     public int getValue()
69     {
70       return value;
71     }
72   }
73
74   // Error Style
75
public static class ErrorStyle
76   {
77     private int value;
78     
79     private static ErrorStyle[] types = new ErrorStyle[0];
80    
81     ErrorStyle(int v)
82     {
83       value = v;
84       ErrorStyle[] oldtypes = types;
85       types = new ErrorStyle[oldtypes.length+1];
86       System.arraycopy(oldtypes, 0, types, 0, oldtypes.length);
87       types[oldtypes.length] = this;
88     }
89
90     static ErrorStyle getErrorStyle(int v)
91     {
92       ErrorStyle found = null;
93       for (int i = 0 ; i < types.length && found == null ; i++)
94       {
95         if (types[i].value == v)
96         {
97           found = types[i];
98         }
99       }
100       return found;
101     }
102
103     public int getValue()
104     {
105       return value;
106     }
107   }
108
109   // Conditions
110
public static class Condition
111   {
112     private int value;
113     
114     private static Condition[] types = new Condition[0];
115    
116     Condition(int v)
117     {
118       value = v;
119       Condition[] oldtypes = types;
120       types = new Condition[oldtypes.length+1];
121       System.arraycopy(oldtypes, 0, types, 0, oldtypes.length);
122       types[oldtypes.length] = this;
123     }
124
125     static Condition getCondition(int v)
126     {
127       Condition found = null;
128       for (int i = 0 ; i < types.length && found == null ; i++)
129       {
130         if (types[i].value == v)
131         {
132           found = types[i];
133         }
134       }
135       return found;
136     }
137
138     public int getValue()
139     {
140       return value;
141     }
142   }
143
144
145   // The values
146
public static final DVType ANY = new DVType(0);
147   public static final DVType INTEGER = new DVType(1);
148   public static final DVType DECIMAL = new DVType(2);
149   public static final DVType LIST = new DVType(3);
150   public static final DVType DATE = new DVType(4);
151   public static final DVType TIME = new DVType(5);
152   public static final DVType TEXT_LENGTH = new DVType(6);
153   public static final DVType FORMULA = new DVType(7);
154
155   // The error styles
156
public static final ErrorStyle STOP = new ErrorStyle(0);
157   public static final ErrorStyle WARNING = new ErrorStyle(1);
158   public static final ErrorStyle INFO = new ErrorStyle(2);
159
160   // The conditions
161
public static final Condition BETWEEN = new Condition(0);
162   public static final Condition NOT_BETWEEN = new Condition(1);
163   public static final Condition EQUAL = new Condition(2);
164   public static final Condition NOT_EQUAL = new Condition(3);
165   public static final Condition GREATER_THAN = new Condition(4);
166   public static final Condition LESS_THAN = new Condition(5);
167   public static final Condition GREATER_EQUAL = new Condition(6);
168   public static final Condition LESS_EQUAL = new Condition(7);
169
170   // The masks
171
private static int STRING_LIST_GIVEN_MASK = 0x80;
172   private static int EMPTY_CELLS_ALLOWED_MASK = 0x100;
173   private static int SUPPRESS_ARROW_MASK = 0x200;
174   private static int SHOW_PROMPT_MASK = 0x40000;
175   private static int SHOW_ERROR_MASK = 0x80000;
176
177   /**
178    * The type
179    */

180   private DVType type;
181
182   /**
183    * The error style
184    */

185   private ErrorStyle errorStyle;
186
187   /**
188    * The condition
189    */

190   private Condition condition;
191
192   /**
193    * String list option
194    */

195   private boolean stringListGiven;
196
197   /**
198    * Empty cells allowed
199    */

200   private boolean emptyCellsAllowed;
201
202   /**
203    * Suppress arrow
204    */

205   private boolean suppressArrow;
206
207   /**
208    * Show prompt
209    */

210   private boolean showPrompt;
211
212   /**
213    * Show error
214    */

215   private boolean showError;
216
217   /**
218    * The title of the prompt box
219    */

220   private String JavaDoc promptTitle;
221
222   /**
223    * The title of the error box
224    */

225   private String JavaDoc errorTitle;
226
227   /**
228    * The text of the prompt box
229    */

230   private String JavaDoc promptText;
231
232   /**
233    * The text of the error box
234    */

235   private String JavaDoc errorText;
236
237   /**
238    * The first formula
239    */

240   private FormulaParser formula1;
241
242   /**
243    * The second formula
244    */

245   private FormulaParser formula2;
246
247   /**
248    * The column number of the cell at the top left of the range
249    */

250   private int column1;
251
252   /**
253    * The row number of the cell at the top left of the range
254    */

255   private int row1;
256
257   /**
258    * The column index of the cell at the bottom right
259    */

260   private int column2;
261
262   /**
263    * The row index of the cell at the bottom right
264    */

265   private int row2;
266
267   /**
268    * Constructor
269    */

270   public DVParser(byte[] data,
271                   ExternalSheet es,
272                   WorkbookMethods nt,
273                   WorkbookSettings ws) throws FormulaException
274   {
275     int options = IntegerHelper.getInt(data[0], data[1], data[2], data[3]);
276     
277     int typeVal = options & 0xf;
278     type = DVType.getType(typeVal);
279
280     int errorStyleVal = (options & 0x70) >> 4;
281     errorStyle = ErrorStyle.getErrorStyle(errorStyleVal);
282
283     int conditionVal = (options & 0xf00000) >> 20;
284     condition = Condition.getCondition(conditionVal);
285
286     stringListGiven = (options & STRING_LIST_GIVEN_MASK) != 0;
287     emptyCellsAllowed = (options & EMPTY_CELLS_ALLOWED_MASK) != 0;
288     suppressArrow = (options & SUPPRESS_ARROW_MASK) != 0;
289     showPrompt = (options & SHOW_PROMPT_MASK) != 0;
290     showError = (options & SHOW_ERROR_MASK) != 0;
291
292     int pos = 4;
293     int length = IntegerHelper.getInt(data[pos], data[pos+1]);
294     promptTitle = StringHelper.getUnicodeString(data, length, pos + 2);
295     pos += length * 2 + 2;
296
297     length = IntegerHelper.getInt(data[pos], data[pos+1]);
298     errorTitle = StringHelper.getUnicodeString(data, length, pos + 2);
299     pos += length * 2 + 2;
300
301     length = IntegerHelper.getInt(data[pos], data[pos+1]);
302     promptText = StringHelper.getUnicodeString(data, length, pos + 2);
303     pos += length * 2 + 2;
304
305     length = IntegerHelper.getInt(data[pos], data[pos+1]);
306     errorText = StringHelper.getUnicodeString(data, length, pos + 2);
307     pos += length * 2 + 2;
308
309     int formulaLength = IntegerHelper.getInt(data[pos], data[pos+1]);
310     pos += 4;
311     if (formulaLength != 0)
312     {
313       byte[] tokens = new byte[formulaLength];
314       System.arraycopy(data, pos, tokens, 0, formulaLength);
315       formula1 = new FormulaParser(tokens, null, es, nt,ws);
316       formula1.parse();
317       pos += formulaLength;
318     }
319
320     formulaLength = IntegerHelper.getInt(data[pos], data[pos+1]);
321     pos += 4;
322     if (formulaLength != 0)
323     {
324       byte[] tokens = new byte[formulaLength];
325       System.arraycopy(data, pos, tokens, 0, formulaLength);
326       formula2 = new FormulaParser(tokens, null, es, nt, ws);
327       formula2.parse();
328       pos += formulaLength;
329     }
330
331     pos += 2;
332
333     row1 = IntegerHelper.getInt(data[pos], data[pos+1]);
334     pos += 2;
335
336     row2 = IntegerHelper.getInt(data[pos], data[pos+1]);
337     pos += 2;
338
339     column1 = IntegerHelper.getInt(data[pos], data[pos+1]);
340     pos += 2;
341
342     column2 = IntegerHelper.getInt(data[pos], data[pos+1]);
343     pos += 2;
344   }
345
346   /**
347    * Gets the data
348    */

349   public byte[] getData()
350   {
351     // Compute the length of the data
352
byte[] f1Bytes = formula1 != null ? formula1.getBytes() : new byte[0];
353     byte[] f2Bytes = formula2 != null ? formula2.getBytes() : new byte[0];
354     int dataLength =
355       4 + // the options
356
promptTitle.length() * 2 + 2 + // the prompt title
357
errorTitle.length() * 2 + 2 + // the error title
358
promptText.length() * 2 + 2 + // the prompt text
359
errorText.length() * 2 + 2 + // the error text
360
f1Bytes.length + 2 + // first formula
361
f2Bytes.length + 2 + // second formula
362
+ 4 + // unused bytes
363
10; // cell range
364

365     byte[] data = new byte[dataLength];
366
367     // The position
368
int pos = 0;
369
370     // The options
371
int options = 0;
372     options |= type.getValue();
373     options |= errorStyle.getValue() << 4;
374     options |= condition.getValue() << 20;
375
376     if (stringListGiven)
377     {
378       options |= STRING_LIST_GIVEN_MASK;
379     }
380
381     if (emptyCellsAllowed)
382     {
383       options |= EMPTY_CELLS_ALLOWED_MASK;
384     }
385
386     if (suppressArrow)
387     {
388       options |= SUPPRESS_ARROW_MASK;
389     }
390
391     if (showPrompt)
392     {
393       options |= SHOW_PROMPT_MASK;
394     }
395
396     if (showError)
397     {
398       options |= SHOW_ERROR_MASK;
399     }
400
401     // The text
402
IntegerHelper.getFourBytes(options, data, pos);
403     pos += 4;
404     
405     IntegerHelper.getTwoBytes(promptTitle.length(), data, pos);
406     pos += 2;
407
408     StringHelper.getUnicodeBytes(promptTitle, data, pos);
409     pos += promptTitle.length() * 2;
410
411     IntegerHelper.getTwoBytes(errorTitle.length(), data, pos);
412     pos += 2;
413
414     StringHelper.getUnicodeBytes(errorTitle, data, pos);
415     pos += errorTitle.length() * 2;
416
417     IntegerHelper.getTwoBytes(promptText.length(), data, pos);
418     pos += 2;
419
420     StringHelper.getUnicodeBytes(promptText, data, pos);
421     pos += promptText.length() * 2;
422
423     IntegerHelper.getTwoBytes(errorText.length(), data, pos);
424     pos += 2;
425
426     StringHelper.getUnicodeBytes(errorText, data, pos);
427     pos += errorText.length() * 2;
428
429     // Formula 1
430
IntegerHelper.getTwoBytes(f1Bytes.length, data, pos);
431     pos += 4;
432     
433     System.arraycopy(f1Bytes, 0, data, pos, f1Bytes.length);
434     pos += f1Bytes.length;
435
436     // Formula 2
437
IntegerHelper.getTwoBytes(f2Bytes.length, data, pos);
438     pos += 2;
439     
440     System.arraycopy(f2Bytes, 0, data, pos, f2Bytes.length);
441     pos += f2Bytes.length;
442
443     // Two bytes not used
444
pos +=2 ;
445
446     // The cell ranges
447
IntegerHelper.getTwoBytes(1, data, pos);
448     pos += 2;
449
450     IntegerHelper.getTwoBytes(row1, data, pos);
451     pos += 2;
452
453     IntegerHelper.getTwoBytes(row2, data, pos);
454     pos += 2;
455
456     IntegerHelper.getTwoBytes(column1, data, pos);
457     pos += 2;
458
459     IntegerHelper.getTwoBytes(column2, data, pos);
460     pos += 2;
461
462     return data;
463   }
464
465   /**
466    * Inserts a row
467    *
468    * @param row the row to insert
469    */

470   public void insertRow(int row)
471   {
472     if (formula1 != null)
473     {
474       formula1.rowInserted(0, row, true);
475     }
476
477     if (formula2 != null)
478     {
479       formula2.rowInserted(0, row, true);
480     }
481
482     if (row1 >= row)
483     {
484       row1++;
485     }
486
487     if (row2 >= row)
488     {
489       row2++;
490     }
491   }
492
493   /**
494    * Inserts a column
495    *
496    * @param col the column to insert
497    */

498   public void insertColumn(int col)
499   {
500     if (formula1 != null)
501     {
502       formula1.columnInserted(0, col, true);
503     }
504
505     if (formula2 != null)
506     {
507       formula2.columnInserted(0, col, true);
508     }
509
510     if (column1 >= col)
511     {
512       column1++;
513     }
514
515     if (column2 >= col)
516     {
517       column2++;
518     }
519   }
520
521   /**
522    * Removes a row
523    *
524    * @param row the row to insert
525    */

526   public void removeRow(int row)
527   {
528     if (formula1 != null)
529     {
530       formula1.rowRemoved(0, row, true);
531     }
532
533     if (formula2 != null)
534     {
535       formula2.rowRemoved(0, row, true);
536     }
537
538     if (row1 > row)
539     {
540       row1--;
541     }
542
543     if (row2 >= row)
544     {
545       row2--;
546     }
547   }
548
549   /**
550    * Removes a column
551    *
552    * @param col the row to remove
553    */

554   public void removeColumn(int col)
555   {
556     if (formula1 != null)
557     {
558       formula1.columnRemoved(0, col, true);
559     }
560
561     if (formula2 != null)
562     {
563       formula2.columnRemoved(0, col, true);
564     }
565
566     if (column1 > col)
567     {
568       column1--;
569     }
570
571     if (column2 >= col)
572     {
573       column2--;
574     }
575   }
576
577   /**
578    * Accessor for first column
579    *
580    * @return the first column
581    */

582   public int getFirstColumn()
583   {
584     return column1;
585   }
586
587   /**
588    * Accessor for the last column
589    *
590    * @return the last column
591    */

592   public int getLastColumn()
593   {
594     return column2;
595   }
596
597   /**
598    * Accessor for first row
599    *
600    * @return the first row
601    */

602   public int getFirstRow()
603   {
604     return row1;
605   }
606
607   /**
608    * Accessor for the last row
609    *
610    * @return the last row
611    */

612   public int getLastRow()
613   {
614     return row2;
615   }
616
617 }
618
Popular Tags