001/*
002Copyright 2006 Jerry Huxtable
003
004Licensed under the Apache License, Version 2.0 (the "License");
005you may not use this file except in compliance with the License.
006You may obtain a copy of the License at
007
008   http://www.apache.org/licenses/LICENSE-2.0
009
010Unless required by applicable law or agreed to in writing, software
011distributed under the License is distributed on an "AS IS" BASIS,
012WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013See the License for the specific language governing permissions and
014limitations under the License.
015*/
016
017package com.jhlabs.image;
018
019/**
020 * A colormap implemented with an array of colors. This corresponds to the IndexColorModel class.
021 */
022public class ArrayColormap implements Colormap, Cloneable {
023        
024        /**
025         * The array of colors.
026         */
027        protected int[] map;
028
029        /**
030         * Construct an all-black colormap.
031         */
032        public ArrayColormap() {
033                this.map = new int[256];
034        }
035
036        /**
037         * Construct a colormap with the given map.
038         * @param map the array of ARGB colors
039         */
040        public ArrayColormap(int[] map) {
041                this.map = map;
042        }
043
044        public Object clone() {
045                try {
046                        ArrayColormap g = (ArrayColormap)super.clone();
047                        g.map = (int[])map.clone();
048                        return g;
049                }
050                catch (CloneNotSupportedException e) {
051                }
052                return null;
053        }
054        
055    /**
056     * Set the array of colors for the colormap.
057     * @param map the colors
058     * @see #getMap
059     */
060        public void setMap(int[] map) {
061                this.map = map;
062        }
063
064    /**
065     * Get the array of colors for the colormap.
066     * @return the colors
067     * @see #setMap
068     */
069        public int[] getMap() {
070                return map;
071        }
072
073        /**
074         * Convert a value in the range 0..1 to an RGB color.
075         * @param v a value in the range 0..1
076         * @return an RGB color
077     * @see #setColor
078         */
079        public int getColor(float v) {
080/*
081                v *= 255;
082                int n = (int)v;
083                float f = v-n;
084                if (n < 0)
085                        return map[0];
086                else if (n >= 255)
087                        return map[255];
088                return ImageMath.mixColors(f, map[n], map[n+1]);
089*/
090                int n = (int)(v*255);
091                if (n < 0)
092                        n = 0;
093                else if (n > 255)
094                        n = 255;
095                return map[n];
096        }
097        
098        /**
099         * Set the color at "index" to "color". Entries are interpolated linearly from
100         * the existing entries at "firstIndex" and "lastIndex" to the new entry.
101         * firstIndex < index < lastIndex must hold.
102     * @param index the position to set
103     * @param firstIndex the position of the first color from which to interpolate
104     * @param lastIndex the position of the second color from which to interpolate
105     * @param color the color to set
106         */
107        public void setColorInterpolated(int index, int firstIndex, int lastIndex, int color) {
108                int firstColor = map[firstIndex];
109                int lastColor = map[lastIndex];
110                for (int i = firstIndex; i <= index; i++)
111                        map[i] = ImageMath.mixColors((float)(i-firstIndex)/(index-firstIndex), firstColor, color);
112                for (int i = index; i < lastIndex; i++)
113                        map[i] = ImageMath.mixColors((float)(i-index)/(lastIndex-index), color, lastColor);
114        }
115
116    /**
117     * Set a range of the colormap, interpolating between two colors.
118     * @param firstIndex the position of the first color
119     * @param lastIndex the position of the second color
120     * @param color1 the first color
121     * @param color2 the second color
122     */
123        public void setColorRange(int firstIndex, int lastIndex, int color1, int color2) {
124                for (int i = firstIndex; i <= lastIndex; i++)
125                        map[i] = ImageMath.mixColors((float)(i-firstIndex)/(lastIndex-firstIndex), color1, color2);
126        }
127
128    /**
129     * Set a range of the colormap to a single color.
130     * @param firstIndex the position of the first color
131     * @param lastIndex the position of the second color
132     * @param color the color
133     */
134        public void setColorRange(int firstIndex, int lastIndex, int color) {
135                for (int i = firstIndex; i <= lastIndex; i++)
136                        map[i] = color;
137        }
138
139    /**
140     * Set one element of the colormap to a given color.
141     * @param index the position of the color
142     * @param color the color
143     * @see #getColor
144     */
145        public void setColor(int index, int color) {
146                map[index] = color;
147        }
148
149}