001/*
002 * Copyright 2010-2015 Institut Pasteur.
003 * 
004 * This file is part of Icy.
005 * 
006 * Icy is free software: you can redistribute it and/or modify
007 * it under the terms of the GNU General Public License as published by
008 * the Free Software Foundation, either version 3 of the License, or
009 * (at your option) any later version.
010 * 
011 * Icy is distributed in the hope that it will be useful,
012 * but WITHOUT ANY WARRANTY; without even the implied warranty of
013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
014 * GNU General Public License for more details.
015 * 
016 * You should have received a copy of the GNU General Public License
017 * along with Icy. If not, see <http://www.gnu.org/licenses/>.
018 */
019package icy.image.colormodel;
020
021import icy.image.lut.LUT;
022import icy.type.DataType;
023import icy.type.TypeUtil;
024
025/**
026 * @author Stephane
027 */
028public class UIntColorModel extends IcyColorModel
029{
030    /**
031     * Define a new UIntColorModel
032     * 
033     * @param numComponents
034     *        number of color component
035     * @param bits
036     */
037    public UIntColorModel(int numComponents, int[] bits)
038    {
039        super(numComponents, DataType.UINT, bits);
040    }
041
042    @Override
043    public int getRGB(Object pixel)
044    {
045        final int[] pix = (int[]) pixel;
046        final int[] scaledData = new int[numComponents];
047
048        for (int comp = 0; comp < numComponents; comp++)
049            scaledData[comp] = (int) colormapScalers[comp].scale(TypeUtil.unsign(pix[comp]));
050
051        return getIcyColorSpace().toRGBUnnorm(scaledData);
052    }
053
054    /**
055     * Same as getRGB but by using the specified LUT instead of internal one
056     * 
057     * @see java.awt.image.ColorModel#getRGB(java.lang.Object)
058     */
059    @Override
060    public int getRGB(Object pixel, LUT lut)
061    {
062        final int[] pix = (int[]) pixel;
063        final int[] scaledData = new int[numComponents];
064
065        for (int comp = 0; comp < numComponents; comp++)
066            scaledData[comp] = (int) lut.getLutChannel(comp).getScaler().scale(TypeUtil.unsign(pix[comp]));
067
068        return lut.getColorSpace().toRGBUnnorm(scaledData);
069    }
070
071    @Override
072    public int[] getComponents(Object pixel, int[] components, int offset)
073    {
074        final int[] result;
075
076        if (components == null)
077            result = new int[offset + numComponents];
078        else
079        {
080            if ((components.length - offset) < numComponents)
081                throw new IllegalArgumentException("Length of components array < number of components in model");
082
083            result = components;
084        }
085
086        final int data[] = (int[]) pixel;
087        final int len = data.length;
088
089        for (int i = 0; i < len; i++)
090            result[offset + i] = data[i];
091
092        return result;
093    }
094
095    @Override
096    public Object getDataElements(int[] components, int offset, Object obj)
097    {
098        if ((components.length - offset) < numComponents)
099            throw new IllegalArgumentException("Component array too small" + " (should be " + numComponents);
100
101        final int[] pixel;
102        final int len = components.length;
103
104        if (obj == null)
105            pixel = new int[numComponents];
106        else
107            pixel = (int[]) obj;
108
109        for (int i = 0; i < len; i++)
110            pixel[i] = components[offset + i];
111
112        return pixel;
113    }
114
115    @Override
116    public Object getDataElements(float[] normComponents, int offset, Object obj)
117    {
118        final int[] pixel;
119
120        if (obj == null)
121            pixel = new int[numComponents];
122        else
123            pixel = (int[]) obj;
124
125        for (int c = 0, nc = offset; c < numComponents; c++, nc++)
126            pixel[c] = TypeUtil.toInt(normalScalers[c].unscale(normComponents[nc]));
127
128        return pixel;
129    }
130
131    @Override
132    public float[] getNormalizedComponents(Object pixel, float[] normComponents, int normOffset)
133    {
134        final float[] result;
135
136        if (normComponents == null)
137            result = new float[numComponents + normOffset];
138        else
139            result = normComponents;
140
141        final int[] data = (int[]) pixel;
142
143        for (int c = 0, nc = normOffset; c < numComponents; c++, nc++)
144            result[nc] = (float) normalScalers[c].scale(TypeUtil.unsign(data[c]));
145
146        return result;
147    }
148}