poi-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From n...@apache.org
Subject svn commit: r953395 - in /poi/trunk: src/documentation/content/xdocs/ src/java/org/apache/poi/hssf/dev/ src/java/org/apache/poi/hssf/model/ src/java/org/apache/poi/hssf/record/ src/java/org/apache/poi/hssf/record/formula/ src/java/org/apache/poi/hssf/u...
Date Thu, 10 Jun 2010 17:07:07 GMT
Author: nick
Date: Thu Jun 10 17:07:06 2010
New Revision: 953395

URL: http://svn.apache.org/viewvc?rev=953395&view=rev
Log:
Apply, with a few tweaks, the patch from bug #48996 - initial support for External Name References
in HSSF formula evaluation

Added:
    poi/trunk/src/testcases/org/apache/poi/hssf/record/formula/TestExternalNameReference.java
    poi/trunk/test-data/spreadsheet/XRefCalc.xls   (with props)
    poi/trunk/test-data/spreadsheet/XRefCalcData.xls   (with props)
Modified:
    poi/trunk/src/documentation/content/xdocs/status.xml
    poi/trunk/src/java/org/apache/poi/hssf/dev/BiffViewer.java
    poi/trunk/src/java/org/apache/poi/hssf/model/InternalWorkbook.java
    poi/trunk/src/java/org/apache/poi/hssf/model/LinkTable.java
    poi/trunk/src/java/org/apache/poi/hssf/record/ExternalNameRecord.java
    poi/trunk/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java
    poi/trunk/src/java/org/apache/poi/hssf/usermodel/HSSFEvaluationWorkbook.java
    poi/trunk/src/java/org/apache/poi/ss/formula/EvaluationWorkbook.java
    poi/trunk/src/java/org/apache/poi/ss/formula/OperationEvaluationContext.java
    poi/trunk/src/java/org/apache/poi/ss/formula/WorkbookEvaluator.java
    poi/trunk/src/java/org/apache/poi/ss/formula/eval/forked/ForkedEvaluationWorkbook.java
    poi/trunk/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFEvaluationWorkbook.java
    poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFFormulaEvaluator.java

Modified: poi/trunk/src/documentation/content/xdocs/status.xml
URL: http://svn.apache.org/viewvc/poi/trunk/src/documentation/content/xdocs/status.xml?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/documentation/content/xdocs/status.xml (original)
+++ poi/trunk/src/documentation/content/xdocs/status.xml Thu Jun 10 17:07:06 2010
@@ -34,6 +34,7 @@
 
     <changes>
         <release version="3.7-SNAPSHOT" date="2010-??-??">
+           <action dev="POI-DEVELOPERS" type="add">48996 - initial support for External
Name References in HSSF formula evaluation</action>
            <action dev="POI-DEVELOPERS" type="fix">46664 - fix up Tab IDs when adding
new sheets, so that print areas don't end up invalid</action>
            <action dev="POI-DEVELOPERS" type="fix">45269 - improve replaceText on HWPF
ranges</action>
            <action dev="POI-DEVELOPERS" type="fix">47815 - correct documentation on
what happens when you request a String from a non-string Formula cell</action>

Modified: poi/trunk/src/java/org/apache/poi/hssf/dev/BiffViewer.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/dev/BiffViewer.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/dev/BiffViewer.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/dev/BiffViewer.java Thu Jun 10 17:07:06 2010
@@ -162,6 +162,7 @@ public final class BiffViewer {
 			case ExtSSTRecord.sid:         return new ExtSSTRecord(in);
 			case ExtendedFormatRecord.sid: return new ExtendedFormatRecord(in);
 			case ExternSheetRecord.sid:    return new ExternSheetRecord(in);
+			case ExternalNameRecord.sid:   return new ExternalNameRecord(in);
 			case FeatRecord.sid:           return new FeatRecord(in);
 			case FeatHdrRecord.sid:        return new FeatHdrRecord(in);
 			case FilePassRecord.sid:       return new FilePassRecord(in);

Modified: poi/trunk/src/java/org/apache/poi/hssf/model/InternalWorkbook.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/model/InternalWorkbook.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/model/InternalWorkbook.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/model/InternalWorkbook.java Thu Jun 10 17:07:06
2010
@@ -81,6 +81,7 @@ import org.apache.poi.hssf.record.formul
 import org.apache.poi.hssf.record.formula.FormulaShifter;
 import org.apache.poi.hssf.record.formula.Ptg;
 import org.apache.poi.hssf.util.HSSFColor;
+import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName;
 import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalSheet;
 import org.apache.poi.util.Internal;
 import org.apache.poi.util.POILogFactory;
@@ -1771,6 +1772,14 @@ public final class InternalWorkbook {
         }
         return new ExternalSheet(extNames[0], extNames[1]);
     }
