CEGUI Gstreamer

Projects using CEGUI or any kind of implementation revolving around CEGUI - Post it here!
Showing off screenshots and giving a short description is highly encouraged!

Moderators: CEGUI MVP, CEGUI Team

User avatar
dermont
Quite a regular
Quite a regular
Posts: 75
Joined: Mon Aug 29, 2005 16:15

CEGUI Gstreamer

Postby dermont » Mon Mar 09, 2015 06:17

Note sure what is the correct board index for things like this.

Anyway, here is the CEGUI (version 08) OpenGL GST example for GStreamer 1.0 in C++ from the following thread. It's based on the Ogre gst 0.10 example but has an aysnch queues and uses glfw3(from code someone posted on here).
viewtopic.php?f=3&t=6978

You have to update the code for your video file in main.cpp "new GSTVideo(your file". It would have been better to have encapsulated the video buffer updates in a texture but it caused threading issues. Also the pipeline could be improved/shortened to replace videoconvert with shaders. You could of course use the GStreamer OpenGL plugin but hopefully it is of some interest to someone.

This is a link to the original from hpesoj:
http://www.ogre3d.org/tikiwiki/tiki-index.php?page=Using+GStreamer+with+Ogre
Attachments
CEGUIForumGST.zip
(8.38 KiB) Downloaded 1072 times

User avatar
Ident
CEGUI Team
Posts: 1998
Joined: Sat Oct 31, 2009 13:57
Location: Austria

Re: CEGUI Gstreamer

Postby Ident » Mon Mar 09, 2015 17:08

Do I understand correctly that gstreamer is a library that allows you to stream textures, e.g. from a video? This would be a killer-feature in CEGUI.
I haven't looked at your code yet. Could you summarise what it does( briefly) ? I am very curious.
CrazyEddie: "I don't like GUIs"

User avatar
dermont
Quite a regular
Quite a regular
Posts: 75
Joined: Mon Aug 29, 2005 16:15

Re: CEGUI Gstreamer

Postby dermont » Mon Mar 09, 2015 18:41

Yes it plays a video with sound on a CEGUI OpenGL texture ( it also works on an Ogre texture). Basically you create a pipeline, either by creating the elements in the pipeline in code or even easier in one line, e.g in python. You can can run/test your pipeline via gst-launch-1.0.

Code: Select all

        pipeline = Gst.parse_launch("""
          uridecodebin  name=demux
             demux. ! audioconvert ! volume name=volume volume=0.1 ! autoaudiosink
             demux.!  videoconvert ! video/x-raw,format=RGBA
          ! appsink name=sink sync=true
        """)


For the above pipeline (appsink name=sink) is a fakesink i.e. won't do anything but allow us to retrieve the video/sample buffer data. In the above example uridecodebin which should play all video types for GStreamer plugins that you have installed. The data can either be retrieved from "new-sample" call back as with the python demo below or via a asyc queue as the C++ example.

http://gstreamer.freedesktop.org/data/d ... eline.html

Since the video width may not be known until the first frame there are some issues/ugly hacks to keep the Texture Size/BasicImage resize in sysn and ensure only updates to the CEGUI texture are from the main thread.

So one BasicImage/Texture per video and any number of Static Images using that basic image. For the list items subclass ListboxItem, pass the image and call render(buffer, finalPos, clipper,PyCEGUI.ColourRect(PyCEGUI.Colour(1.0,1.0,1.0,alpha)))

There is also a gl plugin where you can handle the video conversion via shaders, it previously wasn't maintained but is now part of plugins-bad. So it could done in an easier manner, see the following example:
http://cgit.freedesktop.org/gstreamer/g ... .cpp?h=1.4

Here is the python code for the DragDropDemo replaced with images playing a video.

Code: Select all

import sys, os
import warnings

GST_FLOW_OK = 0


#sys.path.insert(0, "/media/sdb5/Libraries/CEGUI/build/v0-8/lib")
sys.path.insert(0, "/media/sdb5/PYTHONOGRECMAKE/CEGUI/lib")
sys.path.insert(0, "/media/sdb5/Libraries/OGRE/sdk/v1-9/share/cegui-0")
sys.path.insert(0, "/media/sdb5/Libraries/OGRE/sdk/v1-9/share/cegui-0/schemes")

if sys.platform == "linux2":
    ## We need to import the library
    import ctypes
    ctypes.CDLL("/media/sdb5/Libraries/CEGUI/build/v0-8/lib/libCEGUIBase-0.so", ctypes.RTLD_GLOBAL)

import PyCEGUI
import numpy
#print dir(PyCEGUI)

from OpenGL.GL import *
from OpenGL.GLU import *
from OpenGL.GLUT import *
from PIL.Image import open
import gi
gi.require_version('Gst', '1.0')
from gi.repository import Gst, GObject, Gtk, Gdk
# Needed for window.get_xid(), xvimagesink.set_window_handle(), respectively:
from gi.repository import GdkX11, GstVideo
 
# you must have PyCEGUI python package installed (see pypi repository)
# or you must make it work yourself using binary bindings from SDK
import PyCEGUI
import PyCEGUIOpenGLRenderer
#print dir(PyCEGUIOpenGLRenderer)

CEGUI_PATH = "/media/sdb5/Libraries/OGRE/sdk/v1-9/share/cegui-0/"
#CEGUI_PATH = "/media/sdb5/Libraries/CEGUI/src/v0-8/datafiles/"

class GSTListboxItem(PyCEGUI.ListboxItem):
    def __init__(self,text, id, texture,videoSizeThumb):
        PyCEGUI.ListboxItem.__init__(self,text)
        self.d_thumbsize = videoSizeThumb
        self.d_texture = texture
        self.setSelectionBrushImage("WindowsLook/MultiListSelectionBrush");

    def getPixelSize(self):
       return self.d_thumbsize

    def drawImage(self, buffer, targetRect, alpha, clipper):
        finalPos = PyCEGUI.Rectf(targetRect)
        finalPos.setWidth(targetRect.getHeight())
        finalPos.setHeight(targetRect.getHeight())
        self.d_texture.render(buffer, finalPos, clipper,
                              PyCEGUI.ColourRect(PyCEGUI.Colour(1.0,1.0,1.0,alpha)))

    def drawTexture(self, buffer, targetRect, alpha, clipper):

        white = PyCEGUI.Colour(0.5, 0.5, 1.0)
        pixelSize = PyCEGUI.Sizef(1.0,1.0)
        finalRect = PyCEGUI.Rectf(targetRect)
        finalRect.setWidth(targetRect.getWidth())
        finalRect.setHeight(targetRect.getHeight())

        vbuffer = [PyCEGUI.Vertex()]*6

        # top-left
        vbuffer[0].position = PyCEGUI.Vector3f(finalRect.left(), finalRect.top(), 0.0)
        vbuffer[0].colour_val = white
        vbuffer[0].tex_coords = PyCEGUI.Vector2f(0.0, 0.0)
        # bottom-left
        vbuffer[1].position = PyCEGUI.Vector3f(finalRect.left(), finalRect.bottom(), 0.0)
        vbuffer[1].colour_val = white
        vbuffer[1].tex_coords = PyCEGUI.Vector2f(0.0, pixelSize.d_height)
        # bottom-right
        vbuffer[2].position = PyCEGUI.Vector3f(finalRect.right(), finalRect.bottom(), 0.0)
        vbuffer[2].colour_val = white
        vbuffer[2].tex_coords = PyCEGUI.Vector2f(pixelSize.d_width, pixelSize.d_height)
       
        # top-right
        vbuffer[3].position = PyCEGUI.Vector3f(finalRect.right(), finalRect.top(), 0.0)
        vbuffer[3].colour_val = white
        vbuffer[3].tex_coords = PyCEGUI.Vector2f(pixelSize.d_width, 0.0)
        # top-left
        vbuffer[4].position = PyCEGUI.Vector3f(finalRect.left(), finalRect.top(), 0.0)
        vbuffer[4].colour_val = white
        vbuffer[4].tex_coords = PyCEGUI.Vector2f(0.0, 0.0)
        # bottom-right
        vbuffer[5].position = PyCEGUI.Vector3f(finalRect.right(), finalRect.bottom(), 0.0)
        vbuffer[5].colour_val = white
        vbuffer[5].tex_coords = PyCEGUI.Vector2f(pixelSize.d_width, pixelSize.d_height)

        # give our vertices to the buffer for drawing
        buffer.setActiveTexture(self.d_texture)
        #buffer.appendGeometry(vbuffer, 6)
        for i in range(len(vbuffer)):
            buffer.appendVertex(vbuffer[i])

    def draw(self, buffer, targetRect, alpha, clipper):
        #self.drawTexture(buffer, targetRect, alpha, clipper)
        self.drawImage(buffer, targetRect, alpha, clipper)
        #if (d_selected && d_selectBrush != 0)
        #  d_selectBrush->render(buffer, targetRect, clipper,
      #ColourRect(Colour(0.0,0.0,1,0.5)));


