use directly sharedrawweb java code here Signed-off-by: philippe lhardy <philippe.lhardy@astrolabe.coop>
147 lines
3.9 KiB
Java
147 lines
3.9 KiB
Java
/*
|
|
This file is part of ShareDrawWeb.
|
|
|
|
ShareDrawWeb 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.
|
|
|
|
ShareDrawWeb 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 ShareDrawWeb; if not, write to the Free Software
|
|
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
|
|
*/
|
|
|
|
package org.artisanlogiciel.compression.graphics;
|
|
|
|
/*
|
|
simple class to read bitfields
|
|
@see BitFieldWriter
|
|
@author Philippe Lhardy
|
|
*/
|
|
|
|
import java.io.*;
|
|
|
|
class BitFieldReader {
|
|
|
|
// size of nextWord
|
|
final int dataSize = 32;
|
|
|
|
/* offset of next bit to be read in current word
|
|
should ensure bitOffset < dataSize
|
|
*/
|
|
private int bitOffset = 0;
|
|
|
|
/* word used waiting to be fully read
|
|
dataSize is bit size of currentWord
|
|
currentWord is part of word read that begins at bitOffset.
|
|
*/
|
|
private int currentWord = 0;
|
|
|
|
private DataInputStream inputStream;
|
|
|
|
/* value returned is an int between 0 and 2^bits-1 */
|
|
public int read( int bits) throws java.io.IOException {
|
|
int field = 0;
|
|
int head = 0;
|
|
|
|
// a new word is needed
|
|
if ( bitOffset == 0 ) {
|
|
nextWord();
|
|
}
|
|
// if more bits needed that word currently used.
|
|
if ( bits + bitOffset > dataSize) {
|
|
// warning recursive call ( not terminal )
|
|
int bitsize = dataSize - bitOffset;
|
|
head = read( dataSize - bitOffset);
|
|
// current word had entirely been read, need a new one
|
|
// don't do that... nextWord() will be done by next read...
|
|
field = read( bits - bitsize);
|
|
// reconstruct all
|
|
// more significant bits in first word, least in last
|
|
field = field | ( head << (bits - bitsize));
|
|
}
|
|
else {
|
|
// terminal part do the job
|
|
if ( bits == dataSize) {
|
|
// special case to keep sign
|
|
field = currentWord;
|
|
currentWord = 0;
|
|
bitOffset = 0;
|
|
}
|
|
else {
|
|
field = ( currentWord >> ( dataSize - bits) )
|
|
& ( 0x7fffffff >> ( dataSize - 1 - bits) );
|
|
// bits are read then remove them from currentWord
|
|
currentWord <<= bits;
|
|
bitOffset = ( bitOffset + bits ) % dataSize;
|
|
/*
|
|
System.out.println( "size " + Integer.toString(bits)
|
|
+ " value " + Integer.toString(field)
|
|
+ " offset " + Integer.toString(bitOffset)
|
|
+ " currentWord " + Integer.toString( currentWord)
|
|
);
|
|
*/
|
|
}
|
|
}
|
|
|
|
|
|
return field;
|
|
}
|
|
|
|
|
|
private int getInt( byte[] pBytes)
|
|
{
|
|
long field = 0;
|
|
field = pBytes[0]<<24 | pBytes[1]<<16 | pBytes[2]<<8 | pBytes[3];
|
|
return (int) field;
|
|
}
|
|
|
|
|
|
/**
|
|
* doesn't work correctly as readInt
|
|
*/
|
|
private int readInt()
|
|
throws IOException
|
|
{
|
|
byte bytes[]=new byte[4];
|
|
int nr=0;
|
|
int index = 0;
|
|
/* read at least 4 bytes */
|
|
while ( ( nr != -1) && ( index < 4 ) )
|
|
{
|
|
nr = inputStream.read( bytes, index, 4 - index);
|
|
index +=nr;
|
|
}
|
|
return getInt( bytes);
|
|
}
|
|
|
|
|
|
private void nextWord() throws java.io.IOException {
|
|
// read next word
|
|
// currentWord = readInt();
|
|
currentWord= inputStream.readInt();
|
|
bitOffset = 0;
|
|
}
|
|
|
|
/*
|
|
go to next entire word.
|
|
*/
|
|
public void padToWord() throws java.io.IOException {
|
|
if ( bitOffset != 0) {
|
|
nextWord();
|
|
}
|
|
}
|
|
|
|
/* set InputStream */
|
|
public void setInputStream( InputStream input) {
|
|
inputStream = new DataInputStream(input);
|
|
}
|
|
|
|
}
|