-/* $RCSfile$\r
- * $Author$\r
- * $Date$\r
- * $Revision$\r
- *\r
- * Copyright (C) 2006 The Jmol Development Team\r
- *\r
- * Contact: jmol-developers@lists.sf.net\r
- *\r
- * This library is free software; you can redistribute it and/or\r
- * modify it under the terms of the GNU Lesser General Public\r
- * License as published by the Free Software Foundation; either\r
- * version 2.1 of the License, or (at your option) any later version.\r
- *\r
- * This library is distributed in the hope that it will be useful,\r
- * but WITHOUT ANY WARRANTY; without even the implied warranty of\r
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU\r
- * Lesser General Public License for more details.\r
- *\r
- * You should have received a copy of the GNU Lesser General Public\r
- * License along with this library; if not, write to the Free Software\r
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA\r
- * 02110-1301, USA.\r
- */\r
-\r
-package javajs.util;\r
-\r
-import java.io.BufferedInputStream;\r
-import java.io.IOException;\r
-import java.io.InputStream;\r
-import java.io.OutputStream;\r
-\r
-import javajs.J2SIgnoreImport;\r
-import javajs.api.GenericZipInputStream;\r
-import javajs.api.GenericZipTools;\r
-import javajs.api.ZInputStream;\r
-\r
-import java.util.Map;\r
-import java.util.zip.CRC32;\r
-import java.util.zip.GZIPInputStream;\r
-import java.util.zip.ZipEntry;\r
-import java.util.zip.ZipInputStream;\r
-import java.util.zip.ZipOutputStream;\r
-\r
-\r
-/**\r
- * Note the JSmol/HTML5 must use its own version of java.util.zip.ZipOutputStream.\r
- * \r
- */\r
-@J2SIgnoreImport({ java.util.zip.ZipOutputStream.class })\r
-public class ZipTools implements GenericZipTools {\r
-\r
- public ZipTools() {\r
- // for reflection\r
- }\r
- \r
- @Override\r
- public ZInputStream newZipInputStream(InputStream is) {\r
- return newZIS(is);\r
- }\r
-\r
- @SuppressWarnings("resource")\r
- private static ZInputStream newZIS(InputStream is) {\r
- return (is instanceof ZInputStream ? (ZInputStream) is\r
- : is instanceof BufferedInputStream ? new GenericZipInputStream(is)\r
- : new GenericZipInputStream(new BufferedInputStream(is)));\r
- }\r
-\r
- /**\r
- * reads a ZIP file and saves all data in a Hashtable so that the files may be\r
- * organized later in a different order. Also adds a #Directory_Listing entry.\r
- * \r
- * Files are bracketed by BEGIN Directory Entry and END Directory Entry lines,\r
- * similar to CompoundDocument.getAllData.\r
- * \r
- * @param is\r
- * @param subfileList\r
- * @param name0\r
- * prefix for entry listing\r
- * @param binaryFileList\r
- * |-separated list of files that should be saved as xx xx xx hex byte\r
- * strings. The directory listing is appended with ":asBinaryString"\r
- * @param fileData\r
- */\r
- @Override\r
- public void getAllZipData(InputStream is, String[] subfileList,\r
- String name0, String binaryFileList,\r
- Map<String, String> fileData) {\r
- ZipInputStream zis = (ZipInputStream) newZIS(is);\r
- ZipEntry ze;\r
- SB listing = new SB();\r
- binaryFileList = "|" + binaryFileList + "|";\r
- String prefix = PT.join(subfileList, '/', 1);\r
- String prefixd = null;\r
- if (prefix != null) {\r
- prefixd = prefix.substring(0, prefix.indexOf("/") + 1);\r
- if (prefixd.length() == 0)\r
- prefixd = null;\r
- }\r
- try {\r
- while ((ze = zis.getNextEntry()) != null) {\r
- String name = ze.getName();\r
- if (prefix != null && prefixd != null\r
- && !(name.equals(prefix) || name.startsWith(prefixd)))\r
- continue;\r
- //System.out.println("ziputil: " + name);\r
- listing.append(name).appendC('\n');\r
- String sname = "|" + name.substring(name.lastIndexOf("/") + 1) + "|";\r
- boolean asBinaryString = (binaryFileList.indexOf(sname) >= 0);\r
- byte[] bytes = Rdr.getLimitedStreamBytes(zis, ze.getSize());\r
- String str;\r
- if (asBinaryString) {\r
- str = getBinaryStringForBytes(bytes);\r
- name += ":asBinaryString";\r
- } else {\r
- str = Rdr.fixUTF(bytes);\r
- }\r
- str = "BEGIN Directory Entry " + name + "\n" + str\r
- + "\nEND Directory Entry " + name + "\n";\r
- fileData.put(name0 + "|" + name, str);\r
- }\r
- } catch (Exception e) {\r
- }\r
- fileData.put("#Directory_Listing", listing.toString());\r
- }\r
-\r
- private String getBinaryStringForBytes(byte[] bytes) {\r
- SB ret = new SB();\r
- for (int i = 0; i < bytes.length; i++)\r
- ret.append(Integer.toHexString(bytes[i] & 0xFF)).appendC(' ');\r
- return ret.toString();\r
- }\r
-\r
- /**\r
- * iteratively drills into zip files of zip files to extract file content or\r
- * zip file directory. Also works with JAR files.\r
- * \r
- * Does not return "__MACOS" paths\r
- * \r
- * @param bis\r
- * @param list\r
- * @param listPtr\r
- * @param asBufferedInputStream\r
- * for Pmesh\r
- * @return directory listing or subfile contents\r
- */\r
- @Override\r
- public Object getZipFileDirectory(BufferedInputStream bis, String[] list,\r
- int listPtr, boolean asBufferedInputStream) {\r
- SB ret;\r
- if (list == null || listPtr >= list.length)\r
- return getZipDirectoryAsStringAndClose(bis);\r
- bis = Rdr.getPngZipStream(bis, true);\r
- String fileName = list[listPtr];\r
- ZipInputStream zis = new ZipInputStream(bis);\r
- ZipEntry ze;\r
- //System.out.println("fname=" + fileName);\r
- try {\r
- boolean isAll = (fileName.equals("."));\r
- if (isAll || fileName.lastIndexOf("/") == fileName.length() - 1) {\r
- ret = new SB();\r
- while ((ze = zis.getNextEntry()) != null) {\r
- String name = ze.getName();\r
- if (isAll || name.startsWith(fileName))\r
- ret.append(name).appendC('\n');\r
- }\r
- String str = ret.toString();\r
- return (asBufferedInputStream ? Rdr.getBIS(str.getBytes()) : str);\r
- }\r
- int pt = fileName.indexOf(":asBinaryString");\r
- boolean asBinaryString = (pt > 0);\r
- if (asBinaryString)\r
- fileName = fileName.substring(0, pt);\r
- fileName = fileName.replace('\\', '/');\r
- while ((ze = zis.getNextEntry()) != null\r
- && !fileName.equals(ze.getName())) {\r
- }\r
- byte[] bytes = (ze == null ? null : Rdr.getLimitedStreamBytes(zis,\r
- ze.getSize()));\r
- ze = null;\r
- zis.close();\r
- if (bytes == null)\r
- return "";\r
- if (Rdr.isZipB(bytes) || Rdr.isPngZipB(bytes))\r
- return getZipFileDirectory(Rdr.getBIS(bytes), list, ++listPtr,\r
- asBufferedInputStream);\r
- if (asBufferedInputStream)\r
- return Rdr.getBIS(bytes);\r
- if (asBinaryString) {\r
- ret = new SB();\r
- for (int i = 0; i < bytes.length; i++)\r
- ret.append(Integer.toHexString(bytes[i] & 0xFF)).appendC(' ');\r
- return ret.toString();\r
- }\r
- if (Rdr.isGzipB(bytes))\r
- bytes = Rdr.getLimitedStreamBytes(getUnGzippedInputStream(bytes), -1);\r
- return Rdr.fixUTF(bytes);\r
- } catch (Exception e) {\r
- return "";\r
- }\r
- }\r
-\r
- @Override\r
- public byte[] getZipFileContentsAsBytes(BufferedInputStream bis,\r
- String[] list, int listPtr) {\r
- byte[] ret = new byte[0];\r
- String fileName = list[listPtr];\r
- if (fileName.lastIndexOf("/") == fileName.length() - 1)\r
- return ret;\r
- try {\r
- bis = Rdr.getPngZipStream(bis, true);\r
- ZipInputStream zis = new ZipInputStream(bis);\r
- ZipEntry ze;\r
- while ((ze = zis.getNextEntry()) != null) {\r
- if (!fileName.equals(ze.getName()))\r
- continue;\r
- byte[] bytes = Rdr.getLimitedStreamBytes(zis, ze.getSize());\r
- return ((Rdr.isZipB(bytes) || Rdr.isPngZipB(bytes)) && ++listPtr < list.length ? getZipFileContentsAsBytes(\r
- Rdr.getBIS(bytes), list, listPtr) : bytes);\r
- }\r
- } catch (Exception e) {\r
- }\r
- return ret;\r
- }\r
- \r
- @Override\r
- public String getZipDirectoryAsStringAndClose(BufferedInputStream bis) {\r
- SB sb = new SB();\r
- String[] s = new String[0];\r
- try {\r
- s = getZipDirectoryOrErrorAndClose(bis, null);\r
- bis.close();\r
- } catch (Exception e) {\r
- System.out.println(e.toString());\r
- }\r
- for (int i = 0; i < s.length; i++)\r
- sb.append(s[i]).appendC('\n');\r
- return sb.toString();\r
- }\r
-\r
- @Override\r
- public String[] getZipDirectoryAndClose(BufferedInputStream bis,\r
- String manifestID) {\r
- String[] s = new String[0];\r
- try {\r
- s = getZipDirectoryOrErrorAndClose(bis, manifestID);\r
- bis.close();\r
- } catch (Exception e) {\r
- System.out.println(e.toString());\r
- }\r
- return s;\r
- }\r
-\r
- private String[] getZipDirectoryOrErrorAndClose(BufferedInputStream bis,\r
- String manifestID)\r
- throws IOException {\r
- bis = Rdr.getPngZipStream(bis, true);\r
- Lst<String> v = new Lst<String>();\r
- ZipInputStream zis = new ZipInputStream(bis);\r
- ZipEntry ze;\r
- String manifest = null;\r
- while ((ze = zis.getNextEntry()) != null) {\r
- String fileName = ze.getName();\r
- if (manifestID != null && fileName.startsWith(manifestID))\r
- manifest = getStreamAsString(zis);\r
- else if (!fileName.startsWith("__MACOS")) // resource fork not nec.\r
- v.addLast(fileName);\r
- }\r
- zis.close();\r
- if (manifestID != null)\r
- v.add(0, manifest == null ? "" : manifest + "\n############\n");\r
- return v.toArray(new String[v.size()]);\r
- }\r
-\r
- public static String getStreamAsString(InputStream is) throws IOException {\r
- return Rdr.fixUTF(Rdr.getLimitedStreamBytes(is, -1));\r
- }\r
-\r
- @Override\r
- public InputStream newGZIPInputStream(InputStream is) throws IOException {\r
- return new BufferedInputStream(new GZIPInputStream(is, 512));\r
- }\r
-\r
- @Override\r
- public BufferedInputStream getUnGzippedInputStream(byte[] bytes) {\r
- try {\r
- return Rdr.getUnzippedInputStream(this, Rdr.getBIS(bytes));\r
- } catch (Exception e) {\r
- return null;\r
- }\r
- }\r
-\r
- @Override\r
- public void addZipEntry(Object zos, String fileName) throws IOException {\r
- ((ZipOutputStream) zos).putNextEntry(new ZipEntry(fileName));\r
- }\r
-\r
- @Override\r
- public void closeZipEntry(Object zos) throws IOException {\r
- ((ZipOutputStream) zos).closeEntry();\r
- }\r
-\r
- @Override\r
- public Object getZipOutputStream(Object bos) {\r
- /**\r
- * @j2sNative\r
- * \r
- * return javajs.api.Interface.getInterface(\r
- * "java.util.zip.ZipOutputStream").setZOS(bos);\r
- * \r
- */\r
- {\r
- return new ZipOutputStream((OutputStream) bos);\r
- }\r
- }\r
-\r
- @Override\r
- public int getCrcValue(byte[] bytes) {\r
- CRC32 crc = new CRC32();\r
- crc.update(bytes, 0, bytes.length);\r
- return (int) crc.getValue();\r
- }\r
-\r
- @Override\r
- public void readFileAsMap(BufferedInputStream bis, Map<String, Object> bdata, String name) {\r
- int pt = (name == null ? -1 : name.indexOf("|"));\r
- name = (pt >= 0 ? name.substring(pt + 1) : null);\r
- try {\r
- if (Rdr.isPngZipStream(bis)) {\r
- boolean isImage = "_IMAGE_".equals(name);\r
- if (name == null || isImage)\r
- bdata.put((isImage ? "_DATA_" : "_IMAGE_"), new BArray(getPngImageBytes(bis)));\r
- if (!isImage)\r
- cacheZipContents(bis, name, bdata, true);\r
- } else if (Rdr.isZipS(bis)) {\r
- cacheZipContents(bis, name, bdata, true);\r
- } else if (name == null){\r
- bdata.put("_DATA_", new BArray(Rdr.getLimitedStreamBytes(bis, -1)));\r
- } else {\r
- throw new IOException("ZIP file " + name + " not found");\r
- }\r
- bdata.put("$_BINARY_$", Boolean.TRUE);\r
- } catch (IOException e) {\r
- bdata.clear();\r
- bdata.put("_ERROR_", e.getMessage());\r
- }\r
- }\r
-\r
- @Override\r
- public String cacheZipContents(BufferedInputStream bis,\r
- String fileName,\r
- Map<String, Object> cache, \r
- boolean asByteArray) {\r
- ZipInputStream zis = (ZipInputStream) newZIS(bis);\r
- ZipEntry ze;\r
- SB listing = new SB();\r
- long n = 0;\r
- boolean oneFile = (asByteArray && fileName != null);\r
- int pt = (oneFile ? fileName.indexOf("|") : -1);\r
- String file0 = (pt >= 0 ? fileName : null);\r
- if (pt >= 0)\r
- fileName = fileName.substring(0, pt);\r
- try {\r
- while ((ze = zis.getNextEntry()) != null) {\r
- String name = ze.getName();\r
- if (fileName != null) {\r
- if (oneFile) {\r
- if (!name.equalsIgnoreCase(fileName))\r
- continue;\r
- } else {\r
- listing.append(name).appendC('\n');\r
- }\r
- }\r
- long nBytes = ze.getSize();\r
- byte[] bytes = Rdr.getLimitedStreamBytes(zis, nBytes);\r
- if (file0 != null) {\r
- readFileAsMap(Rdr.getBIS(bytes), cache, file0);\r
- return null;\r
- }\r
- n += bytes.length;\r
- Object o = (asByteArray ? new BArray(bytes) : bytes); \r
- cache.put((oneFile ? "_DATA_" : (fileName == null ? "" : fileName + "|") + name), o);\r
- if (oneFile)\r
- break;\r
- }\r
- zis.close();\r
- } catch (Exception e) {\r
- try {\r
- zis.close();\r
- } catch (IOException e1) {\r
- }\r
- return null;\r
- }\r
- if (n == 0 || fileName == null)\r
- return null;\r
- System.out.println("ZipTools cached " + n + " bytes from " + fileName);\r
- return listing.toString();\r
- }\r
-\r
- private static byte[] getPngImageBytes(BufferedInputStream bis) {\r
- try {\r
- if (Rdr.isPngZipStream(bis)) {\r
- int pt_count[] = new int[2];\r
- Rdr.getPngZipPointAndCount(bis, pt_count);\r
- if (pt_count[1] != 0)\r
- return deActivatePngZipB(Rdr.getLimitedStreamBytes(bis, pt_count[0]));\r
- }\r
- return Rdr.getLimitedStreamBytes(bis, -1);\r
- } catch (IOException e) {\r
- return null;\r
- }\r
- }\r
-\r
- /**\r
- * Once a PNGJ image has been extracted, we want to red-line its\r
- * iTXt "Jmol Type PNGJ" tag, since it is no longer associated with\r
- * ZIP data.\r
- * \r
- * @param bytes\r
- * @return disfigured bytes\r
- * \r
- */\r
- private static byte[] deActivatePngZipB(byte[] bytes) {\r
- // \0PNGJ starting at byte 50 changed to \0 NGJ\r
- if (Rdr.isPngZipB(bytes))\r
- bytes[51] = 32;\r
- return bytes;\r
- }\r
-\r
-\r
-\r
-}\r
+/* $RCSfile$
+ * $Author$
+ * $Date$
+ * $Revision$
+ *
+ * Copyright (C) 2006 The Jmol Development Team
+ *
+ * Contact: jmol-developers@lists.sf.net
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA.
+ */
+
+package javajs.util;
+
+import java.io.BufferedInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+
+import javajs.J2SIgnoreImport;
+import javajs.api.GenericZipInputStream;
+import javajs.api.GenericZipTools;
+import javajs.api.ZInputStream;
+
+import java.util.Map;
+import java.util.zip.CRC32;
+import java.util.zip.GZIPInputStream;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipInputStream;
+import java.util.zip.ZipOutputStream;
+
+
+/**
+ * Note the JSmol/HTML5 must use its own version of java.util.zip.ZipOutputStream.
+ *
+ */
+@J2SIgnoreImport({ java.util.zip.ZipOutputStream.class })
+public class ZipTools implements GenericZipTools {
+
+ public ZipTools() {
+ // for reflection
+ }
+
+ @Override
+ public ZInputStream newZipInputStream(InputStream is) {
+ return newZIS(is);
+ }
+
+ @SuppressWarnings("resource")
+ private static ZInputStream newZIS(InputStream is) {
+ return (is instanceof ZInputStream ? (ZInputStream) is
+ : is instanceof BufferedInputStream ? new GenericZipInputStream(is)
+ : new GenericZipInputStream(new BufferedInputStream(is)));
+ }
+
+ /**
+ * reads a ZIP file and saves all data in a Hashtable so that the files may be
+ * organized later in a different order. Also adds a #Directory_Listing entry.
+ *
+ * Files are bracketed by BEGIN Directory Entry and END Directory Entry lines,
+ * similar to CompoundDocument.getAllData.
+ *
+ * @param is
+ * @param subfileList
+ * @param name0
+ * prefix for entry listing
+ * @param binaryFileList
+ * |-separated list of files that should be saved as xx xx xx hex byte
+ * strings. The directory listing is appended with ":asBinaryString"
+ * @param fileData
+ */
+ @Override
+ public void getAllZipData(InputStream is, String[] subfileList,
+ String name0, String binaryFileList,
+ Map<String, String> fileData) {
+ ZipInputStream zis = (ZipInputStream) newZIS(is);
+ ZipEntry ze;
+ SB listing = new SB();
+ binaryFileList = "|" + binaryFileList + "|";
+ String prefix = PT.join(subfileList, '/', 1);
+ String prefixd = null;
+ if (prefix != null) {
+ prefixd = prefix.substring(0, prefix.indexOf("/") + 1);
+ if (prefixd.length() == 0)
+ prefixd = null;
+ }
+ try {
+ while ((ze = zis.getNextEntry()) != null) {
+ String name = ze.getName();
+ if (prefix != null && prefixd != null
+ && !(name.equals(prefix) || name.startsWith(prefixd)))
+ continue;
+ //System.out.println("ziputil: " + name);
+ listing.append(name).appendC('\n');
+ String sname = "|" + name.substring(name.lastIndexOf("/") + 1) + "|";
+ boolean asBinaryString = (binaryFileList.indexOf(sname) >= 0);
+ byte[] bytes = Rdr.getLimitedStreamBytes(zis, ze.getSize());
+ String str;
+ if (asBinaryString) {
+ str = getBinaryStringForBytes(bytes);
+ name += ":asBinaryString";
+ } else {
+ str = Rdr.fixUTF(bytes);
+ }
+ str = "BEGIN Directory Entry " + name + "\n" + str
+ + "\nEND Directory Entry " + name + "\n";
+ fileData.put(name0 + "|" + name, str);
+ }
+ } catch (Exception e) {
+ }
+ fileData.put("#Directory_Listing", listing.toString());
+ }
+
+ private String getBinaryStringForBytes(byte[] bytes) {
+ SB ret = new SB();
+ for (int i = 0; i < bytes.length; i++)
+ ret.append(Integer.toHexString(bytes[i] & 0xFF)).appendC(' ');
+ return ret.toString();
+ }
+
+ /**
+ * iteratively drills into zip files of zip files to extract file content or
+ * zip file directory. Also works with JAR files.
+ *
+ * Does not return "__MACOS" paths
+ *
+ * @param bis
+ * @param list
+ * @param listPtr
+ * @param asBufferedInputStream
+ * for Pmesh
+ * @return directory listing or subfile contents
+ */
+ @Override
+ public Object getZipFileDirectory(BufferedInputStream bis, String[] list,
+ int listPtr, boolean asBufferedInputStream) {
+ SB ret;
+ if (list == null || listPtr >= list.length)
+ return getZipDirectoryAsStringAndClose(bis);
+ bis = Rdr.getPngZipStream(bis, true);
+ String fileName = list[listPtr];
+ ZipInputStream zis = new ZipInputStream(bis);
+ ZipEntry ze;
+ //System.out.println("fname=" + fileName);
+ try {
+ boolean isAll = (fileName.equals("."));
+ if (isAll || fileName.lastIndexOf("/") == fileName.length() - 1) {
+ ret = new SB();
+ while ((ze = zis.getNextEntry()) != null) {
+ String name = ze.getName();
+ if (isAll || name.startsWith(fileName))
+ ret.append(name).appendC('\n');
+ }
+ String str = ret.toString();
+ return (asBufferedInputStream ? Rdr.getBIS(str.getBytes()) : str);
+ }
+ int pt = fileName.indexOf(":asBinaryString");
+ boolean asBinaryString = (pt > 0);
+ if (asBinaryString)
+ fileName = fileName.substring(0, pt);
+ fileName = fileName.replace('\\', '/');
+ while ((ze = zis.getNextEntry()) != null
+ && !fileName.equals(ze.getName())) {
+ }
+ byte[] bytes = (ze == null ? null : Rdr.getLimitedStreamBytes(zis,
+ ze.getSize()));
+ ze = null;
+ zis.close();
+ if (bytes == null)
+ return "";
+ if (Rdr.isZipB(bytes) || Rdr.isPngZipB(bytes))
+ return getZipFileDirectory(Rdr.getBIS(bytes), list, ++listPtr,
+ asBufferedInputStream);
+ if (asBufferedInputStream)
+ return Rdr.getBIS(bytes);
+ if (asBinaryString) {
+ ret = new SB();
+ for (int i = 0; i < bytes.length; i++)
+ ret.append(Integer.toHexString(bytes[i] & 0xFF)).appendC(' ');
+ return ret.toString();
+ }
+ if (Rdr.isGzipB(bytes))
+ bytes = Rdr.getLimitedStreamBytes(getUnGzippedInputStream(bytes), -1);
+ return Rdr.fixUTF(bytes);
+ } catch (Exception e) {
+ return "";
+ }
+ }
+
+ @Override
+ public byte[] getZipFileContentsAsBytes(BufferedInputStream bis,
+ String[] list, int listPtr) {
+ byte[] ret = new byte[0];
+ String fileName = list[listPtr];
+ if (fileName.lastIndexOf("/") == fileName.length() - 1)
+ return ret;
+ try {
+ bis = Rdr.getPngZipStream(bis, true);
+ ZipInputStream zis = new ZipInputStream(bis);
+ ZipEntry ze;
+ while ((ze = zis.getNextEntry()) != null) {
+ if (!fileName.equals(ze.getName()))
+ continue;
+ byte[] bytes = Rdr.getLimitedStreamBytes(zis, ze.getSize());
+ return ((Rdr.isZipB(bytes) || Rdr.isPngZipB(bytes)) && ++listPtr < list.length ? getZipFileContentsAsBytes(
+ Rdr.getBIS(bytes), list, listPtr) : bytes);
+ }
+ } catch (Exception e) {
+ }
+ return ret;
+ }
+
+ @Override
+ public String getZipDirectoryAsStringAndClose(BufferedInputStream bis) {
+ SB sb = new SB();
+ String[] s = new String[0];
+ try {
+ s = getZipDirectoryOrErrorAndClose(bis, null);
+ bis.close();
+ } catch (Exception e) {
+ System.out.println(e.toString());
+ }
+ for (int i = 0; i < s.length; i++)
+ sb.append(s[i]).appendC('\n');
+ return sb.toString();
+ }
+
+ @Override
+ public String[] getZipDirectoryAndClose(BufferedInputStream bis,
+ String manifestID) {
+ String[] s = new String[0];
+ try {
+ s = getZipDirectoryOrErrorAndClose(bis, manifestID);
+ bis.close();
+ } catch (Exception e) {
+ System.out.println(e.toString());
+ }
+ return s;
+ }
+
+ private String[] getZipDirectoryOrErrorAndClose(BufferedInputStream bis,
+ String manifestID)
+ throws IOException {
+ bis = Rdr.getPngZipStream(bis, true);
+ Lst<String> v = new Lst<String>();
+ ZipInputStream zis = new ZipInputStream(bis);
+ ZipEntry ze;
+ String manifest = null;
+ while ((ze = zis.getNextEntry()) != null) {
+ String fileName = ze.getName();
+ if (manifestID != null && fileName.startsWith(manifestID))
+ manifest = getStreamAsString(zis);
+ else if (!fileName.startsWith("__MACOS")) // resource fork not nec.
+ v.addLast(fileName);
+ }
+ zis.close();
+ if (manifestID != null)
+ v.add(0, manifest == null ? "" : manifest + "\n############\n");
+ return v.toArray(new String[v.size()]);
+ }
+
+ public static String getStreamAsString(InputStream is) throws IOException {
+ return Rdr.fixUTF(Rdr.getLimitedStreamBytes(is, -1));
+ }
+
+ @Override
+ public InputStream newGZIPInputStream(InputStream is) throws IOException {
+ return new BufferedInputStream(new GZIPInputStream(is, 512));
+ }
+
+ @Override
+ public BufferedInputStream getUnGzippedInputStream(byte[] bytes) {
+ try {
+ return Rdr.getUnzippedInputStream(this, Rdr.getBIS(bytes));
+ } catch (Exception e) {
+ return null;
+ }
+ }
+
+ @Override
+ public void addZipEntry(Object zos, String fileName) throws IOException {
+ ((ZipOutputStream) zos).putNextEntry(new ZipEntry(fileName));
+ }
+
+ @Override
+ public void closeZipEntry(Object zos) throws IOException {
+ ((ZipOutputStream) zos).closeEntry();
+ }
+
+ @Override
+ public Object getZipOutputStream(Object bos) {
+ /**
+ * @j2sNative
+ *
+ * return javajs.api.Interface.getInterface(
+ * "java.util.zip.ZipOutputStream").setZOS(bos);
+ *
+ */
+ {
+ return new ZipOutputStream((OutputStream) bos);
+ }
+ }
+
+ @Override
+ public int getCrcValue(byte[] bytes) {
+ CRC32 crc = new CRC32();
+ crc.update(bytes, 0, bytes.length);
+ return (int) crc.getValue();
+ }
+
+ @Override
+ public void readFileAsMap(BufferedInputStream bis, Map<String, Object> bdata, String name) {
+ int pt = (name == null ? -1 : name.indexOf("|"));
+ name = (pt >= 0 ? name.substring(pt + 1) : null);
+ try {
+ if (Rdr.isPngZipStream(bis)) {
+ boolean isImage = "_IMAGE_".equals(name);
+ if (name == null || isImage)
+ bdata.put((isImage ? "_DATA_" : "_IMAGE_"), new BArray(getPngImageBytes(bis)));
+ if (!isImage)
+ cacheZipContents(bis, name, bdata, true);
+ } else if (Rdr.isZipS(bis)) {
+ cacheZipContents(bis, name, bdata, true);
+ } else if (name == null){
+ bdata.put("_DATA_", new BArray(Rdr.getLimitedStreamBytes(bis, -1)));
+ } else {
+ throw new IOException("ZIP file " + name + " not found");
+ }
+ bdata.put("$_BINARY_$", Boolean.TRUE);
+ } catch (IOException e) {
+ bdata.clear();
+ bdata.put("_ERROR_", e.getMessage());
+ }
+ }
+
+ @Override
+ public String cacheZipContents(BufferedInputStream bis,
+ String fileName,
+ Map<String, Object> cache,
+ boolean asByteArray) {
+ ZipInputStream zis = (ZipInputStream) newZIS(bis);
+ ZipEntry ze;
+ SB listing = new SB();
+ long n = 0;
+ boolean oneFile = (asByteArray && fileName != null);
+ int pt = (oneFile ? fileName.indexOf("|") : -1);
+ String file0 = (pt >= 0 ? fileName : null);
+ if (pt >= 0)
+ fileName = fileName.substring(0, pt);
+ try {
+ while ((ze = zis.getNextEntry()) != null) {
+ String name = ze.getName();
+ if (fileName != null) {
+ if (oneFile) {
+ if (!name.equalsIgnoreCase(fileName))
+ continue;
+ } else {
+ listing.append(name).appendC('\n');
+ }
+ }
+ long nBytes = ze.getSize();
+ byte[] bytes = Rdr.getLimitedStreamBytes(zis, nBytes);
+ if (file0 != null) {
+ readFileAsMap(Rdr.getBIS(bytes), cache, file0);
+ return null;
+ }
+ n += bytes.length;
+ Object o = (asByteArray ? new BArray(bytes) : bytes);
+ cache.put((oneFile ? "_DATA_" : (fileName == null ? "" : fileName + "|") + name), o);
+ if (oneFile)
+ break;
+ }
+ zis.close();
+ } catch (Exception e) {
+ try {
+ zis.close();
+ } catch (IOException e1) {
+ }
+ return null;
+ }
+ if (n == 0 || fileName == null)
+ return null;
+ System.out.println("ZipTools cached " + n + " bytes from " + fileName);
+ return listing.toString();
+ }
+
+ private static byte[] getPngImageBytes(BufferedInputStream bis) {
+ try {
+ if (Rdr.isPngZipStream(bis)) {
+ int pt_count[] = new int[2];
+ Rdr.getPngZipPointAndCount(bis, pt_count);
+ if (pt_count[1] != 0)
+ return deActivatePngZipB(Rdr.getLimitedStreamBytes(bis, pt_count[0]));
+ }
+ return Rdr.getLimitedStreamBytes(bis, -1);
+ } catch (IOException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Once a PNGJ image has been extracted, we want to red-line its
+ * iTXt "Jmol Type PNGJ" tag, since it is no longer associated with
+ * ZIP data.
+ *
+ * @param bytes
+ * @return disfigured bytes
+ *
+ */
+ private static byte[] deActivatePngZipB(byte[] bytes) {
+ // \0PNGJ starting at byte 50 changed to \0 NGJ
+ if (Rdr.isPngZipB(bytes))
+ bytes[51] = 32;
+ return bytes;
+ }
+
+
+
+}