Package org.gstreamer.swt

Source Code of org.gstreamer.swt.VideoComponent$RGBListener

/*
* Copyright (c) 2008 Peter Bocz
*
* This file is part of gstreamer-java.
*
* This code is free software: you can redistribute it and/or modify it under
* the terms of the GNU Lesser General Public License version 3 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License
* version 3 for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* version 3 along with this work.  If not, see <http://www.gnu.org/licenses/>.
*/

package org.gstreamer.swt;

import java.nio.IntBuffer;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import java.awt.image.BufferedImage;
import java.awt.image.DataBufferInt;

import org.eclipse.swt.SWT;
import org.eclipse.swt.events.PaintEvent;
import org.eclipse.swt.events.PaintListener;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.ImageData;
import org.eclipse.swt.graphics.PaletteData;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Composite;
import org.gstreamer.Element;
import org.gstreamer.elements.RGBDataSink;

public class VideoComponent extends Canvas {

  private BufferedImage currentImage = null;
  private final RGBDataSink videosink;
  private final Lock bufferLock = new ReentrantLock();
  private boolean updatePending = false;
  private int alpha = 255;
  private String ovText;
  private long start = System.currentTimeMillis();
  private boolean keepAspect = true;
  private boolean showOverlay = false;
  private boolean showFPS = false;
  private Color bgColor;

  public VideoComponent(final Composite parent, int style) {
    super(parent, style | SWT.DOUBLE_BUFFERED);

    videosink = new RGBDataSink("GstVideoComponent", new RGBListener());
    videosink.setPassDirectBuffer(true);

    final Font font = new Font(getDisplay(), "Arial", 13, SWT.NORMAL);

    this.addPaintListener(new PaintListener() {

      public void paintControl(PaintEvent event) {
        Point cSize = getSize();
        if (currentImage != null) {
          event.gc.setFont(font);
          int newX = 0, newY = 0;
          int fps = 0;

          int[] Frame = ((DataBufferInt) currentImage.getRaster().getDataBuffer()).getData();
          ImageData imgdata
            = new ImageData(currentImage.getWidth(), currentImage.getHeight(), 24,
                    new PaletteData(0xFF0000, 0x00FF00, 0x0000FF));
          imgdata.setPixels(0, 0, currentImage.getWidth() * currentImage.getHeight(), Frame, 0);

          if ((currentImage.getWidth() != cSize.x) || (currentImage.getHeight() != cSize.y)) {
            int sizeX = cSize.x, sizeY = cSize.y;
            event.gc.setInterpolation(SWT.HIGH);
            if (keepAspect) {
              if (((float) currentImage.getWidth() / (float) cSize.x)
                > ((float) currentImage.getHeight() / (float) cSize.y)) {
                sizeY = cSize.x * currentImage.getHeight() / currentImage.getWidth();
                newY = (cSize.y - sizeY) / 2;
              } else {
                sizeX = cSize.y * currentImage.getWidth() / currentImage.getHeight();
                newX = (cSize.x - sizeX) / 2;
              }
            }
            imgdata = imgdata.scaledTo(sizeX, sizeY);
          }

          if (alpha != event.gc.getAlpha()) {
            event.gc.setAlpha(alpha);
          }
          Image image = new Image(parent.getDisplay(), imgdata);
          event.gc.drawImage(image, newX, newY);

          if (showFPS) {
            fps = (int) (1000 / (System.currentTimeMillis() - start));
          }

          if (showOverlay) {
            event.gc.drawText(ovText, newX + 5, newY + 5, false);
            newY += 20;
          }
          if (showFPS) {
            event.gc.drawText(" FPS:" + fps, newX + 5, newY + 5, false);
          }
          image.dispose();
          if (showFPS) {
            start = System.currentTimeMillis();
          }
        } else {
          if (bgColor != null) {
            event.gc.setBackground(bgColor);
            event.gc.fillRectangle(0, 0, cSize.x, cSize.y);
          }
        }
      }
    });
  }

  /**
   * Retrieves the Gstreamer element, representing the video component
   *
   * @return element
   */
  public Element getElement() {
    return videosink;
  }

  /**
   * Set to keep aspect ratio
   *
   * @param keepAspect
   */
  public void setKeepAspect(boolean keepAspect) {
      this.keepAspect = keepAspect;
  }

  /**
   * Set the aplpha value of the video component. It works fine when overlay
   * is turned off.
   *
   * @param alpha
   */
  public void setAlpha(int alpha) {
    this.alpha = alpha;
  }

  /**
   * Set the overlay text of the video component. It works fine when overlay
   * is turned off.
   *
   * @param text
   */
  public void setOverlay(String text) {
    this.ovText = text;
  }

  /**
   * Set show FPS of the video component. It works fine when overlay is turned
   * off.
   *
   * @param bn
   */
  public void showFPS(boolean bn) {
    this.showFPS = bn;
  }

  /**
   * Set show overlay text. It works fine when overlay is turned off.
   *
   * @param bn
   */
  public void showOverlay(boolean bn) {
    this.showOverlay = bn;
  }

  /**
   * Retrieves the alpha value of the video component
   *
   * @return alpha value of the video component
   */
  public int getAlpha() {
    return alpha;
  }

  private final Runnable update = new Runnable() {

    public void run() {
      bufferLock.lock();
      try {
        if (!isDisposed()) {
          redraw();
        }
        updatePending = false;
      } finally {
        bufferLock.unlock();
      }
    }
  };

  private BufferedImage getBufferedImage(int width, int height) {
    if (currentImage != null && currentImage.getWidth() == width
        && currentImage.getHeight() == height) {
      return currentImage;
    }
    if (currentImage != null) {
      currentImage.flush();
    }
    currentImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
    currentImage.setAccelerationPriority(0.0f);
    return currentImage;
  }

  /**
   * Sets the background color
   *
   * @param bgColor
   */
  public void setBackGroundColor(Color bgColor) {
    this.bgColor = bgColor;
  }

  /**
   * Gets the background color
   *
   * @param bgColor
   */
  public Color getBackGroundColorColor() {
    return bgColor;
  }

  private class RGBListener implements RGBDataSink.Listener {

    public void rgbFrame(boolean isPrerollFrame, int width, int height, IntBuffer rgb) {
      if (!bufferLock.tryLock()) {
        return;
      }
      if (updatePending && !isPrerollFrame) {
        bufferLock.unlock();
        return;
      }
      try {
        final BufferedImage renderImage = getBufferedImage(width, height);
        int[] pixels = ((DataBufferInt) renderImage.getRaster().getDataBuffer()).getData();
        rgb.get(pixels, 0, width * height);
        updatePending = true;
      } finally {
        bufferLock.unlock();
      }
      // Tell Canvas to use the new buffer
      if (!isDisposed()) {
        getDisplay().asyncExec(update);
      }
    }
  }
}
TOP

Related Classes of org.gstreamer.swt.VideoComponent$RGBListener

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.