+    public ExternalName getExternalName(int externSheetIndex, int externNameIndex) {
+       String nameName = linkTable.resolveNameXText(externSheetIndex, externNameIndex);
+       if(nameName == null) {
+          return null;
+       }
+       int ix = linkTable.resolveNameXIx(externSheetIndex, externNameIndex);
+       return new ExternalName(nameName, externNameIndex, ix);
+    }
 
     /**
      * Finds the sheet index for a particular external sheet number.

Modified: poi/trunk/src/java/org/apache/poi/hssf/model/LinkTable.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/model/LinkTable.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/model/LinkTable.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/model/LinkTable.java Thu Jun 10 17:07:06 2010
@@ -124,6 +124,10 @@ final class LinkTable {
 		public String getNameText(int definedNameIndex) {
 			return _externalNameRecords[definedNameIndex].getText();
 		}
+		
+		public int getNameIx(int definedNameIndex) {
+		   return _externalNameRecords[definedNameIndex].getIx();
+		}
 
 		/**
 		 * Performs case-insensitive search
@@ -316,8 +320,12 @@ final class LinkTable {
 		if (!ebr.isExternalReferences()) {
 			return null;
 		}
+		// Sheet name only applies if not a global reference
 		int shIx = _externSheetRecord.getFirstSheetIndexFromRefIndex(extRefIndex);
-		String usSheetName = ebr.getSheetNames()[shIx];
+		String usSheetName = null;
+		if(shIx >= 0) {
+		   usSheetName = ebr.getSheetNames()[shIx];
+		}
 		return new String[] {
 				ebr.getURL(),
 				usSheetName,
@@ -419,6 +427,10 @@ final class LinkTable {
 		int extBookIndex = _externSheetRecord.getExtbookIndexFromRefIndex(refIndex);
 		return _externalBookBlocks[extBookIndex].getNameText(definedNameIndex);
 	}
+	public int resolveNameXIx(int refIndex, int definedNameIndex) {
+      int extBookIndex = _externSheetRecord.getExtbookIndexFromRefIndex(refIndex);
+      return _externalBookBlocks[extBookIndex].getNameIx(definedNameIndex);
+	}
 
 	public NameXPtg getNameXPtg(String name) {
 		// first find any external book block that contains the name:

Modified: poi/trunk/src/java/org/apache/poi/hssf/record/ExternalNameRecord.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/record/ExternalNameRecord.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/record/ExternalNameRecord.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/record/ExternalNameRecord.java Thu Jun 10 17:07:06
2010
@@ -41,7 +41,8 @@ public final class ExternalNameRecord ex
 
 
 	private short  field_1_option_flag;
-	private int  field_2_not_used;
+	private short  field_2_ixals;
+	private short  field_3_not_used;
 	private String field_4_name;
 	private Formula  field_5_name_definition;
 
@@ -96,6 +97,16 @@ public final class ExternalNameRecord ex
 	public String getText() {
 		return field_4_name;
 	}
+	
+	/**
+	 * If this is a local name, then this is the (1 based)
+	 *  index of the name of the Sheet this refers to, as
+	 *  defined in the preceeding {@link SupBookRecord}.
+	 * If it isn't a local name, then it must be zero.
+	 */
+	public short getIx() {
+	   return field_2_ixals;
+	}
 
 	protected int getDataSize(){
 		int result = 2 + 4;  // short and int
@@ -114,10 +125,11 @@ public final class ExternalNameRecord ex
 
 	public void serialize(LittleEndianOutput out) {
 		out.writeShort(field_1_option_flag);
-		out.writeInt(field_2_not_used);
+		out.writeShort(field_2_ixals);
+		out.writeShort(field_3_not_used);
 
-        out.writeByte(field_4_name.length());
-        StringUtil.writeUnicodeStringFlagAndData(out, field_4_name);
+		out.writeByte(field_4_name.length());
+		StringUtil.writeUnicodeStringFlagAndData(out, field_4_name);
 
         if(!isOLELink() && !isStdDocumentNameIdentifier()){
             if(isAutomaticLink()){
@@ -133,7 +145,8 @@ public final class ExternalNameRecord ex
 
 	public ExternalNameRecord(RecordInputStream in) {
 		field_1_option_flag = in.readShort();
-		field_2_not_used    = in.readInt();
+		field_2_ixals       = in.readShort();
+      field_3_not_used    = in.readShort();
 
         int numChars = in.readUByte();
         field_4_name = StringUtil.readUnicodeString(in, numChars);
@@ -166,10 +179,13 @@ public final class ExternalNameRecord ex
 
 	public String toString() {
 		StringBuffer sb = new StringBuffer();
-		sb.append(getClass().getName()).append(" [EXTERNALNAME ");
-		sb.append(" ").append(field_4_name);
-		sb.append(" ix=").append(field_2_not_used);
-		sb.append("]");
+		sb.append("[EXTERNALNAME]\n");
+		sb.append("    .ix      = ").append(field_2_ixals).append("\n");
+		sb.append("    .name    = ").append(field_4_name).append("\n");
+		if(field_5_name_definition != null) {
+		sb.append("    .formula = ").append(field_5_name_definition).append("\n");
+		}
+		sb.append("[/EXTERNALNAME]\n");
 		return sb.toString();
 	}
 }

Modified: poi/trunk/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java Thu Jun 10 17:07:06
2010
@@ -73,7 +73,13 @@ public final class NameXPtg extends Oper
 	public String toFormulaString() {
 		throw new RuntimeException("3D references need a workbook to determine formula text");
 	}
-
+	
+	public String toString(){
+	   String retValue = "NameXPtg:[sheetRefIndex:" + _sheetRefIndex + 
+	      " , nameNumber:" + _nameNumber + "]" ;
+	   return retValue;
+	}
+	
 	public byte getDefaultOperandClass() {
 		return Ptg.CLASS_VALUE;
 	}

Modified: poi/trunk/src/java/org/apache/poi/hssf/usermodel/HSSFEvaluationWorkbook.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/hssf/usermodel/HSSFEvaluationWorkbook.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/hssf/usermodel/HSSFEvaluationWorkbook.java (original)
+++ poi/trunk/src/java/org/apache/poi/hssf/usermodel/HSSFEvaluationWorkbook.java Thu Jun 10
17:07:06 2010
@@ -33,6 +33,7 @@ import org.apache.poi.ss.formula.Formula
 import org.apache.poi.ss.formula.FormulaParsingWorkbook;
 import org.apache.poi.ss.formula.FormulaRenderingWorkbook;
 import org.apache.poi.ss.formula.FormulaType;
+import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName;
 
 /**
  * Internal POI use only
@@ -107,6 +108,10 @@ public final class HSSFEvaluationWorkboo
 	public ExternalSheet getExternalSheet(int externSheetIndex) {
 		return _iBook.getExternalSheet(externSheetIndex);
 	}
+	
+	public ExternalName getExternalName(int externSheetIndex, int externNameIndex) {
+		return _iBook.getExternalName(externSheetIndex, externNameIndex);
+	}
 
 	public String resolveNameXText(NameXPtg n) {
 		return _iBook.resolveNameXText(n.getSheetRefIndex(), n.getNameIndex());

Modified: poi/trunk/src/java/org/apache/poi/ss/formula/EvaluationWorkbook.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/formula/EvaluationWorkbook.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/formula/EvaluationWorkbook.java (original)
+++ poi/trunk/src/java/org/apache/poi/ss/formula/EvaluationWorkbook.java Thu Jun 10 17:07:06
2010
@@ -47,6 +47,7 @@ public interface EvaluationWorkbook {
 	 */
 	ExternalSheet getExternalSheet(int externSheetIndex);
 	int convertFromExternSheetIndex(int externSheetIndex);
+	ExternalName getExternalName(int externSheetIndex, int externNameIndex);
 	EvaluationName getName(NamePtg namePtg);
 	String resolveNameXText(NameXPtg ptg);
 	Ptg[] getFormulaTokens(EvaluationCell cell);
@@ -66,4 +67,24 @@ public interface EvaluationWorkbook {
 			return _sheetName;
 		}
 	}
+	class ExternalName {
+		private final String _nameName;
+		private final int _nameNumber;
+		private final int _ix;
+
+		public ExternalName(String nameName, int nameNumber, int ix) {
+			_nameName = nameName;
+			_nameNumber = nameNumber;
+			_ix = ix;
+		}
+		public String getName() {
+			return _nameName;
+		}
+		public int getNumber() {
+			return _nameNumber;
+		}
+		public int getIx() {
+			return _ix;
+		}
+	}
 }

Modified: poi/trunk/src/java/org/apache/poi/ss/formula/OperationEvaluationContext.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/formula/OperationEvaluationContext.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/formula/OperationEvaluationContext.java (original)
+++ poi/trunk/src/java/org/apache/poi/ss/formula/OperationEvaluationContext.java Thu Jun 10
17:07:06 2010
@@ -17,10 +17,15 @@
 
 package org.apache.poi.ss.formula;
 
+import org.apache.poi.hssf.record.formula.Area3DPtg;
+import org.apache.poi.hssf.record.formula.NameXPtg;
+import org.apache.poi.hssf.record.formula.Ptg;
+import org.apache.poi.hssf.record.formula.Ref3DPtg;
 import org.apache.poi.hssf.record.formula.eval.*;
 import org.apache.poi.hssf.record.formula.functions.FreeRefFunction;
 import org.apache.poi.ss.SpreadsheetVersion;
 import org.apache.poi.ss.formula.CollaboratingWorkbooksEnvironment.WorkbookNotFoundException;
+import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName;
 import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalSheet;
 import org.apache.poi.ss.util.CellReference;
 import org.apache.poi.ss.util.CellReference.NameType;
@@ -254,4 +259,40 @@ public final class OperationEvaluationCo
 		SheetRefEvaluator sre = createExternSheetRefEvaluator(extSheetIndex);
 		return new LazyAreaEval(firstRowIndex, firstColumnIndex, lastRowIndex, lastColumnIndex,
sre);
 	}
+	public ValueEval getNameXEval(NameXPtg nameXPtg) {
+      ExternalSheet externSheet = _workbook.getExternalSheet(nameXPtg.getSheetRefIndex());
+      if(externSheet == null)
+         return new NameXEval(nameXPtg);
+      String workbookName = externSheet.getWorkbookName();
+      ExternalName externName = _workbook.getExternalName(
+            nameXPtg.getSheetRefIndex(), 
+            nameXPtg.getNameIndex()
+      );
+      try{
+         WorkbookEvaluator refWorkbookEvaluator = _bookEvaluator.getOtherWorkbookEvaluator(workbookName);
+         EvaluationName evaluationName = refWorkbookEvaluator.getName(externName.getName(),externName.getIx()-1);
+         if(evaluationName != null && evaluationName.hasFormula()){
+            if (evaluationName.getNameDefinition().length > 1) {
+               throw new RuntimeException("Complex name formulas not supported yet");
+            }
+            Ptg ptg = evaluationName.getNameDefinition()[0];
+            if(ptg instanceof Ref3DPtg){
+               Ref3DPtg ref3D = (Ref3DPtg)ptg;
+               int sheetIndex = refWorkbookEvaluator.getSheetIndexByExternIndex(ref3D.getExternSheetIndex());
+               String sheetName = refWorkbookEvaluator.getSheetName(sheetIndex);
+               SheetRefEvaluator sre = createExternSheetRefEvaluator(workbookName, sheetName);
+               return new LazyRefEval(ref3D.getRow(), ref3D.getColumn(), sre);
+            }else if(ptg instanceof Area3DPtg){
+               Area3DPtg area3D = (Area3DPtg)ptg;
+               int sheetIndex = refWorkbookEvaluator.getSheetIndexByExternIndex(area3D.getExternSheetIndex());
+               String sheetName = refWorkbookEvaluator.getSheetName(sheetIndex);
+               SheetRefEvaluator sre = createExternSheetRefEvaluator(workbookName, sheetName);
+               return new LazyAreaEval(area3D.getFirstRow(), area3D.getFirstColumn(), area3D.getLastRow(),
area3D.getLastColumn(), sre);
+            }
+         }
+         return ErrorEval.REF_INVALID;
+      }catch(WorkbookNotFoundException wnfe){
+         return ErrorEval.REF_INVALID;
+      }
+   }
 }

