我還需要找到一個允許在Java中實現「色度鍵」效果的庫。該視頻包含一些綠色部分,在渲染過程中將其替換爲一張圖片以創建新視頻。Java中的色度鍵效果
我正在將我的問題與已回答的類似問題聯繫起來,但回答不完整(Looking for Chromakey library in Java)。你能否指定你是如何做到這樣做的?幾個月來,我一直未能成功解決同一問題。
c00kiemon5ter指出幾種資源:
- JavaCV
- JAI(Java高級圖像API)
- Java圖像處理食譜
哪一個爲你所做的工作?
我還需要找到一個允許在Java中實現「色度鍵」效果的庫。該視頻包含一些綠色部分,在渲染過程中將其替換爲一張圖片以創建新視頻。Java中的色度鍵效果
我正在將我的問題與已回答的類似問題聯繫起來,但回答不完整(Looking for Chromakey library in Java)。你能否指定你是如何做到這樣做的?幾個月來,我一直未能成功解決同一問題。
c00kiemon5ter指出幾種資源:
哪一個爲你所做的工作?
JavaCV包含很多處理視頻流的方法。
這段代碼應該讓你開始:http://tech.groups.yahoo.com/group/OpenCV/message/59118但是它在Java中可能太慢了。嘗試這種方法:
創建一個過濾器,將所有綠色像素轉換爲蒙版(查找「按顏色選擇」)。
使用蒙版將背景圖像複製到視頻中。
我想貢獻一段代碼,它給了我相當好的結果。我想知道我是否使用了Aaron Digulla建議的類和方法。
請注意,在這種情況下,我的視頻有黑色背景,這就是爲什麼我用背景圖像替換黑色。我希望獲得更好的結果,因爲我可以編輯視頻以獲得綠色背景,因爲黑色更有可能用在視頻主要角色中,並且替換錯誤的像素會導致相當糟糕的效果。
-
package transparentvideo;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Rectangle;
import java.awt.Toolkit;
import java.awt.image.BufferedImage;
import java.awt.image.FilteredImageSource;
import java.awt.image.ImageFilter;
import java.awt.image.ImageProducer;
import java.awt.image.RGBImageFilter;
import java.io.File;
import javax.media.Manager;
import javax.media.Player;
import javax.swing.ImageIcon;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
public class TransparentVideo
{
Player mediaPlayer;
JFrame invisibleFrame;
JFrame visibleFrame;
JLabel videoScreen;
JPanel offScreenVideo;
String backgroundImageFile="nature.jpg";
String videoFile="girl.mov";
public TransparentVideo()
{
invisibleFrame = new JFrame();
invisibleFrame.setSize(400, 400);
Container container=invisibleFrame.getContentPane();
offScreenVideo = getvidComp();
offScreenVideo.setPreferredSize(container.getSize());
offScreenVideo.setVisible(true);
container.add(offScreenVideo);
invisibleFrame.setVisible(true);
visibleFrame=new JFrame();
visibleFrame.setSize(container.getSize());
visibleFrame.setLocationRelativeTo(null);
videoScreen = new JLabel();
visibleFrame.getContentPane().add(videoScreen);
visibleFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
visibleFrame.setVisible(true);
invisibleFrame.setVisible(false);
try
{
while(true)
{
if(mediaPlayer.getState()==Player.Started)
reDraw();
Thread.sleep(100);
}
}
catch (Exception ex)
{
System.out.println(ex.getMessage());
}
}
public void reDraw()
{
BufferedImage bi=new BufferedImage(videoScreen.getWidth(), videoScreen.getHeight(),
BufferedImage.TYPE_INT_ARGB);
bi.getGraphics().drawImage(new ImageIcon(backgroundImageFile).getImage(), 0 , 0 ,
videoScreen.getWidth(), videoScreen.getHeight(), null);
BufferedImage screenShot = createImage((JComponent) offScreenVideo,
new Rectangle(invisibleFrame.getBounds()));
Image im = makeColorTransparent(new ImageIcon(screenShot).getImage(), Color.BLACK);
bi.getGraphics().drawImage(im, 0 ,0 , videoScreen.getWidth(), videoScreen.getHeight(), null);
videoScreen.setIcon(new ImageIcon(bi));
}
public static BufferedImage createImage(Component component, Rectangle region)
{
if (!component.isDisplayable()) {
Dimension d = component.getSize();
if (d.width == 0 || d.height == 0) {
d = component.getPreferredSize();
component.setSize(d);
}
layoutComponent(component);
}
BufferedImage image = new BufferedImage(region.width, region.height, BufferedImage.TYPE_INT_RGB);
Graphics2D g2d = image.createGraphics();
if (!component.isOpaque())
{
g2d.setColor(component.getBackground());
g2d.fillRect(region.x, region.y, region.width, region.height);
}
g2d.translate(-region.x, -region.y);
component.paint(g2d);
g2d.dispose();
return image;
}
public static void layoutComponent(Component component)
{
synchronized (component.getTreeLock())
{
component.doLayout();
if (component instanceof Container)
{
for (Component child : ((Container) component).getComponents())
{
layoutComponent(child);
}
}
}
}
public JPanel getvidComp()
{
Manager.setHint(Manager.LIGHTWEIGHT_RENDERER,true);
try
{
mediaPlayer = Manager.createRealizedPlayer(new File(videoFile).toURL());
mediaPlayer.realize();
mediaPlayer.prefetch();
JPanel video=new JPanel(new BorderLayout());
video.add(mediaPlayer.getVisualComponent()) ;
mediaPlayer.start();
return video;
}
catch(Exception d)
{
return null;
}
}
public static Image makeColorTransparent(Image im, final Color color)
{
ImageFilter filter = new RGBImageFilter()
{
public int markerRGB = color.getRGB() | 0xFF000000;
public final int filterRGB(int x, int y, int rgb)
{
Color c=new Color(rgb);
int red=c.getRed();
int green=c.getGreen();
int blue=c.getBlue();
//if(red<140 && green<140 && blue<140)
{
int alpha=Math.max(Math.max(red , green), Math.max(green, blue))*3;
c=new Color(red , green , blue , alpha>255 ?255 :alpha);
}
return c.getRGB();
}
};
ImageProducer ip = new FilteredImageSource(im.getSource(), filter);
return Toolkit.getDefaultToolkit().createImage(ip);
}
public static void main(String[] args) {
new TransparentVideo();
}
}
'我的連接與已經回答過類似的問題,但與uncomplete answer.`我的問題。我看不到這樣的鏈接。 – 2011-12-14 10:31:06
對不起,我不知道如何鏈接這兩個問題。最後,我在主體中添加了鏈接。 – 2011-12-14 10:36:57