Java tutorial
/* * LumaQQ - Java QQ Client * * Copyright (C) 2004 luma <stubma@163.com> * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program 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 General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ package edu.tsinghua.lumaqq.customface; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.util.Iterator; import org.apache.poi.poifs.filesystem.DirectoryEntry; import org.apache.poi.poifs.filesystem.DocumentEntry; import org.apache.poi.poifs.filesystem.DocumentInputStream; import org.apache.poi.poifs.filesystem.Entry; import org.apache.poi.poifs.filesystem.POIFSFileSystem; import org.eclipse.swt.SWT; import org.eclipse.swt.SWTException; import org.eclipse.swt.graphics.ImageData; import org.eclipse.swt.graphics.ImageLoader; import edu.tsinghua.lumaqq.ecore.face.FaceConstant; import edu.tsinghua.lumaqq.ecore.face.FaceGroup; /** * EIP?EIPPOIFS * POIFS???http://jakarta.apache.org/poi/poifs/fileformat.html * * EIP? * * 1. config, ? * 2. Files, * * configFace.xml?? * Files???????? * ?wordword? * ?word?????0 * Fixed???0Fixed??Faces.xml? * * @author notXX * @author luma */ public class EIPImporter { private static final String CONFIG_DIRECTORY = "config"; private static final String FILES_DIRECTORY = "files"; private static final String CONFIG_FILE = "face.xml"; private static final String THUMB_SUFFIX = "fixed"; private byte[] buffer; private FaceEntry entry; private String destDir; private FileInputStream eipStream; private FaceXMLParser parser; private Iterator<Entry> groupIterator; private Iterator<Entry> faceIterator; private DirectoryEntry currentDir; private DocumentEntry currentFace; @SuppressWarnings("unchecked") public EIPImporter(String file, String destDir) { this.destDir = destDir; buffer = new byte[8192]; POIFSFileSystem eipSystem; try { // eip eipStream = new FileInputStream(file); eipSystem = new POIFSFileSystem(eipStream); // DirectoryEntry configDir = null, fileDir = null; DirectoryEntry root = eipSystem.getRoot(); Iterator<Entry> i = root.getEntries(); while (i.hasNext()) { Entry e = i.next(); if (e.isDirectoryEntry()) { if (CONFIG_DIRECTORY.equals(e.getName().toLowerCase())) configDir = (DirectoryEntry) e; else if (FILES_DIRECTORY.equals(e.getName().toLowerCase())) fileDir = (DirectoryEntry) e; } } // ?? if (configDir == null || fileDir == null) throw new IOException("Can't find correct directories"); // ?face.xml i = configDir.getEntries(); while (i.hasNext()) { Entry e = i.next(); if (e.isDocumentEntry() && CONFIG_FILE.equals(e.getName().toLowerCase())) { DocumentInputStream dis = new DocumentInputStream((DocumentEntry) e); parser = new FaceXMLParser(dis); dis.close(); break; } } // ??face.xml if (parser == null) throw new IOException("Can't find " + CONFIG_FILE); // iterator groupIterator = fileDir.getEntries(); currentDir = fileDir; faceIterator = currentDir.getEntries(); } catch (IOException e) { eipSystem = null; try { if (eipStream != null) { eipStream.close(); eipStream = null; } } catch (IOException e1) { } } } /** * */ public void dispose() { try { if (eipStream != null) eipStream.close(); } catch (IOException e) { } } /** * @return * null??"." */ @SuppressWarnings("unchecked") public FaceEntry getNextEntry() { if (currentDir == null) return null; while (true) { currentFace = getNextDocument(); if (currentFace == null) { currentDir = getNextDir(); if (currentDir == null) return null; faceIterator = currentDir.getEntries(); } else if (currentFace.getName().toLowerCase().endsWith(THUMB_SUFFIX)) continue; else break; } entry = parser.getEntry(currentFace.getName()); entry.groupName = currentDir.getName(); if (entry.groupName.toLowerCase().equals(FILES_DIRECTORY)) entry.groupName = "."; return entry; } /** * ? * * @param g * * @return * true? */ public boolean saveEntry(FaceGroup g) { if (g.getId() == FaceConstant.CUSTOM_HEAD_GROUP_ID) return saveCustomHead(g); else { FileOutputStream fos = null; DocumentInputStream dis = null; try { // ? String filename = destDir + g.getId() + '/' + entry.filename; fos = new FileOutputStream(filename); dis = new DocumentInputStream(currentFace); for (int i = 0; i != -1; i = dis.read(buffer, 0, buffer.length)) fos.write(buffer, 0, i); // ? try { ImageLoader loader = new ImageLoader(); loader.load(filename); ImageData data = loader.data[0].scaledTo(20, 20); loader = new ImageLoader(); loader.data = new ImageData[] { data }; loader.save(destDir + g.getId() + '/' + entry.md5 + "fixed.bmp", SWT.IMAGE_BMP); } catch (SWTException e) { return false; } return true; } catch (IOException e) { return false; } finally { try { if (fos != null) fos.close(); if (dis != null) dis.close(); } catch (IOException e) { } } } } /** * ?? * * @return * true?? */ private boolean saveCustomHead(FaceGroup g) { DocumentInputStream dis = null; try { // ? ByteArrayOutputStream baos = new ByteArrayOutputStream(); dis = new DocumentInputStream(currentFace); for (int i = 0; i != -1; i = dis.read(buffer, 0, buffer.length)) baos.write(buffer, 0, i); // ?ImageData ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray()); ImageData origin = new ImageData(bais); ImageData data = origin.scaledTo(40, 40); // save 40x40 bmp ImageLoader saveLoader = new ImageLoader(); saveLoader.data = new ImageData[] { data }; saveLoader.save(destDir + g.getId() + '/' + entry.md5 + ".bmp", SWT.IMAGE_BMP); // save 20x20 bmp data = origin.scaledTo(20, 20); saveLoader = new ImageLoader(); saveLoader.data = new ImageData[] { data }; saveLoader.save(destDir + g.getId() + '/' + entry.md5 + "fixed.bmp", SWT.IMAGE_BMP); return true; } catch (SWTException e) { return false; } catch (IOException e) { return false; } finally { try { if (dis != null) dis.close(); } catch (IOException e) { } } } /** * @return * ?document entry */ private DocumentEntry getNextDocument() { DocumentEntry de = null; while (faceIterator.hasNext()) { Entry e = faceIterator.next(); if (e.isDocumentEntry()) { de = (DocumentEntry) e; break; } } return de; } /** * @return * */ private DirectoryEntry getNextDir() { DirectoryEntry dir = null; while (groupIterator.hasNext()) { Entry e = groupIterator.next(); if (e.isDirectoryEntry()) { dir = (DirectoryEntry) e; break; } } return dir; } }