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

ij_plugins.debayer2sx.MakeBayer.scala Maven / Gradle / Ivy

The newest version!
/*
 * Image/J Plugins
 * Copyright (C) 2002-2021 Jarek Sacha
 * Author's email: jpsacha at gmail [dot] com
 *
 * 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
 *
 * Latest release available at https://github.com/ij-plugins/ijp-DeBayer2SX
 */

package ij_plugins.debayer2sx

import ij.ImageStack
import ij.process.{ByteProcessor, ColorProcessor, FloatProcessor, ImageProcessor}
import ij_plugins.debayer2sx.DeBayer2Config.MosaicOrder
import ij_plugins.debayer2sx.LoopUtils.copyRanges

/**
  * Create Bayer images from color images. This is mostly useful for testing and demos.
  */
object MakeBayer {

  /**
    * Convert RGB color image to stack of gray level images.
    *
    * @param cp color image
    * @return stack of 3 8-bit images
    */
  def toStack(cp: ColorProcessor): ImageStack = {
    val w: Int = cp.getWidth
    val h: Int = cp.getHeight
    val size: Int = w * h
    val r = new Array[Byte](size)
    val g = new Array[Byte](size)
    val b = new Array[Byte](size)
    cp.getRGB(r, g, b)
    val stack = new ImageStack(w, h)
    stack.addSlice("Red", r)
    stack.addSlice("Green", g)
    stack.addSlice("Blue", b)
    stack.setColorModel(cp.getDefaultColorModel)
    stack
  }

  /**
    * Encode color image in a Bayer pattern.
    *
    * @param cp          input color image
    * @param mosaicOrder filter order
    * @return Bayer pattern coded image.
    */
  def process(cp: ColorProcessor, mosaicOrder: MosaicOrder): ByteProcessor = {
    process(toStack(cp), mosaicOrder).asInstanceOf[ByteProcessor]
  }

  /**
    * Encode color image in a Bayer pattern.
    *
    * @param stack       input color image represented as a stack of 3 gray level images.
    * @param mosaicOrder filter order
    * @return Bayer pattern coded image of the same bit depth as slices in the input stack.
    */
  def process(stack: ImageStack, mosaicOrder: MosaicOrder): ImageProcessor = {

    require(stack.size() == 3)
    require(stack.getBitDepth == 8 || stack.getBitDepth == 16 || stack.getBitDepth == 32)

    val fpR = stack.getProcessor(1).convertToFloatProcessor()
    val fpG = stack.getProcessor(2).convertToFloatProcessor()
    val fpB = stack.getProcessor(3).convertToFloatProcessor()

    val w = stack.getWidth
    val h = stack.getHeight
    val fpBayer = new FloatProcessor(w, h)

    // ip00 ip10
    // ip01 ip11
    val (ip00, ip10, ip01, ip11) = mosaicOrder match {
      case MosaicOrder.B_G =>
        // B G
        // G R
        (fpB, fpG, fpG, fpR)

      case MosaicOrder.G_B =>
        // G B
        // R G
        (fpG, fpB, fpR, fpG)

      case MosaicOrder.G_R =>
        // G R
        // B G
        (fpG, fpR, fpB, fpG)

      case MosaicOrder.R_G =>
        // R G
        // G B
        (fpR, fpG, fpG, fpB)
    }

    // ip00
    copyRanges(fpBayer, Range(0, w, 2), Range(0, h, 2), ip00, Range(0, w, 2), Range(0, h, 2))
    // ip10
    copyRanges(fpBayer, Range(1, w, 2), Range(0, h, 2), ip10, Range(1, w, 2), Range(0, h, 2))
    // ip01
    copyRanges(fpBayer, Range(0, w, 2), Range(1, h, 2), ip01, Range(0, w, 2), Range(1, h, 2))
    // ip11
    copyRanges(fpBayer, Range(1, w, 2), Range(1, h, 2), ip11, Range(1, w, 2), Range(1, h, 2))

    stack.getBitDepth match {
      case 8 => fpBayer.convertToByte(false)
      case 16 => fpBayer.convertToShort(false)
      case 32 => fpBayer.convertToFloat()
      case bitDepth => throw new IllegalArgumentException("Unsupported bit depth: " + bitDepth)
    }
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy