001 /* 002 * 003 004 Licensed under the Apache License, Version 2.0 (the "License"); 005 you may not use this file except in compliance with the License. 006 You may obtain a copy of the License at 007 008 http://www.apache.org/licenses/LICENSE-2.0 009 010 Unless required by applicable law or agreed to in writing, software 011 distributed under the License is distributed on an "AS IS" BASIS, 012 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 See the License for the specific language governing permissions and 014 limitations under the License. 015 */ 016 017 package railo.runtime.img.filter;import java.awt.image.BufferedImage; 018 019 import railo.runtime.engine.ThreadLocalPageContext; 020 import railo.runtime.exp.FunctionException; 021 import railo.runtime.exp.PageException; 022 import railo.runtime.img.ImageUtil; 023 import railo.runtime.type.KeyImpl; 024 import railo.runtime.type.List; 025 import railo.runtime.type.Struct; 026 027 028 029 /** 030 * A filter to posterize an image. 031 */ 032 public class PosterizeFilter extends PointFilter implements DynFiltering { 033 034 private int numLevels; 035 private int[] levels; 036 private boolean initialized = false; 037 038 public PosterizeFilter() { 039 setNumLevels(6); 040 } 041 042 /** 043 * Set the number of levels in the output image. 044 * @param numLevels the number of levels 045 * @see #getNumLevels 046 */ 047 public void setNumLevels(int numLevels) { 048 this.numLevels = numLevels; 049 initialized = false; 050 } 051 052 /** 053 * Get the number of levels in the output image. 054 * @return the number of levels 055 * @see #setNumLevels 056 */ 057 public int getNumLevels() { 058 return numLevels; 059 } 060 061 /** 062 * Initialize the filter. 063 */ 064 protected void initialize() { 065 levels = new int[256]; 066 if (numLevels != 1) 067 for (int i = 0; i < 256; i++) 068 levels[i] = 255 * (numLevels*i / 256) / (numLevels-1); 069 } 070 071 public int filterRGB(int x, int y, int rgb) { 072 if (!initialized) { 073 initialized = true; 074 initialize(); 075 } 076 int a = rgb & 0xff000000; 077 int r = (rgb >> 16) & 0xff; 078 int g = (rgb >> 8) & 0xff; 079 int b = rgb & 0xff; 080 r = levels[r]; 081 g = levels[g]; 082 b = levels[b]; 083 return a | (r << 16) | (g << 8) | b; 084 } 085 086 public String toString() { 087 return "Colors/Posterize..."; 088 } 089 090 public BufferedImage filter(BufferedImage src, Struct parameters) throws PageException {BufferedImage dst=ImageUtil.createBufferedImage(src); 091 Object o; 092 if((o=parameters.removeEL(KeyImpl.init("NumLevels")))!=null)setNumLevels(ImageFilterUtil.toIntValue(o,"NumLevels")); 093 if((o=parameters.removeEL(KeyImpl.init("Dimensions")))!=null){ 094 int[] dim=ImageFilterUtil.toDimensions(o,"Dimensions"); 095 setDimensions(dim[0],dim[1]); 096 } 097 098 // check for arguments not supported 099 if(parameters.size()>0) { 100 throw new FunctionException(ThreadLocalPageContext.get(), "ImageFilter", 3, "parameters", "the parameter"+(parameters.size()>1?"s":"")+" ["+List.arrayToList(parameters.keysAsString(),", ")+"] "+(parameters.size()>1?"are":"is")+" not allowed, only the following parameters are supported [NumLevels, Dimensions]"); 101 } 102 103 return filter(src, dst); 104 } 105 } 106