1 /
55
56 package org.apache.poi.hssf.record;
57
58 import org.apache.poi.util.LittleEndian;
59 import org.apache.poi.util.StringUtil;
60 import java.util.Stack;
61 import org.apache.poi.hssf.record.formula.Ptg;
62 import org.apache.poi.hssf.record.formula.Area3DPtg;
63 import org.apache.poi.hssf.record.formula.Ref3DPtg;
64 import java.util.List;
65 import org.apache.poi.hssf.util.RangeAddress;
66
67
74
75 public class NameRecord extends Record {
76
78 public final static short sid = 0x18;
79 private short field_1_option_flag;
80 private byte field_2_keyboard_shortcut;
81 private byte field_3_length_name_text;
82 private short field_4_length_name_definition;
83 private short field_5_index_to_sheet;
84 private short field_6_equals_to_index_to_sheet;
85 private byte field_7_length_custom_menu;
86 private byte field_8_length_description_text;
87 private byte field_9_length_help_topic_text;
88 private byte field_10_length_status_bar_text;
89 private byte field_11_compressed_unicode_flag;
90 private String field_12_name_text;
91 private Stack field_13_name_definition;
92 private byte[] field_13_raw_name_definition = null;
93 private String field_14_custom_menu_text;
94 private String field_15_description_text;
95 private String field_16_help_topic_text;
96 private String field_17_status_bar_text;
97
98
99 public NameRecord() {
100 field_13_name_definition = new Stack();
101
102 field_12_name_text = new String();
103 field_14_custom_menu_text = new String();
104 field_15_description_text = new String();
105 field_16_help_topic_text = new String();
106 field_17_status_bar_text = new String();
107 }
108
109
116 public NameRecord(short id, short size, byte [] data) {
117 super(id, size, data);
118 }
119
120
128 public NameRecord(short id, short size, byte [] data, int offset) {
129 super(id, size, data, offset);
130 }
131
132
135 public void setOptionFlag(short flag){
136 field_1_option_flag = flag;
137 }
138
139
142 public void setKeyboardShortcut(byte shortcut){
143 field_2_keyboard_shortcut = shortcut;
144 }
145
146
149 public void setNameTextLength(byte length){
150 field_3_length_name_text = length;
151 }
152
153
156 public void setDefinitionTextLength(short length){
157 field_4_length_name_definition = length;
158 }
159
160
164 public void setIndexToSheet(short index){
165 field_5_index_to_sheet = index;
166
167
168 field_6_equals_to_index_to_sheet = index;
169 }
170
171
174 public void setCustomMenuLength(byte length){
175 field_7_length_custom_menu = length;
176 }
177
178
181 public void setDescriptionTextLength(byte length){
182 field_8_length_description_text = length;
183 }
184
185
188 public void setHelpTopicLength(byte length){
189 field_9_length_help_topic_text = length;
190 }
191
192
195 public void setStatusBarLength(byte length){
196 field_10_length_status_bar_text = length;
197 }
198
199
202 public void setCompressedUnicodeFlag(byte flag) {
203 field_11_compressed_unicode_flag = flag;
204 }
205
206
209 public void setNameText(String name){
210 field_12_name_text = name;
211 }
212
213
214
215
216
217
220 public void setCustomMenuText(String text){
221 field_14_custom_menu_text = text;
222 }
223
224
227 public void setDescriptionText(String text){
228 field_15_description_text = text;
229 }
230
231
234 public void setHelpTopicText(String text){
235 field_16_help_topic_text = text;
236 }
237
238
241 public void setStatusBarText(String text){
242 field_17_status_bar_text = text;
243 }
244
245
248 public short getOptionFlag(){
249 return field_1_option_flag;
250 }
251
252
255 public byte getKeyboardShortcut(){
256 return field_2_keyboard_shortcut ;
257 }
258
259
262 public byte getNameTextLength(){
263 return field_3_length_name_text;
264 }
265
266
269 public short getDefinitionTextLength(){
270 return field_4_length_name_definition;
271 }
272
273
276 public short getIndexToSheet(){
277 return field_5_index_to_sheet;
278 }
279
280
283 public byte getCustomMenuLength(){
284 return field_7_length_custom_menu;
285 }
286
287
290 public byte getDescriptionTextLength(){
291 return field_8_length_description_text;
292 }
293
294
297 public byte getHelpTopicLength(){
298 return field_9_length_help_topic_text;
299 }
300
301
304 public byte getStatusBarLength(){
305 return field_10_length_status_bar_text;
306 }
307
308
311 public byte getCompressedUnicodeFlag() {
312 return field_11_compressed_unicode_flag;
313 }
314
315
318 public String getNameText(){
319 return field_12_name_text;
320 }
321
322
325 protected List getNameDefinition() {
326 return ( List ) field_13_name_definition;
327 }
328
329
332 public String getCustomMenuText(){
333 return field_14_custom_menu_text;
334 }
335
336
339 public String getDescriptionText(){
340 return field_15_description_text;
341 }
342
343
346 public String getHelpTopicText(){
347 return field_16_help_topic_text;
348 }
349
350
353 public String getStatusBarText(){
354 return field_17_status_bar_text;
355 }
356
357
363 protected void validateSid(short id) {
364 if (id != sid) {
365 throw new RecordFormatException("NOT A valid Name RECORD");
366 }
367 }
368
369
378 public int serialize(int offset, byte[] data) {
379 LittleEndian.putShort(data, 0 + offset, sid);
380 LittleEndian.putShort(data, 2 + offset, (short)( 15 + getTextsLength()));
381 LittleEndian.putShort(data, 4 + offset, getOptionFlag());
382 data[6 + offset] = getKeyboardShortcut();
383 data[7 + offset] = getNameTextLength();
384 LittleEndian.putShort(data, 8 + offset, getDefinitionTextLength());
385 LittleEndian.putShort(data, 10 + offset, getIndexToSheet());
386 LittleEndian.putShort(data, 12 + offset, getIndexToSheet());
387 data [14 + offset] = getCustomMenuLength();
388 data [15 + offset] = getDescriptionTextLength();
389 data [16 + offset] = getHelpTopicLength();
390 data [17 + offset] = getStatusBarLength();
391 data [18 + offset] = getCompressedUnicodeFlag();
392
393 StringUtil.putCompressedUnicode(getNameText(), data , 19 + offset);
394
395 int start_of_name_definition = 19 + field_3_length_name_text;
396 if (this.field_13_name_definition != null) {
397 serializePtgs(data, start_of_name_definition + offset);
398 } else {
399 System.arraycopy(field_13_raw_name_definition,0,data
400 ,start_of_name_definition + offset,field_13_raw_name_definition.length);
401 }
402
403 int start_of_custom_menu_text = start_of_name_definition + field_4_length_name_definition;
404 StringUtil.putCompressedUnicode(getCustomMenuText(), data , start_of_custom_menu_text + offset);
405
406 int start_of_description_text = start_of_custom_menu_text + field_8_length_description_text;
407 StringUtil.putCompressedUnicode(getDescriptionText(), data , start_of_description_text + offset);
408
409 int start_of_help_topic_text = start_of_description_text + field_9_length_help_topic_text;
410 StringUtil.putCompressedUnicode(getHelpTopicText(), data , start_of_help_topic_text + offset);
411
412 int start_of_status_bar_text = start_of_help_topic_text + field_10_length_status_bar_text;
413 StringUtil.putCompressedUnicode(getStatusBarText(), data , start_of_status_bar_text + offset);
414
415
416 return getRecordSize();
417 }
418
419 private void serializePtgs(byte [] data, int offset) {
420 int pos = offset;
421
422 for (int k = 0; k < field_13_name_definition.size(); k++) {
423 Ptg ptg = ( Ptg ) field_13_name_definition.get(k);
424
425 ptg.writeBytes(data, pos);
426 pos += ptg.getSize();
427 }
428 }
429
430
431
434 public int getTextsLength(){
435 int result;
436
437 result = getNameTextLength() + getDefinitionTextLength() + getDescriptionTextLength() +
438 getHelpTopicLength() + getStatusBarLength();
439
440
441 return result;
442 }
443
444
446 public int getRecordSize(){
447 int result;
448
449 result = 19 + getTextsLength();
450
451 return result;
452 }
453
454
457 public short getExternSheetNumber(){
458 if (field_13_name_definition == null) return 0;
459 Ptg ptg = (Ptg) field_13_name_definition.peek();
460 short result = 0;
461
462 if (ptg.getClass() == Area3DPtg.class){
463 result = ((Area3DPtg) ptg).getExternSheetIndex();
464
465 } else if (ptg.getClass() == Ref3DPtg.class){
466 result = ((Ref3DPtg) ptg).getExternSheetIndex();
467 }
468
469 return result;
470 }
471
472
475 public void setExternSheetNumber(short externSheetNumber){
476 Ptg ptg;
477
478 if (field_13_name_definition == null || field_13_name_definition.isEmpty()){
479 field_13_name_definition = new Stack();
480 ptg = createNewPtg();
481 } else {
482 ptg = (Ptg) field_13_name_definition.peek();
483 }
484
485 if (ptg.getClass() == Area3DPtg.class){
486 ((Area3DPtg) ptg).setExternSheetIndex(externSheetNumber);
487
488 } else if (ptg.getClass() == Ref3DPtg.class){
489 ((Ref3DPtg) ptg).setExternSheetIndex(externSheetNumber);
490 }
491
492 }
493
494 private Ptg createNewPtg(){
495 Ptg ptg = new Area3DPtg();
496 field_13_name_definition.push(ptg);
497
498 return ptg;
499 }
500
501
504 public String getAreaReference(){
505 if (field_13_name_definition == null) return "#REF!";
506 Ptg ptg = (Ptg) field_13_name_definition.peek();
507 String result = "";
508
509 if (ptg.getClass() == Area3DPtg.class){
510 result = ((Area3DPtg) ptg).getArea();
511
512 } else if (ptg.getClass() == Ref3DPtg.class){
513 result = ((Ref3DPtg) ptg).getArea();
514 }
515
516 return result;
517 }
518
519
522 public void setAreaReference(String ref){
523
524 RangeAddress ra = new RangeAddress(ref);
525 Ptg oldPtg;
526 Ptg ptg;
527
528 if (field_13_name_definition==null ||field_13_name_definition.isEmpty()){
529 field_13_name_definition = new Stack();
530 oldPtg = createNewPtg();
531 } else {
532
533 oldPtg = (Ptg) field_13_name_definition.pop();
534 }
535
536 short externSheetIndex = 0;
537
538 if (oldPtg.getClass() == Area3DPtg.class){
539 externSheetIndex = ((Area3DPtg) oldPtg).getExternSheetIndex();
540
541 } else if (oldPtg.getClass() == Ref3DPtg.class){
542 externSheetIndex = ((Ref3DPtg) oldPtg).getExternSheetIndex();
543 }
544
545 if (ra.hasRange()) {
546 ptg = new Area3DPtg();
547 ((Area3DPtg) ptg).setExternSheetIndex(externSheetIndex);
548 ((Area3DPtg) ptg).setArea(ref);
549 this.setDefinitionTextLength((short)((Area3DPtg) ptg).getSize());
550 } else {
551 ptg = new Ref3DPtg();
552 ((Ref3DPtg) ptg).setExternSheetIndex(externSheetIndex);
553 ((Ref3DPtg) ptg).setArea(ref);
554 this.setDefinitionTextLength((short)((Ref3DPtg) ptg).getSize());
555 }
556
557 field_13_name_definition.push(ptg);
558
559 }
560
561
569 protected void fillFields(byte[] data, short size, int offset) {
570 field_1_option_flag = LittleEndian.getShort(data, 0 + offset);
571 field_2_keyboard_shortcut = data [2 + offset];
572 field_3_length_name_text = data [3 + offset];
573 field_4_length_name_definition = LittleEndian.getShort(data, 4 + offset);
574 field_5_index_to_sheet = LittleEndian.getShort(data, 6 + offset);
575 field_6_equals_to_index_to_sheet= LittleEndian.getShort(data, 8 + offset);
576 field_7_length_custom_menu = data [10 + offset];
577 field_8_length_description_text = data [11 + offset];
578 field_9_length_help_topic_text = data [12 + offset];
579 field_10_length_status_bar_text = data [13 + offset];
580
581 field_11_compressed_unicode_flag= data [14 + offset];
582 field_12_name_text = new String(data, 15 + offset,
583 LittleEndian.ubyteToInt(field_3_length_name_text));
584
585 int start_of_name_definition = 15 + field_3_length_name_text;
586 field_13_name_definition = getParsedExpressionTokens(data, field_4_length_name_definition,
587 offset, start_of_name_definition);
588
589 int start_of_custom_menu_text = start_of_name_definition + field_4_length_name_definition;
590 field_14_custom_menu_text = new String(data, start_of_custom_menu_text + offset,
591 LittleEndian.ubyteToInt(field_7_length_custom_menu));
592
593 int start_of_description_text = start_of_custom_menu_text + field_8_length_description_text;
594 field_15_description_text = new String(data, start_of_description_text + offset,
595 LittleEndian.ubyteToInt(field_8_length_description_text));
596
597 int start_of_help_topic_text = start_of_description_text + field_9_length_help_topic_text;
598 field_16_help_topic_text = new String(data, start_of_help_topic_text + offset,
599 LittleEndian.ubyteToInt(field_9_length_help_topic_text));
600
601 int start_of_status_bar_text = start_of_help_topic_text + field_10_length_status_bar_text;
602 field_17_status_bar_text = new String(data, start_of_status_bar_text + offset,
603 LittleEndian.ubyteToInt(field_10_length_status_bar_text));
604
605 }
606
607 private Stack getParsedExpressionTokens(byte [] data, short size,
608 int offset, int start_of_expression) {
609 Stack stack = new Stack();
610 int pos = start_of_expression + offset;
611 int sizeCounter = 0;
612 try {
613 while (sizeCounter < size) {
614 Ptg ptg = Ptg.createPtg(data, pos);
615
616 pos += ptg.getSize();
617 sizeCounter += ptg.getSize();
618 stack.push(ptg);
619 }
620 } catch (java.lang.UnsupportedOperationException uoe) {
621 System.err.println("[WARNING] Unknown Ptg "
622 + uoe.getMessage() );
623 field_13_raw_name_definition=new byte[size];
624 System.arraycopy(data,offset,field_13_raw_name_definition,0,size);
625 return null;
626 }
627 return stack;
628 }
629
630
631
634 public short getSid() {
635 return this.sid;
636 }
637
638 }
639