/*
* Copyright (c) 2011-2016, Peter Abeles. All Rights Reserved.
*
* This file is part of BoofCV (http://boofcv.org).
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package boofcv.demonstrations.segmentation;
import boofcv.abst.segmentation.ImageSuperpixels;
import boofcv.alg.segmentation.ComputeRegionMeanColor;
import boofcv.alg.segmentation.ImageSegmentationOps;
import boofcv.factory.segmentation.FactoryImageSegmentation;
import boofcv.factory.segmentation.FactorySegmentationAlg;
import boofcv.gui.SelectAlgorithmAndInputPanel;
import boofcv.gui.feature.VisualizeRegions;
import boofcv.gui.image.ImagePanel;
import boofcv.gui.image.ShowImages;
import boofcv.io.PathLabel;
import boofcv.io.UtilIO;
import boofcv.io.image.ConvertBufferedImage;
import boofcv.struct.feature.ColorQueue_F32;
import boofcv.struct.image.*;
import org.ddogleg.struct.FastQueue;
import org.ddogleg.struct.GrowQueue_I32;
import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.util.ArrayList;
/**
* Visualization for {@link boofcv.abst.segmentation.ImageSuperpixels}.
*
* @author Peter Abeles
*/
// TODO Show image size on left panel
public class VisualizeImageSegmentationApp
extends SelectAlgorithmAndInputPanel
{
ImageType imageType;
BufferedImage inputImage;
BufferedImage outColor = new BufferedImage(1,1,BufferedImage.TYPE_INT_RGB);
BufferedImage outSegments = new BufferedImage(1,1,BufferedImage.TYPE_INT_RGB);
BufferedImage outBorder = new BufferedImage(1,1,BufferedImage.TYPE_INT_RGB);
ImageSuperpixels alg = null;
int activeDisplay = 0;
T color;
GrayS32 pixelToRegion = new GrayS32(1,1);
SegmentConfigPanel leftPanel;
ImagePanel gui = new ImagePanel();
boolean processImage = false;
boolean busy = false;
public VisualizeImageSegmentationApp() {
this((ImageType)ImageType.pl(3,GrayF32.class));
}
public VisualizeImageSegmentationApp(ImageType imageType ) {
super(1);
this.imageType = imageType;
addAlgorithm(0, "FH04",0);
addAlgorithm(0, "SLIC Superpixel", 1);
addAlgorithm(0, "Mean-Shift", 2);
addAlgorithm(0, "Watershed",3);
color = imageType.createImage(1,1);
JPanel viewArea = new JPanel(new BorderLayout());
leftPanel = new SegmentConfigPanel(this);
viewArea.add(leftPanel, BorderLayout.WEST);
viewArea.add(gui, BorderLayout.CENTER);
declareAlgorithm(0);
setMainGUI(viewArea);
}
public void process(final BufferedImage input) {
setInputImage(input);
this.inputImage = input;
color.reshape(input.getWidth(),input.getHeight());
pixelToRegion.reshape(color.width, color.height);
ConvertBufferedImage.convertFrom(input, color,true);
if( input.getWidth() != outColor.getWidth() || input.getHeight() != outColor.getHeight()) {
outColor = new BufferedImage(color.width,color.height,BufferedImage.TYPE_INT_RGB);
outSegments = new BufferedImage(color.width,color.height,BufferedImage.TYPE_INT_RGB);
outBorder = new BufferedImage(color.width,color.height,BufferedImage.TYPE_INT_RGB);
}
SwingUtilities.invokeLater(new Runnable() {
public void run() {
gui.setPreferredSize(new Dimension(color.getWidth(), color.getHeight()));
gui.setBufferedImage(input);
gui.revalidate();
processImage = true;
}
});
doRefreshAll();
}
@Override
public void loadConfigurationFile(String fileName) {
}
@Override
public void refreshAll(Object[] cookies) {
setActiveAlgorithm(0, null, cookies[0]);
}
@Override
public void setActiveAlgorithm(int indexFamily, String name, Object cookie) {
if (inputImage == null)
return;
synchronized( imageType ) {
busy = true;
leftPanel.setComputing(true);
declareAlgorithm((Integer) cookie);
performSegmentation();
updateActiveDisplay(activeDisplay);
leftPanel.setComputing(false);
busy = false;
gui.repaint();
}
}
private void declareAlgorithm(int which) {
alg = null;
switch( which ) {
case 0: alg = FactoryImageSegmentation.fh04(leftPanel.configFh, imageType); break;
case 1: alg = FactoryImageSegmentation.slic(leftPanel.configSlic, imageType); break;
case 2: alg = FactoryImageSegmentation.meanShift(leftPanel.configMeanShift, imageType); break;
case 3: alg = FactoryImageSegmentation.watershed(leftPanel.configWatershed, imageType); break;
default: throw new RuntimeException("BUG!");
}
leftPanel.switchAlgorithm(which);
}
@Override
public void changeInput(String name, int index) {
BufferedImage image = media.openImage(inputRefs.get(index).getPath());
if (image != null) {
process(image);
}
}
@Override
public boolean getHasProcessedImage() {
return processImage;
}
public void updateActiveDisplay( final int value ) {
activeDisplay = value;
Runnable r = new Runnable() {
public void run() {
if( activeDisplay == 0 ) {
gui.setBufferedImage(outColor);
} else if( activeDisplay == 1 ) {
gui.setBufferedImage(outBorder);
} else if( activeDisplay == 2 ) {
gui.setBufferedImage(outSegments);
}
gui.repaint();
}};
if( SwingUtilities.isEventDispatchThread() )
r.run();
else
SwingUtilities.invokeLater(r);
}
private void performSegmentation() {
long before = System.currentTimeMillis();
alg.segment(color, pixelToRegion);
long after = System.currentTimeMillis();
System.out.println("Total time "+(after-before));
int numSegments = alg.getTotalSuperpixels();
// Computes the mean color inside each region
ImageType type = color.getImageType();
ComputeRegionMeanColor colorize = FactorySegmentationAlg.regionMeanColor(type);
FastQueue segmentColor = new ColorQueue_F32(type.getNumBands());
segmentColor.resize(numSegments);
GrowQueue_I32 regionMemberCount = new GrowQueue_I32();
regionMemberCount.resize(numSegments);
ImageSegmentationOps.countRegionPixels(pixelToRegion, numSegments, regionMemberCount.data);
colorize.process(color,pixelToRegion,regionMemberCount,segmentColor);
VisualizeRegions.regionsColor(pixelToRegion,segmentColor,outColor);
VisualizeRegions.regions(pixelToRegion,segmentColor.size(),outSegments);
// Make edges appear black
ConvertBufferedImage.convertTo(color,outBorder,true);
VisualizeRegions.regionBorders(pixelToRegion,0x000000,outBorder);
}
public void recompute() {
synchronized( imageType ) {
if( busy )
return;
busy = true;
}
doRefreshAll();
}
public static void main(String[] args) {
ImageType> imageType = ImageType.pl(3,GrayF32.class);
// ImageType> imageType = ImageType.pl(3,GrayU8.class);
// ImageType imageType = ImageType.single(GrayF32.class);
// ImageType imageType = ImageType.single(GrayU8.class);
VisualizeImageSegmentationApp app = new VisualizeImageSegmentationApp(imageType);
// app.setBaseDirectory(UtilIO.pathExample("segment/");
// app.loadInputData(UtilIO.pathExample("segment/segment.txt");
java.util.List inputs = new ArrayList();
inputs.add(new PathLabel("Horses", UtilIO.pathExample("segment/berkeley_horses.jpg")));
inputs.add(new PathLabel("Kangaroo", UtilIO.pathExample("segment/berkeley_kangaroo.jpg")));
inputs.add(new PathLabel("Man", UtilIO.pathExample("segment/berkeley_man.jpg")));
inputs.add(new PathLabel("Pines People", UtilIO.pathExample("segment/mountain_pines_people.jpg")));
inputs.add(new PathLabel("Sunflowers", UtilIO.pathExample("sunflowers.jpg")));
inputs.add(new PathLabel("Shapes", UtilIO.pathExample("shapes/shapes01.png")));
app.setInputList(inputs);
// wait for it to process one image so that the size isn't all screwed up
while (!app.getHasProcessedImage()) {
Thread.yield();
}
ShowImages.showWindow(app, "Image Segmentation",true);
}
}
Ads help maintain this website.