Modified: poi/trunk/src/java/org/apache/poi/ss/formula/WorkbookEvaluator.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/formula/WorkbookEvaluator.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/formula/WorkbookEvaluator.java (original)
+++ poi/trunk/src/java/org/apache/poi/ss/formula/WorkbookEvaluator.java Thu Jun 10 17:07:06
2010
@@ -65,6 +65,7 @@ import org.apache.poi.hssf.record.formul
 import org.apache.poi.hssf.record.formula.functions.FreeRefFunction;
 import org.apache.poi.hssf.record.formula.functions.IfFunc;
 import org.apache.poi.hssf.record.formula.udf.UDFFinder;
+import org.apache.poi.hssf.usermodel.HSSFEvaluationWorkbook;
 import org.apache.poi.hssf.util.CellReference;
 import org.apache.poi.ss.formula.CollaboratingWorkbooksEnvironment.WorkbookNotFoundException;
 import org.apache.poi.ss.formula.eval.NotImplementedException;
@@ -124,6 +125,19 @@ public final class WorkbookEvaluator {
 	/* package */ EvaluationSheet getSheet(int sheetIndex) {
 		return _workbook.getSheet(sheetIndex);
 	}
+	
+	/* package */ EvaluationName getName(String name, int sheetIndex) {
+		NamePtg namePtg = null;
+		if(_workbook instanceof HSSFEvaluationWorkbook){
+			namePtg =((HSSFEvaluationWorkbook)_workbook).getName(name, sheetIndex).createPtg();
+		}
+
+		if(namePtg == null) {
+			return null;
+		} else {
+			return _workbook.getName(namePtg);
+		}
+	}
 
 	private static boolean isDebugLogEnabled() {
 		return false;
@@ -223,6 +237,10 @@ public final class WorkbookEvaluator {
 		}
 		return result.intValue();
 	}
+	
+	/* package */ int getSheetIndexByExternIndex(int externSheetIndex) {
+	   return _workbook.convertFromExternSheetIndex(externSheetIndex);
+	}
 
 
 	/**
@@ -524,7 +542,7 @@ public final class WorkbookEvaluator {
 			throw new RuntimeException("Don't now how to evalate name '" + nameRecord.getNameText()
+ "'");
 		}
 		if (ptg instanceof NameXPtg) {
-			return new NameXEval(((NameXPtg) ptg));
+		   return ec.getNameXEval(((NameXPtg) ptg));
 		}
 
 		if (ptg instanceof IntPtg) {

Modified: poi/trunk/src/java/org/apache/poi/ss/formula/eval/forked/ForkedEvaluationWorkbook.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/formula/eval/forked/ForkedEvaluationWorkbook.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/formula/eval/forked/ForkedEvaluationWorkbook.java
(original)
+++ poi/trunk/src/java/org/apache/poi/ss/formula/eval/forked/ForkedEvaluationWorkbook.java
Thu Jun 10 17:07:06 2010
@@ -106,6 +106,10 @@ final class ForkedEvaluationWorkbook imp
 	public EvaluationSheet getSheet(int sheetIndex) {
 		return getSharedSheet(getSheetName(sheetIndex));
 	}
+	
+	public ExternalName getExternalName(int externSheetIndex, int externNameIndex) {
+	   return _masterBook.getExternalName(externSheetIndex, externNameIndex);
+	}
 
 	public int getSheetIndex(EvaluationSheet sheet) {
 		if (sheet instanceof ForkedEvaluationSheet) {

Modified: poi/trunk/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFEvaluationWorkbook.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFEvaluationWorkbook.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFEvaluationWorkbook.java (original)
+++ poi/trunk/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFEvaluationWorkbook.java Thu
Jun 10 17:07:06 2010
@@ -29,6 +29,7 @@ import org.apache.poi.ss.formula.Formula
 import org.apache.poi.ss.formula.FormulaParsingWorkbook;
 import org.apache.poi.ss.formula.FormulaRenderingWorkbook;
 import org.apache.poi.ss.formula.FormulaType;
+import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName;
 import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTDefinedName;
 
 /**
@@ -94,6 +95,10 @@ public final class XSSFEvaluationWorkboo
 	public String getSheetName(int sheetIndex) {
 		return _uBook.getSheetName(sheetIndex);
 	}
+	
+	public ExternalName getExternalName(int externSheetIndex, int externNameIndex) {
+	   throw new RuntimeException("Not implemented yet");
+	}
 
 	public NameXPtg getNameXPtg(String name) {
 		// may require to return null to make tests pass

Added: poi/trunk/src/testcases/org/apache/poi/hssf/record/formula/TestExternalNameReference.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/hssf/record/formula/TestExternalNameReference.java?rev=953395&view=auto
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/hssf/record/formula/TestExternalNameReference.java
(added)
+++ poi/trunk/src/testcases/org/apache/poi/hssf/record/formula/TestExternalNameReference.java
Thu Jun 10 17:07:06 2010
@@ -0,0 +1,106 @@
+/* ====================================================================
+   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.hssf.record.formula;
+
+
+import junit.framework.TestCase;
+
+import org.apache.poi.hssf.HSSFTestDataSamples;
+import org.apache.poi.hssf.usermodel.HSSFCell;
+import org.apache.poi.hssf.usermodel.HSSFFormulaEvaluator;
+import org.apache.poi.hssf.usermodel.HSSFWorkbook;
+import org.apache.poi.hssf.util.CellReference;
+/**
+ * Tests for proper calculation of named ranges from external workbooks.
+ * 
+ * 
+ * @author Stephen Wolke (smwolke at geistig.com)
+ */
+public final class TestExternalNameReference extends TestCase {
+	double MARKUP_COST = 1.9d;
+	double MARKUP_COST_1 = 1.8d;
+	double MARKUP_COST_2 = 1.5d;
+	double PART_COST = 12.3d;
+	double NEW_QUANT = 7.0d;
+	double NEW_PART_COST = 15.3d;
+	/**
+	 * tests <tt>NameXPtg for external cell reference by name</tt> and logic in
Workbook below that   
+	 */
+	public void testReadCalcSheet() {
+	    try{
+		HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("XRefCalc.xls");
+		assertEquals("Sheet1!$A$2", wb.getName("QUANT").getRefersToFormula());
+		assertEquals("Sheet1!$B$2", wb.getName("PART").getRefersToFormula());
+		assertEquals("x123",wb.getSheet("Sheet1").getRow(1).getCell(1).getStringCellValue());
+		assertEquals("Sheet1!$C$2", wb.getName("UNITCOST").getRefersToFormula());
+		CellReference cellRef = new CellReference(wb.getName("UNITCOST").getRefersToFormula());
+		HSSFCell cell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		assertEquals("VLOOKUP(PART,COSTS,2,FALSE)",cell.getCellFormula());
+		assertEquals("Sheet1!$D$2", wb.getName("COST").getRefersToFormula());
+		cellRef = new CellReference(wb.getName("COST").getRefersToFormula());
+		cell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		assertEquals("UNITCOST*Quant",cell.getCellFormula());
+		assertEquals("Sheet1!$E$2", wb.getName("TOTALCOST").getRefersToFormula());
+		cellRef = new CellReference(wb.getName("TOTALCOST").getRefersToFormula());
+		cell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		assertEquals("Cost*Markup_Cost",cell.getCellFormula());
+	    }catch(Exception e){
+		fail();
+	    }
+	}
+	
+	public void testReadReferencedSheet() {
+	    try{
+		HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("XRefCalcData.xls");
+		assertEquals("CostSheet!$A$2:$B$3", wb.getName("COSTS").getRefersToFormula());
+		assertEquals("x123",wb.getSheet("CostSheet").getRow(1).getCell(0).getStringCellValue());
+		assertEquals(PART_COST,wb.getSheet("CostSheet").getRow(1).getCell(1).getNumericCellValue());
+		assertEquals("MarkupSheet!$B$1", wb.getName("Markup_Cost").getRefersToFormula());
+		assertEquals(MARKUP_COST_1,wb.getSheet("MarkupSheet").getRow(0).getCell(1).getNumericCellValue());
+	    }catch(Exception e){
+		fail();
+	    }
+	}
+	
+	public void testEvaluate() throws Exception {
+		HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("XRefCalc.xls");
+		HSSFWorkbook wb2 = HSSFTestDataSamples.openSampleWorkbook("XRefCalcData.xls");
+		CellReference cellRef = new CellReference(wb.getName("QUANT").getRefersToFormula());
+		HSSFCell cell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		cell.setCellValue(NEW_QUANT);
+		cell = wb2.getSheet("CostSheet").getRow(1).getCell(1);
+		cell.setCellValue(NEW_PART_COST);
+		HSSFFormulaEvaluator evaluator = new HSSFFormulaEvaluator(wb);
+		HSSFFormulaEvaluator evaluatorCost = new HSSFFormulaEvaluator(wb2);
+		String[] bookNames = { "XRefCalc.xls", "XRefCalcData.xls" };
+		HSSFFormulaEvaluator[] evaluators = { evaluator, evaluatorCost, };
+		HSSFFormulaEvaluator.setupEnvironment(bookNames, evaluators);
+		cellRef = new CellReference(wb.getName("UNITCOST").getRefersToFormula());
+		HSSFCell uccell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		cellRef = new CellReference(wb.getName("COST").getRefersToFormula());
+		HSSFCell ccell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		cellRef = new CellReference(wb.getName("TOTALCOST").getRefersToFormula());
+		HSSFCell tccell = wb.getSheet(cellRef.getSheetName()).getRow(cellRef.getRow()).getCell((int)cellRef.getCol());
+		evaluator.evaluateFormulaCell(uccell);
+		evaluator.evaluateFormulaCell(ccell);
+		evaluator.evaluateFormulaCell(tccell);
+		assertEquals(NEW_PART_COST, uccell.getNumericCellValue());
+		assertEquals(NEW_PART_COST*NEW_QUANT, ccell.getNumericCellValue());
+		assertEquals(NEW_PART_COST*NEW_QUANT*MARKUP_COST_2, tccell.getNumericCellValue());
+	}
+}

Modified: poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFFormulaEvaluator.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFFormulaEvaluator.java?rev=953395&r1=953394&r2=953395&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFFormulaEvaluator.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFFormulaEvaluator.java Thu
Jun 10 17:07:06 2010
@@ -215,4 +215,65 @@ public final class TestHSSFFormulaEvalua
 		assertEquals(3, evalCount);
 		assertEquals(2.0, ((NumberEval)ve).getNumberValue(), 0D);
 	}