class GSTTexture():
    def __init__(self,name):
        self.videoSizeNew = PyCEGUI.Sizef(float(1), float(1))
        self.videoRect = PyCEGUI.Rectf(0.0, 0.0, float(1), float(1))

        self.texture = None
        self.texName = name
        self.textnum = 0
        self.dirty = False

    def setSize(self,width, height):
        if width != self.videoSizeNew.d_width or height!=self.videoSizeNew.d_height:
            self.videoSizeNew = PyCEGUI.Sizef(float(width), float(height))
            self.videoRect = PyCEGUI.Rectf(0.0, 0.0, float(self.videoSizeNew.d_width), float(self.videoSizeNew.d_height))
            self.dirty = True

    def resize(self):
        videoSize = self.texture.getOriginalDataSize()
        if self.dirty:
            self.texture.setTextureSize(self.videoSizeNew)

    def update(self, videoBufferData):

        videoSize = self.texture.getOriginalDataSize()
        ##print videoSize.d_width, videoSize.d_height

        if videoBufferData is None:
            return None

        pixelFormatSize = int(videoBufferData.get_size() / videoSize.d_width / videoSize.d_height)
        pixelFormat = PyCEGUI.Texture.PF_RGBA
        if pixelFormatSize==3:
            pixelFormat = PyCEGUI.Texture.PF_RGB
        ##print pixelFormatSize, videoBufferData.get_size(),self.videoRect.right(),self.videoRect.bottom()

        # blit to our texture
        bm = (ctypes.c_ubyte * int(self.videoSize.d_width)*int(videoSize.d_height)*int(pixelFormatSize))()
        ctypes.memmove(bm, videoBufferData.extract_dup(0, videoBufferData.get_size()), videoBufferData.get_size())
        self.texture.blitFromMemory(PyCEGUIOpenGLRenderer.CastVoidPtr(ctypes.addressof(bm)),self.videoRect)

        # clean up
        self.videoBufferNew = False
        if not videoBufferData is None:
            del videoBufferData
        videoBufferData = None

    def getTexture(self):
        return self.texture

    def getRect(self):
        return self.videoRect

    def setBasicImage(self,img):
        self.basicImage = img

    def setTexture(self,texture):
        self.texture = texture
        self.videoSize = texture.getOriginalDataSize()
        #self.videoSizeNew = self.videoSize
        self.videoRect = PyCEGUI.Rectf(0.0, 0.0, float(self.videoSize.d_width), float(self.videoSize.d_height))



class GSTCEGUIVideo(GSTTexture):
    def __init__(self, callback, name):
        GObject.threads_init()
        self.bufferData = None
        self.bufferDataReady = False

        GSTTexture.__init__(self,"TEST")
        Gst.init(None)
        pipeline = Gst.parse_launch("""
          uridecodebin  name=demux
             demux. ! audioconvert ! volume name=volume volume=0.1 ! autoaudiosink
             demux.!  videoconvert ! video/x-raw,format=RGBA
          ! appsink name=sink sync=true
        """)

        #if (err is not None):
        #    print ("could not construct pipeline: %s\n", err)
        #    #g_error_free (error);

        mAppSink = pipeline.get_by_name ("sink")

        mAppSink.set_property("emit-signals", True)
        mAppSink.set_property("max-buffers", 1)
        mAppSink.set_property("drop", 1)

        mAppSink.connect("new-sample",self.onNewBuffer, self)
        mAppSink.connect("new_preroll",self.onNewPreroll, self)

        bus = pipeline.get_bus()
        bus.connect('message::error', self.on_error)

        decodebin = pipeline.get_by_name("demux")
        #decodebin.set_property("uri", "file://///media/sdb5/Development/OGRE/demos/joy.mov")
        decodebin.set_property("uri", "file://///media/sdb5/Development/CEGUI/CEGUIGStreamer1.0/Cheerios1960.mpg")

        pipeline.set_state(Gst.State.PLAYING)

        self.pipeline = pipeline
        self.mAppSink = mAppSink


    def onNewBuffer(self, sink, userData):

        sample = sink.emit('pull-sample')
        caps = sample.get_caps() 

        for i in range(caps.get_size()):
            structure = caps.get_structure(i)
            (OK,width) = structure.get_int("width")
            (OK,height) = structure.get_int("height")
            (OK, ratioNum, ratioDen) = structure.get_fraction("pixel-aspect-ratio")
            if (OK):
                pixelRatio = float(ratioNum) / float(ratioDen)
        userData.bufferData = sample.get_buffer()
        userData.bufferDataReady = True
        userData.setSize(width,height)

        return Gst.FlowReturn.OK
 
    def onNewPreroll(self,appsink, data):
        return Gst.FlowReturn.OK

    def on_error(self, bus, msg):
        print('on_error():', msg.parse_error())

    def pause(self):
        self.pipeline.set_state(Gst.State.PAUSED)

    def play(self):
        self.pipeline.set_state(Gst.State.PLAYING)

    def __del__(self):
        self.pipeline.set_state(Gst.State.PAUSED)
        self.pipeline.set_state(Gst.State.NULL)
        del self.pipeline



 
