⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sstdeserializer.java

📁 Office格式转换代码
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
     * contains the same kind of data that the SST record contains,     * with the following exceptions:     * <P>     * <OL>     * <LI>The string counts at the beginning of the SST record are     *     not in the Continue record     * <LI>The first string in the Continue record might NOT begin     *     with a size. If the last string in the previous record is     *     continued in this record, the size is determined by that     *     last string in the previous record; the first string will     *     begin with a flag byte, followed by the remaining bytes (or     *     words) of the last string from the previous     *     record. Otherwise, the first string in the record will     *     begin with a string length     * </OL>     *     * @param record the Continue record's byte data     */    public void processContinueRecord( final byte[] record )    {        if ( isStringFinished() )        {            final int offset = continueSkipBytes;            initVars();            manufactureStrings( record, offset);        }        else        {            // reset the wide bit because that can change across a continuation. the fact that it's            // actually rich text doesn't change across continuations even though the rich text            // may on longer be set in the "new" option flag.  confusing huh?            wideChar = ( record[0] & 1 ) == 1;            if ( stringSpansContinuation( record.length - LittleEndianConsts.BYTE_SIZE ) )            {                processEntireContinuation( record );            }            else            {                readStringRemainder( record );            }        }    }    /**     * Reads the remainder string and any subsequent strings from the continuation record.     *     * @param record  The entire continuation record data.     */    private void readStringRemainder( final byte[] record )    {        int stringRemainderSizeInBytes = calculateByteCount( charCount-getContinuationCharsRead() );        byte[] unicodeStringData = new byte[SSTRecord.STRING_MINIMAL_OVERHEAD                + stringRemainderSizeInBytes];        // write the string length        LittleEndian.putShort( unicodeStringData, 0, (short) (charCount-getContinuationCharsRead()) );        // write the options flag        unicodeStringData[LittleEndianConsts.SHORT_SIZE] = createOptionByte( wideChar, richText, extendedText );        // copy the bytes/words making up the string; skipping        // past all the overhead of the str_data array        arraycopy( record, LittleEndianConsts.BYTE_SIZE, unicodeStringData,                SSTRecord.STRING_MINIMAL_OVERHEAD,                stringRemainderSizeInBytes );        // use special constructor to create the final string        UnicodeString string = new UnicodeString( UnicodeString.sid,                (short) unicodeStringData.length, unicodeStringData,                unfinishedString );        Integer integer = new Integer( strings.size() );        addToStringTable( strings, integer, string );        int newOffset = offsetForContinuedRecord( stringRemainderSizeInBytes );        manufactureStrings( record, newOffset);    }    /**     * Calculates the size of the string in bytes based on the character width     */    private int stringSizeInBytes()    {        return calculateByteCount( charCount );    }    /**     * Calculates the size of the string in byes.  This figure includes all the over     * heads for the string.     */    private int totalStringSize()    {        return stringSizeInBytes()                + stringHeaderOverhead()                + LittleEndianConsts.INT_SIZE * runCount                + extensionLength;    }    private int stringHeaderOverhead()    {        return SSTRecord.STRING_MINIMAL_OVERHEAD                + ( richText ? LittleEndianConsts.SHORT_SIZE : 0 )                + ( extendedText ? LittleEndianConsts.INT_SIZE : 0 );    }    private int offsetForContinuedRecord( int stringRemainderSizeInBytes )    {        int offset = stringRemainderSizeInBytes + runCount * LittleEndianConsts.INT_SIZE + extensionLength;                if (stringRemainderSizeInBytes != 0)          //If a portion of the string remains then the wideChar options byte is repeated,          //so need to skip this.          offset += + LittleEndianConsts.BYTE_SIZE;        return offset;      }    private byte createOptionByte( boolean wideChar, boolean richText, boolean farEast )    {        return (byte) ( ( wideChar ? 1 : 0 ) + ( farEast ? 4 : 0 ) + ( richText ? 8 : 0 ) );    }    /**     * If the continued record is so long is spans into the next continue then     * simply suck the remaining string data into the existing <code>unfinishedString</code>.     *     * @param record    The data from the continuation record.     */    private void processEntireContinuation( final byte[] record )    {        // create artificial data to create a UnicodeString        int dataLengthInBytes = record.length - LittleEndianConsts.BYTE_SIZE;        byte[] unicodeStringData = new byte[record.length + LittleEndianConsts.SHORT_SIZE];        int charsRead = calculateCharCount( dataLengthInBytes );        LittleEndian.putShort( unicodeStringData, (byte) 0, (short) charsRead );        arraycopy( record, 0, unicodeStringData, LittleEndianConsts.SHORT_SIZE, record.length );        UnicodeString ucs = new UnicodeString( UnicodeString.sid, (short) unicodeStringData.length, unicodeStringData, unfinishedString);        unfinishedString = ucs.getString();        setContinuationCharsRead( getContinuationCharsRead() + charsRead );        if (getContinuationCharsRead() == charCount) {          Integer integer = new Integer( strings.size() );          addToStringTable( strings, integer, ucs );        }    }    private boolean stringSpansContinuation( int continuationSizeInBytes )    {        return calculateByteCount( charCount - getContinuationCharsRead() ) > continuationSizeInBytes;    }    /**     * @return the number of characters we expect in the first     *         sub-record in a subsequent continuation record     */    int getContinuationCharsRead()    {        return continuationReadChars;    }    private void setContinuationCharsRead( final int count )    {        continuationReadChars = count;    }    private int calculateByteCount( final int character_count )    {        return character_count * ( wideChar ? LittleEndianConsts.SHORT_SIZE : LittleEndianConsts.BYTE_SIZE );    }    /**     * Copies an array from the specified source array, beginning at the     * specified position, to the specified position of the destination array.     * A subsequence of array components are copied from the source     * array referenced by <code>src</code> to the destination array     * referenced by <code>dst</code>. The number of components copied is     * equal to the <code>length</code> argument. The components at     * positions <code>srcOffset</code> through     * <code>srcOffset+length-1</code> in the source array are copied into     * positions <code>dstOffset</code> through     * <code>dstOffset+length-1</code>, respectively, of the destination     * array.     * <p>     * If the <code>src</code> and <code>dst</code> arguments refer to the     * same array object, then the copying is performed as if the     * components at positions <code>srcOffset</code> through     * <code>srcOffset+length-1</code> were first copied to a temporary     * array with <code>length</code> components and then the contents of     * the temporary array were copied into positions     * <code>dstOffset</code> through <code>dstOffset+length-1</code> of the     * destination array.     * <p>     * If <code>dst</code> is <code>null</code>, then a     * <code>NullPointerException</code> is thrown.     * <p>     * If <code>src</code> is <code>null</code>, then a     * <code>NullPointerException</code> is thrown and the destination     * array is not modified.     * <p>     * Otherwise, if any of the following is true, an     * <code>ArrayStoreException</code> is thrown and the destination is     * not modified:     * <ul>     * <li>The <code>src</code> argument refers to an object that is not an     *     array.     * <li>The <code>dst</code> argument refers to an object that is not an     *     array.     * <li>The <code>src</code> argument and <code>dst</code> argument refer to     *     arrays whose component types are different primitive types.     * <li>The <code>src</code> argument refers to an array with a primitive     *     component type and the <code>dst</code> argument refers to an array     *     with a reference component type.     * <li>The <code>src</code> argument refers to an array with a reference     *     component type and the <code>dst</code> argument refers to an array     *     with a primitive component type.     * </ul>     * <p>     * Otherwise, if any of the following is true, an     * <code>IndexOutOfBoundsException</code> is     * thrown and the destination is not modified:     * <ul>     * <li>The <code>srcOffset</code> argument is negative.     * <li>The <code>dstOffset</code> argument is negative.     * <li>The <code>length</code> argument is negative.     * <li><code>srcOffset+length</code> is greater than     *     <code>src.length</code>, the length of the source array.     * <li><code>dstOffset+length</code> is greater than     *     <code>dst.length</code>, the length of the destination array.     * </ul>     * <p>     * Otherwise, if any actual component of the source array from     * position <code>srcOffset</code> through     * <code>srcOffset+length-1</code> cannot be converted to the component     * type of the destination array by assignment conversion, an     * <code>ArrayStoreException</code> is thrown. In this case, let     * <b><i>k</i></b> be the smallest nonnegative integer less than     * length such that <code>src[srcOffset+</code><i>k</i><code>]</code>     * cannot be converted to the component type of the destination     * array; when the exception is thrown, source array components from     * positions <code>srcOffset</code> through     * <code>srcOffset+</code><i>k</i><code>-1</code>     * will already have been copied to destination array positions     * <code>dstOffset</code> through     * <code>dstOffset+</code><i>k</I><code>-1</code> and no other     * positions of the destination array will have been modified.     * (Because of the restrictions already itemized, this     * paragraph effectively applies only to the situation where both     * arrays have component types that are reference types.)     *     * @param      src          the source array.     * @param      src_position start position in the source array.     * @param      dst          the destination array.     * @param      dst_position pos   start position in the destination data.     * @param      length       the number of array elements to be copied.     * @exception  IndexOutOfBoundsException  if copying would cause     *               access of data outside array bounds.     * @exception  ArrayStoreException  if an element in the <code>src</code>     *               array could not be stored into the <code>dest</code> array     *               because of a type mismatch.     * @exception  NullPointerException if either <code>src</code> or     *               <code>dst</code> is <code>null</code>.     */    private void arraycopy( byte[] src, int src_position,                            byte[] dst, int dst_position,                            int length )    {        System.arraycopy( src, src_position, dst, dst_position, length );    }    /**     * @return the unfinished string     */    String getUnfinishedString()    {        return unfinishedString;    }    /**     * @return true if current string uses wide characters     */    boolean isWideChar()    {        return wideChar;    }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -