public void addFilter(JMenu menu, final ImageFilter f) { JMenuItem item = new JMenuItem(f.getMenuName()); menu.add(item); item.addActionListener( new ActionListener() { public void actionPerformed(ActionEvent e) { swapImages(); f.apply(pic1, pic2); lab.setIcon(pic2.getJLabel().getIcon()); sliderPanel.setVisible(false); pack(); repaint(); } }); }
/** * Do the filter operation * * @param src The source BufferedImage. Can be any type. * @param dst The destination image. If not null, must be of type TYPE_INT_RGB, TYPE_INT_ARGB or * TYPE_INT_ARGB_PRE * @return the filtered image */ public BufferedImage filter(BufferedImage src, BufferedImage dst) { int width = src.getWidth(); int height = src.getHeight(); BufferedImageConsumer consumer = new BufferedImageConsumer(dst); ImageFilter fltr = filter.getFilterInstance(consumer); fltr.setDimensions(width, height); /* ColorModel cm = src.getColorModel(); if (cm.getPixelSize() == 8) { // byte. indexed or gray: WritableRaster raster = src.getRaster(); byte pixels[] = new byte[width]; // calculate scanline by scanline in order to safe memory. // It also seems to run faster like that for (int y = 0; y < height; y++) { raster.getDataElements(0, y, width, 1, pixels); fltr.setPixels(0, y, width, 1, cm, pixels, 0, width); } } else { // integer, use the simple rgb mode: WritableRaster raster = src.getRaster(); int pixels[] = new int[width]; // calculate scanline by scanline in order to safe memory. // It also seems to run faster like that for (int y = 0; y < height; y++) { raster.getDataElements(0, y, width, 1, pixels); fltr.setPixels(0, y, width, 1, cm, pixels, 0, width); } } */ // Always work in integer mode. this is more effective, and most // filters convert to integer internally anyhow ColorModel cm = new SimpleColorModel(); // Create a BufferedImage of only 1 pixel height for fetching the rows of the image in the // correct format (ARGB) // This speeds up things by more than factor 2, compared to the standard BufferedImage.getRGB // solution, // which is supposed to be fast too. This is probably the case because drawing to BufferedImages // uses // very optimized code which may even be hardware accelerated. BufferedImage row = new BufferedImage(width, 1, BufferedImage.TYPE_INT_ARGB); Graphics2D g2d = row.createGraphics(); int pixels[] = ((DataBufferInt) row.getRaster().getDataBuffer()).getData(); // Make sure alpha values do not add up for each row: g2d.setComposite(AlphaComposite.Src); // Calculate scanline by scanline in order to safe memory. // It also seems to run faster like that for (int y = 0; y < height; y++) { g2d.drawImage(src, null, 0, -y); // Now pixels contains the rgb values of the row y! // filter this row now: fltr.setPixels(0, y, width, 1, cm, pixels, 0, width); } g2d.dispose(); // The consumer now contains the filtered image, return it. return consumer.getImage(); }