class BaseApp(object):
    def __init__(self):
        glutInit(sys.argv)
        glutInitDisplayMode(GLUT_DEPTH|GLUT_DOUBLE|GLUT_RGBA)
        glutInitWindowSize(800, 800)
        glutInitWindowPosition(100, 100)
        glutCreateWindow("Crazy Eddie's GUI Mk-2 - glut Base Application")
        glutSetCursor(GLUT_CURSOR_NONE)
 
        glutDisplayFunc(self.displayFunc)
        glutReshapeFunc(self.reshapeFunc)
        glutMouseFunc(self.mouseFunc)
        glutMotionFunc(self.mouseMotionFunc)
        glutPassiveMotionFunc(self.mouseMotionFunc)

        self.VideoPlayer = None
        self.videoImage = None
        self.videoImageParent = None
        self.videoBasicImage = None
        self.videoTexture = None
        self.videoItem = None
        self.mListBox = None
        self.DragstaticImages = []
 
        PyCEGUIOpenGLRenderer.OpenGLRenderer.bootstrapSystem()
 
    def __del__(self):
        if (self.VideoPlayer is not None):
            del self.VideoPlayer
        PyCEGUIOpenGLRenderer.OpenGLRenderer.destroySystem()

 
    def initialiseResources(self):
        rp = PyCEGUI.System.getSingleton().getResourceProvider()
 
        rp.setResourceGroupDirectory("schemes", CEGUI_PATH + "schemes")
        rp.setResourceGroupDirectory("imagesets", CEGUI_PATH + "imagesets")
        rp.setResourceGroupDirectory("fonts", CEGUI_PATH + "fonts")
        rp.setResourceGroupDirectory("layouts", CEGUI_PATH + "layouts")
        rp.setResourceGroupDirectory("looknfeels", CEGUI_PATH + "looknfeel")
        rp.setResourceGroupDirectory("schemas", CEGUI_PATH + "xml_schemas")
 
        PyCEGUI.ImageManager.setImagesetDefaultResourceGroup("imagesets")
        PyCEGUI.Font.setDefaultResourceGroup("fonts")
        PyCEGUI.Scheme.setDefaultResourceGroup("schemes")
        PyCEGUI.WidgetLookManager.setDefaultResourceGroup("looknfeels")
        PyCEGUI.WindowManager.setDefaultResourceGroup("layouts")

        parser = PyCEGUI.System.getSingleton().getXMLParser()
        if parser.isPropertyPresent("SchemaDefaultResourceGroup"):
            parser.setProperty("SchemaDefaultResourceGroup", "schemas")     

        self.VideoPlayer = GSTCEGUIVideo(self, "Test")

    def createDrop(self,root):
        self.mDragWindow = root.getChild("MainWindow")
        self.slot1 = root.getChild("MainWindow/Slot1")
        self.DragContainer1 = root.getChild("MainWindow/Slot1/DragContainer1")
        staticImage = root.getChild("MainWindow/Slot1/DragContainer1/Image")
        staticImage.setProperty("Image", self.videoBasicImage.getName())
        staticImage.invalidate()
        staticImage.setProperty("MousePassThroughEnabled", "True")
        self.DragstaticImages.append(staticImage)

        self.DragContainer2 = root.getChild("MainWindow/Slot6/DragContainer2")
        staticImage = root.getChild("MainWindow/Slot6/DragContainer2/Image")
        staticImage.setProperty("Image", self.videoBasicImage.getName())
        staticImage.invalidate()
        staticImage.setProperty("MousePassThroughEnabled", "True")
        self.DragstaticImages.append(staticImage)

        d = "MainWindow/Slot"
        for i in range(1,12):
            slot = root.getChild(d+str(i))
            slot.subscribeEvent(PyCEGUI.Window.EventDragDropItemDropped, self.onItemDropped)


    def createDrop3(self,root):
        self.mDragWindow = PyCEGUI.WindowManager.getSingleton().createWindow("WindowsLook/FrameWindow", "DragWindow")
        self.mDragWindow.setSize(PyCEGUI.USize(PyCEGUI.UDim(float(0.5), 0) , PyCEGUI.UDim(float(0.5), 0)))
        self.mDragWindow.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0.3, 0.0), PyCEGUI.UDim(0.3, 0.0)))
        root.addChild(self.mDragWindow)

        #<Window name="Slot1" type="WindowsLook/Static">
        #        <Property name="Position" value="{{0.05,0},{0.05,0}}" />
        #        <Property name="Size" value="{{0.2,0},{0.26,0}}" />

        # static image
        slotid = 0
        for i in range(1):
            for j in range(1):
                slotid+=1
                static = PyCEGUI.WindowManager.getSingleton().createWindow("TaharezLook/StaticImage", "Slot" + str(slotid))
                static.setSize(PyCEGUI.USize(PyCEGUI.UDim(float(.22), 0) , PyCEGUI.UDim(float(.22), 0)))
                static.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0.05 + float(j*0.24), 0.0), PyCEGUI.UDim(0.05 + float(i)*0.24, 0.0)))
                self.mDragWindow.addChild(static)
                static.subscribeEvent(PyCEGUI.Window.EventDragDropItemDropped, self.onItemDropped)

                if slotid==1 or slot_id==6:
                    dragContainer = PyCEGUI.WindowManager.getSingleton().createWindow("TaharezLook/DragContainer", "Drag" + str(slotid))
                    dragContainer.setArea(PyCEGUI.UVector2(PyCEGUI.UDim(0.05 , 0.0), PyCEGUI.UDim(0.05 , 0.0)),PyCEGUI.UVector2(PyCEGUI.UDim(0.95 , 0.0), PyCEGUI.UDim(0.95 , 0.0)))
                    static.addChild(dragContainer)
                    static.subscribeEvent(PyCEGUI.Window.EventDragDropItemDropped, self.onItemDropped)

                    staticImage = PyCEGUI.WindowManager.getSingleton().createWindow("TaharezLook/StaticImage", "StaticImage" + str(slotid))
                    staticImage.setSize(PyCEGUI.USize(PyCEGUI.UDim(float(0.0), 0.0) , PyCEGUI.UDim(float(1.0), 1.0)))
                    #staticImage.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0.05 + float(j*0.24), 0.0), PyCEGUI.UDim(0.05 + float(i)*0.24, 0.0)))
                    staticImage.setProperty("Image", self.videoBasicImage.getName())
                    staticImage.invalidate()
                    staticImage.setProperty("MousePassThroughEnabled", "True")
                    self.DragstaticImages.append(staticImage)
                    static.addChild(staticImage)
                    #staticImage.subscribeEvent(PyCEGUI.Window.EventDragDropItemDropped, self.onItemDropped)
                    #self.DragstaticImages.append(staticImage)


    def onItemDropped(self,args):
        print args # shows in this case this is a cegui.WindowEventArgs
        print dir(args)
        w = args.window
        #val = w.CurrentValue
        print w.getName() #,"received",val
        if not args.window.getChildCount():
            # add dragdrop item as child of target if target has no item already
            args.window.addChild(args.dragDropItem)
            # Now we must reset the item position from it's 'dropped' location,
            # since we're now a child of an entirely different window
            args.dragDropItem.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0.05, 0),PyCEGUI.UDim(0.05, 0)))


    def createVideoListBox(self,parent):
        self.mListBox = PyCEGUI.WindowManager.getSingleton().createWindow("WindowsLook/MultiColumnList", "MyListBox")
        self.mListBox.setSize(PyCEGUI.USize(PyCEGUI.UDim(float(0.3), 0) , PyCEGUI.UDim(float(0.8), 0)))
        self.mListBox.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0.7, 0.0), PyCEGUI.UDim(0.2, 0.0)))

        self.mListBox.addColumn("Column1", 0, PyCEGUI.UDim(1.0, 1.0))
        #self.mListBox.addColumn("Column2", 1, PyCEGUI.UDim(0.2, 0.20))
        #self.mListBox.addColumn("Column3", 2, PyCEGUI.UDim(0.4, 0.20))

        self.videoItems = []
        thumbSize = PyCEGUI.Sizef(128.0,128.0)
        #for j in range(3):
        mRow = self.mListBox.addRow()
        self.videoItem = GSTListboxItem("TEST", 0 , self.videoBasicImage,thumbSize)
        self.mListBox.setItem(self.videoItem, 0, mRow);

        mRow = self.mListBox.addRow()
        self.videoItem2 = GSTListboxItem("TEST", 0 , self.videoBasicImage,thumbSize)
        self.mListBox.setItem(self.videoItem2, 0, mRow);

        parent.addChild(self.mListBox)

    def createVideo(self,parent):

        ## create dummy video size/rect, we need to update/resize texture main thread when video size is known
        videoSize = PyCEGUI.Sizef(1, 1 )
        rect = PyCEGUI.Rectf(0.0, 0.0, 1, 1 )

        # texture
        self.texture = PyCEGUI.System.getSingleton().getRenderer().createTexture("Video",videoSize)

        # basic image
        cim = PyCEGUI.ImageManager.getSingleton().create("BasicImage", self.texture.getName()+"BasicImage")
        cim.setTexture(self.texture)
        self.VideoPlayer.setTexture(self.texture)
        cim.setArea(rect)
        cim.setAutoScaled(PyCEGUI.ASM_Disabled  )

        # static image
        staticImage = PyCEGUI.WindowManager.getSingleton().createWindow("TaharezLook/StaticImage", self.texture.getName()+"StaticImage")
        staticImage.setSize(PyCEGUI.USize(PyCEGUI.UDim(float(1), 0) , PyCEGUI.UDim(float(1), 0)))
        staticImage.setPosition(PyCEGUI.UVector2(PyCEGUI.UDim(0, 0.0), PyCEGUI.UDim(0, 0.0)))

        # static image
        staticImage.setProperty("Image", cim.getName())

        parent.addChild(staticImage)
        staticImage.invalidate()
        parent.invalidate(True)

        self.videoBasicImage = cim
        self.videoImage = staticImage
        self.videoImageParent = parent
        self.texture = None


    def setupUI(self):

        PyCEGUI.SchemeManager.getSingleton().createFromFile("TaharezLook.scheme")
        PyCEGUI.SchemeManager.getSingleton().createFromFile("WindowsLook.scheme")
        PyCEGUI.SchemeManager.getSingleton().createFromFile("VanillaSkin.scheme")

        PyCEGUI.System.getSingleton().getDefaultGUIContext().getMouseCursor().setDefaultImage("TaharezLook/MouseArrow")
 
        root = PyCEGUI.WindowManager.getSingleton().loadLayoutFromFile("DragDropDemo.layout")
        PyCEGUI.System.getSingleton().getDefaultGUIContext().setRootWindow(root)
        self.wnd = PyCEGUI.WindowManager.getSingleton().createWindow("TaharezLook/FrameWindow", "Demo Window")
        root.addChild(self.wnd)

        root.addChild(self.wnd)

        self.createVideo(self.wnd)
        self.createVideoListBox(root)
        self.createDrop(root)

    def run(self):
        self.reshapeFunc(1024,768)
        self.initialiseResources()
        self.setupUI()
 
        self.lastFrameTime = glutGet(GLUT_ELAPSED_TIME)
        self.updateFPS = 0
        glutMainLoop()
 
    def displayFunc(self):
        thisTime = glutGet(GLUT_ELAPSED_TIME)
        elapsed = (thisTime - self.lastFrameTime) / 1000.0
        self.lastFrameTime = thisTime
        self.updateFPS = self.updateFPS - elapsed
 
        PyCEGUI.System.getSingleton().injectTimePulse(elapsed)

        # do rendering for this frame.
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)

        ## we have to call texture resizes/updates from main thread so can't call from callbacks
        if not self.VideoPlayer.texture is None:

            ## the texture has been resized, we don't know the video size until we retrieve
            ## from the caps
            if self.VideoPlayer.dirty:
                self.videoBasicImage.setArea(self.VideoPlayer.videoRect)
                self.VideoPlayer.texture.setTextureSize(self.VideoPlayer.videoSizeNew)
                self.VideoPlayer.setTexture(self.VideoPlayer.texture)

            ## we have GST buffer data to update our texture
            if self.VideoPlayer.bufferDataReady:
                self.VideoPlayer.bufferDataReady = False
                self.VideoPlayer.update(self.VideoPlayer.bufferData)
                self.videoImageParent.invalidate(True)
                self.videoImage.invalidate(True)
                self.mListBox.invalidate(True)
                self.mDragWindow.invalidate(True)

        PyCEGUI.System.getSingleton().renderAllGUIContexts()

        glutPostRedisplay()
        glutSwapBuffers()
 
    def reshapeFunc(self, width, height):
        glViewport(0, 0, width, height)
        glMatrixMode(GL_PROJECTION)
        glLoadIdentity()
        gluPerspective(60.0, width / height, 1.0, 50.0)
        glMatrixMode(GL_MODELVIEW)
        PyCEGUI.System.getSingleton().notifyDisplaySizeChanged(PyCEGUI.Sizef(float(width), float(height) ))

 
    def mouseFunc(self, button, state, x, y):
        if button == GLUT_LEFT_BUTTON:
            if state == GLUT_UP:
                #if self.VideoPlayer:
                #    self.VideoPlayer.pause()
                PyCEGUI.System.getSingleton().getDefaultGUIContext().injectMouseButtonUp(PyCEGUI.LeftButton)
            else:
                PyCEGUI.System.getSingleton().getDefaultGUIContext().injectMouseButtonDown(PyCEGUI.LeftButton)
 
        elif button == GLUT_RIGHT_BUTTON:
            if state == GLUT_UP:
                #if self.VideoPlayer:
                #    self.VideoPlayer.play()
                PyCEGUI.System.getSingleton().getDefaultGUIContext().injectMouseButtonUp(PyCEGUI.RightButton)
            else:
                PyCEGUI.System.getSingleton().getDefaultGUIContext().injectMouseButtonDown(PyCEGUI.RightButton)
 
    def mouseMotionFunc(self, x, y):
        PyCEGUI.System.getSingleton().getDefaultGUIContext().injectMousePosition(x, y)
 
app = BaseApp()
app.run()
del app



gst.png


The python module(s) for GStreamer are excellent and since CEGUI has it's own python module there nothing to stop you (other than threading issues) from creating/running say the above script from C++ and playing a video without having to build against GStreamer.

User avatar
Ident
CEGUI Team
Posts: 1998
Joined: Sat Oct 31, 2009 13:57
Location: Austria

Re: CEGUI Gstreamer

Postby Ident » Tue Mar 10, 2015 22:35

Very interesting, thanks for the share. I will look into this in a couple of weeks (not much time atm) and will definitely report back. This seems like something with a lot of potential. If I get it to run, I hope to make a CEGUI wiki article based on what you wrote, I will of course reference your work.

I will move this thread in the User Projects subforum, I think thats more fitting.
CrazyEddie: "I don't like GUIs"


Return to “User Projects”

Who is online

Users browsing this forum: No registered users and 4 guests