<property name="scratchpad.output.test.dir" location="build/scratchpad-test-classes"/>
<property name="scratchpad.testokfile" location="build/scratchpad-testokfile.txt"/>
- <!-- Contributed software: -->
- <property name="contrib.src" location="src/contrib/src"/>
- <property name="contrib.src.test" location="src/contrib/testcases"/>
- <property name="contrib.reports.test" location="build/contrib-test-results"/>
- <property name="contrib.output.dir" location="build/contrib-classes"/>
- <property name="contrib.output.test.dir" location="build/contrib-test-classes"/>
- <property name="contrib.testokfile" location="build/contrib-testokfile.txt"/>
-
<!-- Examples: -->
<property name="examples.src" location="src/examples/src"/>
<property name="examples.output.dir" location="build/examples-classes"/>
<pathelement location="${main.output.dir}"/>
</path>
- <path id="contrib.classpath">
- <path refid="main.classpath"/>
- <pathelement location="${main.output.dir}"/>
- </path>
-
<path id="ooxml.classpath">
<pathelement location="${ooxml.jsr173.jar}"/>
<pathelement location="${ooxml.dom4j.jar}"/>
Timestamp ${DSTAMP}
The main targets of interest are:
- clean Erase all build work products (ie. everything in the build directory)
- - compile Compile all files from main, ooxml, contrib and scratchpad
- - test Run all unit tests from main, ooxml, contrib and scratchpad
+ - compile Compile all files from main, ooxml and scratchpad
+ - test Run all unit tests from main, ooxml and scratchpad
- jar Produce jar files
- site Generate all documentation (Requires Apache Forrest)
- dist Create a distribution (Requires Apache Forrest)
<mkdir dir="${scratchpad.output.dir}"/>
<mkdir dir="${scratchpad.output.test.dir}"/>
<mkdir dir="${scratchpad.reports.test}"/>
- <mkdir dir="${contrib.output.dir}"/>
- <mkdir dir="${contrib.output.test.dir}"/>
- <mkdir dir="${contrib.reports.test}"/>
<mkdir dir="${ooxml.output.dir}"/>
<mkdir dir="${ooxml.output.test.dir}"/>
<mkdir dir="${ooxml.reports.test}"/>
</target>
<target name="compile" depends="init, compile-main,
- compile-scratchpad, compile-contrib, compile-examples"
- description="Compiles the POI main classes, scratchpad, contrib and examples"/>
+ compile-scratchpad, compile-examples"
+ description="Compiles the POI main classes, scratchpad and examples"/>
<target name="compile-all" depends="compile,compile-ooxml-lite"/>
</copy>
</target>
- <target name="compile-contrib" depends="compile-main">
- <javac target="${jdk.version.class}"
- source="${jdk.version.source}"
- destdir="${contrib.output.dir}"
- srcdir="${contrib.src}"
- debug="${compile.debug}"
- encoding="${java.source.encoding}"
- fork="yes">
- <classpath refid="contrib.classpath"/>
- </javac>
- <javac target="${jdk.version.class}"
- source="${jdk.version.source}"
- failonerror="true"
- destdir="${contrib.output.test.dir}"
- srcdir="${contrib.src.test}"
- debug="${compile.debug}"
- encoding="${java.source.encoding}"
- fork="yes">
- <classpath>
- <path refid="contrib.classpath"/>
- <pathelement path="${contrib.output.dir}"/>
- </classpath>
- </javac>
- </target>
-
<target name="compile-examples" depends="compile-main,compile-scratchpad,compile-ooxml">
<javac target="${jdk.version.class}"
source="${jdk.version.source}"
<delete file="${version.java}"/>
</target>
- <target name="test" depends="compile,test-main,test-scratchpad,test-contrib,test-ooxml"
- description="Tests main, contrib, scratchpad and ooxml"/>
+ <target name="test" depends="compile,test-main,test-scratchpad,test-ooxml"
+ description="Tests main, scratchpad and ooxml"/>
<target name="test-all" depends="test,test-ooxml-lite"/>
<target name="-test-main-check">
<echo file="${scratchpad.testokfile}" append="false" message="testok"/>
</target>
- <target name="-test-contrib-check">
- <uptodate property="contrib.test.notRequired" targetfile="${contrib.testokfile}">
- <srcfiles dir="${contrib.src}"/>
- <srcfiles dir="${contrib.src.test}"/>
- </uptodate>
- </target>
-
- <target name="test-contrib" depends="compile-main,compile-contrib,-test-contrib-check"
- unless="contrib.test.notRequired">
- <junit printsummary="yes" fork="yes" haltonfailure="${halt.on.test.failure}"
- failureproperty="contrib.test.failed">
- <classpath>
- <path refid="contrib.classpath"/>
- <pathelement location="${main.output.dir}"/>
- <pathelement location="${contrib.output.dir}"/>
- <pathelement location="${contrib.output.test.dir}"/>
- </classpath>
- <syspropertyset refid="junit.properties"/>
- <jvmarg value="${poi.test.locale}"/>
- <formatter type="plain"/>
- <batchtest todir="${contrib.reports.test}">
- <fileset dir="${contrib.src.test}">
- <include name="**/Test*.java"/>
- <exclude name="**/AllTests.java"/>
- </fileset>
- </batchtest>
- </junit>
- <delete file="${contrib.testokfile}"/>
- <antcall target="-test-contrib-write-testfile"/>
- </target>
-
- <target name="-test-contrib-write-testfile" unless="contrib.test.failed">
- <echo file="${contrib.testokfile}" append="false" message="testok"/>
- </target>
-
<target name="-test-ooxml-check">
<uptodate property="ooxml.test.notRequired" targetfile="${ooxml.testokfile}">
<srcfiles dir="${ooxml.src}"/>
<include name="org/apache/poi/**"/>
<exclude name="org/apache/poi/hdf/**"/>
</packageset>
- <packageset dir="${contrib.src}" defaultexcludes="yes">
- <include name="org/apache/poi/**"/>
- </packageset>
<packageset dir="${ooxml.src}" defaultexcludes="yes">
<include name="org/apache/poi/**"/>
</packageset>
<classpath id="javadoc.classpath">
<path refid="main.classpath"/>
<path refid="scratchpad.classpath"/>
- <path refid="contrib.classpath"/>
<path refid="ooxml.classpath"/>
<path path="${env.CLASSPATH}"/>
</classpath>
</replacetokens>
</filterchain>
</copy>
- <copy file="maven/poi-contrib.pom" tofile="${dist.dir}/poi-contrib-${version.id}.pom">
- <filterchain>
- <replacetokens>
- <token key="VERSION" value="${version.id}"/>
- </replacetokens>
- </filterchain>
- </copy>
<copy file="maven/poi-scratchpad.pom" tofile="${dist.dir}/poi-scratchpad-${version.id}.pom">
<filterchain>
<replacetokens>
<fileset dir="${main.output.dir}"/>
<metainf dir="legal/"/>
</jar>
- <jar destfile="${dist.dir}/${jar.name}-contrib-${version.id}-${DSTAMP}.jar"
- manifest="build/poi-manifest.mf">
- <fileset dir="${contrib.output.dir}"/>
- <metainf dir="legal/"/>
- </jar>
<jar destfile="${dist.dir}/${jar.name}-scratchpad-${version.id}-${DSTAMP}.jar"
manifest="build/poi-manifest.mf">
<fileset dir="${scratchpad.output.dir}"/>
<fileset dir="${scratchpad.src}"/>
<metainf dir="legal/"/>
</jar>
- <jar destfile="${dist.dir}/${jar.name}-contrib-${version.id}-sources-${DSTAMP}.jar"
- manifest="build/poi-manifest.mf">
- <fileset dir="${contrib.src}"/>
- <metainf dir="legal/"/>
- </jar>
<jar destfile="${dist.dir}/${jar.name}-ooxml-${version.id}-sources-${DSTAMP}.jar"
manifest="build/poi-manifest.mf">
<fileset dir="${ooxml.src}"/>
<!-- jars to include in binary assemblies -->
<patternset id="bin.dist.jars">
<include name="${jar.name}-${version.id}-${DSTAMP}.jar"/>
- <include name="${jar.name}-contrib-${version.id}-${DSTAMP}.jar"/>
<include name="${jar.name}-scratchpad-${version.id}-${DSTAMP}.jar"/>
<include name="${jar.name}-ooxml-${version.id}-${DSTAMP}.jar"/>
<include name="${jar.name}-examples-${version.id}-${DSTAMP}.jar"/>
<target name="mvn-install" depends="maven.ant.tasks-check,jar,maven-poms">
<m2-install artifactId="poi"/>
<m2-install artifactId="poi-scratchpad"/>
- <m2-install artifactId="poi-contrib"/>
<m2-install artifactId="poi-ooxml"/>
<m2-install artifactId="poi-examples"/>
<m2-install artifactId="poi-ooxml-schemas"/>
<exclude name="documentation/content/xdocs/dtd/" />
<exclude name="documentation/content/xdocs/entity/" />
<exclude name="scratchpad/testcases/dummy.txt" />
- <exclude name="contrib/testcases/dummy.txt" />
<exclude name="examples/lib/dummy.txt" />
</fileset>
</rat:report>
VERSION=@VERSION@
DSTAMP=@DSTAMP@
-for artifactId in poi poi-scratchpad poi-contrib poi-ooxml poi-examples poi-ooxml-schemas
+for artifactId in poi poi-scratchpad poi-ooxml poi-examples poi-ooxml-schemas
do
mvn gpg:sign-and-deploy-file -DrepositoryId=apache-releases -P apache-releases \
-Durl=$M2_REPOSITORY \
+++ /dev/null
-<?xml version="1.0"?>
-<!--
-
- 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.
-
--->
-
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
-
- <modelVersion>4.0.0</modelVersion>
- <groupId>org.apache.poi</groupId>
- <artifactId>poi-contrib</artifactId>
- <version>@VERSION@</version>
- <packaging>jar</packaging>
- <name>Apache POI</name>
- <url>http://poi.apache.org/</url>
- <description>Apache POI - Java API To Access Microsoft Format Files</description>
-
- <mailingLists>
- <mailingList>
- <name>POI Users List</name>
- <subscribe>user-subscribe@poi.apache.org</subscribe>
- <unsubscribe>user-unsubscribe@poi.apache.org</unsubscribe>
- <archive>http://mail-archives.apache.org/mod_mbox/poi-user/</archive>
- </mailingList>
- <mailingList>
- <name>POI Developer List</name>
- <subscribe>dev-subscribe@poi.apache.org</subscribe>
- <unsubscribe>dev-unsubscribe@poi.apache.org</unsubscribe>
- <archive>http://mail-archives.apache.org/mod_mbox/poi-dev/</archive>
- </mailingList>
- </mailingLists>
-
- <licenses>
- <license>
- <name>The Apache Software License, Version 2.0</name>
- <url>http://www.apache.org/licenses/LICENSE-2.0.txt</url>
- </license>
- </licenses>
-
- <organization>
- <name>Apache Software Foundation</name>
- <url>http://www.apache.org/</url>
- </organization>
-
- <dependencies>
- <dependency>
- <groupId>org.apache.poi</groupId>
- <artifactId>poi</artifactId>
- <version>@VERSION@</version>
- </dependency>
- <dependency>
- <groupId>commons-logging</groupId>
- <artifactId>commons-logging</artifactId>
- <version>1.1</version>
- <scope>runtime</scope>
- </dependency>
- <dependency>
- <groupId>log4j</groupId>
- <artifactId>log4j</artifactId>
- <version>1.2.13</version>
- <scope>runtime</scope>
- </dependency>
- </dependencies>
-
-</project>
+++ /dev/null
-
-/* ====================================================================
- 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.contrib.metrics;
-
-import java.awt.*;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.util.Properties;
-
-@SuppressWarnings("deprecation")
-public class FontMetricsDumper
-{
- public static void main( String[] args ) throws IOException
- {
-
- Properties props = new Properties();
-
- Font[] allFonts = GraphicsEnvironment.getLocalGraphicsEnvironment().getAllFonts();
- for ( int i = 0; i < allFonts.length; i++ )
- {
- String fontName = allFonts[i].getFontName();
-
- Font font = new Font(fontName, Font.BOLD, 10);
- FontMetrics fontMetrics = Toolkit.getDefaultToolkit().getFontMetrics(font);
- int fontHeight = fontMetrics.getHeight();
-
- props.setProperty("font." + fontName + ".height", fontHeight+"");
- StringBuffer characters = new StringBuffer();
- for (char c = 'a'; c <= 'z'; c++)
- {
- characters.append( c + ", " );
- }
- for (char c = 'A'; c <= 'Z'; c++)
- {
- characters.append( c + ", " );
- }
- for (char c = '0'; c <= '9'; c++)
- {
- characters.append( c + ", " );
- }
- StringBuffer widths = new StringBuffer();
- for (char c = 'a'; c <= 'z'; c++)
- {
- widths.append( fontMetrics.getWidths()[c] + ", " );
- }
- for (char c = 'A'; c <= 'Z'; c++)
- {
- widths.append( fontMetrics.getWidths()[c] + ", " );
- }
- for (char c = '0'; c <= '9'; c++)
- {
- widths.append( fontMetrics.getWidths()[c] + ", " );
- }
- props.setProperty("font." + fontName + ".characters", characters.toString());
- props.setProperty("font." + fontName + ".widths", widths.toString());
- }
-
- FileOutputStream fileOut = new FileOutputStream("font_metrics.properties");
- try
- {
- props.store(fileOut, "Font Metrics");
- }
- finally
- {
- fileOut.close();
- }
- }
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.io.BufferedReader;
-import java.io.IOException;
-import java.io.InputStreamReader;
-
-import org.apache.poi.hpsf.ClassID;
-
-
-
-/**
- * <p>Provides utility methods for encoding and decoding hexadecimal
- * data.</p>
- *
- * @author Rainer Klute (klute@rainer-klute.de) - with portions from Tomcat
- */
-public class Codec
-{
-
- /**
- * <p>The nibbles' hexadecimal values. A nibble is a half byte.</p>
- */
- protected static final byte hexval[] =
- {(byte) '0', (byte) '1', (byte) '2', (byte) '3',
- (byte) '4', (byte) '5', (byte) '6', (byte) '7',
- (byte) '8', (byte) '9', (byte) 'A', (byte) 'B',
- (byte) 'C', (byte) 'D', (byte) 'E', (byte) 'F'};
-
-
-
- /**
- * <p>Converts a string into its hexadecimal notation.</p>
- */
- public static String hexEncode(final String s)
- {
- return hexEncode(s.getBytes());
- }
-
-
-
- /**
- * <p>Converts a byte array into its hexadecimal notation.</p>
- */
- public static String hexEncode(final byte[] s)
- {
- return hexEncode(s, 0, s.length);
- }
-
-
-
- /**
- * <p>Converts a part of a byte array into its hexadecimal
- * notation.</p>
- */
- public static String hexEncode(final byte[] s, final int offset,
- final int length)
- {
- StringBuffer b = new StringBuffer(length * 2);
- for (int i = offset; i < offset + length; i++)
- {
- int c = s[i];
- b.append((char) hexval[(c & 0xF0) >> 4]);
- b.append((char) hexval[(c & 0x0F) >> 0]);
- }
- return b.toString();
- }
-
-
-
- /**
- * <p>Converts a single byte into its hexadecimal notation.</p>
- */
- public static String hexEncode(final byte b)
- {
- StringBuffer sb = new StringBuffer(2);
- sb.append((char) hexval[(b & 0xF0) >> 4]);
- sb.append((char) hexval[(b & 0x0F) >> 0]);
- return sb.toString();
- }
-
-
-
- /**
- * <p>Converts a short value (16-bit) into its hexadecimal
- * notation.</p>
- */
- public static String hexEncode(final short s)
- {
- StringBuffer sb = new StringBuffer(4);
- sb.append((char) hexval[(s & 0xF000) >> 12]);
- sb.append((char) hexval[(s & 0x0F00) >> 8]);
- sb.append((char) hexval[(s & 0x00F0) >> 4]);
- sb.append((char) hexval[(s & 0x000F) >> 0]);
- return sb.toString();
- }
-
-
-
- /**
- * <p>Converts an int value (32-bit) into its hexadecimal
- * notation.</p>
- */
- public static String hexEncode(final int i)
- {
- StringBuffer sb = new StringBuffer(8);
- sb.append((char) hexval[(i & 0xF0000000) >> 28]);
- sb.append((char) hexval[(i & 0x0F000000) >> 24]);
- sb.append((char) hexval[(i & 0x00F00000) >> 20]);
- sb.append((char) hexval[(i & 0x000F0000) >> 16]);
- sb.append((char) hexval[(i & 0x0000F000) >> 12]);
- sb.append((char) hexval[(i & 0x00000F00) >> 8]);
- sb.append((char) hexval[(i & 0x000000F0) >> 4]);
- sb.append((char) hexval[(i & 0x0000000F) >> 0]);
- return sb.toString();
- }
-
-
-
- /**
- * <p>Converts a long value (64-bit) into its hexadecimal
- * notation.</p>
- */
- public static String hexEncode(final long l)
- {
- StringBuffer sb = new StringBuffer(16);
- sb.append(hexEncode((int) (l & 0xFFFFFFFF00000000L) >> 32));
- sb.append(hexEncode((int) (l & 0x00000000FFFFFFFFL) >> 0));
- return sb.toString();
- }
-
-
-
- /**
- * <p>Converts a class ID into its hexadecimal notation.</p>
- */
- public static String hexEncode(final ClassID classID)
- {
- return hexEncode(classID.getBytes());
- }
-
-
-
- /**
- * <p>Decodes the hexadecimal representation of a sequence of
- * bytes into a byte array. Each character in the string
- * represents a nibble (half byte) and must be one of the
- * characters '0'-'9', 'A'-'F' or 'a'-'f'.</p>
- *
- * @param s The string to be decoded
- *
- * @return The bytes
- *
- * @throws IllegalArgumentException if the string does not contain
- * a valid representation of a byte sequence.
- */
- public static byte[] hexDecode(final String s)
- {
- final int length = s.length();
-
- /* The string to be converted must have an even number of
- characters. */
- if (length % 2 == 1)
- throw new IllegalArgumentException
- ("String has odd length " + length);
- byte[] b = new byte[length / 2];
- char[] c = new char[length];
- s.toUpperCase().getChars(0, length, c, 0);
- for (int i = 0; i < length; i += 2)
- b[i/2] = (byte) (decodeNibble(c[i]) << 4 & 0xF0 |
- decodeNibble(c[i+1]) & 0x0F);
- return b;
- }
-
-
-
- /**
- * <p>Decodes a nibble.</p>
- *
- * @param c A character in the range '0'-'9' or 'A'-'F'. Lower
- * case is not supported here.
- *
- * @return The decoded nibble in the range 0-15
- *
- * @throws IllegalArgumentException if <em>c</em> is not a
- * permitted character
- */
- protected static byte decodeNibble(final char c)
- {
- for (byte i = 0; i < hexval.length; i++)
- if ((byte) c == hexval[i])
- return i;
- throw new IllegalArgumentException("\"" + c + "\"" +
- " does not represent a nibble.");
- }
-
-
-
- /**
- * <p>For testing.</p>
- */
- public static void main(final String args[])
- throws IOException
- {
- final BufferedReader in =
- new BufferedReader(new InputStreamReader(System.in));
- String s;
- do
- {
- s = in.readLine();
- if (s != null)
- {
- String bytes = hexEncode(s);
- System.out.print("Hex encoded (String): ");
- System.out.println(bytes);
- System.out.print("Hex encoded (byte[]): ");
- System.out.println(hexEncode(s.getBytes()));
- System.out.print("Re-decoded (byte[]): ");
- System.out.println(new String(hexDecode(bytes)));
- }
- }
- while (s != null);
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.io.*;
-import org.apache.poi.poifs.filesystem.*;
-
-/**
- * <p>Describes the most important (whatever that is) features of a
- * {@link POIFSDocument}.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class DocumentDescriptor
-{
- String name;
- POIFSDocumentPath path;
- DocumentInputStream stream;
-
- int size;
- byte[] bytes;
-
-
- /**
- * <p>Creates a {@link DocumentDescriptor}.</p>
- *
- * @param name The stream's name.
- *
- * @param path The stream's path in the POI filesystem hierarchy.
- *
- * @param stream The stream.
- *
- * @param nrOfBytes The maximum number of bytes to display in a
- * dump starting at the beginning of the stream.
- */
- public DocumentDescriptor(final String name,
- final POIFSDocumentPath path,
- final DocumentInputStream stream,
- final int nrOfBytes)
- {
- this.name = name;
- this.path = path;
- this.stream = stream;
- try
- {
- size = stream.available();
- if (stream.markSupported())
- {
- stream.mark(nrOfBytes);
- final byte[] b = new byte[nrOfBytes];
- final int read = stream.read(b, 0, Math.min(size, b.length));
- bytes = new byte[read];
- System.arraycopy(b, 0, bytes, 0, read);
- stream.reset();
- }
- }
- catch (IOException ex)
- {
- System.out.println(ex);
- }
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.awt.*;
-import javax.swing.*;
-import javax.swing.tree.*;
-
-/**
- * <p>{@link TreeCellRenderer} for a {@link DocumentDescriptor}. The
- * renderer is extremly rudimentary since displays only the document's
- * name, its size and its fist few bytes.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class DocumentDescriptorRenderer extends DefaultTreeCellRenderer
-{
-
- public Component getTreeCellRendererComponent(final JTree tree,
- final Object value,
- final boolean selected,
- final boolean expanded,
- final boolean leaf,
- final int row,
- final boolean hasFocus)
- {
- final DocumentDescriptor d = (DocumentDescriptor)
- ((DefaultMutableTreeNode) value).getUserObject();
- final JPanel p = new JPanel();
- final JTextArea text = new JTextArea();
- text.append(renderAsString(d));
- text.setFont(new Font("Monospaced", Font.PLAIN, 10));
- p.add(text);
- if (selected)
- Util.invert(text);
- return p;
- }
-
-
- /**
- * <p>Renders {@link DocumentDescriptor} as a string.</p>
- */
- protected String renderAsString(final DocumentDescriptor d)
- {
- final StringBuffer b = new StringBuffer();
- b.append("Name: ");
- b.append(d.name);
- b.append(" (");
- b.append(Codec.hexEncode(d.name));
- b.append(") \n");
-
- b.append("Size: ");
- b.append(d.size);
- b.append(" bytes\n");
-
- b.append("First bytes: ");
- b.append(Codec.hexEncode(d.bytes));
-
- return b.toString();
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.awt.*;
-import javax.swing.*;
-import javax.swing.tree.*;
-import java.util.*;
-
-/**
- * <p>This is a {@link TreeCellRenderer} implementation which is able
- * to render arbitrary objects. The {@link ExtendableTreeCellRenderer}
- * does not do the rendering itself but instead dispatches to
- * class-specific renderers. A class/renderer pair must be registered
- * using the {@link #register} method. If a class has no registered
- * renderer, the renderer of its closest superclass is used. Since the
- * {@link ExtendableTreeCellRenderer} always has a default renderer
- * for the {@link Object} class, rendering is always possible. The
- * default {@link Object} renderer can be replaced by another renderer
- * but it cannot be unregistered.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class ExtendableTreeCellRenderer implements TreeCellRenderer
-{
-
- /**
- * <p>Maps classes to renderers.</p>
- */
- protected Map renderers;
-
-
-
- public ExtendableTreeCellRenderer()
- {
- renderers = new HashMap();
- register(Object.class, new DefaultTreeCellRenderer()
- {
- public Component getTreeCellRendererComponent
- (JTree tree, Object value, boolean selected,
- boolean expanded, boolean leaf, int row, boolean hasFocus)
- {
- final String s = value.toString();
- final JLabel l = new JLabel(s + " ");
- if (selected)
- {
- Util.invert(l);
- l.setOpaque(true);
- }
- return l;
- }
- });
- }
-
-
-
- /**
- * <p>Registers a renderer for a class.</p>
- **/
- public void register(final Class c, final TreeCellRenderer renderer)
- {
- renderers.put(c, renderer);
- }
-
-
-
- /**
- * <p>Unregisters a renderer for a class. The renderer for the
- * {@link Object} class cannot be unregistered.</p>
- */
- public void unregister(final Class c)
- {
- if (c == Object.class)
- throw new IllegalArgumentException
- ("Renderer for Object cannot be unregistered.");
- renderers.put(c, null);
- }
-
-
-
- /**
- * <p>Renders an object in a tree cell depending of the object's
- * class.</p>
- *
- * @see TreeCellRenderer#getTreeCellRendererComponent
- */
- public Component getTreeCellRendererComponent
- (final JTree tree, final Object value, final boolean selected,
- final boolean expanded, final boolean leaf, final int row,
- final boolean hasFocus)
- {
- final String NULL = "null";
- TreeCellRenderer r;
- Object userObject;
- if (value == null)
- userObject = NULL;
- else
- {
- userObject = ((DefaultMutableTreeNode) value).getUserObject();
- if (userObject == null)
- userObject = NULL;
- }
- r = findRenderer(userObject.getClass());
- return r.getTreeCellRendererComponent
- (tree, value, selected, expanded, leaf, row,
- hasFocus);
- }
-
-
-
- /**
- * <p>Find the renderer for the specified class.</p>
- */
- protected TreeCellRenderer findRenderer(final Class c)
- {
- final TreeCellRenderer r = (TreeCellRenderer) renderers.get(c);
- if (r != null)
- /* The class has a renderer. */
- return r;
-
- /* The class has no renderer, try the superclass, if any. */
- final Class superclass = c.getSuperclass();
- if (superclass != null) {
- return findRenderer(superclass);
- }
- return null;
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.awt.event.WindowAdapter;
-import java.awt.event.WindowEvent;
-import java.io.FileInputStream;
-import java.io.IOException;
-
-import javax.swing.JFrame;
-import javax.swing.JScrollPane;
-import javax.swing.JTree;
-import javax.swing.tree.DefaultMutableTreeNode;
-import javax.swing.tree.DefaultTreeModel;
-import javax.swing.tree.MutableTreeNode;
-
-import org.apache.poi.poifs.eventfilesystem.POIFSReader;
-
-/**
- * <p>The main class of the POI Browser. It shows the structure of POI
- * filesystems (Microsoft Office documents) in a {@link
- * JTree}. Specify their filenames on the command line!</p>
- *
- * @see POIFSReader
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class POIBrowser extends JFrame
-{
-
- /**
- * <p>The tree's root node must be visible to all methods.</p>
- */
- protected MutableTreeNode rootNode;
-
-
-
- /**
- * <p>Takes a bunch of file names as command line parameters,
- * opens each of them as a POI filesystem and displays their
- * internal structures in a {@link JTree}.</p>
- */
- public static void main(String[] args)
- {
- new POIBrowser().run(args);
- }
-
-
-
- protected void run(String[] args)
- {
- addWindowListener(new WindowAdapter()
- {
- public void windowClosing(WindowEvent e)
- {
- System.exit(0);
- }
- });
-
- /* Create the tree model with a root node. The latter is
- * invisible but it must be present because a tree model
- * always needs a root. */
- rootNode = new DefaultMutableTreeNode("POI Filesystems");
- DefaultTreeModel treeModel = new DefaultTreeModel(rootNode);
-
- /* Create the tree UI element. */
- final JTree treeUI = new JTree(treeModel);
- getContentPane().add(new JScrollPane(treeUI));
-
- /* Add the POI filesystems to the tree. */
- int displayedFiles = 0;
- for (int i = 0; i < args.length; i++)
- {
- final String filename = args[i];
- try
- {
- POIFSReader r = new POIFSReader();
- r.registerListener(new TreeReaderListener(filename, rootNode));
- r.read(new FileInputStream(filename));
- displayedFiles++;
- }
- catch (IOException ex)
- {
- System.err.println(filename + ": " + ex);
- }
- catch (Throwable t)
- {
- System.err.println("Unexpected exception while reading \"" +
- filename + "\":");
- t.printStackTrace(System.err);
- }
- }
-
- /* Exit if there is no file to display (none specified or only
- * files with problems). */
- if (displayedFiles == 0)
- {
- System.out.println("No POI filesystem(s) to display.");
- System.exit(0);
- }
-
- /* Make the tree UI element visible. */
- treeUI.setRootVisible(true);
- treeUI.setShowsRootHandles(true);
- ExtendableTreeCellRenderer etcr = new ExtendableTreeCellRenderer();
- etcr.register(DocumentDescriptor.class,
- new DocumentDescriptorRenderer());
- etcr.register(PropertySetDescriptor.class,
- new PropertySetDescriptorRenderer());
- treeUI.setCellRenderer(etcr);
- setSize(600, 450);
- setTitle("POI Browser 0.09");
- setVisible(true);
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-
-import org.apache.poi.hpsf.MarkUnsupportedException;
-import org.apache.poi.hpsf.NoPropertySetStreamException;
-import org.apache.poi.hpsf.PropertySet;
-import org.apache.poi.hpsf.PropertySetFactory;
-import org.apache.poi.poifs.filesystem.DocumentInputStream;
-import org.apache.poi.poifs.filesystem.POIFSDocumentPath;
-
-/**
- * <p>Describes the most important (whatever that is) features of a
- * stream containing a {@link PropertySet}.</p>
- *
- * @author Rainer Klute (klute@rainer-klute.de)
- */
-public class PropertySetDescriptor extends DocumentDescriptor
-{
-
- protected PropertySet propertySet;
-
- /**
- * <p>Returns this {@link PropertySetDescriptor}'s {@link
- * PropertySet}.</p>
- */
- public PropertySet getPropertySet()
- {
- return propertySet;
- }
-
-
-
- /**
- * <p>Creates a {@link PropertySetDescriptor} by reading a {@link
- * PropertySet} from a {@link DocumentInputStream}.</p>
- *
- * @param name The stream's name.
- *
- * @param path The stream's path in the POI filesystem hierarchy.
- *
- * @param stream The stream.
- *
- * @param nrOfBytesToDump The maximum number of bytes to display in a
- * dump starting at the beginning of the stream.
- */
- public PropertySetDescriptor(final String name,
- final POIFSDocumentPath path,
- final DocumentInputStream stream,
- final int nrOfBytesToDump)
- throws NoPropertySetStreamException,
- MarkUnsupportedException, UnsupportedEncodingException,
- IOException
- {
- super(name, path, stream, nrOfBytesToDump);
- propertySet = PropertySetFactory.create(stream);
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.awt.Color;
-import java.awt.Component;
-import java.awt.Font;
-import java.util.Iterator;
-import java.util.List;
-
-import javax.swing.JPanel;
-import javax.swing.JTextArea;
-import javax.swing.JTree;
-import javax.swing.tree.DefaultMutableTreeNode;
-
-import org.apache.poi.hpsf.Property;
-import org.apache.poi.hpsf.PropertySet;
-import org.apache.poi.hpsf.Section;
-import org.apache.poi.hpsf.SummaryInformation;
-
-/**
- * <p>Renders a {@link PropertySetDescriptor} by more or less dumping
- * the stuff into a {@link JTextArea}.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class PropertySetDescriptorRenderer extends DocumentDescriptorRenderer
-{
-
- public Component getTreeCellRendererComponent(final JTree tree,
- final Object value,
- final boolean selected,
- final boolean expanded,
- final boolean leaf,
- final int row,
- final boolean hasFocus)
- {
- final PropertySetDescriptor d = (PropertySetDescriptor)
- ((DefaultMutableTreeNode) value).getUserObject();
- final PropertySet ps = d.getPropertySet();
- final JPanel p = new JPanel();
- final JTextArea text = new JTextArea();
- text.setBackground(new Color(200, 255, 200));
- text.setFont(new Font("Monospaced", Font.PLAIN, 10));
- text.append(renderAsString(d));
- text.append("\nByte order: " +
- Codec.hexEncode((short) ps.getByteOrder()));
- text.append("\nFormat: " +
- Codec.hexEncode((short) ps.getFormat()));
- text.append("\nOS version: " +
- Codec.hexEncode(ps.getOSVersion()));
- text.append("\nClass ID: " +
- Codec.hexEncode(ps.getClassID()));
- text.append("\nSection count: " + ps.getSectionCount());
- text.append(sectionsToString(ps.getSections()));
- p.add(text);
-
- if (ps instanceof SummaryInformation)
- {
- /* Use the convenience methods. */
- final SummaryInformation si = (SummaryInformation) ps;
- text.append("\n");
- text.append("\nTitle: " + si.getTitle());
- text.append("\nSubject: " + si.getSubject());
- text.append("\nAuthor: " + si.getAuthor());
- text.append("\nKeywords: " + si.getKeywords());
- text.append("\nComments: " + si.getComments());
- text.append("\nTemplate: " + si.getTemplate());
- text.append("\nLast Author: " + si.getLastAuthor());
- text.append("\nRev. Number: " + si.getRevNumber());
- text.append("\nEdit Time: " + si.getEditTime());
- text.append("\nLast Printed: " + si.getLastPrinted());
- text.append("\nCreate Date/Time: " + si.getCreateDateTime());
- text.append("\nLast Save Date/Time: " + si.getLastSaveDateTime());
- text.append("\nPage Count: " + si.getPageCount());
- text.append("\nWord Count: " + si.getWordCount());
- text.append("\nChar Count: " + si.getCharCount());
- // text.append("\nThumbnail: " + si.getThumbnail());
- text.append("\nApplication Name: " + si.getApplicationName());
- text.append("\nSecurity: " + si.getSecurity());
- }
-
- if (selected)
- Util.invert(text);
- return p;
- }
-
-
-
- /**
- * <p>Returns a string representation of a list of {@link
- * Section}s.</p>
- */
- protected String sectionsToString(final List sections)
- {
- final StringBuffer b = new StringBuffer();
- int count = 1;
- for (Iterator i = sections.iterator(); i.hasNext();)
- {
- Section s = (Section) i.next();
- String d = toString(s, "Section " + count++);
- b.append(d);
- }
- return b.toString();
- }
-
-
-
- /**
- * <p>Returns a string representation of a {@link Section}.</p>
- * @param s the section
- * @param name the section's name
- * @return a string representation of the {@link Section}
- */
- protected String toString(final Section s, final String name)
- {
- final StringBuffer b = new StringBuffer();
- b.append("\n" + name + " Format ID: ");
- b.append(Codec.hexEncode(s.getFormatID()));
- b.append("\n" + name + " Offset: " + s.getOffset());
- b.append("\n" + name + " Section size: " + s.getSize());
- b.append("\n" + name + " Property count: " + s.getPropertyCount());
-
- final Property[] properties = s.getProperties();
- for (int i = 0; i < properties.length; i++)
- {
- final Property p = properties[i];
- final long id = p.getID();
- final long type = p.getType();
- final Object value = p.getValue();
- b.append('\n');
- b.append(name);
- b.append(", Name: ");
- b.append(id);
- b.append(" (");
- b.append(s.getPIDString(id));
- b.append("), Type: ");
- b.append(type);
- b.append(", Value: ");
- if (value instanceof byte[])
- {
- byte[] b2 = (byte[]) value;
- b.append("0x" + Codec.hexEncode(b2, 0, 4));
- b.append(' ');
- b.append("0x" + Codec.hexEncode(b2, 4, b2.length - 4));
- }
- else if (value != null)
- b.append(value.toString());
- else
- b.append("null");
- }
- return b.toString();
- }
-
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import javax.swing.tree.DefaultMutableTreeNode;
-import javax.swing.tree.MutableTreeNode;
-
-import org.apache.poi.hpsf.HPSFException;
-import org.apache.poi.poifs.eventfilesystem.POIFSReaderEvent;
-import org.apache.poi.poifs.eventfilesystem.POIFSReaderListener;
-import org.apache.poi.poifs.filesystem.DocumentInputStream;
-import org.apache.poi.poifs.filesystem.POIFSDocumentPath;
-
-/**
- * <p>Organizes document information in a tree model in order to be
- * e.g. displayed in a Swing {@link javax.swing.JTree}. An instance of this
- * class is created with a root tree node ({@link MutableTreeNode}) and
- * registered as a {@link POIFSReaderListener} with a {@link
- * org.apache.poi.poifs.eventfilesystem.POIFSReader}. While the latter processes
- * a POI filesystem it calls this class' {@link #processPOIFSReaderEvent} for
- * each document it has been registered for. This method appends the document it
- * processes at the appropriate position into the tree rooted at the
- * above mentioned root tree node.</p>
- *
- * <p>The root tree node should be the root tree node of a {@link
- * javax.swing.tree.TreeModel}.</p>
- *
- * <p>A top-level element in the tree model, i.e. an immediate child
- * node of the root node, describes a POI filesystem as such. It is
- * suggested to use the file's name (as seen by the operating system)
- * but it could be any other string.</p>
- *
- * <p>The value of a tree node is a {@link DocumentDescriptor}. Unlike
- * a {@link org.apache.poi.poifs.filesystem.POIFSDocument} which may be as heavy
- * as many megabytes, an instance of {@link DocumentDescriptor} is a
- * light-weight object and contains only some meta-information about a
- * document.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class TreeReaderListener implements POIFSReaderListener
-{
-
- /**
- * <p>The tree's root node. POI filesystems get attached to this
- * node as children.</p>
- */
- protected MutableTreeNode rootNode;
-
- /**
- * <p>Maps filenames and POI document paths to their associated
- * tree nodes.</p>
- */
- protected Map pathToNode;
-
- /**
- * <p>The name of the file this {@link TreeReaderListener}
- * processes. It is used to identify a top-level element in the
- * tree. Alternatively any other string can be used. It is just a
- * label which should identify a POI filesystem.</p>
- */
- protected String filename;
-
-
-
- /**
- * <p>Creates a {@link TreeReaderListener} which should then be
- * registered with a
- * {@link org.apache.poi.poifs.eventfilesystem.POIFSReader}.</p>
- *
- * @param filename The name of the POI filesystem, i.e. the name
- * of the file the POI filesystem resides in. Alternatively any
- * other string can be used.
- *
- * @param rootNode All document information will be attached as
- * descendands to this tree node.
- */
- public TreeReaderListener(final String filename,
- final MutableTreeNode rootNode)
- {
- this.filename = filename;
- this.rootNode = rootNode;
- pathToNode = new HashMap(15); // Should be a reasonable guess.
- }
-
-
-
- /** <p>The number of bytes to dump.</p> */
- private int nrOfBytes = 50;
-
- public void setNrOfBytes(final int nrOfBytes)
- {
- this.nrOfBytes = nrOfBytes;
- }
-
- public int getNrOfBytes()
- {
- return nrOfBytes;
- }
-
-
-
- /**
- * <p>A document in the POI filesystem has been opened for
- * reading. This method retrieves properties of the document and
- * adds them to a tree model.</p>
- */
- public void processPOIFSReaderEvent(final POIFSReaderEvent event)
- {
- DocumentDescriptor d;
- final DocumentInputStream is = event.getStream();
- if (!is.markSupported())
- throw new UnsupportedOperationException(is.getClass().getName() +
- " does not support mark().");
-
- /* Try do handle this document as a property set. We receive
- * an exception if is no property set and handle it as a
- * document of some other format. We are not concerned about
- * that document's details. */
- try
- {
- d = new PropertySetDescriptor(event.getName(), event.getPath(),
- is, nrOfBytes);
- }
- catch (HPSFException ex)
- {
- d = new DocumentDescriptor(event.getName(), event.getPath(),
- is, nrOfBytes);
- }
- catch (Throwable t)
- {
- System.err.println
- ("Unexpected exception while processing " +
- event.getName() + " in " + event.getPath().toString());
- t.printStackTrace(System.err);
- throw new RuntimeException(t.getMessage());
- }
-
- is.close();
-
- final MutableTreeNode parentNode = getNode(d.path, filename, rootNode);
- final MutableTreeNode nameNode = new DefaultMutableTreeNode(d.name);
- parentNode.insert(nameNode, 0);
- final MutableTreeNode dNode = new DefaultMutableTreeNode(d);
- nameNode.insert(dNode, 0);
- }
-
-
-
- /**
- * <p>Locates the parent node for a document entry in the tree
- * model. If the parent node does not yet exist it will be
- * created, too. This is done recursively, if needed.</p>
- *
- * @param path The tree node for this path is located.
- *
- * @param fsName The name of the POI filesystem. This is just a
- * string which is displayed in the tree at the top lovel.
- *
- * @param root The root node.
- */
- private MutableTreeNode getNode(final POIFSDocumentPath path,
- final String fsName,
- final MutableTreeNode root)
- {
- MutableTreeNode n = (MutableTreeNode) pathToNode.get(path);
- if (n != null)
- /* Node found in map, just return it. */
- return n;
- if (path.length() == 0)
- {
- /* This is the root path of the POI filesystem. Its tree
- * node is resp. must be located below the tree node of
- * the POI filesystem itself. This is a tree node with the
- * POI filesystem's name (this the operating system file's
- * name) as its key it the path-to-node map. */
- n = (MutableTreeNode) pathToNode.get(fsName);
- if (n == null)
- {
- /* A tree node for the POI filesystem does not yet
- * exist. */
- n = new DefaultMutableTreeNode(fsName);
- pathToNode.put(fsName, n);
- root.insert(n, 0);
- }
- return n;
- }
- /* else - The path is somewhere down in the POI filesystem's
- * hierarchy. We need the tree node of this path's parent
- * and attach our new node to it. */
- final String name = path.getComponent(path.length() - 1);
- final POIFSDocumentPath parentPath = path.getParent();
- final MutableTreeNode parentNode =
- getNode(parentPath, fsName, root);
- n = new DefaultMutableTreeNode(name);
- pathToNode.put(path, n);
- parentNode.insert(n, 0);
- return n;
- }
-}
+++ /dev/null
-/* ====================================================================
- 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.contrib.poibrowser;
-
-import java.awt.*;
-import javax.swing.*;
-
-/**
- * <p>Contains various (well, just one at the moment) static utility
- * methods.</p>
- *
- * @author Rainer Klute <a
- * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
- */
-public class Util {
-
- /**
- * <p>Makes a Swing component inverted by swapping its foreground
- * and background colors. Hint: Depending on your needs it might
- * also be a good idea to call <tt>c.setOpaque(true)</tt>.</p>
- */
- public static void invert(JComponent c) {
- Color invBackground = c.getForeground();
- Color invForeground = c.getBackground();
- c.setBackground(invBackground);
- c.setForeground(invForeground);
- }
-}
-
+++ /dev/null
-<!doctype html public "-//W3C//DTD HTML 4.0//EN//">
-<!--
-/* ====================================================================
- 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.
- ==================================================================== */
--->
-
-<html>
- <head>
- <title></title>
- </head>
-
- <body>
- <div>
- <p>The <strong>POI Browser</strong> is a very simple Swing GUI tool that
- displays the internal structure of a Microsoft Office file. It concentrates
- on streams in the <em>Horrible Property Set Format (HPSF)</em>. In order to
- access these streams the POI Browser uses the package
- <tt>org.apache.poi.hpsf</tt>.</p>
-
- <p>A file in Microsoft's Office format can be seen as a filesystem within a
- file. For example, a Word document like <var>sample.doc</var> is just a
- simple file from the operation system's point of view. However, internally
- it is organized into various directories and files. For example,
- <var>sample.doc</var> might consist of the three internal files (or
- "streams", as Microsoft calls them) <tt>\001CompObj</tt>,
- <tt>\005SummaryInformation</tt>, and <tt>WordDocument</tt>. (In these names
- \001 and \005 denote the unprintable characters with the character codes 1
- and 5, respectively.) A more complicated Word file typically contains a
- directory named <tt>ObjectPool</tt> with more directories and files nested
- within it.</p>
-
- <p>The POI Browser makes these internal structures visible. It takes one or
- more Microsoft files as input on the command line and shows directories and
- files in a tree-like structure. On the top-level POI Browser displays the
- (operating system) filenames. An internal file (i.e. a "stream" or a
- "document") is shown with its name, its size and a hexadecimal dump of its
- first bytes.</p>
- </div>
-
- <div>
- <h3>Property Set Streams</h3>
-
- <p>The POI Browser pays special attention to property set streams. For
- example, the <tt>\005SummaryInformation</tt> stream contains information
- like title and author of the document. The POI Browser opens every stream
- in a POI filesystem. If it encounters a property set stream, it displays
- not just its first bytes but analyses the whole stream and displays its
- contents in a more or less readable manner.</p>
- </div>
-
- <div>
- <h3>Running POI Browser</h3>
-
- <p>Running the POI Browser requires you to start a Java Virtual Machine
- (JVM) and to set up a valid classpath so that the JVM can find all the Java
- classes it needs. These are the main POI classes and the "contrib" POI
- classes.</p>
-
- <p>The following instructions assume that you have set up your Java
- enviromnent variables properly, i.e. the variable JAVA_HOME contains the
- name of your Java installation directory and the variable PATH includes the
- <var>bin</var> subdirectory of the Java installation directory. At the time
- of this writing the current POI version was 2.5.1-final dating from August
- 4th, 2004. The example statements reflect version numbering and
- date. Change the commands accordingly if you are running the POI Browser of
- a later or earlier than this!</p>
-
- <div>
- <h4>Running POI Browser on Unix</h4>
-
- <p>Suppose you have unpacked the POI 2.5.1 release in the
- <var>/opt/local/poi</var> directory of your Unix box. Then the following
- command starts the POI Browser and displays the structure of the files
- <var>MyWord.doc</var>, <var>MyExcel.xls</var> and
- <var>MyPowerpoint.ppt</var>:</p>
-
- <pre>java -classpath /opt/local/poi/poi-2.5.1-final-20040804.jar:/opt/local/poi/poi-contrib-2.5.1-final-20040804.jar org.apache.poi.contrib.poibrowser.POIBrowser MyWord.doc MyExcel.xls MyPowerpoint.ppt</pre>
- </div>
-
- <div>
- <h4>Running POI Browser on Windows</h4>
-
- <p>Suppose you have unpacked the POI 2.5.1 release in the
- <var>C:\Programs\POI</var> directory of your Windows box. Then the following
- command starts the POI Browser and displays the structure of the files
- <var>MyWord.doc</var>, <var>MyExcel.xls</var> and
- <var>MyPowerpoint.ppt</var>:</p>
-
- <pre>java -classpath C:\Programs\POI\poi-2.5.1-final-20040804.jar;C:\Programs\POI\poi-contrib-2.5.1-final-20040804.jar org.apache.poi.contrib.poibrowser.POIBrowser MyWord.doc MyExcel.xls MyPowerpoint.ppt</pre>
- </div>
-
- </div>
- </body>
-</html>
-
-<!-- Keep this comment at the end of the file
-Local variables:
-sgml-default-dtd-file:"HTML_4.0_Strict.ced"
-mode: html
-sgml-omittag:t
-sgml-shorttag:nil
-sgml-namecase-general:t
-sgml-general-insert-case:lower
-sgml-minimize-attributes:nil
-sgml-always-quote-attributes:t
-sgml-indent-step:1
-sgml-indent-data:t
-sgml-parent-document:nil
-sgml-exposed-tags:nil
-sgml-local-catalogs:nil
-sgml-local-ecat-files:nil
-End:
--->
+++ /dev/null
-/* ====================================================================
- 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.usermodel.contrib;
-
-
-import org.apache.poi.hssf.usermodel.HSSFCell;
-import org.apache.poi.hssf.usermodel.HSSFCellStyle;
-import org.apache.poi.hssf.usermodel.HSSFFont;
-import org.apache.poi.hssf.usermodel.HSSFRow;
-import org.apache.poi.hssf.usermodel.HSSFSheet;
-import org.apache.poi.hssf.usermodel.HSSFWorkbook;
-import org.apache.poi.ss.usermodel.contrib.CellUtil;
-
-/**
- * Various utility functions that make working with a cells and rows easier. The various
- * methods that deal with style's allow you to create your HSSFCellStyles as you need them.
- * When you apply a style change to a cell, the code will attempt to see if a style already
- * exists that meets your needs. If not, then it will create a new style. This is to prevent
- * creating too many styles. there is an upper limit in Excel on the number of styles that
- * can be supported.
- *
- *@author Eric Pugh epugh@upstate.com
- */
-public final class HSSFCellUtil {
-
- private HSSFCellUtil() {
- // no instances of this class
- }
-
- /**
- * Get a row from the spreadsheet, and create it if it doesn't exist.
- *
- *@param rowIndex The 0 based row number
- *@param sheet The sheet that the row is part of.
- *@return The row indicated by the rowCounter
- */
- public static HSSFRow getRow(int rowIndex, HSSFSheet sheet) {
- return (HSSFRow) CellUtil.getRow(rowIndex, sheet);
- }
-
- /**
- * Get a specific cell from a row. If the cell doesn't exist,
- * then create it.
- *
- *@param row The row that the cell is part of
- *@param columnIndex The column index that the cell is in.
- *@return The cell indicated by the column.
- */
- public static HSSFCell getCell(HSSFRow row, int columnIndex) {
- return (HSSFCell) CellUtil.getCell(row, columnIndex);
- }
-
- /**
- * Creates a cell, gives it a value, and applies a style if provided
- *
- * @param row the row to create the cell in
- * @param column the column index to create the cell in
- * @param value The value of the cell
- * @param style If the style is not null, then set
- * @return A new HSSFCell
- */
- public static HSSFCell createCell(HSSFRow row, int column, String value, HSSFCellStyle style) {
- return (HSSFCell) CellUtil.createCell(row, column, value, style);
- }
-
- /**
- * Create a cell, and give it a value.
- *
- *@param row the row to create the cell in
- *@param column the column index to create the cell in
- *@param value The value of the cell
- *@return A new HSSFCell.
- */
- public static HSSFCell createCell(HSSFRow row, int column, String value) {
- return createCell( row, column, value, null );
- }
-
- /**
- * Take a cell, and align it.
- *
- *@param cell the cell to set the alignment for
- *@param workbook The workbook that is being worked with.
- *@param align the column alignment to use.
- *
- * @see HSSFCellStyle for alignment options
- */
- public static void setAlignment(HSSFCell cell, HSSFWorkbook workbook, short align) {
- CellUtil.setAlignment(cell, workbook, align);
- }
-
- /**
- * Take a cell, and apply a font to it
- *
- *@param cell the cell to set the alignment for
- *@param workbook The workbook that is being worked with.
- *@param font The HSSFFont that you want to set...
- */
- public static void setFont(HSSFCell cell, HSSFWorkbook workbook, HSSFFont font) {
- CellUtil.setFont(cell, workbook, font);
- }
-
- /**
- * This method attempt to find an already existing HSSFCellStyle that matches
- * what you want the style to be. If it does not find the style, then it
- * creates a new one. If it does create a new one, then it applies the
- * propertyName and propertyValue to the style. This is necessary because
- * Excel has an upper limit on the number of Styles that it supports.
- *
- *@param workbook The workbook that is being worked with.
- *@param propertyName The name of the property that is to be
- * changed.
- *@param propertyValue The value of the property that is to be
- * changed.
- *@param cell The cell that needs it's style changes
- */
- public static void setCellStyleProperty(HSSFCell cell, HSSFWorkbook workbook,
- String propertyName, Object propertyValue) {
- CellUtil.setCellStyleProperty(cell, workbook, propertyName, propertyValue);
- }
-
- /**
- * Looks for text in the cell that should be unicode, like α and provides the
- * unicode version of it.
- *
- *@param cell The cell to check for unicode values
- *@return translated to unicode
- */
- public static HSSFCell translateUnicodeValues(HSSFCell cell){
- CellUtil.translateUnicodeValues(cell);
- return cell;
- }
-}
+++ /dev/null
-/* ====================================================================
- 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.usermodel.contrib;
-
-import org.apache.poi.hssf.usermodel.HSSFSheet;
-import org.apache.poi.hssf.usermodel.HSSFWorkbook;
-import org.apache.poi.ss.usermodel.contrib.RegionUtil;
-import org.apache.poi.ss.util.CellRangeAddress;
-import org.apache.poi.ss.util.Region;
-
-/**
- * Various utility functions that make working with a region of cells easier.
- *
- * @author Eric Pugh epugh@upstate.com
- */
-public final class HSSFRegionUtil {
-
- private HSSFRegionUtil() {
- // no instances of this class
- }
-
- private static CellRangeAddress toCRA(Region region) {
- return Region.convertToCellRangeAddress(region);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setBorderLeft(short border, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setBorderLeft(border, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the left border for a region of cells by manipulating the cell style
- * of the individual cells on the left
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderLeft(int border, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setBorderLeft(border, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setLeftBorderColor(short color, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setLeftBorderColor(color, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the leftBorderColor attribute of the HSSFRegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setLeftBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setLeftBorderColor(color, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setBorderRight(short border, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setBorderRight(border, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the borderRight attribute of the HSSFRegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderRight(int border, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setBorderRight(border, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setRightBorderColor(short color, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setRightBorderColor(color, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the rightBorderColor attribute of the HSSFRegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setRightBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setRightBorderColor(color, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setBorderBottom(short border, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setBorderBottom(border, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the borderBottom attribute of the HSSFRegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderBottom(int border, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setBorderBottom(border, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setBottomBorderColor(short color, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setBottomBorderColor(color, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the bottomBorderColor attribute of the HSSFRegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBottomBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setBottomBorderColor(color, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setBorderTop(short border, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setBorderTop(border, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the borderBottom attribute of the HSSFRegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderTop(int border, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setBorderTop(border, region, sheet, workbook);
- }
-
- /**
- * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
- */
- public static void setTopBorderColor(short color, Region region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- setTopBorderColor(color, toCRA(region), sheet, workbook);
- }
- /**
- * Sets the topBorderColor attribute of the HSSFRegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setTopBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
- HSSFWorkbook workbook) {
- RegionUtil.setTopBorderColor(color, region, sheet, workbook);
- }
-}
+++ /dev/null
-/* ====================================================================
- 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.usermodel.contrib;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.poi.ss.usermodel.Cell;
-import org.apache.poi.ss.usermodel.CellStyle;
-import org.apache.poi.ss.usermodel.Font;
-import org.apache.poi.ss.usermodel.Row;
-import org.apache.poi.ss.usermodel.Sheet;
-import org.apache.poi.ss.usermodel.Workbook;
-
-/**
- * Various utility functions that make working with a cells and rows easier. The various methods
- * that deal with style's allow you to create your CellStyles as you need them. When you apply a
- * style change to a cell, the code will attempt to see if a style already exists that meets your
- * needs. If not, then it will create a new style. This is to prevent creating too many styles.
- * there is an upper limit in Excel on the number of styles that can be supported.
- *
- *@author Eric Pugh epugh@upstate.com
- *@author (secondary) Avinash Kewalramani akewalramani@accelrys.com
- */
-public final class CellUtil {
-
- public static final String ALIGNMENT = "alignment";
- public static final String BORDER_BOTTOM = "borderBottom";
- public static final String BORDER_LEFT = "borderLeft";
- public static final String BORDER_RIGHT = "borderRight";
- public static final String BORDER_TOP = "borderTop";
- public static final String BOTTOM_BORDER_COLOR = "bottomBorderColor";
- public static final String DATA_FORMAT = "dataFormat";
- public static final String FILL_BACKGROUND_COLOR = "fillBackgroundColor";
- public static final String FILL_FOREGROUND_COLOR = "fillForegroundColor";
- public static final String FILL_PATTERN = "fillPattern";
- public static final String FONT = "font";
- public static final String HIDDEN = "hidden";
- public static final String INDENTION = "indention";
- public static final String LEFT_BORDER_COLOR = "leftBorderColor";
- public static final String LOCKED = "locked";
- public static final String RIGHT_BORDER_COLOR = "rightBorderColor";
- public static final String ROTATION = "rotation";
- public static final String TOP_BORDER_COLOR = "topBorderColor";
- public static final String VERTICAL_ALIGNMENT = "verticalAlignment";
- public static final String WRAP_TEXT = "wrapText";
-
- private static UnicodeMapping unicodeMappings[];
-
- private static final class UnicodeMapping {
-
- public final String entityName;
- public final String resolvedValue;
-
- public UnicodeMapping(String pEntityName, String pResolvedValue) {
- entityName = "&" + pEntityName + ";";
- resolvedValue = pResolvedValue;
- }
- }
-
- private CellUtil() {
- // no instances of this class
- }
-
- /**
- * Get a row from the spreadsheet, and create it if it doesn't exist.
- *
- *@param rowIndex The 0 based row number
- *@param sheet The sheet that the row is part of.
- *@return The row indicated by the rowCounter
- */
- public static Row getRow(int rowIndex, Sheet sheet) {
- Row row = sheet.getRow(rowIndex);
- if (row == null) {
- row = sheet.createRow(rowIndex);
- }
- return row;
- }
-
-
- /**
- * Get a specific cell from a row. If the cell doesn't exist, then create it.
- *
- *@param row The row that the cell is part of
- *@param columnIndex The column index that the cell is in.
- *@return The cell indicated by the column.
- */
- public static Cell getCell(Row row, int columnIndex) {
- Cell cell = row.getCell(columnIndex);
-
- if (cell == null) {
- cell = row.createCell(columnIndex);
- }
- return cell;
- }
-
-
- /**
- * Creates a cell, gives it a value, and applies a style if provided
- *
- * @param row the row to create the cell in
- * @param column the column index to create the cell in
- * @param value The value of the cell
- * @param style If the style is not null, then set
- * @return A new Cell
- */
- public static Cell createCell(Row row, int column, String value, CellStyle style) {
- Cell cell = getCell(row, column);
-
- cell.setCellValue(cell.getRow().getSheet().getWorkbook().getCreationHelper()
- .createRichTextString(value));
- if (style != null) {
- cell.setCellStyle(style);
- }
- return cell;
- }
-
-
- /**
- * Create a cell, and give it a value.
- *
- *@param row the row to create the cell in
- *@param column the column index to create the cell in
- *@param value The value of the cell
- *@return A new Cell.
- */
- public static Cell createCell(Row row, int column, String value) {
- return createCell(row, column, value, null);
- }
-
-
- /**
- * Take a cell, and align it.
- *
- *@param cell the cell to set the alignment for
- *@param workbook The workbook that is being worked with.
- *@param align the column alignment to use.
- *
- * @see CellStyle for alignment options
- */
- public static void setAlignment(Cell cell, Workbook workbook, short align) {
- setCellStyleProperty(cell, workbook, ALIGNMENT, Short.valueOf(align));
- }
-
- /**
- * Take a cell, and apply a font to it
- *
- *@param cell the cell to set the alignment for
- *@param workbook The workbook that is being worked with.
- *@param font The Font that you want to set...
- */
- public static void setFont(Cell cell, Workbook workbook, Font font) {
- setCellStyleProperty(cell, workbook, FONT, font.getIndex());
- }
-
- /**
- * This method attempt to find an already existing CellStyle that matches what you want the
- * style to be. If it does not find the style, then it creates a new one. If it does create a
- * new one, then it applies the propertyName and propertyValue to the style. This is necessary
- * because Excel has an upper limit on the number of Styles that it supports.
- *
- *@param workbook The workbook that is being worked with.
- *@param propertyName The name of the property that is to be changed.
- *@param propertyValue The value of the property that is to be changed.
- *@param cell The cell that needs it's style changes
- */
- public static void setCellStyleProperty(Cell cell, Workbook workbook, String propertyName,
- Object propertyValue) {
- CellStyle originalStyle = cell.getCellStyle();
- CellStyle newStyle = null;
- Map<String, Object> values = getFormatProperties(originalStyle);
- values.put(propertyName, propertyValue);
-
- // index seems like what index the cellstyle is in the list of styles for a workbook.
- // not good to compare on!
- short numberCellStyles = workbook.getNumCellStyles();
-
- for (short i = 0; i < numberCellStyles; i++) {
- CellStyle wbStyle = workbook.getCellStyleAt(i);
- Map<String, Object> wbStyleMap = getFormatProperties(wbStyle);
-
- if (wbStyleMap.equals(values)) {
- newStyle = wbStyle;
- break;
- }
- }
-
- if (newStyle == null) {
- newStyle = workbook.createCellStyle();
- setFormatProperties(newStyle, workbook, values);
- }
-
- cell.setCellStyle(newStyle);
- }
-
- /**
- * Returns a map containing the format properties of the given cell style.
- *
- * @param style cell style
- * @return map of format properties (String -> Object)
- * @see #setFormatProperties(CellStyle, Map)
- */
- private static Map<String, Object> getFormatProperties(CellStyle style) {
- Map<String, Object> properties = new HashMap<String, Object>();
- putShort(properties, ALIGNMENT, style.getAlignment());
- putShort(properties, BORDER_BOTTOM, style.getBorderBottom());
- putShort(properties, BORDER_LEFT, style.getBorderLeft());
- putShort(properties, BORDER_RIGHT, style.getBorderRight());
- putShort(properties, BORDER_TOP, style.getBorderTop());
- putShort(properties, BOTTOM_BORDER_COLOR, style.getBottomBorderColor());
- putShort(properties, DATA_FORMAT, style.getDataFormat());
- putShort(properties, FILL_BACKGROUND_COLOR, style.getFillBackgroundColor());
- putShort(properties, FILL_FOREGROUND_COLOR, style.getFillForegroundColor());
- putShort(properties, FILL_PATTERN, style.getFillPattern());
- putShort(properties, FONT, style.getFontIndex());
- putBoolean(properties, HIDDEN, style.getHidden());
- putShort(properties, INDENTION, style.getIndention());
- putShort(properties, LEFT_BORDER_COLOR, style.getLeftBorderColor());
- putBoolean(properties, LOCKED, style.getLocked());
- putShort(properties, RIGHT_BORDER_COLOR, style.getRightBorderColor());
- putShort(properties, ROTATION, style.getRotation());
- putShort(properties, TOP_BORDER_COLOR, style.getTopBorderColor());
- putShort(properties, VERTICAL_ALIGNMENT, style.getVerticalAlignment());
- putBoolean(properties, WRAP_TEXT, style.getWrapText());
- return properties;
- }
-
- /**
- * Sets the format properties of the given style based on the given map.
- *
- * @param style cell style
- * @param workbook parent workbook
- * @param properties map of format properties (String -> Object)
- * @see #getFormatProperties(CellStyle)
- */
- private static void setFormatProperties(CellStyle style, Workbook workbook, Map<String, Object> properties) {
- style.setAlignment(getShort(properties, ALIGNMENT));
- style.setBorderBottom(getShort(properties, BORDER_BOTTOM));
- style.setBorderLeft(getShort(properties, BORDER_LEFT));
- style.setBorderRight(getShort(properties, BORDER_RIGHT));
- style.setBorderTop(getShort(properties, BORDER_TOP));
- style.setBottomBorderColor(getShort(properties, BOTTOM_BORDER_COLOR));
- style.setDataFormat(getShort(properties, DATA_FORMAT));
- style.setFillBackgroundColor(getShort(properties, FILL_BACKGROUND_COLOR));
- style.setFillForegroundColor(getShort(properties, FILL_FOREGROUND_COLOR));
- style.setFillPattern(getShort(properties, FILL_PATTERN));
- style.setFont(workbook.getFontAt(getShort(properties, FONT)));
- style.setHidden(getBoolean(properties, HIDDEN));
- style.setIndention(getShort(properties, INDENTION));
- style.setLeftBorderColor(getShort(properties, LEFT_BORDER_COLOR));
- style.setLocked(getBoolean(properties, LOCKED));
- style.setRightBorderColor(getShort(properties, RIGHT_BORDER_COLOR));
- style.setRotation(getShort(properties, ROTATION));
- style.setTopBorderColor(getShort(properties, TOP_BORDER_COLOR));
- style.setVerticalAlignment(getShort(properties, VERTICAL_ALIGNMENT));
- style.setWrapText(getBoolean(properties, WRAP_TEXT));
- }
-
- /**
- * Utility method that returns the named short value form the given map.
- * @return zero if the property does not exist, or is not a {@link Short}.
- *
- * @param properties map of named properties (String -> Object)
- * @param name property name
- * @return property value, or zero
- */
- private static short getShort(Map<String, Object> properties, String name) {
- Object value = properties.get(name);
- if (value instanceof Short) {
- return ((Short) value).shortValue();
- }
- return 0;
- }
-
- /**
- * Utility method that returns the named boolean value form the given map.
- * @return false if the property does not exist, or is not a {@link Boolean}.
- *
- * @param properties map of properties (String -> Object)
- * @param name property name
- * @return property value, or false
- */
- private static boolean getBoolean(Map<String, Object> properties, String name) {
- Object value = properties.get(name);
- if (value instanceof Boolean) {
- return ((Boolean) value).booleanValue();
- }
- return false;
- }
-
- /**
- * Utility method that puts the named short value to the given map.
- *
- * @param properties map of properties (String -> Object)
- * @param name property name
- * @param value property value
- */
- private static void putShort(Map<String, Object> properties, String name, short value) {
- properties.put(name, Short.valueOf(value));
- }
-
- /**
- * Utility method that puts the named boolean value to the given map.
- *
- * @param properties map of properties (String -> Object)
- * @param name property name
- * @param value property value
- */
- private static void putBoolean(Map<String, Object> properties, String name, boolean value) {
- properties.put(name, Boolean.valueOf(value));
- }
-
- /**
- * Looks for text in the cell that should be unicode, like α and provides the
- * unicode version of it.
- *
- *@param cell The cell to check for unicode values
- *@return translated to unicode
- */
- public static Cell translateUnicodeValues(Cell cell) {
-
- String s = cell.getRichStringCellValue().getString();
- boolean foundUnicode = false;
- String lowerCaseStr = s.toLowerCase();
-
- for (int i = 0; i < unicodeMappings.length; i++) {
- UnicodeMapping entry = unicodeMappings[i];
- String key = entry.entityName;
- if (lowerCaseStr.indexOf(key) != -1) {
- s = s.replaceAll(key, entry.resolvedValue);
- foundUnicode = true;
- }
- }
- if (foundUnicode) {
- cell.setCellValue(cell.getRow().getSheet().getWorkbook().getCreationHelper()
- .createRichTextString(s));
- }
- return cell;
- }
-
- static {
- unicodeMappings = new UnicodeMapping[] {
- um("alpha", "\u03B1" ),
- um("beta", "\u03B2" ),
- um("gamma", "\u03B3" ),
- um("delta", "\u03B4" ),
- um("epsilon", "\u03B5" ),
- um("zeta", "\u03B6" ),
- um("eta", "\u03B7" ),
- um("theta", "\u03B8" ),
- um("iota", "\u03B9" ),
- um("kappa", "\u03BA" ),
- um("lambda", "\u03BB" ),
- um("mu", "\u03BC" ),
- um("nu", "\u03BD" ),
- um("xi", "\u03BE" ),
- um("omicron", "\u03BF" ),
- };
- }
-
- private static UnicodeMapping um(String entityName, String resolvedValue) {
- return new UnicodeMapping(entityName, resolvedValue);
- }
-}
+++ /dev/null
-/* ====================================================================
- 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.usermodel.contrib;
-
-import org.apache.poi.ss.usermodel.Cell;
-import org.apache.poi.ss.usermodel.Row;
-import org.apache.poi.ss.usermodel.Sheet;
-import org.apache.poi.ss.usermodel.Workbook;
-import org.apache.poi.ss.util.CellRangeAddress;
-
-/**
- * Various utility functions that make working with a region of cells easier.
- *
- * @author Eric Pugh epugh@upstate.com
- * @author (secondary) Avinash Kewalramani akewalramani@accelrys.com
- */
-public final class RegionUtil {
-
- private RegionUtil() {
- // no instances of this class
- }
-
- /**
- * For setting the same property on many cells to the same value
- */
- private static final class CellPropertySetter {
-
- private final Workbook _workbook;
- private final String _propertyName;
- private final Short _propertyValue;
-
-
- public CellPropertySetter(Workbook workbook, String propertyName, int value) {
- _workbook = workbook;
- _propertyName = propertyName;
- _propertyValue = Short.valueOf((short) value);
- }
-
-
- public void setProperty(Row row, int column) {
- Cell cell = CellUtil.getCell(row, column);
- CellUtil.setCellStyleProperty(cell, _workbook, _propertyName, _propertyValue);
- }
- }
-
- /**
- * Sets the left border for a region of cells by manipulating the cell style of the individual
- * cells on the left
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderLeft(int border, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int rowStart = region.getFirstRow();
- int rowEnd = region.getLastRow();
- int column = region.getFirstColumn();
-
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_LEFT, border);
- for (int i = rowStart; i <= rowEnd; i++) {
- cps.setProperty(CellUtil.getRow(i, sheet), column);
- }
- }
-
- /**
- * Sets the leftBorderColor attribute of the RegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setLeftBorderColor(int color, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int rowStart = region.getFirstRow();
- int rowEnd = region.getLastRow();
- int column = region.getFirstColumn();
-
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.LEFT_BORDER_COLOR,
- color);
- for (int i = rowStart; i <= rowEnd; i++) {
- cps.setProperty(CellUtil.getRow(i, sheet), column);
- }
- }
-
- /**
- * Sets the borderRight attribute of the RegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderRight(int border, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int rowStart = region.getFirstRow();
- int rowEnd = region.getLastRow();
- int column = region.getLastColumn();
-
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_RIGHT, border);
- for (int i = rowStart; i <= rowEnd; i++) {
- cps.setProperty(CellUtil.getRow(i, sheet), column);
- }
- }
-
- /**
- * Sets the rightBorderColor attribute of the RegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setRightBorderColor(int color, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int rowStart = region.getFirstRow();
- int rowEnd = region.getLastRow();
- int column = region.getLastColumn();
-
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.RIGHT_BORDER_COLOR,
- color);
- for (int i = rowStart; i <= rowEnd; i++) {
- cps.setProperty(CellUtil.getRow(i, sheet), column);
- }
- }
-
- /**
- * Sets the borderBottom attribute of the RegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderBottom(int border, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int colStart = region.getFirstColumn();
- int colEnd = region.getLastColumn();
- int rowIndex = region.getLastRow();
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_BOTTOM, border);
- Row row = CellUtil.getRow(rowIndex, sheet);
- for (int i = colStart; i <= colEnd; i++) {
- cps.setProperty(row, i);
- }
- }
-
- /**
- * Sets the bottomBorderColor attribute of the RegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBottomBorderColor(int color, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int colStart = region.getFirstColumn();
- int colEnd = region.getLastColumn();
- int rowIndex = region.getLastRow();
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BOTTOM_BORDER_COLOR,
- color);
- Row row = CellUtil.getRow(rowIndex, sheet);
- for (int i = colStart; i <= colEnd; i++) {
- cps.setProperty(row, i);
- }
- }
-
- /**
- * Sets the borderBottom attribute of the RegionUtil object
- *
- * @param border The new border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setBorderTop(int border, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int colStart = region.getFirstColumn();
- int colEnd = region.getLastColumn();
- int rowIndex = region.getFirstRow();
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_TOP, border);
- Row row = CellUtil.getRow(rowIndex, sheet);
- for (int i = colStart; i <= colEnd; i++) {
- cps.setProperty(row, i);
- }
- }
-
- /**
- * Sets the topBorderColor attribute of the RegionUtil object
- *
- * @param color The color of the border
- * @param region The region that should have the border
- * @param workbook The workbook that the region is on.
- * @param sheet The sheet that the region is on.
- */
- public static void setTopBorderColor(int color, CellRangeAddress region, Sheet sheet,
- Workbook workbook) {
- int colStart = region.getFirstColumn();
- int colEnd = region.getLastColumn();
- int rowIndex = region.getFirstRow();
- CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.TOP_BORDER_COLOR, color);
- Row row = CellUtil.getRow(rowIndex, sheet);
- for (int i = colStart; i <= colEnd; i++) {
- cps.setProperty(row, i);
- }
- }
-}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
+
+import org.apache.poi.hpsf.ClassID;
+
+
+
+/**
+ * <p>Provides utility methods for encoding and decoding hexadecimal
+ * data.</p>
+ *
+ * @author Rainer Klute (klute@rainer-klute.de) - with portions from Tomcat
+ */
+public class Codec
+{
+
+ /**
+ * <p>The nibbles' hexadecimal values. A nibble is a half byte.</p>
+ */
+ protected static final byte hexval[] =
+ {(byte) '0', (byte) '1', (byte) '2', (byte) '3',
+ (byte) '4', (byte) '5', (byte) '6', (byte) '7',
+ (byte) '8', (byte) '9', (byte) 'A', (byte) 'B',
+ (byte) 'C', (byte) 'D', (byte) 'E', (byte) 'F'};
+
+
+
+ /**
+ * <p>Converts a string into its hexadecimal notation.</p>
+ */
+ public static String hexEncode(final String s)
+ {
+ return hexEncode(s.getBytes());
+ }
+
+
+
+ /**
+ * <p>Converts a byte array into its hexadecimal notation.</p>
+ */
+ public static String hexEncode(final byte[] s)
+ {
+ return hexEncode(s, 0, s.length);
+ }
+
+
+
+ /**
+ * <p>Converts a part of a byte array into its hexadecimal
+ * notation.</p>
+ */
+ public static String hexEncode(final byte[] s, final int offset,
+ final int length)
+ {
+ StringBuffer b = new StringBuffer(length * 2);
+ for (int i = offset; i < offset + length; i++)
+ {
+ int c = s[i];
+ b.append((char) hexval[(c & 0xF0) >> 4]);
+ b.append((char) hexval[(c & 0x0F) >> 0]);
+ }
+ return b.toString();
+ }
+
+
+
+ /**
+ * <p>Converts a single byte into its hexadecimal notation.</p>
+ */
+ public static String hexEncode(final byte b)
+ {
+ StringBuffer sb = new StringBuffer(2);
+ sb.append((char) hexval[(b & 0xF0) >> 4]);
+ sb.append((char) hexval[(b & 0x0F) >> 0]);
+ return sb.toString();
+ }
+
+
+
+ /**
+ * <p>Converts a short value (16-bit) into its hexadecimal
+ * notation.</p>
+ */
+ public static String hexEncode(final short s)
+ {
+ StringBuffer sb = new StringBuffer(4);
+ sb.append((char) hexval[(s & 0xF000) >> 12]);
+ sb.append((char) hexval[(s & 0x0F00) >> 8]);
+ sb.append((char) hexval[(s & 0x00F0) >> 4]);
+ sb.append((char) hexval[(s & 0x000F) >> 0]);
+ return sb.toString();
+ }
+
+
+
+ /**
+ * <p>Converts an int value (32-bit) into its hexadecimal
+ * notation.</p>
+ */
+ public static String hexEncode(final int i)
+ {
+ StringBuffer sb = new StringBuffer(8);
+ sb.append((char) hexval[(i & 0xF0000000) >> 28]);
+ sb.append((char) hexval[(i & 0x0F000000) >> 24]);
+ sb.append((char) hexval[(i & 0x00F00000) >> 20]);
+ sb.append((char) hexval[(i & 0x000F0000) >> 16]);
+ sb.append((char) hexval[(i & 0x0000F000) >> 12]);
+ sb.append((char) hexval[(i & 0x00000F00) >> 8]);
+ sb.append((char) hexval[(i & 0x000000F0) >> 4]);
+ sb.append((char) hexval[(i & 0x0000000F) >> 0]);
+ return sb.toString();
+ }
+
+
+
+ /**
+ * <p>Converts a long value (64-bit) into its hexadecimal
+ * notation.</p>
+ */
+ public static String hexEncode(final long l)
+ {
+ StringBuffer sb = new StringBuffer(16);
+ sb.append(hexEncode((int) (l & 0xFFFFFFFF00000000L) >> 32));
+ sb.append(hexEncode((int) (l & 0x00000000FFFFFFFFL) >> 0));
+ return sb.toString();
+ }
+
+
+
+ /**
+ * <p>Converts a class ID into its hexadecimal notation.</p>
+ */
+ public static String hexEncode(final ClassID classID)
+ {
+ return hexEncode(classID.getBytes());
+ }
+
+
+
+ /**
+ * <p>Decodes the hexadecimal representation of a sequence of
+ * bytes into a byte array. Each character in the string
+ * represents a nibble (half byte) and must be one of the
+ * characters '0'-'9', 'A'-'F' or 'a'-'f'.</p>
+ *
+ * @param s The string to be decoded
+ *
+ * @return The bytes
+ *
+ * @throws IllegalArgumentException if the string does not contain
+ * a valid representation of a byte sequence.
+ */
+ public static byte[] hexDecode(final String s)
+ {
+ final int length = s.length();
+
+ /* The string to be converted must have an even number of
+ characters. */
+ if (length % 2 == 1)
+ throw new IllegalArgumentException
+ ("String has odd length " + length);
+ byte[] b = new byte[length / 2];
+ char[] c = new char[length];
+ s.toUpperCase().getChars(0, length, c, 0);
+ for (int i = 0; i < length; i += 2)
+ b[i/2] = (byte) (decodeNibble(c[i]) << 4 & 0xF0 |
+ decodeNibble(c[i+1]) & 0x0F);
+ return b;
+ }
+
+
+
+ /**
+ * <p>Decodes a nibble.</p>
+ *
+ * @param c A character in the range '0'-'9' or 'A'-'F'. Lower
+ * case is not supported here.
+ *
+ * @return The decoded nibble in the range 0-15
+ *
+ * @throws IllegalArgumentException if <em>c</em> is not a
+ * permitted character
+ */
+ protected static byte decodeNibble(final char c)
+ {
+ for (byte i = 0; i < hexval.length; i++)
+ if ((byte) c == hexval[i])
+ return i;
+ throw new IllegalArgumentException("\"" + c + "\"" +
+ " does not represent a nibble.");
+ }
+
+
+
+ /**
+ * <p>For testing.</p>
+ */
+ public static void main(final String args[])
+ throws IOException
+ {
+ final BufferedReader in =
+ new BufferedReader(new InputStreamReader(System.in));
+ String s;
+ do
+ {
+ s = in.readLine();
+ if (s != null)
+ {
+ String bytes = hexEncode(s);
+ System.out.print("Hex encoded (String): ");
+ System.out.println(bytes);
+ System.out.print("Hex encoded (byte[]): ");
+ System.out.println(hexEncode(s.getBytes()));
+ System.out.print("Re-decoded (byte[]): ");
+ System.out.println(new String(hexDecode(bytes)));
+ }
+ }
+ while (s != null);
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.io.*;
+import org.apache.poi.poifs.filesystem.*;
+
+/**
+ * <p>Describes the most important (whatever that is) features of a
+ * {@link POIFSDocument}.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class DocumentDescriptor
+{
+ String name;
+ POIFSDocumentPath path;
+ DocumentInputStream stream;
+
+ int size;
+ byte[] bytes;
+
+
+ /**
+ * <p>Creates a {@link DocumentDescriptor}.</p>
+ *
+ * @param name The stream's name.
+ *
+ * @param path The stream's path in the POI filesystem hierarchy.
+ *
+ * @param stream The stream.
+ *
+ * @param nrOfBytes The maximum number of bytes to display in a
+ * dump starting at the beginning of the stream.
+ */
+ public DocumentDescriptor(final String name,
+ final POIFSDocumentPath path,
+ final DocumentInputStream stream,
+ final int nrOfBytes)
+ {
+ this.name = name;
+ this.path = path;
+ this.stream = stream;
+ try
+ {
+ size = stream.available();
+ if (stream.markSupported())
+ {
+ stream.mark(nrOfBytes);
+ final byte[] b = new byte[nrOfBytes];
+ final int read = stream.read(b, 0, Math.min(size, b.length));
+ bytes = new byte[read];
+ System.arraycopy(b, 0, bytes, 0, read);
+ stream.reset();
+ }
+ }
+ catch (IOException ex)
+ {
+ System.out.println(ex);
+ }
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.awt.*;
+import javax.swing.*;
+import javax.swing.tree.*;
+
+/**
+ * <p>{@link TreeCellRenderer} for a {@link DocumentDescriptor}. The
+ * renderer is extremly rudimentary since displays only the document's
+ * name, its size and its fist few bytes.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class DocumentDescriptorRenderer extends DefaultTreeCellRenderer
+{
+
+ public Component getTreeCellRendererComponent(final JTree tree,
+ final Object value,
+ final boolean selected,
+ final boolean expanded,
+ final boolean leaf,
+ final int row,
+ final boolean hasFocus)
+ {
+ final DocumentDescriptor d = (DocumentDescriptor)
+ ((DefaultMutableTreeNode) value).getUserObject();
+ final JPanel p = new JPanel();
+ final JTextArea text = new JTextArea();
+ text.append(renderAsString(d));
+ text.setFont(new Font("Monospaced", Font.PLAIN, 10));
+ p.add(text);
+ if (selected)
+ Util.invert(text);
+ return p;
+ }
+
+
+ /**
+ * <p>Renders {@link DocumentDescriptor} as a string.</p>
+ */
+ protected String renderAsString(final DocumentDescriptor d)
+ {
+ final StringBuffer b = new StringBuffer();
+ b.append("Name: ");
+ b.append(d.name);
+ b.append(" (");
+ b.append(Codec.hexEncode(d.name));
+ b.append(") \n");
+
+ b.append("Size: ");
+ b.append(d.size);
+ b.append(" bytes\n");
+
+ b.append("First bytes: ");
+ b.append(Codec.hexEncode(d.bytes));
+
+ return b.toString();
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.awt.*;
+import javax.swing.*;
+import javax.swing.tree.*;
+import java.util.*;
+
+/**
+ * <p>This is a {@link TreeCellRenderer} implementation which is able
+ * to render arbitrary objects. The {@link ExtendableTreeCellRenderer}
+ * does not do the rendering itself but instead dispatches to
+ * class-specific renderers. A class/renderer pair must be registered
+ * using the {@link #register} method. If a class has no registered
+ * renderer, the renderer of its closest superclass is used. Since the
+ * {@link ExtendableTreeCellRenderer} always has a default renderer
+ * for the {@link Object} class, rendering is always possible. The
+ * default {@link Object} renderer can be replaced by another renderer
+ * but it cannot be unregistered.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class ExtendableTreeCellRenderer implements TreeCellRenderer
+{
+
+ /**
+ * <p>Maps classes to renderers.</p>
+ */
+ protected Map renderers;
+
+
+
+ public ExtendableTreeCellRenderer()
+ {
+ renderers = new HashMap();
+ register(Object.class, new DefaultTreeCellRenderer()
+ {
+ public Component getTreeCellRendererComponent
+ (JTree tree, Object value, boolean selected,
+ boolean expanded, boolean leaf, int row, boolean hasFocus)
+ {
+ final String s = value.toString();
+ final JLabel l = new JLabel(s + " ");
+ if (selected)
+ {
+ Util.invert(l);
+ l.setOpaque(true);
+ }
+ return l;
+ }
+ });
+ }
+
+
+
+ /**
+ * <p>Registers a renderer for a class.</p>
+ **/
+ public void register(final Class c, final TreeCellRenderer renderer)
+ {
+ renderers.put(c, renderer);
+ }
+
+
+
+ /**
+ * <p>Unregisters a renderer for a class. The renderer for the
+ * {@link Object} class cannot be unregistered.</p>
+ */
+ public void unregister(final Class c)
+ {
+ if (c == Object.class)
+ throw new IllegalArgumentException
+ ("Renderer for Object cannot be unregistered.");
+ renderers.put(c, null);
+ }
+
+
+
+ /**
+ * <p>Renders an object in a tree cell depending of the object's
+ * class.</p>
+ *
+ * @see TreeCellRenderer#getTreeCellRendererComponent
+ */
+ public Component getTreeCellRendererComponent
+ (final JTree tree, final Object value, final boolean selected,
+ final boolean expanded, final boolean leaf, final int row,
+ final boolean hasFocus)
+ {
+ final String NULL = "null";
+ TreeCellRenderer r;
+ Object userObject;
+ if (value == null)
+ userObject = NULL;
+ else
+ {
+ userObject = ((DefaultMutableTreeNode) value).getUserObject();
+ if (userObject == null)
+ userObject = NULL;
+ }
+ r = findRenderer(userObject.getClass());
+ return r.getTreeCellRendererComponent
+ (tree, value, selected, expanded, leaf, row,
+ hasFocus);
+ }
+
+
+
+ /**
+ * <p>Find the renderer for the specified class.</p>
+ */
+ protected TreeCellRenderer findRenderer(final Class c)
+ {
+ final TreeCellRenderer r = (TreeCellRenderer) renderers.get(c);
+ if (r != null)
+ /* The class has a renderer. */
+ return r;
+
+ /* The class has no renderer, try the superclass, if any. */
+ final Class superclass = c.getSuperclass();
+ if (superclass != null) {
+ return findRenderer(superclass);
+ }
+ return null;
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.awt.event.WindowAdapter;
+import java.awt.event.WindowEvent;
+import java.io.FileInputStream;
+import java.io.IOException;
+
+import javax.swing.JFrame;
+import javax.swing.JScrollPane;
+import javax.swing.JTree;
+import javax.swing.tree.DefaultMutableTreeNode;
+import javax.swing.tree.DefaultTreeModel;
+import javax.swing.tree.MutableTreeNode;
+
+import org.apache.poi.poifs.eventfilesystem.POIFSReader;
+
+/**
+ * <p>The main class of the POI Browser. It shows the structure of POI
+ * filesystems (Microsoft Office documents) in a {@link
+ * JTree}. Specify their filenames on the command line!</p>
+ *
+ * @see POIFSReader
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class POIBrowser extends JFrame
+{
+
+ /**
+ * <p>The tree's root node must be visible to all methods.</p>
+ */
+ protected MutableTreeNode rootNode;
+
+
+
+ /**
+ * <p>Takes a bunch of file names as command line parameters,
+ * opens each of them as a POI filesystem and displays their
+ * internal structures in a {@link JTree}.</p>
+ */
+ public static void main(String[] args)
+ {
+ new POIBrowser().run(args);
+ }
+
+
+
+ protected void run(String[] args)
+ {
+ addWindowListener(new WindowAdapter()
+ {
+ public void windowClosing(WindowEvent e)
+ {
+ System.exit(0);
+ }
+ });
+
+ /* Create the tree model with a root node. The latter is
+ * invisible but it must be present because a tree model
+ * always needs a root. */
+ rootNode = new DefaultMutableTreeNode("POI Filesystems");
+ DefaultTreeModel treeModel = new DefaultTreeModel(rootNode);
+
+ /* Create the tree UI element. */
+ final JTree treeUI = new JTree(treeModel);
+ getContentPane().add(new JScrollPane(treeUI));
+
+ /* Add the POI filesystems to the tree. */
+ int displayedFiles = 0;
+ for (int i = 0; i < args.length; i++)
+ {
+ final String filename = args[i];
+ try
+ {
+ POIFSReader r = new POIFSReader();
+ r.registerListener(new TreeReaderListener(filename, rootNode));
+ r.read(new FileInputStream(filename));
+ displayedFiles++;
+ }
+ catch (IOException ex)
+ {
+ System.err.println(filename + ": " + ex);
+ }
+ catch (Throwable t)
+ {
+ System.err.println("Unexpected exception while reading \"" +
+ filename + "\":");
+ t.printStackTrace(System.err);
+ }
+ }
+
+ /* Exit if there is no file to display (none specified or only
+ * files with problems). */
+ if (displayedFiles == 0)
+ {
+ System.out.println("No POI filesystem(s) to display.");
+ System.exit(0);
+ }
+
+ /* Make the tree UI element visible. */
+ treeUI.setRootVisible(true);
+ treeUI.setShowsRootHandles(true);
+ ExtendableTreeCellRenderer etcr = new ExtendableTreeCellRenderer();
+ etcr.register(DocumentDescriptor.class,
+ new DocumentDescriptorRenderer());
+ etcr.register(PropertySetDescriptor.class,
+ new PropertySetDescriptorRenderer());
+ treeUI.setCellRenderer(etcr);
+ setSize(600, 450);
+ setTitle("POI Browser 0.09");
+ setVisible(true);
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+
+import org.apache.poi.hpsf.MarkUnsupportedException;
+import org.apache.poi.hpsf.NoPropertySetStreamException;
+import org.apache.poi.hpsf.PropertySet;
+import org.apache.poi.hpsf.PropertySetFactory;
+import org.apache.poi.poifs.filesystem.DocumentInputStream;
+import org.apache.poi.poifs.filesystem.POIFSDocumentPath;
+
+/**
+ * <p>Describes the most important (whatever that is) features of a
+ * stream containing a {@link PropertySet}.</p>
+ *
+ * @author Rainer Klute (klute@rainer-klute.de)
+ */
+public class PropertySetDescriptor extends DocumentDescriptor
+{
+
+ protected PropertySet propertySet;
+
+ /**
+ * <p>Returns this {@link PropertySetDescriptor}'s {@link
+ * PropertySet}.</p>
+ */
+ public PropertySet getPropertySet()
+ {
+ return propertySet;
+ }
+
+
+
+ /**
+ * <p>Creates a {@link PropertySetDescriptor} by reading a {@link
+ * PropertySet} from a {@link DocumentInputStream}.</p>
+ *
+ * @param name The stream's name.
+ *
+ * @param path The stream's path in the POI filesystem hierarchy.
+ *
+ * @param stream The stream.
+ *
+ * @param nrOfBytesToDump The maximum number of bytes to display in a
+ * dump starting at the beginning of the stream.
+ */
+ public PropertySetDescriptor(final String name,
+ final POIFSDocumentPath path,
+ final DocumentInputStream stream,
+ final int nrOfBytesToDump)
+ throws NoPropertySetStreamException,
+ MarkUnsupportedException, UnsupportedEncodingException,
+ IOException
+ {
+ super(name, path, stream, nrOfBytesToDump);
+ propertySet = PropertySetFactory.create(stream);
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.awt.Color;
+import java.awt.Component;
+import java.awt.Font;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.swing.JPanel;
+import javax.swing.JTextArea;
+import javax.swing.JTree;
+import javax.swing.tree.DefaultMutableTreeNode;
+
+import org.apache.poi.hpsf.Property;
+import org.apache.poi.hpsf.PropertySet;
+import org.apache.poi.hpsf.Section;
+import org.apache.poi.hpsf.SummaryInformation;
+
+/**
+ * <p>Renders a {@link PropertySetDescriptor} by more or less dumping
+ * the stuff into a {@link JTextArea}.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class PropertySetDescriptorRenderer extends DocumentDescriptorRenderer
+{
+
+ public Component getTreeCellRendererComponent(final JTree tree,
+ final Object value,
+ final boolean selected,
+ final boolean expanded,
+ final boolean leaf,
+ final int row,
+ final boolean hasFocus)
+ {
+ final PropertySetDescriptor d = (PropertySetDescriptor)
+ ((DefaultMutableTreeNode) value).getUserObject();
+ final PropertySet ps = d.getPropertySet();
+ final JPanel p = new JPanel();
+ final JTextArea text = new JTextArea();
+ text.setBackground(new Color(200, 255, 200));
+ text.setFont(new Font("Monospaced", Font.PLAIN, 10));
+ text.append(renderAsString(d));
+ text.append("\nByte order: " +
+ Codec.hexEncode((short) ps.getByteOrder()));
+ text.append("\nFormat: " +
+ Codec.hexEncode((short) ps.getFormat()));
+ text.append("\nOS version: " +
+ Codec.hexEncode(ps.getOSVersion()));
+ text.append("\nClass ID: " +
+ Codec.hexEncode(ps.getClassID()));
+ text.append("\nSection count: " + ps.getSectionCount());
+ text.append(sectionsToString(ps.getSections()));
+ p.add(text);
+
+ if (ps instanceof SummaryInformation)
+ {
+ /* Use the convenience methods. */
+ final SummaryInformation si = (SummaryInformation) ps;
+ text.append("\n");
+ text.append("\nTitle: " + si.getTitle());
+ text.append("\nSubject: " + si.getSubject());
+ text.append("\nAuthor: " + si.getAuthor());
+ text.append("\nKeywords: " + si.getKeywords());
+ text.append("\nComments: " + si.getComments());
+ text.append("\nTemplate: " + si.getTemplate());
+ text.append("\nLast Author: " + si.getLastAuthor());
+ text.append("\nRev. Number: " + si.getRevNumber());
+ text.append("\nEdit Time: " + si.getEditTime());
+ text.append("\nLast Printed: " + si.getLastPrinted());
+ text.append("\nCreate Date/Time: " + si.getCreateDateTime());
+ text.append("\nLast Save Date/Time: " + si.getLastSaveDateTime());
+ text.append("\nPage Count: " + si.getPageCount());
+ text.append("\nWord Count: " + si.getWordCount());
+ text.append("\nChar Count: " + si.getCharCount());
+ // text.append("\nThumbnail: " + si.getThumbnail());
+ text.append("\nApplication Name: " + si.getApplicationName());
+ text.append("\nSecurity: " + si.getSecurity());
+ }
+
+ if (selected)
+ Util.invert(text);
+ return p;
+ }
+
+
+
+ /**
+ * <p>Returns a string representation of a list of {@link
+ * Section}s.</p>
+ */
+ protected String sectionsToString(final List sections)
+ {
+ final StringBuffer b = new StringBuffer();
+ int count = 1;
+ for (Iterator i = sections.iterator(); i.hasNext();)
+ {
+ Section s = (Section) i.next();
+ String d = toString(s, "Section " + count++);
+ b.append(d);
+ }
+ return b.toString();
+ }
+
+
+
+ /**
+ * <p>Returns a string representation of a {@link Section}.</p>
+ * @param s the section
+ * @param name the section's name
+ * @return a string representation of the {@link Section}
+ */
+ protected String toString(final Section s, final String name)
+ {
+ final StringBuffer b = new StringBuffer();
+ b.append("\n" + name + " Format ID: ");
+ b.append(Codec.hexEncode(s.getFormatID()));
+ b.append("\n" + name + " Offset: " + s.getOffset());
+ b.append("\n" + name + " Section size: " + s.getSize());
+ b.append("\n" + name + " Property count: " + s.getPropertyCount());
+
+ final Property[] properties = s.getProperties();
+ for (int i = 0; i < properties.length; i++)
+ {
+ final Property p = properties[i];
+ final long id = p.getID();
+ final long type = p.getType();
+ final Object value = p.getValue();
+ b.append('\n');
+ b.append(name);
+ b.append(", Name: ");
+ b.append(id);
+ b.append(" (");
+ b.append(s.getPIDString(id));
+ b.append("), Type: ");
+ b.append(type);
+ b.append(", Value: ");
+ if (value instanceof byte[])
+ {
+ byte[] b2 = (byte[]) value;
+ b.append("0x" + Codec.hexEncode(b2, 0, 4));
+ b.append(' ');
+ b.append("0x" + Codec.hexEncode(b2, 4, b2.length - 4));
+ }
+ else if (value != null)
+ b.append(value.toString());
+ else
+ b.append("null");
+ }
+ return b.toString();
+ }
+
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import javax.swing.tree.DefaultMutableTreeNode;
+import javax.swing.tree.MutableTreeNode;
+
+import org.apache.poi.hpsf.HPSFException;
+import org.apache.poi.poifs.eventfilesystem.POIFSReaderEvent;
+import org.apache.poi.poifs.eventfilesystem.POIFSReaderListener;
+import org.apache.poi.poifs.filesystem.DocumentInputStream;
+import org.apache.poi.poifs.filesystem.POIFSDocumentPath;
+
+/**
+ * <p>Organizes document information in a tree model in order to be
+ * e.g. displayed in a Swing {@link javax.swing.JTree}. An instance of this
+ * class is created with a root tree node ({@link MutableTreeNode}) and
+ * registered as a {@link POIFSReaderListener} with a {@link
+ * org.apache.poi.poifs.eventfilesystem.POIFSReader}. While the latter processes
+ * a POI filesystem it calls this class' {@link #processPOIFSReaderEvent} for
+ * each document it has been registered for. This method appends the document it
+ * processes at the appropriate position into the tree rooted at the
+ * above mentioned root tree node.</p>
+ *
+ * <p>The root tree node should be the root tree node of a {@link
+ * javax.swing.tree.TreeModel}.</p>
+ *
+ * <p>A top-level element in the tree model, i.e. an immediate child
+ * node of the root node, describes a POI filesystem as such. It is
+ * suggested to use the file's name (as seen by the operating system)
+ * but it could be any other string.</p>
+ *
+ * <p>The value of a tree node is a {@link DocumentDescriptor}. Unlike
+ * a {@link org.apache.poi.poifs.filesystem.POIFSDocument} which may be as heavy
+ * as many megabytes, an instance of {@link DocumentDescriptor} is a
+ * light-weight object and contains only some meta-information about a
+ * document.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class TreeReaderListener implements POIFSReaderListener
+{
+
+ /**
+ * <p>The tree's root node. POI filesystems get attached to this
+ * node as children.</p>
+ */
+ protected MutableTreeNode rootNode;
+
+ /**
+ * <p>Maps filenames and POI document paths to their associated
+ * tree nodes.</p>
+ */
+ protected Map pathToNode;
+
+ /**
+ * <p>The name of the file this {@link TreeReaderListener}
+ * processes. It is used to identify a top-level element in the
+ * tree. Alternatively any other string can be used. It is just a
+ * label which should identify a POI filesystem.</p>
+ */
+ protected String filename;
+
+
+
+ /**
+ * <p>Creates a {@link TreeReaderListener} which should then be
+ * registered with a
+ * {@link org.apache.poi.poifs.eventfilesystem.POIFSReader}.</p>
+ *
+ * @param filename The name of the POI filesystem, i.e. the name
+ * of the file the POI filesystem resides in. Alternatively any
+ * other string can be used.
+ *
+ * @param rootNode All document information will be attached as
+ * descendands to this tree node.
+ */
+ public TreeReaderListener(final String filename,
+ final MutableTreeNode rootNode)
+ {
+ this.filename = filename;
+ this.rootNode = rootNode;
+ pathToNode = new HashMap(15); // Should be a reasonable guess.
+ }
+
+
+
+ /** <p>The number of bytes to dump.</p> */
+ private int nrOfBytes = 50;
+
+ public void setNrOfBytes(final int nrOfBytes)
+ {
+ this.nrOfBytes = nrOfBytes;
+ }
+
+ public int getNrOfBytes()
+ {
+ return nrOfBytes;
+ }
+
+
+
+ /**
+ * <p>A document in the POI filesystem has been opened for
+ * reading. This method retrieves properties of the document and
+ * adds them to a tree model.</p>
+ */
+ public void processPOIFSReaderEvent(final POIFSReaderEvent event)
+ {
+ DocumentDescriptor d;
+ final DocumentInputStream is = event.getStream();
+ if (!is.markSupported())
+ throw new UnsupportedOperationException(is.getClass().getName() +
+ " does not support mark().");
+
+ /* Try do handle this document as a property set. We receive
+ * an exception if is no property set and handle it as a
+ * document of some other format. We are not concerned about
+ * that document's details. */
+ try
+ {
+ d = new PropertySetDescriptor(event.getName(), event.getPath(),
+ is, nrOfBytes);
+ }
+ catch (HPSFException ex)
+ {
+ d = new DocumentDescriptor(event.getName(), event.getPath(),
+ is, nrOfBytes);
+ }
+ catch (Throwable t)
+ {
+ System.err.println
+ ("Unexpected exception while processing " +
+ event.getName() + " in " + event.getPath().toString());
+ t.printStackTrace(System.err);
+ throw new RuntimeException(t.getMessage());
+ }
+
+ is.close();
+
+ final MutableTreeNode parentNode = getNode(d.path, filename, rootNode);
+ final MutableTreeNode nameNode = new DefaultMutableTreeNode(d.name);
+ parentNode.insert(nameNode, 0);
+ final MutableTreeNode dNode = new DefaultMutableTreeNode(d);
+ nameNode.insert(dNode, 0);
+ }
+
+
+
+ /**
+ * <p>Locates the parent node for a document entry in the tree
+ * model. If the parent node does not yet exist it will be
+ * created, too. This is done recursively, if needed.</p>
+ *
+ * @param path The tree node for this path is located.
+ *
+ * @param fsName The name of the POI filesystem. This is just a
+ * string which is displayed in the tree at the top lovel.
+ *
+ * @param root The root node.
+ */
+ private MutableTreeNode getNode(final POIFSDocumentPath path,
+ final String fsName,
+ final MutableTreeNode root)
+ {
+ MutableTreeNode n = (MutableTreeNode) pathToNode.get(path);
+ if (n != null)
+ /* Node found in map, just return it. */
+ return n;
+ if (path.length() == 0)
+ {
+ /* This is the root path of the POI filesystem. Its tree
+ * node is resp. must be located below the tree node of
+ * the POI filesystem itself. This is a tree node with the
+ * POI filesystem's name (this the operating system file's
+ * name) as its key it the path-to-node map. */
+ n = (MutableTreeNode) pathToNode.get(fsName);
+ if (n == null)
+ {
+ /* A tree node for the POI filesystem does not yet
+ * exist. */
+ n = new DefaultMutableTreeNode(fsName);
+ pathToNode.put(fsName, n);
+ root.insert(n, 0);
+ }
+ return n;
+ }
+ /* else - The path is somewhere down in the POI filesystem's
+ * hierarchy. We need the tree node of this path's parent
+ * and attach our new node to it. */
+ final String name = path.getComponent(path.length() - 1);
+ final POIFSDocumentPath parentPath = path.getParent();
+ final MutableTreeNode parentNode =
+ getNode(parentPath, fsName, root);
+ n = new DefaultMutableTreeNode(name);
+ pathToNode.put(path, n);
+ parentNode.insert(n, 0);
+ return n;
+ }
+}
--- /dev/null
+/* ====================================================================
+ 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.contrib.poibrowser;
+
+import java.awt.*;
+import javax.swing.*;
+
+/**
+ * <p>Contains various (well, just one at the moment) static utility
+ * methods.</p>
+ *
+ * @author Rainer Klute <a
+ * href="mailto:klute@rainer-klute.de"><klute@rainer-klute.de></a>
+ */
+public class Util {
+
+ /**
+ * <p>Makes a Swing component inverted by swapping its foreground
+ * and background colors. Hint: Depending on your needs it might
+ * also be a good idea to call <tt>c.setOpaque(true)</tt>.</p>
+ */
+ public static void invert(JComponent c) {
+ Color invBackground = c.getForeground();
+ Color invForeground = c.getBackground();
+ c.setBackground(invBackground);
+ c.setForeground(invForeground);
+ }
+}
+
--- /dev/null
+/* ====================================================================
+ 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.usermodel.contrib;
+
+
+import org.apache.poi.hssf.usermodel.HSSFCell;
+import org.apache.poi.hssf.usermodel.HSSFCellStyle;
+import org.apache.poi.hssf.usermodel.HSSFFont;
+import org.apache.poi.hssf.usermodel.HSSFRow;
+import org.apache.poi.hssf.usermodel.HSSFSheet;
+import org.apache.poi.hssf.usermodel.HSSFWorkbook;
+import org.apache.poi.ss.usermodel.contrib.CellUtil;
+
+/**
+ * Various utility functions that make working with a cells and rows easier. The various
+ * methods that deal with style's allow you to create your HSSFCellStyles as you need them.
+ * When you apply a style change to a cell, the code will attempt to see if a style already
+ * exists that meets your needs. If not, then it will create a new style. This is to prevent
+ * creating too many styles. there is an upper limit in Excel on the number of styles that
+ * can be supported.
+ *
+ *@author Eric Pugh epugh@upstate.com
+ */
+public final class HSSFCellUtil {
+
+ private HSSFCellUtil() {
+ // no instances of this class
+ }
+
+ /**
+ * Get a row from the spreadsheet, and create it if it doesn't exist.
+ *
+ *@param rowIndex The 0 based row number
+ *@param sheet The sheet that the row is part of.
+ *@return The row indicated by the rowCounter
+ */
+ public static HSSFRow getRow(int rowIndex, HSSFSheet sheet) {
+ return (HSSFRow) CellUtil.getRow(rowIndex, sheet);
+ }
+
+ /**
+ * Get a specific cell from a row. If the cell doesn't exist,
+ * then create it.
+ *
+ *@param row The row that the cell is part of
+ *@param columnIndex The column index that the cell is in.
+ *@return The cell indicated by the column.
+ */
+ public static HSSFCell getCell(HSSFRow row, int columnIndex) {
+ return (HSSFCell) CellUtil.getCell(row, columnIndex);
+ }
+
+ /**
+ * Creates a cell, gives it a value, and applies a style if provided
+ *
+ * @param row the row to create the cell in
+ * @param column the column index to create the cell in
+ * @param value The value of the cell
+ * @param style If the style is not null, then set
+ * @return A new HSSFCell
+ */
+ public static HSSFCell createCell(HSSFRow row, int column, String value, HSSFCellStyle style) {
+ return (HSSFCell) CellUtil.createCell(row, column, value, style);
+ }
+
+ /**
+ * Create a cell, and give it a value.
+ *
+ *@param row the row to create the cell in
+ *@param column the column index to create the cell in
+ *@param value The value of the cell
+ *@return A new HSSFCell.
+ */
+ public static HSSFCell createCell(HSSFRow row, int column, String value) {
+ return createCell( row, column, value, null );
+ }
+
+ /**
+ * Take a cell, and align it.
+ *
+ *@param cell the cell to set the alignment for
+ *@param workbook The workbook that is being worked with.
+ *@param align the column alignment to use.
+ *
+ * @see HSSFCellStyle for alignment options
+ */
+ public static void setAlignment(HSSFCell cell, HSSFWorkbook workbook, short align) {
+ CellUtil.setAlignment(cell, workbook, align);
+ }
+
+ /**
+ * Take a cell, and apply a font to it
+ *
+ *@param cell the cell to set the alignment for
+ *@param workbook The workbook that is being worked with.
+ *@param font The HSSFFont that you want to set...
+ */
+ public static void setFont(HSSFCell cell, HSSFWorkbook workbook, HSSFFont font) {
+ CellUtil.setFont(cell, workbook, font);
+ }
+
+ /**
+ * This method attempt to find an already existing HSSFCellStyle that matches
+ * what you want the style to be. If it does not find the style, then it
+ * creates a new one. If it does create a new one, then it applies the
+ * propertyName and propertyValue to the style. This is necessary because
+ * Excel has an upper limit on the number of Styles that it supports.
+ *
+ *@param workbook The workbook that is being worked with.
+ *@param propertyName The name of the property that is to be
+ * changed.
+ *@param propertyValue The value of the property that is to be
+ * changed.
+ *@param cell The cell that needs it's style changes
+ */
+ public static void setCellStyleProperty(HSSFCell cell, HSSFWorkbook workbook,
+ String propertyName, Object propertyValue) {
+ CellUtil.setCellStyleProperty(cell, workbook, propertyName, propertyValue);
+ }
+
+ /**
+ * Looks for text in the cell that should be unicode, like α and provides the
+ * unicode version of it.
+ *
+ *@param cell The cell to check for unicode values
+ *@return translated to unicode
+ */
+ public static HSSFCell translateUnicodeValues(HSSFCell cell){
+ CellUtil.translateUnicodeValues(cell);
+ return cell;
+ }
+}
--- /dev/null
+/* ====================================================================
+ 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.usermodel.contrib;
+
+import org.apache.poi.hssf.usermodel.HSSFSheet;
+import org.apache.poi.hssf.usermodel.HSSFWorkbook;
+import org.apache.poi.ss.usermodel.contrib.RegionUtil;
+import org.apache.poi.ss.util.CellRangeAddress;
+import org.apache.poi.ss.util.Region;
+
+/**
+ * Various utility functions that make working with a region of cells easier.
+ *
+ * @author Eric Pugh epugh@upstate.com
+ */
+public final class HSSFRegionUtil {
+
+ private HSSFRegionUtil() {
+ // no instances of this class
+ }
+
+ private static CellRangeAddress toCRA(Region region) {
+ return Region.convertToCellRangeAddress(region);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setBorderLeft(short border, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setBorderLeft(border, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the left border for a region of cells by manipulating the cell style
+ * of the individual cells on the left
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderLeft(int border, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setBorderLeft(border, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setLeftBorderColor(short color, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setLeftBorderColor(color, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the leftBorderColor attribute of the HSSFRegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setLeftBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setLeftBorderColor(color, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setBorderRight(short border, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setBorderRight(border, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the borderRight attribute of the HSSFRegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderRight(int border, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setBorderRight(border, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setRightBorderColor(short color, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setRightBorderColor(color, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the rightBorderColor attribute of the HSSFRegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setRightBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setRightBorderColor(color, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setBorderBottom(short border, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setBorderBottom(border, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the borderBottom attribute of the HSSFRegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderBottom(int border, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setBorderBottom(border, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setBottomBorderColor(short color, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setBottomBorderColor(color, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the bottomBorderColor attribute of the HSSFRegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBottomBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setBottomBorderColor(color, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setBorderTop(short border, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setBorderTop(border, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the borderBottom attribute of the HSSFRegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderTop(int border, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setBorderTop(border, region, sheet, workbook);
+ }
+
+ /**
+ * @deprecated (Aug 2008) use {@link CellRangeAddress} instead of {@link Region}
+ */
+ public static void setTopBorderColor(short color, Region region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ setTopBorderColor(color, toCRA(region), sheet, workbook);
+ }
+ /**
+ * Sets the topBorderColor attribute of the HSSFRegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setTopBorderColor(int color, CellRangeAddress region, HSSFSheet sheet,
+ HSSFWorkbook workbook) {
+ RegionUtil.setTopBorderColor(color, region, sheet, workbook);
+ }
+}
--- /dev/null
+/* ====================================================================
+ 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.usermodel.contrib;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.poi.ss.usermodel.Cell;
+import org.apache.poi.ss.usermodel.CellStyle;
+import org.apache.poi.ss.usermodel.Font;
+import org.apache.poi.ss.usermodel.Row;
+import org.apache.poi.ss.usermodel.Sheet;
+import org.apache.poi.ss.usermodel.Workbook;
+
+/**
+ * Various utility functions that make working with a cells and rows easier. The various methods
+ * that deal with style's allow you to create your CellStyles as you need them. When you apply a
+ * style change to a cell, the code will attempt to see if a style already exists that meets your
+ * needs. If not, then it will create a new style. This is to prevent creating too many styles.
+ * there is an upper limit in Excel on the number of styles that can be supported.
+ *
+ *@author Eric Pugh epugh@upstate.com
+ *@author (secondary) Avinash Kewalramani akewalramani@accelrys.com
+ */
+public final class CellUtil {
+
+ public static final String ALIGNMENT = "alignment";
+ public static final String BORDER_BOTTOM = "borderBottom";
+ public static final String BORDER_LEFT = "borderLeft";
+ public static final String BORDER_RIGHT = "borderRight";
+ public static final String BORDER_TOP = "borderTop";
+ public static final String BOTTOM_BORDER_COLOR = "bottomBorderColor";
+ public static final String DATA_FORMAT = "dataFormat";
+ public static final String FILL_BACKGROUND_COLOR = "fillBackgroundColor";
+ public static final String FILL_FOREGROUND_COLOR = "fillForegroundColor";
+ public static final String FILL_PATTERN = "fillPattern";
+ public static final String FONT = "font";
+ public static final String HIDDEN = "hidden";
+ public static final String INDENTION = "indention";
+ public static final String LEFT_BORDER_COLOR = "leftBorderColor";
+ public static final String LOCKED = "locked";
+ public static final String RIGHT_BORDER_COLOR = "rightBorderColor";
+ public static final String ROTATION = "rotation";
+ public static final String TOP_BORDER_COLOR = "topBorderColor";
+ public static final String VERTICAL_ALIGNMENT = "verticalAlignment";
+ public static final String WRAP_TEXT = "wrapText";
+
+ private static UnicodeMapping unicodeMappings[];
+
+ private static final class UnicodeMapping {
+
+ public final String entityName;
+ public final String resolvedValue;
+
+ public UnicodeMapping(String pEntityName, String pResolvedValue) {
+ entityName = "&" + pEntityName + ";";
+ resolvedValue = pResolvedValue;
+ }
+ }
+
+ private CellUtil() {
+ // no instances of this class
+ }
+
+ /**
+ * Get a row from the spreadsheet, and create it if it doesn't exist.
+ *
+ *@param rowIndex The 0 based row number
+ *@param sheet The sheet that the row is part of.
+ *@return The row indicated by the rowCounter
+ */
+ public static Row getRow(int rowIndex, Sheet sheet) {
+ Row row = sheet.getRow(rowIndex);
+ if (row == null) {
+ row = sheet.createRow(rowIndex);
+ }
+ return row;
+ }
+
+
+ /**
+ * Get a specific cell from a row. If the cell doesn't exist, then create it.
+ *
+ *@param row The row that the cell is part of
+ *@param columnIndex The column index that the cell is in.
+ *@return The cell indicated by the column.
+ */
+ public static Cell getCell(Row row, int columnIndex) {
+ Cell cell = row.getCell(columnIndex);
+
+ if (cell == null) {
+ cell = row.createCell(columnIndex);
+ }
+ return cell;
+ }
+
+
+ /**
+ * Creates a cell, gives it a value, and applies a style if provided
+ *
+ * @param row the row to create the cell in
+ * @param column the column index to create the cell in
+ * @param value The value of the cell
+ * @param style If the style is not null, then set
+ * @return A new Cell
+ */
+ public static Cell createCell(Row row, int column, String value, CellStyle style) {
+ Cell cell = getCell(row, column);
+
+ cell.setCellValue(cell.getRow().getSheet().getWorkbook().getCreationHelper()
+ .createRichTextString(value));
+ if (style != null) {
+ cell.setCellStyle(style);
+ }
+ return cell;
+ }
+
+
+ /**
+ * Create a cell, and give it a value.
+ *
+ *@param row the row to create the cell in
+ *@param column the column index to create the cell in
+ *@param value The value of the cell
+ *@return A new Cell.
+ */
+ public static Cell createCell(Row row, int column, String value) {
+ return createCell(row, column, value, null);
+ }
+
+
+ /**
+ * Take a cell, and align it.
+ *
+ *@param cell the cell to set the alignment for
+ *@param workbook The workbook that is being worked with.
+ *@param align the column alignment to use.
+ *
+ * @see CellStyle for alignment options
+ */
+ public static void setAlignment(Cell cell, Workbook workbook, short align) {
+ setCellStyleProperty(cell, workbook, ALIGNMENT, Short.valueOf(align));
+ }
+
+ /**
+ * Take a cell, and apply a font to it
+ *
+ *@param cell the cell to set the alignment for
+ *@param workbook The workbook that is being worked with.
+ *@param font The Font that you want to set...
+ */
+ public static void setFont(Cell cell, Workbook workbook, Font font) {
+ setCellStyleProperty(cell, workbook, FONT, font.getIndex());
+ }
+
+ /**
+ * This method attempt to find an already existing CellStyle that matches what you want the
+ * style to be. If it does not find the style, then it creates a new one. If it does create a
+ * new one, then it applies the propertyName and propertyValue to the style. This is necessary
+ * because Excel has an upper limit on the number of Styles that it supports.
+ *
+ *@param workbook The workbook that is being worked with.
+ *@param propertyName The name of the property that is to be changed.
+ *@param propertyValue The value of the property that is to be changed.
+ *@param cell The cell that needs it's style changes
+ */
+ public static void setCellStyleProperty(Cell cell, Workbook workbook, String propertyName,
+ Object propertyValue) {
+ CellStyle originalStyle = cell.getCellStyle();
+ CellStyle newStyle = null;
+ Map<String, Object> values = getFormatProperties(originalStyle);
+ values.put(propertyName, propertyValue);
+
+ // index seems like what index the cellstyle is in the list of styles for a workbook.
+ // not good to compare on!
+ short numberCellStyles = workbook.getNumCellStyles();
+
+ for (short i = 0; i < numberCellStyles; i++) {
+ CellStyle wbStyle = workbook.getCellStyleAt(i);
+ Map<String, Object> wbStyleMap = getFormatProperties(wbStyle);
+
+ if (wbStyleMap.equals(values)) {
+ newStyle = wbStyle;
+ break;
+ }
+ }
+
+ if (newStyle == null) {
+ newStyle = workbook.createCellStyle();
+ setFormatProperties(newStyle, workbook, values);
+ }
+
+ cell.setCellStyle(newStyle);
+ }
+
+ /**
+ * Returns a map containing the format properties of the given cell style.
+ *
+ * @param style cell style
+ * @return map of format properties (String -> Object)
+ * @see #setFormatProperties(org.apache.poi.ss.usermodel.CellStyle, org.apache.poi.ss.usermodel.Workbook, java.util.Map)
+ */
+ private static Map<String, Object> getFormatProperties(CellStyle style) {
+ Map<String, Object> properties = new HashMap<String, Object>();
+ putShort(properties, ALIGNMENT, style.getAlignment());
+ putShort(properties, BORDER_BOTTOM, style.getBorderBottom());
+ putShort(properties, BORDER_LEFT, style.getBorderLeft());
+ putShort(properties, BORDER_RIGHT, style.getBorderRight());
+ putShort(properties, BORDER_TOP, style.getBorderTop());
+ putShort(properties, BOTTOM_BORDER_COLOR, style.getBottomBorderColor());
+ putShort(properties, DATA_FORMAT, style.getDataFormat());
+ putShort(properties, FILL_BACKGROUND_COLOR, style.getFillBackgroundColor());
+ putShort(properties, FILL_FOREGROUND_COLOR, style.getFillForegroundColor());
+ putShort(properties, FILL_PATTERN, style.getFillPattern());
+ putShort(properties, FONT, style.getFontIndex());
+ putBoolean(properties, HIDDEN, style.getHidden());
+ putShort(properties, INDENTION, style.getIndention());
+ putShort(properties, LEFT_BORDER_COLOR, style.getLeftBorderColor());
+ putBoolean(properties, LOCKED, style.getLocked());
+ putShort(properties, RIGHT_BORDER_COLOR, style.getRightBorderColor());
+ putShort(properties, ROTATION, style.getRotation());
+ putShort(properties, TOP_BORDER_COLOR, style.getTopBorderColor());
+ putShort(properties, VERTICAL_ALIGNMENT, style.getVerticalAlignment());
+ putBoolean(properties, WRAP_TEXT, style.getWrapText());
+ return properties;
+ }
+
+ /**
+ * Sets the format properties of the given style based on the given map.
+ *
+ * @param style cell style
+ * @param workbook parent workbook
+ * @param properties map of format properties (String -> Object)
+ * @see #getFormatProperties(CellStyle)
+ */
+ private static void setFormatProperties(CellStyle style, Workbook workbook, Map<String, Object> properties) {
+ style.setAlignment(getShort(properties, ALIGNMENT));
+ style.setBorderBottom(getShort(properties, BORDER_BOTTOM));
+ style.setBorderLeft(getShort(properties, BORDER_LEFT));
+ style.setBorderRight(getShort(properties, BORDER_RIGHT));
+ style.setBorderTop(getShort(properties, BORDER_TOP));
+ style.setBottomBorderColor(getShort(properties, BOTTOM_BORDER_COLOR));
+ style.setDataFormat(getShort(properties, DATA_FORMAT));
+ style.setFillBackgroundColor(getShort(properties, FILL_BACKGROUND_COLOR));
+ style.setFillForegroundColor(getShort(properties, FILL_FOREGROUND_COLOR));
+ style.setFillPattern(getShort(properties, FILL_PATTERN));
+ style.setFont(workbook.getFontAt(getShort(properties, FONT)));
+ style.setHidden(getBoolean(properties, HIDDEN));
+ style.setIndention(getShort(properties, INDENTION));
+ style.setLeftBorderColor(getShort(properties, LEFT_BORDER_COLOR));
+ style.setLocked(getBoolean(properties, LOCKED));
+ style.setRightBorderColor(getShort(properties, RIGHT_BORDER_COLOR));
+ style.setRotation(getShort(properties, ROTATION));
+ style.setTopBorderColor(getShort(properties, TOP_BORDER_COLOR));
+ style.setVerticalAlignment(getShort(properties, VERTICAL_ALIGNMENT));
+ style.setWrapText(getBoolean(properties, WRAP_TEXT));
+ }
+
+ /**
+ * Utility method that returns the named short value form the given map.
+ * @return zero if the property does not exist, or is not a {@link Short}.
+ *
+ * @param properties map of named properties (String -> Object)
+ * @param name property name
+ * @return property value, or zero
+ */
+ private static short getShort(Map<String, Object> properties, String name) {
+ Object value = properties.get(name);
+ if (value instanceof Short) {
+ return ((Short) value).shortValue();
+ }
+ return 0;
+ }
+
+ /**
+ * Utility method that returns the named boolean value form the given map.
+ * @return false if the property does not exist, or is not a {@link Boolean}.
+ *
+ * @param properties map of properties (String -> Object)
+ * @param name property name
+ * @return property value, or false
+ */
+ private static boolean getBoolean(Map<String, Object> properties, String name) {
+ Object value = properties.get(name);
+ if (value instanceof Boolean) {
+ return ((Boolean) value).booleanValue();
+ }
+ return false;
+ }
+
+ /**
+ * Utility method that puts the named short value to the given map.
+ *
+ * @param properties map of properties (String -> Object)
+ * @param name property name
+ * @param value property value
+ */
+ private static void putShort(Map<String, Object> properties, String name, short value) {
+ properties.put(name, Short.valueOf(value));
+ }
+
+ /**
+ * Utility method that puts the named boolean value to the given map.
+ *
+ * @param properties map of properties (String -> Object)
+ * @param name property name
+ * @param value property value
+ */
+ private static void putBoolean(Map<String, Object> properties, String name, boolean value) {
+ properties.put(name, Boolean.valueOf(value));
+ }
+
+ /**
+ * Looks for text in the cell that should be unicode, like α and provides the
+ * unicode version of it.
+ *
+ *@param cell The cell to check for unicode values
+ *@return translated to unicode
+ */
+ public static Cell translateUnicodeValues(Cell cell) {
+
+ String s = cell.getRichStringCellValue().getString();
+ boolean foundUnicode = false;
+ String lowerCaseStr = s.toLowerCase();
+
+ for (int i = 0; i < unicodeMappings.length; i++) {
+ UnicodeMapping entry = unicodeMappings[i];
+ String key = entry.entityName;
+ if (lowerCaseStr.indexOf(key) != -1) {
+ s = s.replaceAll(key, entry.resolvedValue);
+ foundUnicode = true;
+ }
+ }
+ if (foundUnicode) {
+ cell.setCellValue(cell.getRow().getSheet().getWorkbook().getCreationHelper()
+ .createRichTextString(s));
+ }
+ return cell;
+ }
+
+ static {
+ unicodeMappings = new UnicodeMapping[] {
+ um("alpha", "\u03B1" ),
+ um("beta", "\u03B2" ),
+ um("gamma", "\u03B3" ),
+ um("delta", "\u03B4" ),
+ um("epsilon", "\u03B5" ),
+ um("zeta", "\u03B6" ),
+ um("eta", "\u03B7" ),
+ um("theta", "\u03B8" ),
+ um("iota", "\u03B9" ),
+ um("kappa", "\u03BA" ),
+ um("lambda", "\u03BB" ),
+ um("mu", "\u03BC" ),
+ um("nu", "\u03BD" ),
+ um("xi", "\u03BE" ),
+ um("omicron", "\u03BF" ),
+ };
+ }
+
+ private static UnicodeMapping um(String entityName, String resolvedValue) {
+ return new UnicodeMapping(entityName, resolvedValue);
+ }
+}
--- /dev/null
+/* ====================================================================
+ 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.usermodel.contrib;
+
+import org.apache.poi.ss.usermodel.Cell;
+import org.apache.poi.ss.usermodel.Row;
+import org.apache.poi.ss.usermodel.Sheet;
+import org.apache.poi.ss.usermodel.Workbook;
+import org.apache.poi.ss.util.CellRangeAddress;
+
+/**
+ * Various utility functions that make working with a region of cells easier.
+ *
+ * @author Eric Pugh epugh@upstate.com
+ * @author (secondary) Avinash Kewalramani akewalramani@accelrys.com
+ */
+public final class RegionUtil {
+
+ private RegionUtil() {
+ // no instances of this class
+ }
+
+ /**
+ * For setting the same property on many cells to the same value
+ */
+ private static final class CellPropertySetter {
+
+ private final Workbook _workbook;
+ private final String _propertyName;
+ private final Short _propertyValue;
+
+
+ public CellPropertySetter(Workbook workbook, String propertyName, int value) {
+ _workbook = workbook;
+ _propertyName = propertyName;
+ _propertyValue = Short.valueOf((short) value);
+ }
+
+
+ public void setProperty(Row row, int column) {
+ Cell cell = CellUtil.getCell(row, column);
+ CellUtil.setCellStyleProperty(cell, _workbook, _propertyName, _propertyValue);
+ }
+ }
+
+ /**
+ * Sets the left border for a region of cells by manipulating the cell style of the individual
+ * cells on the left
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderLeft(int border, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int rowStart = region.getFirstRow();
+ int rowEnd = region.getLastRow();
+ int column = region.getFirstColumn();
+
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_LEFT, border);
+ for (int i = rowStart; i <= rowEnd; i++) {
+ cps.setProperty(CellUtil.getRow(i, sheet), column);
+ }
+ }
+
+ /**
+ * Sets the leftBorderColor attribute of the RegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setLeftBorderColor(int color, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int rowStart = region.getFirstRow();
+ int rowEnd = region.getLastRow();
+ int column = region.getFirstColumn();
+
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.LEFT_BORDER_COLOR,
+ color);
+ for (int i = rowStart; i <= rowEnd; i++) {
+ cps.setProperty(CellUtil.getRow(i, sheet), column);
+ }
+ }
+
+ /**
+ * Sets the borderRight attribute of the RegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderRight(int border, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int rowStart = region.getFirstRow();
+ int rowEnd = region.getLastRow();
+ int column = region.getLastColumn();
+
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_RIGHT, border);
+ for (int i = rowStart; i <= rowEnd; i++) {
+ cps.setProperty(CellUtil.getRow(i, sheet), column);
+ }
+ }
+
+ /**
+ * Sets the rightBorderColor attribute of the RegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setRightBorderColor(int color, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int rowStart = region.getFirstRow();
+ int rowEnd = region.getLastRow();
+ int column = region.getLastColumn();
+
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.RIGHT_BORDER_COLOR,
+ color);
+ for (int i = rowStart; i <= rowEnd; i++) {
+ cps.setProperty(CellUtil.getRow(i, sheet), column);
+ }
+ }
+
+ /**
+ * Sets the borderBottom attribute of the RegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderBottom(int border, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int colStart = region.getFirstColumn();
+ int colEnd = region.getLastColumn();
+ int rowIndex = region.getLastRow();
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_BOTTOM, border);
+ Row row = CellUtil.getRow(rowIndex, sheet);
+ for (int i = colStart; i <= colEnd; i++) {
+ cps.setProperty(row, i);
+ }
+ }
+
+ /**
+ * Sets the bottomBorderColor attribute of the RegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBottomBorderColor(int color, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int colStart = region.getFirstColumn();
+ int colEnd = region.getLastColumn();
+ int rowIndex = region.getLastRow();
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BOTTOM_BORDER_COLOR,
+ color);
+ Row row = CellUtil.getRow(rowIndex, sheet);
+ for (int i = colStart; i <= colEnd; i++) {
+ cps.setProperty(row, i);
+ }
+ }
+
+ /**
+ * Sets the borderBottom attribute of the RegionUtil object
+ *
+ * @param border The new border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setBorderTop(int border, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int colStart = region.getFirstColumn();
+ int colEnd = region.getLastColumn();
+ int rowIndex = region.getFirstRow();
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.BORDER_TOP, border);
+ Row row = CellUtil.getRow(rowIndex, sheet);
+ for (int i = colStart; i <= colEnd; i++) {
+ cps.setProperty(row, i);
+ }
+ }
+
+ /**
+ * Sets the topBorderColor attribute of the RegionUtil object
+ *
+ * @param color The color of the border
+ * @param region The region that should have the border
+ * @param workbook The workbook that the region is on.
+ * @param sheet The sheet that the region is on.
+ */
+ public static void setTopBorderColor(int color, CellRangeAddress region, Sheet sheet,
+ Workbook workbook) {
+ int colStart = region.getFirstColumn();
+ int colEnd = region.getLastColumn();
+ int rowIndex = region.getFirstRow();
+ CellPropertySetter cps = new CellPropertySetter(workbook, CellUtil.TOP_BORDER_COLOR, color);
+ Row row = CellUtil.getRow(rowIndex, sheet);
+ for (int i = colStart; i <= colEnd; i++) {
+ cps.setProperty(row, i);
+ }
+ }
+}
--- /dev/null
+
+/* ====================================================================
+ 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.contrib.metrics;
+
+import java.awt.*;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.util.Properties;
+
+@SuppressWarnings("deprecation")
+public class FontMetricsDumper
+{
+ public static void main( String[] args ) throws IOException
+ {
+
+ Properties props = new Properties();
+
+ Font[] allFonts = GraphicsEnvironment.getLocalGraphicsEnvironment().getAllFonts();
+ for ( int i = 0; i < allFonts.length; i++ )
+ {
+ String fontName = allFonts[i].getFontName();
+
+ Font font = new Font(fontName, Font.BOLD, 10);
+ FontMetrics fontMetrics = Toolkit.getDefaultToolkit().getFontMetrics(font);
+ int fontHeight = fontMetrics.getHeight();
+
+ props.setProperty("font." + fontName + ".height", fontHeight+"");
+ StringBuffer characters = new StringBuffer();
+ for (char c = 'a'; c <= 'z'; c++)
+ {
+ characters.append( c + ", " );
+ }
+ for (char c = 'A'; c <= 'Z'; c++)
+ {
+ characters.append( c + ", " );
+ }
+ for (char c = '0'; c <= '9'; c++)
+ {
+ characters.append( c + ", " );
+ }
+ StringBuffer widths = new StringBuffer();
+ for (char c = 'a'; c <= 'z'; c++)
+ {
+ widths.append( fontMetrics.getWidths()[c] + ", " );
+ }
+ for (char c = 'A'; c <= 'Z'; c++)
+ {
+ widths.append( fontMetrics.getWidths()[c] + ", " );
+ }
+ for (char c = '0'; c <= '9'; c++)
+ {
+ widths.append( fontMetrics.getWidths()[c] + ", " );
+ }
+ props.setProperty("font." + fontName + ".characters", characters.toString());
+ props.setProperty("font." + fontName + ".widths", widths.toString());
+ }
+
+ FileOutputStream fileOut = new FileOutputStream("font_metrics.properties");
+ try
+ {
+ props.store(fileOut, "Font Metrics");
+ }
+ finally
+ {
+ fileOut.close();
+ }
+ }
+}