mirror of https://github.com/apache/poi.git
Bugzilla 53025: Updatad documentation and example on data validations
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1340042 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
ea50937abc
commit
a91a13bb2a
|
@ -68,10 +68,11 @@
|
|||
<li><link href="#CellComments">How to set cell comments</link></li>
|
||||
<li><link href="#Autofit">How to adjust column width to fit the contents</link></li>
|
||||
<li><link href="#Hyperlinks">Hyperlinks</link></li>
|
||||
<li><link href="#Validation">Data Validation</link></li>
|
||||
<li><link href="#Validation">Data Validations</link></li>
|
||||
<li><link href="#Embedded">Embedded Objects</link></li>
|
||||
<li><link href="#Autofilter">Autofilters</link></li>
|
||||
<li><link href="#ConditionalFormatting">Conditional Formatting</link></li>
|
||||
<li><link href="#Hiding">Hiding and Un-Hiding Rows</link></li>
|
||||
</ul>
|
||||
</section>
|
||||
<section><title>Features</title>
|
||||
|
@ -1486,40 +1487,45 @@ Examples:
|
|||
</section>
|
||||
<anchor id="Validation"/>
|
||||
<section><title>Data Validations</title>
|
||||
<p><strong>Check the value a user enters into a cell against one or more predefined value(s).</strong></p>
|
||||
<p>The following code will limit the value the user can enter into cell A1 to one of three integer values, 10, 20 or 30.</p>
|
||||
<p>
|
||||
As of version 3.8, POI has slightly different syntax to work with data validations with .xls and .xlsx formats.
|
||||
</p>
|
||||
<section>
|
||||
<title>hssf.usermodel (binary .xls format)</title>
|
||||
<p><strong>Check the value a user enters into a cell against one or more predefined value(s).</strong></p>
|
||||
<p>The following code will limit the value the user can enter into cell A1 to one of three integer values, 10, 20 or 30.</p>
|
||||
<source>
|
||||
Workbook workbook = new HSSFWorkbook();
|
||||
Sheet sheet = workbook.createSheet("Data Validation");
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(
|
||||
0, 0, 0, 0);
|
||||
DVConstraint dvConstraint = DVConstraint.createExplicitListConstraint(
|
||||
new String[]{"10", "20", "30"});
|
||||
DataValidation dataValidation = new HSSFDataValidation
|
||||
(addressList, dvConstraint);
|
||||
dataValidation.setSuppressDropDownArrow(true);
|
||||
sheet.addValidationData(dataValidation);
|
||||
HSSFWorkbook workbook = new HSSFWorkbook();
|
||||
HSSFSheet sheet = workbook.createSheet("Data Validation");
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(
|
||||
0, 0, 0, 0);
|
||||
DVConstraint dvConstraint = DVConstraint.createExplicitListConstraint(
|
||||
new String[]{"10", "20", "30"});
|
||||
DataValidation dataValidation = new HSSFDataValidation
|
||||
(addressList, dvConstraint);
|
||||
dataValidation.setSuppressDropDownArrow(true);
|
||||
sheet.addValidationData(dataValidation);
|
||||
</source>
|
||||
<p><strong> Drop Down Lists:</strong></p>
|
||||
<p>This code will do the same but offer the user a drop down list to select a value from.</p>
|
||||
<source>
|
||||
Workbook workbook = new HSSFWorkbook();
|
||||
Sheet sheet = workbook.createSheet("Data Validation");
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(
|
||||
0, 0, 0, 0);
|
||||
DVConstraint dvConstraint = DVConstraint.createExplicitListConstraint(
|
||||
new String[]{"10", "20", "30"});
|
||||
DataValidation dataValidation = new HSSFDataValidation
|
||||
(addressList, dvConstraint);
|
||||
dataValidation.setSuppressDropDownArrow(false);
|
||||
sheet.addValidationData(dataValidation);
|
||||
HSSFWorkbook workbook = new HSSFWorkbook();
|
||||
HSSFSheet sheet = workbook.createSheet("Data Validation");
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(
|
||||
0, 0, 0, 0);
|
||||
DVConstraint dvConstraint = DVConstraint.createExplicitListConstraint(
|
||||
new String[]{"10", "20", "30"});
|
||||
DataValidation dataValidation = new HSSFDataValidation
|
||||
(addressList, dvConstraint);
|
||||
dataValidation.setSuppressDropDownArrow(false);
|
||||
sheet.addValidationData(dataValidation);
|
||||
</source>
|
||||
<p><strong>Messages On Error:</strong></p>
|
||||
<p>To create a message box that will be shown to the user if the value they enter is invalid.</p>
|
||||
<source>
|
||||
dataValidation.setErrorStyle(DataValidation.ErrorStyle.STOP);
|
||||
dataValidation.createErrorBox("Box Title", "Message Text");
|
||||
</source>
|
||||
</source>
|
||||
<p>Replace 'Box Title' with the text you wish to display in the message box's title bar
|
||||
and 'Message Text' with the text of your error message.</p>
|
||||
<p><strong>Prompts:</strong></p>
|
||||
|
@ -1531,6 +1537,7 @@ Examples:
|
|||
<p>The text encapsulated in the first parameter passed to the createPromptBox() method will appear emboldened
|
||||
and as a title to the prompt whilst the second will be displayed as the text of the message.
|
||||
The createExplicitListConstraint() method can be passed and array of String(s) containing interger, floating point, dates or text values.</p>
|
||||
|
||||
<p><strong>Further Data Validations:</strong></p>
|
||||
<p>To obtain a validation that would check the value entered was, for example, an integer between 10 and 100,
|
||||
use the DVConstraint.createNumericConstraint(int, int, String, String) factory method.</p>
|
||||
|
@ -1550,7 +1557,6 @@ Examples:
|
|||
the setSuppressDropDownArrow(false) method call will simply be ignored.</p>
|
||||
<p>Date and time constraints can be created by calling the createDateConstraint(int, String, String, String)
|
||||
or the createTimeConstraint(int, String, String). Both are very similar to the above and are explained in the javadoc. </p>
|
||||
|
||||
<p><strong>Creating Data Validations From Spreadsheet Cells.</strong></p>
|
||||
<p>The contents of specific cells can be used to provide the values for the data validation
|
||||
and the DVConstraint.createFormulaListConstraint(String) method supports this.
|
||||
|
@ -1587,6 +1593,281 @@ Examples:
|
|||
</source><p>and nor will this:</p><source>
|
||||
dvConstraint = DVConstraint.createFormulaListConstraint("'Sheet1'!$A$1:$A$3");
|
||||
</source>
|
||||
</section>
|
||||
<section>
|
||||
<title>xssf.usermodel (.xlsx format)</title>
|
||||
<p>
|
||||
Data validations work similarly when you are creating an xml based, SpreadsheetML,
|
||||
workbook file; but there are differences. Explicit casts are required, for example,
|
||||
in a few places as much of the support for data validations in the xssf stream was
|
||||
built into the unifying ss stream, of which more later. Other differences are
|
||||
noted with comments in the code.
|
||||
</p>
|
||||
|
||||
<p><strong>Check the value the user enters into a cell against one or more predefined value(s).</strong></p>
|
||||
<source>
|
||||
XSSFWorkbook workbook = new XSSFWorkbook();
|
||||
XSSFSheet sheet = workbook.createSheet("Data Validation");
|
||||
XSSFDataValidationHelper dvHelper = new XSSFDataValidationHelper(sheet);
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createExplicitListConstraint(new String[]{"11", "21", "31"});
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
XSSFDataValidation validation =(XSSFDataValidation)dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
|
||||
// Here the boolean value false is passed to the setSuppressDropDownArrow()
|
||||
// method. In the hssf.usermodel examples above, the value passed to this
|
||||
// method is true.
|
||||
validation.setSuppressDropDownArrow(false);
|
||||
|
||||
// Note this extra method call. If this method call is omitted, or if the
|
||||
// boolean value false is passed, then Excel will not validate the value the
|
||||
// user enters into the cell.
|
||||
validation.setShowErrorBox(true);
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
|
||||
<p><strong>Drop Down Lists:</strong></p>
|
||||
<p>This code will do the same but offer the user a drop down list to select a value from.</p>
|
||||
<source>
|
||||
XSSFWorkbook workbook = new XSSFWorkbook();
|
||||
XSSFSheet sheet = workbook.createSheet("Data Validation");
|
||||
XSSFDataValidationHelper dvHelper = new XSSFDataValidationHelper(sheet);
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createExplicitListConstraint(new String[]{"11", "21", "31"});
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
XSSFDataValidation validation = (XSSFDataValidation)dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
validation.setShowErrorBox(true);
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
<p>Note that the call to the setSuppressDropDowmArrow() method can either be simply excluded or replaced with:</p>
|
||||
<source>
|
||||
validation.setSuppressDropDownArrow(true);
|
||||
</source>
|
||||
|
||||
<p><strong>Prompts and Error Messages:</strong></p>
|
||||
<p>
|
||||
These both exactly mirror the hssf.usermodel so please refer to the 'Messages On Error:' and 'Prompts:' sections above.
|
||||
</p>
|
||||
|
||||
<p><strong>Further Data Validations:</strong></p>
|
||||
<p>
|
||||
To obtain a validation that would check the value entered was, for example,
|
||||
an integer between 10 and 100, use the XSSFDataValidationHelper(s) createNumericConstraint(int, int, String, String) factory method.
|
||||
</p>
|
||||
<source>
|
||||
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createNumericConstraint(
|
||||
XSSFDataValidationConstraint.ValidationType.INTEGER,
|
||||
XSSFDataValidationConstraint.OperatorType.BETWEEN,
|
||||
"10", "100");
|
||||
</source>
|
||||
<p>
|
||||
The values passed to the final two String parameters can be formulas; the '=' symbol is used to denote a formula.
|
||||
Thus, the following would create a validation the allows values only if they fall between the results of summing two cell ranges
|
||||
</p>
|
||||
<source>
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createNumericConstraint(
|
||||
XSSFDataValidationConstraint.ValidationType.INTEGER,
|
||||
XSSFDataValidationConstraint.OperatorType.BETWEEN,
|
||||
"=SUM(A1:A10)", "=SUM(B24:B27)");
|
||||
</source>
|
||||
<p>
|
||||
It is not possible to create a drop down list if the createNumericConstraint() method is called,
|
||||
the setSuppressDropDownArrow(true) method call will simply be ignored.
|
||||
</p>
|
||||
<p>
|
||||
Please check the javadoc for other constraint types as examples for those will not be included here.
|
||||
There are, for example, methods defined on the XSSFDataValidationHelper class allowing you to create
|
||||
the following types of constraint; date, time, decimal, integer, numeric, formula, text length and custom constraints.
|
||||
</p>
|
||||
<p><strong>Creating Data Validations From Spread Sheet Cells:</strong></p>
|
||||
<p>
|
||||
One other type of constraint not mentioned above is the formula list constraint.
|
||||
It allows you to create a validation that takes it value(s) from a range of cells. This code
|
||||
</p>
|
||||
<source>
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createFormulaListConstraint("$A$1:$F$1");
|
||||
</source>
|
||||
|
||||
<p>
|
||||
would create a validation that took it's values from cells in the range A1 to F1.
|
||||
</p>
|
||||
<p>
|
||||
The usefulness of this technique can be extended if you use named ranges like this;
|
||||
</p>
|
||||
|
||||
<source>
|
||||
XSSFName name = workbook.createName();
|
||||
name.setNameName("data");
|
||||
name.setRefersToFormula("$B$1:$F$1");
|
||||
XSSFDataValidationHelper dvHelper = new XSSFDataValidationHelper(sheet);
|
||||
XSSFDataValidationConstraint dvConstraint = (XSSFDataValidationConstraint)
|
||||
dvHelper.createFormulaListConstraint("data");
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(
|
||||
0, 0, 0, 0);
|
||||
XSSFDataValidation validation = (XSSFDataValidation)
|
||||
dvHelper.createValidation(dvConstraint, addressList);
|
||||
validation.setSuppressDropDownArrow(true);
|
||||
validation.setShowErrorBox(true);
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
<p>
|
||||
OpenOffice Calc has slightly different rules with regard to the scope of names.
|
||||
Excel supports both Workbook and Sheet scope for a name but Calc does not, it seems only to support Sheet scope for a name.
|
||||
Thus it is often best to fully qualify the name for the region or area something like this;
|
||||
</p>
|
||||
<source>
|
||||
XSSFName name = workbook.createName();
|
||||
name.setNameName("data");
|
||||
name.setRefersToFormula("'Data Validation'!$B$1:$F$1");
|
||||
....
|
||||
</source>
|
||||
<p>
|
||||
This does open a further, interesting opportunity however and that is to place all of the data for the validation(s) into named ranges of cells on a hidden sheet within the workbook. These ranges can then be explicitly identified in the setRefersToFormula() method argument.
|
||||
</p>
|
||||
</section>
|
||||
<section><title>ss.usermodel</title>
|
||||
<p>
|
||||
The classes within the ss.usermodel package allow developers to create code that can be used
|
||||
to generate both binary (.xls) and SpreadsheetML (.xlsx) workbooks.
|
||||
</p>
|
||||
<p>
|
||||
The techniques used to create data validations share much in common with the xssf.usermodel examples above.
|
||||
As a result just one or two examples will be presented here.
|
||||
</p>
|
||||
<p><strong>Check the value the user enters into a cell against one or more predefined value(s).</strong></p>
|
||||
<source>
|
||||
Workbook workbook = new XSSFWorkbook(); // or new HSSFWorkbook
|
||||
Sheet sheet = workbook.createSheet("Data Validation");
|
||||
DataValidationHelper dvHelper = sheet.getDataValidationHelper();
|
||||
DataValidationConstraint dvConstraint = dvHelper.createExplicitListConstraint(
|
||||
new String[]{"13", "23", "33"});
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
DataValidation validation = dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
// Note the check on the actual type of the DataValidation object.
|
||||
// If it is an instance of the XSSFDataValidation class then the
|
||||
// boolean value 'false' must be passed to the setSuppressDropDownArrow()
|
||||
// method and an explicit call made to the setShowErrorBox() method.
|
||||
if(validation instanceof XSSFDataValidation) {
|
||||
validation.setSuppressDropDownArrow(false);
|
||||
validation.setShowErrorBox(true);
|
||||
}
|
||||
else {
|
||||
// If the Datavalidation contains an instance of the HSSFDataValidation
|
||||
// class then 'true' should be passed to the setSuppressDropDownArrow()
|
||||
// method and the call to setShowErrorBox() is not necessary.
|
||||
validation.setSuppressDropDownArrow(true);
|
||||
}
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
|
||||
<p><strong>Drop Down Lists:</strong></p>
|
||||
|
||||
<p>This code will do the same but offer the user a drop down list to select a value from.</p>
|
||||
|
||||
<source>
|
||||
Workbook workbook = new XSSFWorkbook(); // or new HSSFWorkbook
|
||||
Sheet sheet = workbook.createSheet("Data Validation");
|
||||
DataValidationHelper dvHelper = sheet.getDataValidationHelper();
|
||||
DataValidationConstraint dvConstraint = dvHelper.createExplicitListConstraint(
|
||||
new String[]{"13", "23", "33"});
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
DataValidation validation = dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
// Note the check on the actual type of the DataValidation object.
|
||||
// If it is an instance of the XSSFDataValidation class then the
|
||||
// boolean value 'false' must be passed to the setSuppressDropDownArrow()
|
||||
// method and an explicit call made to the setShowErrorBox() method.
|
||||
if(validation instanceof XSSFDataValidation) {
|
||||
validation.setSuppressDropDownArrow(true);
|
||||
validation.setShowErrorBox(true);
|
||||
}
|
||||
else {
|
||||
// If the Datavalidation contains an instance of the HSSFDataValidation
|
||||
// class then 'true' should be passed to the setSuppressDropDownArrow()
|
||||
// method and the call to setShowErrorBox() is not necessary.
|
||||
validation.setSuppressDropDownArrow(false);
|
||||
}
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
|
||||
<p><strong>Prompts and Error Messages:</strong></p>
|
||||
<p>
|
||||
These both exactly mirror the hssf.usermodel so please refer to the 'Messages On Error:' and 'Prompts:' sections above.
|
||||
</p>
|
||||
<p>
|
||||
As the differences between the ss.usermodel and xssf.usermodel examples are small -
|
||||
restricted largely to the way the DataValidationHelper is obtained, the lack of any
|
||||
need to explicitly cast data types and the small difference in behaviour between
|
||||
the hssf and xssf interpretation of the setSuppressDropDowmArrow() method,
|
||||
no further examples will be included in this section.
|
||||
</p>
|
||||
<p><strong>Advanced Data Validations.</strong></p>
|
||||
<p><strong>Dependent Drop Down Lists.</strong></p>
|
||||
<p>
|
||||
In some cases, it may be necessary to present to the user a sheet which contains more than one drop down list.
|
||||
Further, the choice the user makes in one drop down list may affect the options that are presented to them in
|
||||
the second or subsequent drop down lists. One technique that may be used to implement this behaviour will now be explained.
|
||||
</p>
|
||||
<p>
|
||||
There are two keys to the technique; one is to use named areas or regions of cells to hold the data for the drop down lists,
|
||||
the second is to use the INDIRECT() function to convert between the name and the actual addresses of the cells.
|
||||
In the example section there is a complete working example- called LinkedDropDownLists.java -
|
||||
that demonstrates how to create linked or dependent drop down lists. Only the more relevant points are explained here.
|
||||
</p>
|
||||
<p>
|
||||
To create two drop down lists where the options shown in the second depend upon the selection made in the first,
|
||||
begin by creating a named region of cells to hold all of the data for populating the first drop down list.
|
||||
Next, create a data validation that will look to this named area for its data, something like this;
|
||||
</p>
|
||||
<source>
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
DataValidationHelper dvHelper = sheet.getDataValidationHelper();
|
||||
DataValidationConstraint dvConstraint = dvHelper.createFormulaListConstraint(
|
||||
"CHOICES");
|
||||
DataValidation validation = dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
<p>
|
||||
Note that the name of the area - in the example above it is 'CHOICES' -
|
||||
is simply passed to the createFormulaListConstraint() method. This is sufficient
|
||||
to cause Excel to populate the drop down list with data from that named region.
|
||||
</p>
|
||||
<p>
|
||||
Next, for each of the options the user could select in the first drop down list,
|
||||
create a matching named region of cells. The name of that region should match the
|
||||
text the user could select in the first drop down list. Note, in the example,
|
||||
all upper case letters are used in the names of the regions of cells.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
Now, very similar code can be used to create a second, linked, drop down list;
|
||||
</p>
|
||||
|
||||
<source>
|
||||
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, 1, 1);
|
||||
DataValidationConstraint dvConstraint = dvHelper.createFormulaListConstraint(
|
||||
"INDIRECT(UPPER($A$1))");
|
||||
DataValidation validation = dvHelper.createValidation(
|
||||
dvConstraint, addressList);
|
||||
sheet.addValidationData(validation);
|
||||
</source>
|
||||
|
||||
<p>
|
||||
The key here is in the following Excel function - INDIRECT(UPPER($A$1)) - which is used to populate the second,
|
||||
linked, drop down list. Working from the inner-most pair of brackets, it instructs Excel to look
|
||||
at the contents of cell A1, to convert what it reads there into upper case – as upper case letters are used
|
||||
in the names of each region - and then convert this name into the addresses of those cells that contain
|
||||
the data to populate another drop down list.
|
||||
</p>
|
||||
</section>
|
||||
</section>
|
||||
<anchor id="Embedded"/>
|
||||
<section><title>Embedded Objects</title>
|
||||
|
@ -1715,5 +1996,52 @@ Examples:
|
|||
</p>
|
||||
|
||||
</section>
|
||||
<anchor id="Hiding"/>
|
||||
<section><title>Hiding and Un-Hiding Rows</title>
|
||||
<p>
|
||||
Using Excel, it is possible to hide a row on a worksheet by selecting that row (or rows),
|
||||
right clicking once on the right hand mouse button and selecting 'Hide' from the pop=up menu that appears.
|
||||
</p>
|
||||
<p>
|
||||
To emulate this using POI, simply call the setZeroHeight() method on an instance of either
|
||||
XSSFRow or HSSFRow (the method is defined on the ss.usermodel.Row interface that both classes implement), like this:
|
||||
</p>
|
||||
<source>
|
||||
Workbook workbook = new XSSFWorkbook(); // OR new HSSFWorkbook()
|
||||
Sheet sheet = workbook.createSheet(0);
|
||||
Row row = workbook.createRow(0);
|
||||
row.setZeroHeight();
|
||||
</source>
|
||||
<p>
|
||||
If the file were saved away to disc now, then the first row on the first sheet would not be visible.
|
||||
</p>
|
||||
<p>
|
||||
Using Excel, it is possible to unhide previously hidden rows by selecting the row above and the row below
|
||||
the one that is hidden and then pressing and holding down the Ctrl key, the Shift and the pressing
|
||||
the number 9 before releasing them all.
|
||||
</p>
|
||||
<p>
|
||||
To emulate this behaviour using POI do something like this:
|
||||
</p>
|
||||
<source>
|
||||
Workbook workbook = WorkbookFactory.create(new File(.......));
|
||||
Sheet = workbook.getSheetAt(0);
|
||||
Iterator<Row> row Iter = sheet.iterator();
|
||||
while(rowIter.hasNext()) {
|
||||
Row row = rowIter.next();
|
||||
if(row.getZeroHeight()) {
|
||||
row.setZeroHeight(false);
|
||||
}
|
||||
}
|
||||
</source>
|
||||
<p>
|
||||
If the file were saved away to disc now, any previously hidden rows on the first sheet of the workbook would now be visible.
|
||||
</p>
|
||||
<p>
|
||||
The example illustrates two features. Firstly, that it is possible to unhide a row simply by calling the setZeroHeight()
|
||||
method and passing the boolean value 'false'. Secondly, it ilustrates how to test whther a row is hidden or not.
|
||||
Simply call the getZeroHeight() method and it will return 'true' if the row is hidden, 'false' otherwise.
|
||||
</p>
|
||||
</section>
|
||||
</body>
|
||||
</document>
|
||||
|
|
|
@ -34,6 +34,8 @@
|
|||
|
||||
<changes>
|
||||
<release version="3.9-beta1" date="2012-??-??">
|
||||
<action dev="poi-developers" type="add">53025 - Updatad documentation and example on using Data Validations </action>
|
||||
<action dev="poi-developers" type="add">53227 - Corrected AddDimensionedImage.java to support XSSF/SXSSF </action>
|
||||
<action dev="poi-developers" type="add">53058 - Utility for representing drawings contained in a binary Excel file as a XML tree</action>
|
||||
<action dev="poi-developers" type="add">53165 - HWPF support for fetching the description (alt text) of a picture</action>
|
||||
<action dev="poi-developers" type="fix">48528 - support negative arguments to the DATE() function</action>
|
||||
|
|
|
@ -0,0 +1,228 @@
|
|||
/* ====================================================================
|
||||
Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
contributor license agreements. See the NOTICE file distributed with
|
||||
this work for additional information regarding copyright ownership.
|
||||
The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
(the "License"); you may not use this file except in compliance with
|
||||
the License. You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
==================================================================== */
|
||||
|
||||
package org.apache.poi.ss.examples;
|
||||
import java.io.*;
|
||||
import org.apache.poi.xssf.usermodel.*;
|
||||
import org.apache.poi.hssf.usermodel.*;
|
||||
import org.apache.poi.ss.usermodel.*;
|
||||
import org.apache.poi.ss.util.CellRangeAddressList;
|
||||
|
||||
/**
|
||||
* Demonstrates one technique that may be used to create linked or dependent
|
||||
* drop down lists. This refers to a situation in which the selection made
|
||||
* in one drop down list affects the options that are displayed in the second
|
||||
* or subsequent drop down list(s). In this example, the value the user selects
|
||||
* from the down list in cell A1 will affect the values displayed in the linked
|
||||
* drop down list in cell B1. For the sake of simplicity, the data for the drop
|
||||
* down lists is included on the same worksheet but this does not have to be the
|
||||
* case; the data could appear on a separate sheet. If this were done, then the
|
||||
* names for the regions would have to be different, they would have to include
|
||||
* the name of the sheet.
|
||||
*
|
||||
* There are two keys to this technique. The first is the use of named area or
|
||||
* regions of cells to hold the data for the drop down lists and the second is
|
||||
* making use of the INDIRECT() function to convert a name into the addresses
|
||||
* of the cells it refers to.
|
||||
*
|
||||
* Note that whilst this class builds just two linked drop down lists, there is
|
||||
* nothing to prevent more being created. Quite simply, use the value selected
|
||||
* by the user in one drop down list to determine what is shown in another and the
|
||||
* value selected in that drop down list to determine what is shown in a third,
|
||||
* and so on. Also, note that the data for the drop down lists is contained on
|
||||
* contained on the same sheet as the validations themselves. This is done simply
|
||||
* for simplicity and there is nothing to prevent a separate sheet being created
|
||||
* and used to hold the data. If this is done then problems may be encountered
|
||||
* if the sheet is opened with OpenOffice Calc. To prevent these problems, it is
|
||||
* better to include the name of the sheet when calling the setRefersToFormula()
|
||||
* method.
|
||||
*
|
||||
* @author Mark Beardsley [msb at apache.org]
|
||||
* @version 1.00 30th March 2012
|
||||
*/
|
||||
public class LinkedDropDownLists {
|
||||
|
||||
LinkedDropDownLists(String workbookName) {
|
||||
File file = null;
|
||||
FileOutputStream fos = null;
|
||||
Workbook workbook = null;
|
||||
Sheet sheet = null;
|
||||
DataValidationHelper dvHelper = null;
|
||||
DataValidationConstraint dvConstraint = null;
|
||||
DataValidation validation = null;
|
||||
CellRangeAddressList addressList = null;
|
||||
try {
|
||||
|
||||
// Using the ss.usermodel allows this class to support both binary
|
||||
// and xml based workbooks. The choice of which one to create is
|
||||
// made by checking the file extension.
|
||||
if (workbookName.endsWith(".xlsx")) {
|
||||
workbook = new XSSFWorkbook();
|
||||
} else {
|
||||
workbook = new HSSFWorkbook();
|
||||
}
|
||||
|
||||
// Build the sheet that will hold the data for the validations. This
|
||||
// must be done first as it will create names that are referenced
|
||||
// later.
|
||||
sheet = workbook.createSheet("Linked Validations");
|
||||
LinkedDropDownLists.buildDataSheet(sheet);
|
||||
|
||||
// Build the first data validation to occupy cell A1. Note
|
||||
// that it retrieves it's data from the named area or region called
|
||||
// CHOICES. Further information about this can be found in the
|
||||
// static buildDataSheet() method below.
|
||||
addressList = new CellRangeAddressList(0, 0, 0, 0);
|
||||
dvHelper = sheet.getDataValidationHelper();
|
||||
dvConstraint = dvHelper.createFormulaListConstraint("CHOICES");
|
||||
validation = dvHelper.createValidation(dvConstraint, addressList);
|
||||
sheet.addValidationData(validation);
|
||||
|
||||
// Now, build the linked or dependent drop down list that will
|
||||
// occupy cell B1. The key to the whole process is the use of the
|
||||
// INDIRECT() function. In the buildDataSheet(0 method, a series of
|
||||
// named regions are created and the names of three of them mirror
|
||||
// the options available to the user in the first drop down list
|
||||
// (in cell A1). Using the INDIRECT() function makes it possible
|
||||
// to convert the selection the user makes in that first drop down
|
||||
// into the addresses of a named region of cells and then to use
|
||||
// those cells to populate the second drop down list.
|
||||
addressList = new CellRangeAddressList(0, 0, 1, 1);
|
||||
dvConstraint = dvHelper.createFormulaListConstraint(
|
||||
"INDIRECT(UPPER($A$1))");
|
||||
validation = dvHelper.createValidation(dvConstraint, addressList);
|
||||
sheet.addValidationData(validation);
|
||||
|
||||
file = new File(workbookName);
|
||||
fos = new FileOutputStream(file);
|
||||
workbook.write(fos);
|
||||
} catch (IOException ioEx) {
|
||||
System.out.println("Caught a: " + ioEx.getClass().getName());
|
||||
System.out.println("Message: " + ioEx.getMessage());
|
||||
System.out.println("Stacktrace follws:.....");
|
||||
ioEx.printStackTrace(System.out);
|
||||
} finally {
|
||||
try {
|
||||
if (fos != null) {
|
||||
fos.close();
|
||||
fos = null;
|
||||
}
|
||||
} catch (IOException ioEx) {
|
||||
System.out.println("Caught a: " + ioEx.getClass().getName());
|
||||
System.out.println("Message: " + ioEx.getMessage());
|
||||
System.out.println("Stacktrace follws:.....");
|
||||
ioEx.printStackTrace(System.out);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Called to populate the named areas/regions. The contents of the cells on
|
||||
* row one will be used to populate the first drop down list. The contents of
|
||||
* the cells on rows two, three and four will be used to populate the second
|
||||
* drop down list, just which row will be determined by the choice the user
|
||||
* makes in the first drop down list.
|
||||
*
|
||||
* In all cases, the approach is to create a row, create and populate cells
|
||||
* with data and then specify a name that identifies those cells. With the
|
||||
* exception of the first range, the names that are chosen for each range
|
||||
* of cells are quite important. In short, each of the options the user
|
||||
* could select in the first drop down list is used as the name for another
|
||||
* range of cells. Thus, in this example, the user can select either
|
||||
* 'Animal', 'Vegetable' or 'Mineral' in the first drop down and so the
|
||||
* sheet contains ranges named 'ANIMAL', 'VEGETABLE' and 'MINERAL'.
|
||||
*
|
||||
* @param dataSheet An instance of a class that implements the Sheet Sheet
|
||||
* interface (HSSFSheet or XSSFSheet).
|
||||
*/
|
||||
private static final void buildDataSheet(Sheet dataSheet) {
|
||||
Row row = null;
|
||||
Cell cell = null;
|
||||
Name name = null;
|
||||
|
||||
// The first row will hold the data for the first validation.
|
||||
row = dataSheet.createRow(10);
|
||||
cell = row.createCell(0);
|
||||
cell.setCellValue("Animal");
|
||||
cell = row.createCell(1);
|
||||
cell.setCellValue("Vegetable");
|
||||
cell = row.createCell(2);
|
||||
cell.setCellValue("Mineral");
|
||||
name = dataSheet.getWorkbook().createName();
|
||||
name.setRefersToFormula("$A$11:$C$11");
|
||||
name.setNameName("CHOICES");
|
||||
|
||||
// The next three rows will hold the data that will be used to
|
||||
// populate the second, or linked, drop down list.
|
||||
row = dataSheet.createRow(11);
|
||||
cell = row.createCell(0);
|
||||
cell.setCellValue("Lion");
|
||||
cell = row.createCell(1);
|
||||
cell.setCellValue("Tiger");
|
||||
cell = row.createCell(2);
|
||||
cell.setCellValue("Leopard");
|
||||
cell = row.createCell(3);
|
||||
cell.setCellValue("Elephant");
|
||||
cell = row.createCell(4);
|
||||
cell.setCellValue("Eagle");
|
||||
cell = row.createCell(5);
|
||||
cell.setCellValue("Horse");
|
||||
cell = row.createCell(6);
|
||||
cell.setCellValue("Zebra");
|
||||
name = dataSheet.getWorkbook().createName();
|
||||
name.setRefersToFormula("$A$12:$G$12");
|
||||
name.setNameName("ANIMAL");
|
||||
|
||||
row = dataSheet.createRow(12);
|
||||
cell = row.createCell(0);
|
||||
cell.setCellValue("Cabbage");
|
||||
cell = row.createCell(1);
|
||||
cell.setCellValue("Cauliflower");
|
||||
cell = row.createCell(2);
|
||||
cell.setCellValue("Potato");
|
||||
cell = row.createCell(3);
|
||||
cell.setCellValue("Onion");
|
||||
cell = row.createCell(4);
|
||||
cell.setCellValue("Beetroot");
|
||||
cell = row.createCell(5);
|
||||
cell.setCellValue("Asparagus");
|
||||
cell = row.createCell(6);
|
||||
cell.setCellValue("Spinach");
|
||||
cell = row.createCell(7);
|
||||
cell.setCellValue("Chard");
|
||||
name = dataSheet.getWorkbook().createName();
|
||||
name.setRefersToFormula("$A$13:$H$13");
|
||||
name.setNameName("VEGETABLE");
|
||||
|
||||
row = dataSheet.createRow(13);
|
||||
cell = row.createCell(0);
|
||||
cell.setCellValue("Bauxite");
|
||||
cell = row.createCell(1);
|
||||
cell.setCellValue("Quartz");
|
||||
cell = row.createCell(2);
|
||||
cell.setCellValue("Feldspar");
|
||||
cell = row.createCell(3);
|
||||
cell.setCellValue("Shist");
|
||||
cell = row.createCell(4);
|
||||
cell.setCellValue("Shale");
|
||||
cell = row.createCell(5);
|
||||
cell.setCellValue("Mica");
|
||||
name = dataSheet.getWorkbook().createName();
|
||||
name.setRefersToFormula("$A$14:$F$14");
|
||||
name.setNameName("MINERAL");
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue