KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > poi > hssf > contrib > view > SVFractionalFormat


1
2 /* ====================================================================
3    Copyright 2002-2004 Apache Software Foundation
4
5    Licensed under the Apache License, Version 2.0 (the "License");
6    you may not use this file except in compliance with the License.
7    You may obtain a copy of the License at
8
9        http://www.apache.org/licenses/LICENSE-2.0
10
11    Unless required by applicable law or agreed to in writing, software
12    distributed under the License is distributed on an "AS IS" BASIS,
13    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14    See the License for the specific language governing permissions and
15    limitations under the License.
16 ==================================================================== */

17         
18
19 package org.apache.poi.hssf.contrib.view;
20
21 import java.text.*;
22
23 /**
24  * This class is used to format cells into their fractional format.
25  *
26  * I cant be 100% sure that the same fractional value will be displayed as in
27  * excel but then again it is a lossy formating mode anyway
28  *
29  * @author Jason Height
30  * @since 15 July 2002
31  */

32 public class SVFractionalFormat extends Format {
33   private short ONE_DIGIT = 1;
34   private short TWO_DIGIT = 2;
35   private short THREE_DIGIT = 3;
36   private short UNITS = 4;
37   private int units = 1;
38   private short mode = -1;
39
40   /** Constructs a new FractionalFormatter
41    *
42    * The formatStr defines how the number will be formatted
43    * # ?/? Up to one digit
44    * # ??/?? Up to two digits
45    * # ???/??? Up to three digits
46    * # ?/2 In halves
47    * # ?/4 In quarters
48    * # ?/8 In eighths
49    * # ?/16 In sixteenths
50    * # ?/10 In tenths
51    * # ?/100 In hundredths
52    */

53   public SVFractionalFormat(String JavaDoc formatStr) {
54     if ("# ?/?".equals(formatStr))
55       mode = ONE_DIGIT;
56     else if ("# ??/??".equals(formatStr))
57       mode = TWO_DIGIT;
58     else if ("# ???/???".equals(formatStr))
59       mode = THREE_DIGIT;
60     else if ("# ?/2".equals(formatStr)) {
61       mode = UNITS;
62       units = 2;
63     } else if ("# ?/4".equals(formatStr)) {
64       mode = UNITS;
65       units = 4;
66     } else if ("# ?/8".equals(formatStr)) {
67       mode = UNITS;
68       units = 8;
69     } else if ("# ?/16".equals(formatStr)) {
70       mode = UNITS;
71       units = 16;
72     } else if ("# ?/10".equals(formatStr)) {
73       mode = UNITS;
74       units = 10;
75     } else if ("# ?/100".equals(formatStr)) {
76       mode = UNITS;
77       units = 100;
78     }
79   }
80
81   /**
82    * Returns a fractional string representation of a double to a maximum denominator size
83    *
84    * This code has been translated to java from the following web page.
85    * http://www.codeproject.com/cpp/fraction.asp
86    * Originally coded in c++ By Dean Wyant dwyant@mindspring.com
87    * The code on the web page is freely available.
88    *
89    * @param f Description of the Parameter
90    * @param MaxDen Description of the Parameter
91    * @return Description of the Return Value
92    */

93   private String JavaDoc format(final double f, final int MaxDen) {
94     long Whole = (long)f;
95     int sign = 1;
96     if (f < 0) {
97       sign = -1;
98     }
99     double Precision = 0.00001;
100     double AllowedError = Precision;
101     double d = Math.abs(f);
102     d -= Whole;
103     double Frac = d;
104     double Diff = Frac;
105     long Num = 1;
106     long Den = 0;
107     long A = 0;
108     long B = 0;
109     long i = 0;
110     if (Frac > Precision) {
111       while (true) {
112         d = 1.0 / d;
113         i = (long) (d + Precision);
114         d -= i;
115         if (A > 0) {
116           Num = i * Num + B;
117         }
118         Den = (long) (Num / Frac + 0.5);
119         Diff = Math.abs((double) Num / Den - Frac);
120         if (Den > MaxDen) {
121           if (A > 0) {
122             Num = A;
123             Den = (long) (Num / Frac + 0.5);
124             Diff = Math.abs((double) Num / Den - Frac);
125           } else {
126             Den = MaxDen;
127             Num = 1;
128             Diff = Math.abs((double) Num / Den - Frac);
129             if (Diff > Frac) {
130               Num = 0;
131               Den = 1;
132               // Keeps final check below from adding 1 and keeps Den from being 0
133
Diff = Frac;
134             }
135           }
136           break;
137         }
138         if ((Diff <= AllowedError) || (d < Precision)) {
139           break;
140         }
141         Precision = AllowedError / Diff;
142         // This calcualtion of Precision does not always provide results within
143
// Allowed Error. It compensates for loss of significant digits that occurs.
144
// It helps to round the inprecise reciprocal values to i.
145
B = A;
146         A = Num;
147       }
148     }
149     if (Num == Den) {
150       Whole++;
151       Num = 0;
152       Den = 0;
153     } else if (Den == 0) {
154       Num = 0;
155     }
156     if (sign < 0) {
157       if (Whole == 0) {
158         Num = -Num;
159       } else {
160         Whole = -Whole;
161       }
162     }
163     return new StringBuffer JavaDoc().append(Whole).append(" ").append(Num).append("/").append(Den).toString();
164   }
165
166   /** This method formats the double in the units specified.
167    * The usints could be any number but in this current implementation it is
168    * halves (2), quaters (4), eigths (8) etc
169    */

170   private String JavaDoc formatUnit(double f, int units) {
171     long Whole = (long)f;
172     f -= Whole;
173     long Num = Math.round(f * units);
174
175     return new StringBuffer JavaDoc().append(Whole).append(" ").append(Num).append("/").append(units).toString();
176   }
177
178   public final String JavaDoc format(double val) {
179     if (mode == ONE_DIGIT) {
180       return format(val, 9);
181     } else if (mode == TWO_DIGIT) {
182       return format(val, 99);
183     } else if (mode == THREE_DIGIT) {
184       return format(val, 999);
185     } else if (mode == UNITS) {
186       return formatUnit(val , units);
187     }
188     throw new RuntimeException JavaDoc("Unexpected Case");
189   }
190
191   public StringBuffer JavaDoc format(Object JavaDoc obj,
192                                       StringBuffer JavaDoc toAppendTo,
193                                       FieldPosition pos) {
194     if (obj instanceof Number JavaDoc) {
195       toAppendTo.append(format(((Number JavaDoc)obj).doubleValue()));
196       return toAppendTo;
197     }
198     else throw new IllegalArgumentException JavaDoc("Can only handle Numbers");
199   }
200
201   public Object JavaDoc parseObject(String JavaDoc source,
202                                    ParsePosition status) {
203     //JMH TBD
204
return null;
205   }
206
207   public Object JavaDoc parseObject(String JavaDoc source)
208                    throws ParseException {
209     //JMH TBD
210
return null;
211   }
212
213   public Object JavaDoc clone() {
214     //JMH TBD
215
return null;
216   }
217
218
219 }
220
Popular Tags