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

boofcv.alg.transform.wavelet.impl.ImplWaveletTransformInner Maven / Gradle / Ivy

Go to download

BoofCV is an open source Java library for real-time computer vision and robotics applications.

There is a newer version: 0.26
Show newest version
/*
 * Copyright (c) 2011-2013, Peter Abeles. All Rights Reserved.
 *
 * This file is part of BoofCV (http://boofcv.org).
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package boofcv.alg.transform.wavelet.impl;

import boofcv.alg.transform.wavelet.UtilWavelet;
import boofcv.struct.image.ImageFloat32;
import boofcv.struct.image.ImageSInt32;
import boofcv.struct.wavelet.WlCoef_F32;
import boofcv.struct.wavelet.WlCoef_I32;


/**
 * 

* Standard algorithm for forward and inverse wavelet transform which has been optimized to only * process the inner portion of the image by excluding the border. *

* *

* DO NOT MODIFY: This class was automatically generated by {@link GenerateImplWaveletTransformInner} *

* * @author Peter Abeles */ @SuppressWarnings({"ForLoopReplaceableByForEach"}) public class ImplWaveletTransformInner { public static void horizontal( WlCoef_F32 coefficients , ImageFloat32 input , ImageFloat32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final float[] alpha = coefficients.scaling; final float[] beta = coefficients.wavelet; final float dataIn[] = input.data; final float dataOut[] = output.data; final int width = output.width; final int height = input.height; final int widthD2 = width/2; final int startX = UtilWavelet.borderForwardLower(coefficients); final int endOffsetX = input.width - UtilWavelet.borderForwardUpper(coefficients,input.width) - startX; for( int y = 0; y < height; y++ ) { int indexIn = input.startIndex + input.stride*y + startX; int indexOut = output.startIndex + output.stride*y + startX/2; int end = indexIn + endOffsetX; for( ; indexIn < end; indexIn += 2 ) { float scale = 0; int index = indexIn+offsetA; for( int i = 0; i < alpha.length; i++ ) { scale += (dataIn[index++])*alpha[i]; } float wavelet = 0; index = indexIn+offsetB; for( int i = 0; i < beta.length; i++ ) { wavelet += (dataIn[index++])*beta[i]; } dataOut[ indexOut+widthD2] = wavelet; dataOut[ indexOut++ ] = scale; } } } public static void vertical( WlCoef_F32 coefficients , ImageFloat32 input , ImageFloat32 output ) { final int offsetA = coefficients.offsetScaling*input.stride; final int offsetB = coefficients.offsetWavelet*input.stride; final float[] alpha = coefficients.scaling; final float[] beta = coefficients.wavelet; final float dataIn[] = input.data; final float dataOut[] = output.data; final int width = input.width; final int height = output.height; final int heightD2 = (height/2)*output.stride; final int startY = UtilWavelet.borderForwardLower(coefficients); final int endY = input.height - UtilWavelet.borderForwardUpper(coefficients,input.width); for( int y = startY; y < endY; y += 2 ) { int indexIn = input.startIndex + input.stride*y; int indexOut = output.startIndex + output.stride*(y/2); for( int x = 0; x < width; x++, indexIn++) { float scale = 0; int index = indexIn + offsetA; for( int i = 0; i < alpha.length; i++ ) { scale += (dataIn[index])*alpha[i]; index += input.stride; } float wavelet = 0; index = indexIn + offsetB; for( int i = 0; i < beta.length; i++ ) { wavelet += (dataIn[index])*beta[i]; index += input.stride; } dataOut[indexOut+heightD2] = wavelet; dataOut[indexOut++] = scale; } } } public static void horizontalInverse( WlCoef_F32 coefficients , ImageFloat32 input , ImageFloat32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final float[] alpha = coefficients.scaling; final float[] beta = coefficients.wavelet; float []trends = new float[ output.width ]; float []details = new float[ output.width ]; final int width = input.width; final int height = output.height; final int widthD2 = width/2; final int lowerBorder = UtilWavelet.borderForwardLower(coefficients); final int upperBorder = output.width - UtilWavelet.borderForwardUpper(coefficients,output.width); for( int y = 0; y < height; y++ ) { // initialize details and trends arrays int indexSrc = input.startIndex + y*input.stride+lowerBorder/2; for( int x = lowerBorder; x < upperBorder; x += 2 , indexSrc++ ) { float a = input.data[ indexSrc ] ; float d = input.data[ indexSrc + widthD2 ] ; // add the trend for( int i = 0; i < 2; i++ ) trends[i+x+offsetA] = a*alpha[i]; // add the detail signal for( int i = 0; i < 2; i++ ) details[i+x+offsetB] = d*beta[i]; } for( int i = upperBorder+offsetA; i < upperBorder; i++ ) trends[i] = 0; for( int i = upperBorder+offsetB; i < upperBorder; i++ ) details[i] = 0; // perform the normal inverse transform indexSrc = input.startIndex + y*input.stride+lowerBorder/2; for( int x = lowerBorder; x < upperBorder; x += 2 , indexSrc++ ) { float a = input.data[ indexSrc ] ; float d = input.data[ indexSrc + widthD2 ] ; // add the trend for( int i = 2; i < alpha.length; i++ ) { trends[i+x+offsetA] += a*alpha[i]; } // add the detail signal for( int i = 2; i < beta.length; i++ ) { details[i+x+offsetB] += d*beta[i]; } } int indexDst = output.startIndex + y*output.stride + lowerBorder; for( int x = lowerBorder; x < upperBorder; x++ ) { output.data[ indexDst++ ] = (trends[x] + details[x]); } } } public static void verticalInverse( WlCoef_F32 coefficients , ImageFloat32 input , ImageFloat32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final float[] alpha = coefficients.scaling; final float[] beta = coefficients.wavelet; float []trends = new float[ output.height ]; float []details = new float[ output.height ]; final int width = output.width; final int height = input.height; final int heightD2 = (height/2)*input.stride; final int lowerBorder = UtilWavelet.borderForwardLower(coefficients); final int upperBorder = output.height - UtilWavelet.borderForwardUpper(coefficients,output.height); for( int x = 0; x < width; x++) { int indexSrc = input.startIndex + (lowerBorder/2)*input.stride + x; for( int y = lowerBorder; y < upperBorder; y += 2 , indexSrc += input.stride ) { float a = input.data[ indexSrc ] ; float d = input.data[ indexSrc + heightD2 ] ; // add the trend for( int i = 0; i < 2; i++ ) trends[i+y+offsetA] = a*alpha[i]; // add the detail signal for( int i = 0; i < 2; i++ ) details[i+y+offsetB] = d*beta[i]; } for( int i = upperBorder+offsetA; i < upperBorder; i++ ) trends[i] = 0; for( int i = upperBorder+offsetB; i < upperBorder; i++ ) details[i] = 0; // perform the normal inverse transform indexSrc = input.startIndex + (lowerBorder/2)*input.stride + x; for( int y = lowerBorder; y < upperBorder; y += 2 , indexSrc += input.stride ) { float a = input.data[indexSrc] ; float d = input.data[indexSrc+heightD2] ; // add the 'average' signal for( int i = 2; i < alpha.length; i++ ) { trends[y+offsetA+i] += a*alpha[i]; } // add the detail signal for( int i = 2; i < beta.length; i++ ) { details[y+offsetB+i] += d*beta[i]; } } int indexDst = output.startIndex + x + lowerBorder*output.stride; for( int y = lowerBorder; y < upperBorder; y++ , indexDst += output.stride ) { output.data[ indexDst ] = (trends[y] + details[y]); } } } public static void horizontal( WlCoef_I32 coefficients , ImageSInt32 input , ImageSInt32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final int[] alpha = coefficients.scaling; final int[] beta = coefficients.wavelet; final int dataIn[] = input.data; final int dataOut[] = output.data; final int width = output.width; final int height = input.height; final int widthD2 = width/2; final int startX = UtilWavelet.borderForwardLower(coefficients); final int endOffsetX = input.width - UtilWavelet.borderForwardUpper(coefficients,input.width) - startX; for( int y = 0; y < height; y++ ) { int indexIn = input.startIndex + input.stride*y + startX; int indexOut = output.startIndex + output.stride*y + startX/2; int end = indexIn + endOffsetX; for( ; indexIn < end; indexIn += 2 ) { int scale = 0; int index = indexIn+offsetA; for( int i = 0; i < alpha.length; i++ ) { scale += (dataIn[index++])*alpha[i]; } int wavelet = 0; index = indexIn+offsetB; for( int i = 0; i < beta.length; i++ ) { wavelet += (dataIn[index++])*beta[i]; } scale = 2*scale/coefficients.denominatorScaling; wavelet = 2*wavelet/coefficients.denominatorWavelet; dataOut[ indexOut+widthD2] = wavelet; dataOut[ indexOut++ ] = scale; } } } public static void vertical( WlCoef_I32 coefficients , ImageSInt32 input , ImageSInt32 output ) { final int offsetA = coefficients.offsetScaling*input.stride; final int offsetB = coefficients.offsetWavelet*input.stride; final int[] alpha = coefficients.scaling; final int[] beta = coefficients.wavelet; final int dataIn[] = input.data; final int dataOut[] = output.data; final int width = input.width; final int height = output.height; final int heightD2 = (height/2)*output.stride; final int startY = UtilWavelet.borderForwardLower(coefficients); final int endY = input.height - UtilWavelet.borderForwardUpper(coefficients,input.width); for( int y = startY; y < endY; y += 2 ) { int indexIn = input.startIndex + input.stride*y; int indexOut = output.startIndex + output.stride*(y/2); for( int x = 0; x < width; x++, indexIn++) { int scale = 0; int index = indexIn + offsetA; for( int i = 0; i < alpha.length; i++ ) { scale += (dataIn[index])*alpha[i]; index += input.stride; } int wavelet = 0; index = indexIn + offsetB; for( int i = 0; i < beta.length; i++ ) { wavelet += (dataIn[index])*beta[i]; index += input.stride; } scale = 2*scale/coefficients.denominatorScaling; wavelet = 2*wavelet/coefficients.denominatorWavelet; dataOut[indexOut+heightD2] = wavelet; dataOut[indexOut++] = scale; } } } public static void horizontalInverse( WlCoef_I32 coefficients , ImageSInt32 input , ImageSInt32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final int[] alpha = coefficients.scaling; final int[] beta = coefficients.wavelet; int []trends = new int[ output.width ]; int []details = new int[ output.width ]; final int width = input.width; final int height = output.height; final int widthD2 = width/2; final int lowerBorder = UtilWavelet.borderForwardLower(coefficients); final int upperBorder = output.width - UtilWavelet.borderForwardUpper(coefficients,output.width); final int e = coefficients.denominatorScaling*2; final int f = coefficients.denominatorWavelet*2; final int ef = e*f; final int ef2 = ef/2; for( int y = 0; y < height; y++ ) { // initialize details and trends arrays int indexSrc = input.startIndex + y*input.stride+lowerBorder/2; for( int x = lowerBorder; x < upperBorder; x += 2 , indexSrc++ ) { int a = input.data[ indexSrc ] ; int d = input.data[ indexSrc + widthD2 ] ; // add the trend for( int i = 0; i < 2; i++ ) trends[i+x+offsetA] = a*alpha[i]; // add the detail signal for( int i = 0; i < 2; i++ ) details[i+x+offsetB] = d*beta[i]; } for( int i = upperBorder+offsetA; i < upperBorder; i++ ) trends[i] = 0; for( int i = upperBorder+offsetB; i < upperBorder; i++ ) details[i] = 0; // perform the normal inverse transform indexSrc = input.startIndex + y*input.stride+lowerBorder/2; for( int x = lowerBorder; x < upperBorder; x += 2 , indexSrc++ ) { int a = input.data[ indexSrc ] ; int d = input.data[ indexSrc + widthD2 ] ; // add the trend for( int i = 2; i < alpha.length; i++ ) { trends[i+x+offsetA] += a*alpha[i]; } // add the detail signal for( int i = 2; i < beta.length; i++ ) { details[i+x+offsetB] += d*beta[i]; } } int indexDst = output.startIndex + y*output.stride + lowerBorder; for( int x = lowerBorder; x < upperBorder; x++ ) { output.data[ indexDst++ ] = UtilWavelet.round(trends[x]*f + details[x]*e , ef2,ef); } } } public static void verticalInverse( WlCoef_I32 coefficients , ImageSInt32 input , ImageSInt32 output ) { final int offsetA = coefficients.offsetScaling; final int offsetB = coefficients.offsetWavelet; final int[] alpha = coefficients.scaling; final int[] beta = coefficients.wavelet; int []trends = new int[ output.height ]; int []details = new int[ output.height ]; final int width = output.width; final int height = input.height; final int heightD2 = (height/2)*input.stride; final int lowerBorder = UtilWavelet.borderForwardLower(coefficients); final int upperBorder = output.height - UtilWavelet.borderForwardUpper(coefficients,output.height); final int e = coefficients.denominatorScaling*2; final int f = coefficients.denominatorWavelet*2; final int ef = e*f; final int ef2 = ef/2; for( int x = 0; x < width; x++) { int indexSrc = input.startIndex + (lowerBorder/2)*input.stride + x; for( int y = lowerBorder; y < upperBorder; y += 2 , indexSrc += input.stride ) { int a = input.data[ indexSrc ] ; int d = input.data[ indexSrc + heightD2 ] ; // add the trend for( int i = 0; i < 2; i++ ) trends[i+y+offsetA] = a*alpha[i]; // add the detail signal for( int i = 0; i < 2; i++ ) details[i+y+offsetB] = d*beta[i]; } for( int i = upperBorder+offsetA; i < upperBorder; i++ ) trends[i] = 0; for( int i = upperBorder+offsetB; i < upperBorder; i++ ) details[i] = 0; // perform the normal inverse transform indexSrc = input.startIndex + (lowerBorder/2)*input.stride + x; for( int y = lowerBorder; y < upperBorder; y += 2 , indexSrc += input.stride ) { int a = input.data[indexSrc] ; int d = input.data[indexSrc+heightD2] ; // add the 'average' signal for( int i = 2; i < alpha.length; i++ ) { trends[y+offsetA+i] += a*alpha[i]; } // add the detail signal for( int i = 2; i < beta.length; i++ ) { details[y+offsetB+i] += d*beta[i]; } } int indexDst = output.startIndex + x + lowerBorder*output.stride; for( int y = lowerBorder; y < upperBorder; y++ , indexDst += output.stride ) { output.data[ indexDst ] = UtilWavelet.round(trends[y]*f + details[y]*e , ef2 , ef); } } } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy