#!/usr/bin/ruby

# 
# sample script: 
#       JMF Demo
#

require 'yajb/jbridge'
include JavaBridge

JBRIDGE_OPTIONS = {
  :classpath => "$CLASSPATH;jmf.jar", # for windows (classpath separator ";")
}

jimport "java.awt.*"
jimport "java.awt.event.*"
jimport "javax.media.*"
jimport "javax.media.format.*"
jimport "javax.swing.*"
jimport "javax.imageio.*"

VF = :VideoFormat

#### Initializing JMF

# Selecting a format
dev_list = :CaptureDeviceManager.jclass.getDeviceList(VF.jnew( VF.jclass.RGB ) )
if dev_list.size < 1 then
  puts "No available video device."
  abort
end
dataSource = :Manager.jclass.createDataSource(dev_list.get(0).getLocator)
formatControl = dataSource.getFormatControls[0]
formats = formatControl.getSupportedFormats
formats.each{|i| puts i.toString}
formatControl.setFormat(formats[0])

# Start up the processor
processor = :Manager.jclass.createProcessor(dataSource)
processor.configure
sleep(0.5)
processor.setContentDescriptor(nil)
processor.prefetch
sleep(0.5)


### GUI Construction
frame = :JFrame.jnew("JMF Demo")
panel = :JPanel.jnew( :BorderLayout.jnew )
panel.add(processor.getVisualComponent(), :BorderLayout.jclass.CENTER)

capt_btn = :JButton.jnew("capt")
action = :ActionListener.jext
class << action
  def init(p)
    @processor = p
  end

  def actionPerformed(e)
    frameGrabbingCtrl = @processor.getControl("javax.media.control.FrameGrabbingControl")
    if frameGrabbingCtrl.nil?
      puts "Can not get a FrameGrabbingControl!"
    else
      image2jpeg(:java_io_File.jnew("a.jpg"),buffer2img(frameGrabbingCtrl.grabFrame()),0.9)
    end
  end

  def buffer2img(buffer)
    format = buffer.getFormat
    btoi = :javax_media_util_BufferToImage.jnew(format)
    size = format.getSize
    img = btoi.createImage(buffer)
    bimage = :java_awt_image_BufferedImage.jnew(size.width, size.height, :java_awt_image_BufferedImage.jclass.TYPE_INT_RGB)
    g2d = bimage.createGraphics
    g2d.drawImage(img,0,0,nil)
    return bimage
  end

  def image2jpeg(obj,image,compressionQuality)
    nimg = :IIOImage.jnew(image,nil,nil)
    writers = :ImageIO.jclass.getImageWritersByFormatName("jpeg")
    writer = writers.next
    ios = :ImageIO.jclass.createImageOutputStream(obj)
    writer.setOutput(ios)
    
    param = :javax_imageio_plugins_jpeg_JPEGImageWriteParam.jnew(nil)
    param.setCompressionMode(:ImageWriteParam.jclass.MODE_EXPLICIT)
    param.setCompressionQuality(compressionQuality)
    writer.write(nil,nimg,param)
    ios.flush
    writer.dispose
    ios.close
  end
end
action.init(processor)

capt_btn.addActionListener(action)
panel.add(capt_btn, :BorderLayout.jclass.SOUTH)
frame.getContentPane.add(panel)

wc = :WindowAdapter.jext
wc.jdef(:windowClosing) do |e|
  wakeup_thread
end
frame.addWindowListener(wc)
frame.pack
frame.show
processor.start

stop_thread