+	
+	/**
+	 * Ensures that we can handle NameXPtgs in the formulas
+	 *  we parse.
+	 */
+	public void testXRefs() throws Exception {
+      HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("XRefCalc.xls");
+      HSSFWorkbook wbData = HSSFTestDataSamples.openSampleWorkbook("XRefCalcData.xls");
+      Cell cell;
+      
+      // VLookup on a name in another file
+      cell = wb.getSheetAt(0).getRow(1).getCell(2);
+      assertEquals(Cell.CELL_TYPE_FORMULA, cell.getCellType());
+      assertEquals(Cell.CELL_TYPE_NUMERIC, cell.getCachedFormulaResultType());
+      assertEquals(12.30, cell.getNumericCellValue(), 0.0001);
+      // WARNING - this is wrong!
+      // The file name should be showing, but bug #45970 is fixed
+      //  we seem to loose it
+      assertEquals("VLOOKUP(PART,COSTS,2,FALSE)", cell.getCellFormula());
+      
+      
+      // Simple reference to a name in another file
+      cell = wb.getSheetAt(0).getRow(1).getCell(4);
+      assertEquals(Cell.CELL_TYPE_FORMULA, cell.getCellType());
+      assertEquals(Cell.CELL_TYPE_NUMERIC, cell.getCachedFormulaResultType());
+      assertEquals(36.90, cell.getNumericCellValue(), 0.0001);
+      // WARNING - this is wrong!
+      // The file name should be showing, but bug #45970 is fixed
+      //  we seem to loose it
+      assertEquals("Cost*Markup_Cost", cell.getCellFormula());
+      
+      
+      // Evaluate the cells
+      HSSFFormulaEvaluator eval = new HSSFFormulaEvaluator(wb);
+      HSSFFormulaEvaluator.setupEnvironment(
+            new String[] { "XRefCalc.xls", "XRefCalcData.xls" },
+            new HSSFFormulaEvaluator[] {
+                  eval,
+                  new HSSFFormulaEvaluator(wbData)
+            }
+      );
+      eval.evaluateFormulaCell(
+            wb.getSheetAt(0).getRow(1).getCell(2)
+      );      
+      eval.evaluateFormulaCell(
+            wb.getSheetAt(0).getRow(1).getCell(4)
+      );      
+      
+
+      // Re-check VLOOKUP one
+      cell = wb.getSheetAt(0).getRow(1).getCell(2);
+      assertEquals(Cell.CELL_TYPE_FORMULA, cell.getCellType());
+      assertEquals(Cell.CELL_TYPE_NUMERIC, cell.getCachedFormulaResultType());
+      assertEquals(12.30, cell.getNumericCellValue(), 0.0001);
+      
+      // Re-check ref one
+      cell = wb.getSheetAt(0).getRow(1).getCell(4);
+      assertEquals(Cell.CELL_TYPE_FORMULA, cell.getCellType());
+      assertEquals(Cell.CELL_TYPE_NUMERIC, cell.getCachedFormulaResultType());
+      assertEquals(36.90, cell.getNumericCellValue(), 0.0001);
+   }
 }

Added: poi/trunk/test-data/spreadsheet/XRefCalc.xls
URL: http://svn.apache.org/viewvc/poi/trunk/test-data/spreadsheet/XRefCalc.xls?rev=953395&view=auto
==============================================================================
Binary file - no diff available.

Propchange: poi/trunk/test-data/spreadsheet/XRefCalc.xls
------------------------------------------------------------------------------
    svn:mime-type = application/octet-stream

Added: poi/trunk/test-data/spreadsheet/XRefCalcData.xls
URL: http://svn.apache.org/viewvc/poi/trunk/test-data/spreadsheet/XRefCalcData.xls?rev=953395&view=auto
==============================================================================
Binary file - no diff available.

Propchange: poi/trunk/test-data/spreadsheet/XRefCalcData.xls
------------------------------------------------------------------------------
    svn:mime-type = application/octet-stream



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@poi.apache.org
For additional commands, e-mail: commits-help@poi.apache.org


Mime
View raw message