Save This Page
Home » jexcelapi_2_6_8 » jxl.write.biff » [javadoc | source]
    1   /*********************************************************************
    2   *
    3   *      Copyright (C) 2001 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.write.biff;
   21   
   22   import common.Assert;
   23   import common.Logger;
   24   
   25   import jxl.Cell;
   26   import jxl.CellFeatures;
   27   import jxl.Sheet;
   28   import jxl.biff.DataValidation;
   29   import jxl.biff.DataValiditySettingsRecord;
   30   import jxl.biff.FormattingRecords;
   31   import jxl.biff.IntegerHelper;
   32   import jxl.biff.NumFormatRecordsException;
   33   import jxl.biff.Type;
   34   import jxl.biff.WritableRecordData;
   35   import jxl.biff.XFRecord;
   36   import jxl.biff.drawing.ComboBox;
   37   import jxl.biff.drawing.Comment;
   38   import jxl.format.CellFormat;
   39   import jxl.write.WritableCell;
   40   import jxl.write.WritableCellFeatures;
   41   import jxl.write.WritableWorkbook;
   42   
   43   /**
   44    * Abstract class which stores the common data used for cells, such
   45    * as row, column and formatting information.  
   46    * Any record which directly represents the contents of a cell, such
   47    * as labels and numbers, are derived from this class
   48    * data store
   49    */
   50   public abstract class CellValue extends WritableRecordData 
   51     implements WritableCell
   52   {
   53     /**
   54      * The logger
   55      */
   56     private static Logger logger = Logger.getLogger(CellValue.class);
   57     
   58     /**
   59      * The row in the worksheet at which this cell is located
   60      */
   61     private int row;
   62   
   63     /**
   64      * The column in the worksheet at which this cell is located
   65      */
   66     private int column;
   67   
   68     /**
   69      * The format applied to this cell
   70      */
   71     private XFRecord format;
   72     
   73     /**
   74      * A handle to the formatting records, used in case we want
   75      * to change the format of the cell once it has been added
   76      * to the spreadsheet
   77      */
   78     private FormattingRecords formattingRecords;
   79   
   80     /**
   81      * A flag to indicate that this record is already referenced within
   82      * a worksheet
   83      */
   84     private boolean referenced;
   85   
   86     /**
   87      * A handle to the sheet
   88      */
   89     private WritableSheetImpl sheet;
   90   
   91     /**
   92      * The cell features
   93      */
   94     private WritableCellFeatures features;
   95   
   96     /**
   97      * Internal copied flag, to prevent cell features being added multiple
   98      * times to the drawing array
   99      */
  100     private boolean copied;
  101   
  102     /**
  103      * Constructor used when building writable cells from the Java API
  104      * 
  105      * @param c the column
  106      * @param t the type indicator
  107      * @param r the row
  108      */
  109     protected CellValue(Type t, int c, int r)
  110     {
  111       this(t, c, r, WritableWorkbook.NORMAL_STYLE);
  112       copied = false;
  113     }
  114   
  115     /**
  116      * Constructor used when creating a writable cell from a read-only cell 
  117      * (when copying a workbook)
  118      * 
  119      * @param c the cell to clone
  120      * @param t the type of this cell
  121      */
  122     protected CellValue(Type t, Cell c)
  123     {
  124       this(t, c.getColumn(), c.getRow());
  125       copied = true;
  126   
  127       format = (XFRecord) c.getCellFormat();
  128       
  129       if (c.getCellFeatures() != null)
  130       {
  131         features = new WritableCellFeatures(c.getCellFeatures());
  132         features.setWritableCell(this);
  133       }
  134     }
  135   
  136     /**
  137      * Overloaded constructor used when building writable cells from the 
  138      * Java API which also takes a format
  139      * 
  140      * @param c the column
  141      * @param t the cell type
  142      * @param r the row
  143      * @param st the format to apply to this cell
  144      */
  145     protected CellValue(Type t, int c, int r, CellFormat st)
  146     {
  147       super(t);
  148       row    = r;
  149       column = c;
  150       format = (XFRecord) st;
  151       referenced = false;
  152       copied = false;
  153     }
  154   
  155     /**
  156      * Copy constructor 
  157      * 
  158      * @param c the column
  159      * @param t the cell type
  160      * @param r the row
  161      * @param cv the value to copy
  162      */
  163     protected CellValue(Type t, int c, int r, CellValue cv)
  164     {
  165       super(t);
  166       row    = r;
  167       column = c;
  168       format = cv.format;
  169       referenced = false;
  170       copied = false; // used during a deep copy, so the cell features need 
  171                       // to be added again
  172   
  173       if (cv.features != null)
  174       {
  175         features = new WritableCellFeatures(cv.features);
  176         features.setWritableCell(this);
  177       }
  178     }
  179   
  180     /**
  181      * An API function which sets the format to apply to this cell
  182      * 
  183      * @param cf the format to apply to this cell
  184      */
  185     public void setCellFormat(CellFormat cf)
  186     {
  187       format = (XFRecord) cf;
  188   
  189       // If the referenced flag has not been set, this cell has not
  190       // been added to the spreadsheet, so we don't need to perform
  191       // any further logic
  192       if (!referenced)
  193       {
  194         return;
  195       }
  196   
  197       // The cell has already been added to the spreadsheet, so the 
  198       // formattingRecords reference must be initialized
  199       Assert.verify(formattingRecords != null);
  200   
  201       addCellFormat();
  202     }
  203   
  204     /**
  205      * Returns the row number of this cell
  206      * 
  207      * @return the row number of this cell
  208      */
  209     public int getRow()
  210     {
  211       return row;
  212     }
  213   
  214     /**
  215      * Returns the column number of this cell
  216      * 
  217      * @return the column number of this cell
  218      */
  219     public int getColumn()
  220     {
  221       return column;
  222     }
  223   
  224     /**
  225      * Indicates whether or not this cell is hidden, by virtue of either
  226      * the entire row or column being collapsed
  227      *
  228      * @return TRUE if this cell is hidden, FALSE otherwise
  229      */
  230     public boolean isHidden()
  231     {
  232       ColumnInfoRecord cir = sheet.getColumnInfo(column);
  233       
  234       if (cir != null && cir.getWidth() == 0)
  235       {
  236         return true;
  237       }
  238   
  239       RowRecord rr = sheet.getRowInfo(row);
  240   
  241       if (rr != null && (rr.getRowHeight() == 0 || rr.isCollapsed()))
  242       {
  243         return true;
  244       }
  245   
  246       return false;
  247     }
  248   
  249     /**
  250      * Gets the data to write to the output file
  251      * 
  252      * @return the binary data
  253      */
  254     public byte[] getData()
  255     {
  256       byte[] mydata = new byte[6];
  257       IntegerHelper.getTwoBytes(row, mydata, 0);
  258       IntegerHelper.getTwoBytes(column, mydata, 2);
  259       IntegerHelper.getTwoBytes(format.getXFIndex(), mydata, 4);
  260       return mydata;
  261     }
  262   
  263     /**
  264      * Called when the cell is added to the worksheet in order to indicate
  265      * that this object is already added to the worksheet
  266      * This method also verifies that the associated formats and formats
  267      * have been initialized correctly
  268      * 
  269      * @param fr the formatting records
  270      * @param ss the shared strings used within the workbook
  271      * @param s the sheet this is being added to
  272      */
  273     void setCellDetails(FormattingRecords fr, SharedStrings ss, 
  274                         WritableSheetImpl s)
  275     {
  276       referenced = true;
  277       sheet = s;
  278       formattingRecords = fr;
  279   
  280       addCellFormat();
  281       addCellFeatures();
  282     }
  283   
  284     /**
  285      * Internal method to see if this cell is referenced within the workbook.
  286      * Once this has been placed in the workbook, it becomes immutable
  287      * 
  288      * @return TRUE if this cell has been added to a sheet, FALSE otherwise
  289      */
  290     final boolean isReferenced()
  291     {
  292       return referenced;
  293     }
  294   
  295     /**
  296      * Gets the internal index of the formatting record
  297      * 
  298      * @return the index of the format record
  299      */
  300     final int getXFIndex()
  301     {
  302       return format.getXFIndex();
  303     }
  304   
  305     /**
  306      * API method which gets the format applied to this cell
  307      * 
  308      * @return the format for this cell
  309      */
  310     public CellFormat getCellFormat()
  311     {
  312       return format;
  313     }
  314   
  315     /**
  316      * Increments the row of this cell by one.  Invoked by the sheet when 
  317      * inserting rows
  318      */
  319     void incrementRow()
  320     {
  321       row++;
  322   
  323       if (features != null)
  324       {
  325         Comment c = features.getCommentDrawing();
  326         if (c != null)
  327         {
  328           c.setX(column);
  329           c.setY(row);
  330         }
  331       }
  332     }
  333   
  334     /**
  335      * Decrements the row of this cell by one.  Invoked by the sheet when 
  336      * removing rows
  337      */
  338     void decrementRow()
  339     {
  340       row--;
  341   
  342       if (features != null)
  343       {
  344         Comment c = features.getCommentDrawing();
  345         if ( c!= null)
  346         {
  347           c.setX(column);
  348           c.setY(row);
  349         }
  350   
  351         if (features.hasDropDown())
  352         {
  353           logger.warn("need to change value for drop down drawing");
  354         }
  355       }
  356     }
  357   
  358     /**
  359      * Increments the column of this cell by one.  Invoked by the sheet when 
  360      * inserting columns
  361      */
  362     void incrementColumn()
  363     {
  364       column++;
  365   
  366       if (features != null)
  367       {
  368         Comment c = features.getCommentDrawing();
  369         if (c != null)
  370         {
  371           c.setX(column);
  372           c.setY(row);
  373         }
  374       }
  375   
  376     }
  377   
  378     /**
  379      * Decrements the column of this cell by one.  Invoked by the sheet when 
  380      * removing columns
  381      */
  382     void decrementColumn()
  383     {
  384       column--;
  385   
  386       if (features != null)
  387       {
  388         Comment c = features.getCommentDrawing();
  389         if (c != null)
  390         {
  391           c.setX(column);
  392           c.setY(row);
  393         }
  394       }
  395   
  396     }
  397   
  398     /**
  399      * Called when a column is inserted on the specified sheet.  Notifies all
  400      * RCIR cells of this change. The default implementation here does nothing
  401      *
  402      * @param s the sheet on which the column was inserted
  403      * @param sheetIndex the sheet index on which the column was inserted
  404      * @param col the column number which was inserted
  405      */
  406     void columnInserted(Sheet s, int sheetIndex, int col)
  407     {
  408     }
  409   
  410     /**
  411      * Called when a column is removed on the specified sheet.  Notifies all
  412      * RCIR cells of this change. The default implementation here does nothing
  413      *
  414      * @param s the sheet on which the column was inserted
  415      * @param sheetIndex the sheet index on which the column was inserted
  416      * @param col the column number which was inserted
  417      */
  418     void columnRemoved(Sheet s, int sheetIndex, int col)
  419     {
  420     }
  421   
  422     /**
  423      * Called when a row is inserted on the specified sheet.  Notifies all
  424      * RCIR cells of this change. The default implementation here does nothing
  425      *
  426      * @param s the sheet on which the column was inserted
  427      * @param sheetIndex the sheet index on which the column was inserted
  428      * @param row the column number which was inserted
  429      */
  430     void rowInserted(Sheet s, int sheetIndex, int row)
  431     {
  432     }
  433   
  434     /**
  435      * Called when a row is inserted on the specified sheet.  Notifies all
  436      * RCIR cells of this change. The default implementation here does nothing
  437      *
  438      * @param s the sheet on which the row was removed
  439      * @param sheetIndex the sheet index on which the column was removed
  440      * @param row the column number which was removed
  441      */
  442     void rowRemoved(Sheet s, int sheetIndex, int row)
  443     {
  444     }
  445   
  446     /**
  447      * Accessor for the sheet containing this cell
  448      *
  449      * @return the sheet containing this cell
  450      */
  451     protected WritableSheetImpl getSheet()
  452     {
  453       return sheet;
  454     }
  455   
  456     /**
  457      * Adds the format information to the shared records.  Performs the necessary
  458      * checks (and clones) to ensure that the formats are not shared.
  459      * Called from setCellDetails and setCellFormat
  460      */
  461     private void addCellFormat()
  462     {
  463       // Check to see if the format is one of the shared Workbook defaults.  If
  464       // so, then get hold of the Workbook's specific instance
  465       Styles styles = sheet.getWorkbook().getStyles();
  466       format = styles.getFormat(format);
  467   
  468       try
  469       {      
  470         if (!format.isInitialized())
  471         {
  472           formattingRecords.addStyle(format);
  473         }
  474       }
  475       catch (NumFormatRecordsException e)
  476       {
  477         logger.warn("Maximum number of format records exceeded.  Using " +
  478                     "default format.");
  479         format = styles.getNormalStyle();
  480       }
  481     }
  482   
  483     /**
  484      * Accessor for the cell features
  485      *
  486      * @return the cell features or NULL if this cell doesn't have any
  487      */
  488     public CellFeatures getCellFeatures()
  489     {
  490       return features;
  491     }
  492   
  493     /**
  494      * Accessor for the cell features
  495      *
  496      * @return the cell features or NULL if this cell doesn't have any
  497      */
  498     public WritableCellFeatures getWritableCellFeatures()
  499     {
  500       return features;
  501     }
  502   
  503     /**
  504      * Sets the cell features
  505      *
  506      * @param cf the cell features
  507      */
  508     public void setCellFeatures(WritableCellFeatures cf)
  509     {
  510       if (features != null) 
  511       {
  512         logger.warn("current cell features not null - overwriting");
  513       }
  514   
  515       features = cf;
  516       cf.setWritableCell(this);
  517   
  518       // If the cell is already on the worksheet, then add the cell features
  519       // to the workbook
  520       if (referenced)
  521       {
  522         addCellFeatures();
  523       }
  524     }
  525   
  526     /**
  527      * Handles any addition cell features, such as comments or data 
  528      * validation.  Called internally from this class when a cell is 
  529      * added to the workbook, and also externally from BaseCellFeatures
  530      * following a call to setComment
  531      */
  532     public final void addCellFeatures()
  533     {
  534       if (features == null)
  535       {
  536         return;
  537       }
  538   
  539       if (copied == true)
  540       {
  541         copied = false;
  542   
  543         /*
  544         if (features.hasDataValidation())
  545         {
  546           DataValidation dv = sheet.getDataValidation();
  547           DataValiditySettingsRecord dvsr = 
  548             dv.getDataValiditySettings(column, row);
  549           features.setValidationSettings(dvsr);
  550         }
  551         else
  552         {
  553           // For comments, make sure we go the whole nine yards when
  554           // the comment gets added to the sheet
  555           copied = false;
  556         }
  557         */
  558   
  559         return;
  560       }
  561   
  562       if (features.getComment() != null)
  563       {
  564         Comment comment = new Comment(features.getComment(), 
  565                                       column, row);
  566         comment.setWidth(features.getCommentWidth());
  567         comment.setHeight(features.getCommentHeight());
  568         sheet.addDrawing(comment);      
  569         sheet.getWorkbook().addDrawing(comment);
  570         features.setCommentDrawing(comment);
  571       }
  572   
  573       if (features.hasDataValidation())
  574       {
  575         try
  576         {
  577           features.getDVParser().setCell(column, 
  578                                          row, 
  579                                          sheet.getWorkbook(), 
  580                                          sheet.getWorkbook(),
  581                                          sheet.getWorkbookSettings());
  582         }
  583         catch (jxl.biff.formula.FormulaException e)
  584         {
  585           e.printStackTrace();
  586           Assert.verify(false);
  587         }
  588         sheet.addValidationCell(this);
  589         if (!features.hasDropDown())
  590         {
  591           return;
  592         }
  593         
  594         // Get the combo box drawing object for list validations
  595         if (sheet.getComboBox() == null)
  596         {
  597           ComboBox cb = new ComboBox();
  598           sheet.addDrawing(cb);
  599           sheet.getWorkbook().addDrawing(cb);
  600           sheet.setComboBox(cb);
  601         }
  602   
  603         features.setComboBox(sheet.getComboBox());
  604       }
  605     }
  606   
  607     /**
  608      * Removes the cell features from the Workbook/Worksheet.  Called when
  609      * a cell is being removed/replaced from a worksheet
  610      */
  611     public final void removeCellFeatures()
  612     {
  613       if (features == null)
  614       {
  615         return;
  616       }
  617   
  618       // Remove the comment
  619       features.removeComment();
  620   
  621       // Remove the data validation
  622       features.removeDataValidation();
  623     }
  624   
  625   
  626     /**
  627      * Called by the cell features to remove a comment
  628      *
  629      * @param c the comment to remove
  630      */
  631     public final void removeComment(Comment c)
  632     {
  633       sheet.removeDrawing(c);
  634     }
  635   
  636     /**
  637      * Called by the cell features to remove the data validation
  638      */
  639     public final void removeDataValidation()
  640     {
  641       sheet.removeDataValidation(this);
  642     }
  643   
  644     /**
  645      * Called when doing a copy of a writable object to indicate the source
  646      * was writable than a read only copy and certain things (most notably
  647      * the comments will need to be re-evaluated)
  648      *
  649      * @param boolean the copied flag
  650      */
  651     final void setCopied(boolean c)
  652     {
  653       copied = c;
  654     }
  655   
  656   }

Save This Page
Home » jexcelapi_2_6_8 » jxl.write.biff » [javadoc | source]