package org.eclipse.swt.internal.image;

/*
 * (c) Copyright IBM Corp. 2000, 2001.
 * All Rights Reserved
 */

public class PngHuffmanTables {
	PngHuffmanTable literalTable;
	PngHuffmanTable distanceTable;
	
	static PngHuffmanTable FixedLiteralTable;
	static PngHuffmanTable FixedDistanceTable;
	
	static final int LiteralTableSize = 288;
	static final int[] FixedLiteralLengths = {
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
        9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,
        9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,
        9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,
        9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,
        9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 7, 7, 7, 7, 7, 7, 7, 7,
        7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8, 8, 8, 8, 8, 8,
	};

	static final int DistanceTableSize = 32;
	static final int[] FixedDistanceLengths = {
		5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
		5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
	};
	
	static final int LengthCodeTableSize = 19;
	static final int[] LengthCodeOrder = {
		16, 17, 18, 0, 8, 7, 9, 6, 10, 5,
		11, 4, 12, 3, 13, 2, 14, 1, 15
	};
	
static PngHuffmanTables getDynamicTables(PngDecodingDataStream stream){
	return new PngHuffmanTables(stream);
}
static PngHuffmanTables getFixedTables() {
	return new PngHuffmanTables();
}

private PngHuffmanTable getFixedLiteralTable() {
	if (FixedLiteralTable == null) {
		FixedLiteralTable = new PngHuffmanTable(FixedLiteralLengths);
	}
	return FixedLiteralTable;
}

private PngHuffmanTable getFixedDistanceTable() {
	if (FixedDistanceTable == null) {
		FixedDistanceTable = new PngHuffmanTable(FixedDistanceLengths);
	}
	return FixedDistanceTable;
}

private PngHuffmanTables () {
	super();
	literalTable = getFixedLiteralTable();
	distanceTable = getFixedDistanceTable();
}

private PngHuffmanTables (PngDecodingDataStream stream) {
	super();
	
	int literals = PngLzBlockReader.FIRST_LENGTH_CODE 
		+ stream.getNextIdatBits(5);
	int distances = PngLzBlockReader.FIRST_DISTANCE_CODE 
		+ stream.getNextIdatBits(5);
	int codeLengthCodes = PngLzBlockReader.FIRST_CODE_LENGTH_CODE 
		+ stream.getNextIdatBits(4);
	
	if (codeLengthCodes > PngLzBlockReader.LAST_CODE_LENGTH_CODE) {
		stream.error();
	}
	
	/* Tricky, tricky, tricky. The length codes are stored in
	 * a very odd order. (For the order, see the definition of
	 * the static field lengthCodeOrder.) Also, the data may 
	 * not contain values for all the codes. It may just contain 
	 * values for the first X number of codes. The table should
	 * be of size <LengthCodeTableSize> regardless of the number
	 * of values actually given in the table.
	 */	
	int[] lengthCodes = new int[LengthCodeTableSize];
	for (int i = 0; i < codeLengthCodes; i++) {
		lengthCodes[LengthCodeOrder[i]] = stream.getNextIdatBits(3);
	}
	PngHuffmanTable codeLengthsTable = new PngHuffmanTable(lengthCodes);
	
	int[] literalLengths = readLengths(
		stream, literals, codeLengthsTable, LiteralTableSize);
	int[] distanceLengths = readLengths(
		stream, distances, codeLengthsTable, DistanceTableSize);
	
	literalTable = new PngHuffmanTable(literalLengths);
	distanceTable = new PngHuffmanTable(distanceLengths);
}

private int [] readLengths (PngDecodingDataStream stream, 
	int numLengths, 
	PngHuffmanTable lengthsTable,
	int tableSize) 
{
	int[] lengths = new int[tableSize];
	
	for (int index = 0; index < numLengths;) {
		int value = lengthsTable.getNextValue(stream);
		if (value < 16) {
			// Literal value
			lengths[index] = value;
			index++;
		} else if (value == 16) {
			// Repeat the previous code 3-6 times.
			int count = stream.getNextIdatBits(2) + 3;
			for (int i = 0; i < count; i++) {
				lengths[index] = lengths [index - 1];
				index++;
			}
		} else if (value == 17) {
			// Repeat 0 3-10 times.
			int count = stream.getNextIdatBits(3) + 3;
			for (int i = 0; i < count; i++) {
				lengths[index] = 0;
				index++;
			}
		} else if (value == 18) {
			// Repeat 0 11-138 times.
			int count = stream.getNextIdatBits(7) + 11;
			for (int i = 0; i < count; i++) {
				lengths[index] = 0;
				index++;
			}
		} else {
			stream.error();
		}
	}
	return lengths;
}

int getNextLiteralValue(PngDecodingDataStream stream) {
	return literalTable.getNextValue(stream);
}

int getNextDistanceValue(PngDecodingDataStream stream) {
	return distanceTable.getNextValue(stream);
}

}
