All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.jpedal.parser.image.SMaskDecoder Maven / Gradle / Ivy

There is a newer version: 20151002
Show newest version
/*
* ===========================================
* Java Pdf Extraction Decoding Access Library
* ===========================================
*
* Project Info:  http://www.idrsolutions.com
* Help section for developers at http://www.idrsolutions.com/support/
*
* (C) Copyright 1997-2015 IDRsolutions and Contributors.
*
* This file is part of JPedal/JPDF2HTML5
*
    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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA


*
* ---------------
* SMaskDecoder.java
* ---------------
*/

package org.jpedal.parser.image;

import java.nio.ByteBuffer;
import java.util.Arrays;
import org.jpedal.color.ColorSpaces;
import org.jpedal.color.GenericColorSpace;
import org.jpedal.color.JPEGDecoder;
import org.jpedal.io.ColorSpaceConvertor;
import org.jpedal.objects.raw.PdfDictionary;
import org.jpedal.objects.raw.PdfObject;
import org.jpedal.parser.image.data.ImageData;

/**
 *
 * @author markee
 */
class SMaskDecoder {
    
    public static byte[] applyJPX_JBIG_Smask(final ImageData imageData, final ImageData smaskData, byte[] maskData,PdfObject imageObject, PdfObject maskObject, GenericColorSpace colorSpace, GenericColorSpace maskCS){
        byte[] objectData = imageData.getObjectData();
        int iw=imageData.getWidth();
        int ih=imageData.getHeight();
        int id=imageData.getDepth();
        
        float[] matte = maskObject.getFloatArray(PdfDictionary.Matte);
        
        smaskData.getFilter(maskObject);
        if(smaskData.isDCT()){
            maskData=JPEGDecoder.getBytesFromJPEG(maskData,maskCS,maskObject);
            maskObject.setMixedArray(PdfDictionary.Filter,null);
            maskObject.setDecodedStream(maskData);
        }else if(smaskData.isJPX()){
            maskData=JPeg2000ImageDecoder.getBytesFromJPEG2000(maskData,maskCS,maskObject);
            maskObject.setMixedArray(PdfDictionary.Filter,null);
            maskObject.setDecodedStream(maskData);
        }else {
            objectData = ColorSpaceConvertor.normaliseTo8Bit(id, iw, ih, objectData);
        }
                
        int sw=smaskData.getWidth();
        int sh=smaskData.getHeight();
        int sd=smaskData.getDepth();
        
        float [] decodeArr = maskObject.getFloatArray(PdfDictionary.Decode);
                
        if(decodeArr!=null && decodeArr[0]==1 && decodeArr[1]==0){ // data inverted refer to dec2011/example.pdf
            for (int i = 0; i < maskData.length; i++) {
                maskData[i]^= 0xff;
            }
        }
        
        byte[] index=colorSpace.getIndexedMap();
       
        if(index!=null){
            index=colorSpace.convertIndexToRGB(index);
            objectData=ColorSpaceConvertor.convertIndexToRGBByte(index, iw, ih, imageData.getCompCount(), id, objectData, false, false);
        } else if (imageData.isDCT() || imageData.isJPX() || imageData.isJBIG()) {      
         
        } else if(colorSpace.getID()==ColorSpaces.DeviceGray){
            objectData=colorSpace.dataToRGBByteArray(objectData,iw,ih,false);
            if(matte!=null){
                matte = new float[]{matte[0],matte[0],matte[0]};
            }
        } else if(colorSpace.getID()==ColorSpaces.CalRGB){
        } else if(colorSpace.getID()==ColorSpaces.DeviceRGB){
        } else {
            objectData=colorSpace.dataToRGBByteArray(objectData,iw,ih,false);   
        }
        
        maskData = ColorSpaceConvertor.normaliseTo8Bit(sd,sw, sh, maskData);
        
        int imageDim = iw*ih;
        int maskDim = sw*sh;
        if(imageDim>maskDim){
            maskData  = getScaledBytes(maskData, sw, sh, iw, ih);            
        }else if(maskDim>imageDim){
            objectData = getScaledBytes(objectData, iw, ih, sw, sh);
            imageDim = maskDim;
            iw = sw;
            ih = sh;
        }else{
            //do nothing
        }
        int p = 0;
               
        ByteBuffer buffer = ByteBuffer.allocate(iw*ih*4);
                        
        if (imageDim == objectData.length) {
            int aa = 0;
            for (int i = 0; i < imageDim; i++) {
                byte r = objectData[i] ;
                for (int j = 0; j < 3; j++) {
                    buffer.put(r);
                }
                buffer.put(maskData[aa++]); // write out maskData[aa++] directly and lose a ?
            }
        } else {
            if(matte!=null){
                for (int i = 0; i < maskData.length; i++) {
                    int a = maskData[i] & 0xff;
                    int r = objectData[p++] & 0xff;
                    int g = objectData[p++] & 0xff;
                    int b = objectData[p++] & 0xff;
                    
                    if(a!=0){
                        double k = 255.0/a;
                        r = (int) ((r-matte[0])*k+matte[0]);
                        g = (int) ((g-matte[1])*k+matte[1]);
                        b = (int) ((b-matte[2])*k+matte[2]);

                        r = r < 0 ? 0 : r > 255 ? 255 : r;
                        g = g < 0 ? 0 : g > 255 ? 255 : g;
                        b = b < 0 ? 0 : b > 255 ? 255 : b;
                    }
                    byte[] bb = {(byte)r,(byte)g,(byte)b,(byte)a};
                    buffer.put(bb);
                    
                }
            }else{
                int expected = imageDim*3;
                if(objectData.length> 16);
//            yDiff = y - (yr << 16);
//            yDiffMinus = 65536 - yDiff;
//            yIndex = yr * sw;
//            x = 0;
//            for (int j = 0; j < dw; j++) {
//                xr = (int) (x >> 16);
//                xDiff = x - (xr << 16);
//                xDiffMinus = 65536 - xDiff;
//                index = yIndex + xr;
//
//                A = data[index] & 0xff;
//                B = data[index + 1] & 0xff;
//                C = data[index + sw] & 0xff;
//                D = data[index + sw + 1] & 0xff;
//
//                gray = (int) ((A * xDiffMinus * yDiffMinus
//                        + B * xDiff * yDiffMinus
//                        + C * yDiff * xDiffMinus
//                        + D * xDiff * yDiff) >> 32);
//
//                temp[offset++] = (byte) gray;
//
//                x += xRatio;
//            }
//            y += yRatio;
//        }
//        return temp;
    }
    
    static byte[] applySMask(byte[] maskData, final ImageData imageData,final GenericColorSpace decodeColorData, final PdfObject newSMask, final PdfObject XObject) {
        
        byte[] objectData=imageData.getObjectData();
        
        /*
        * Image data
        */
        int w=imageData.getWidth();
        int h=imageData.getHeight();
        int d=imageData.getDepth();
        
        /*
        * Smask data (ASSUME single component at moment)
        */
        final int maskW=newSMask.getInt(PdfDictionary.Width);
        final int maskH=newSMask.getInt(PdfDictionary.Height);
        final int maskD=newSMask.getInt(PdfDictionary.BitsPerComponent);
        
        objectData = MaskDataDecoder.convertSmaskData(decodeColorData, objectData, w, h, imageData, d, maskD, maskData, newSMask);
        
        //needs to be 'normalised to 8  bit'
        if(maskD!=8){
            maskData=ColorSpaceConvertor.normaliseTo8Bit(maskD, maskW, maskH, maskData);
        }
        
        //add mask as a element so we now have argb
        if(w==maskW && h==maskH){
            //System.out.println("Same size");
            objectData=buildUnscaledByteArray(w, h, objectData, maskData);
        }else if(w15){
                is4Bit=false;
                break;
            }
        }
        
        if(is4Bit){
            for (int ii=0;ii




© 2015 - 2024 Weber Informatics LLC | Privacy Policy