public static void process_sub(GrayU8 orig,
								   GrayS16 derivX,
								   GrayS16 derivY) {
		final byte[] data = orig.data;
		final short[] imgX = derivX.data;
		final short[] imgY = derivY.data;

		final int width = orig.getWidth();
		final int height = orig.getHeight() - 1;
		final int strideSrc = orig.getStride();

		//CONCURRENT_BELOW BoofConcurrency.loopFor(1,height,y->{
		for (int y = 1; y < height; y++) {
			int indexSrc = orig.startIndex + orig.stride * y + 1;
			final int endX = indexSrc + width - 2;

			int indexX = derivX.startIndex + derivX.stride * y + 1;
			int indexY = derivY.startIndex + derivY.stride * y + 1;

			for (; indexSrc < endX; indexSrc++) {
				int v = (data[indexSrc + strideSrc + 1] & 0xFF) - (data[indexSrc - strideSrc - 1] & 0xFF);
				int w = (data[indexSrc + strideSrc - 1] & 0xFF) - (data[indexSrc - strideSrc + 1] & 0xFF);

				imgY[indexY++] = (short) (((data[indexSrc + strideSrc] & 0xFF) - (data[indexSrc - strideSrc] & 0xFF)) * 2 + v + w);

				imgX[indexX++] = (short) (((data[indexSrc + 1] & 0xFF) - (data[indexSrc - 1] & 0xFF)) * 2 + v - w);
			}
		}
		//CONCURRENT_ABOVE });
	}
public static void process_sub ( GrayU8 orig , GrayS16 derivX , GrayS16 derivY ) { final byte [ ] data = orig . data ; final short [ ] imgX = derivX . data ; final short [ ] imgY = derivY . data ; final int width = orig . getWidth ( ) ; final int height = orig . getHeight ( ) - 1 ; final int strideSrc = orig . getStride ( ) ; for ( int y = 1 ; y < height ; y ++ ) { int indexSrc = orig . startIndex + orig . stride * y + 1 ; final int endX = indexSrc + width - 2 ; int indexX = derivX . startIndex + derivX . stride * y + 1 ; int indexY = derivY . startIndex + derivY . stride * y + 1 ; for ( ; indexSrc < endX ; indexSrc ++ ) { int v = ( data [ indexSrc + strideSrc + 1 ] & 0xFF ) - ( data [ indexSrc - strideSrc - 1 ] & 0xFF ) ; int w = ( data [ indexSrc + strideSrc - 1 ] & 0xFF ) - ( data [ indexSrc - strideSrc + 1 ] & 0xFF ) ; imgY [ indexY ++ ] = ( short ) ( ( ( data [ indexSrc + strideSrc ] & 0xFF ) - ( data [ indexSrc - strideSrc ] & 0xFF ) ) * 2 + v + w ) ; imgX [ indexX ++ ] = ( short ) ( ( ( data [ indexSrc + 1 ] & 0xFF ) - ( data [ indexSrc - 1 ] & 0xFF ) ) * 2 + v - w ) ; } } }
Computes derivative of GrayU8.  Inputs can be sub-images.