| Index: webrtc/modules/video_render/mac/video_render_agl.cc
|
| diff --git a/webrtc/modules/video_render/mac/video_render_agl.cc b/webrtc/modules/video_render/mac/video_render_agl.cc
|
| deleted file mode 100644
|
| index 3243563b2bf901e1e268637273247fa0e72ba3f2..0000000000000000000000000000000000000000
|
| --- a/webrtc/modules/video_render/mac/video_render_agl.cc
|
| +++ /dev/null
|
| @@ -1,1987 +0,0 @@
|
| -/*
|
| - * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
|
| - *
|
| - * Use of this source code is governed by a BSD-style license
|
| - * that can be found in the LICENSE file in the root of the source
|
| - * tree. An additional intellectual property rights grant can be found
|
| - * in the file PATENTS. All contributing project authors may
|
| - * be found in the AUTHORS file in the root of the source tree.
|
| - */
|
| -
|
| -#include "webrtc/engine_configurations.h"
|
| -
|
| -#if defined(CARBON_RENDERING)
|
| -
|
| -#include "webrtc/modules/video_render/mac/video_render_agl.h"
|
| -
|
| -// includes
|
| -#include "webrtc/common_video/libyuv/include/webrtc_libyuv.h"
|
| -#include "webrtc/system_wrappers/include/critical_section_wrapper.h"
|
| -#include "webrtc/system_wrappers/include/event_wrapper.h"
|
| -#include "webrtc/system_wrappers/include/trace.h"
|
| -
|
| -namespace webrtc {
|
| -
|
| -/*
|
| - *
|
| - * VideoChannelAGL
|
| - *
|
| - */
|
| -
|
| -#pragma mark VideoChannelAGL constructor
|
| -
|
| -VideoChannelAGL::VideoChannelAGL(AGLContext& aglContext, int iId, VideoRenderAGL* owner) :
|
| - _aglContext( aglContext),
|
| - _id( iId),
|
| - _owner( owner),
|
| - _width( 0),
|
| - _height( 0),
|
| - _stretchedWidth( 0),
|
| - _stretchedHeight( 0),
|
| - _startWidth( 0.0f),
|
| - _startHeight( 0.0f),
|
| - _stopWidth( 0.0f),
|
| - _stopHeight( 0.0f),
|
| - _xOldWidth( 0),
|
| - _yOldHeight( 0),
|
| - _oldStretchedHeight(0),
|
| - _oldStretchedWidth( 0),
|
| - _buffer( 0),
|
| - _bufferSize( 0),
|
| - _incomingBufferSize(0),
|
| - _bufferIsUpdated( false),
|
| - _sizeInitialized( false),
|
| - _numberOfStreams( 0),
|
| - _bVideoSizeStartedChanging(false),
|
| - _pixelFormat( GL_RGBA),
|
| - _pixelDataType( GL_UNSIGNED_INT_8_8_8_8),
|
| - _texture( 0)
|
| -
|
| -{
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Constructor", __FUNCTION__, __LINE__);
|
| -}
|
| -
|
| -VideoChannelAGL::~VideoChannelAGL()
|
| -{
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Destructor", __FUNCTION__, __LINE__);
|
| - if (_buffer)
|
| - {
|
| - delete [] _buffer;
|
| - _buffer = NULL;
|
| - }
|
| -
|
| - aglSetCurrentContext(_aglContext);
|
| -
|
| - if (_texture != 0)
|
| - {
|
| - glDeleteTextures(1, (const GLuint*) &_texture);
|
| - _texture = 0;
|
| - }
|
| -}
|
| -
|
| -int32_t VideoChannelAGL::RenderFrame(const uint32_t streamId,
|
| - VideoFrame& videoFrame) {
|
| - _owner->LockAGLCntx();
|
| - if (_width != videoFrame.width() ||
|
| - _height != videoFrame.height()) {
|
| - if (FrameSizeChange(videoFrame.width(), videoFrame.height(), 1) == -1) {
|
| - WEBRTC_TRACE(kTraceError, kTraceVideoRenderer, _id, "%s:%d FrameSize
|
| - Change returned an error", __FUNCTION__, __LINE__);
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| - }
|
| -
|
| - _owner->UnlockAGLCntx();
|
| - return DeliverFrame(videoFrame);
|
| -}
|
| -
|
| -int VideoChannelAGL::UpdateSize(int /*width*/, int /*height*/)
|
| -{
|
| - _owner->LockAGLCntx();
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoChannelAGL::UpdateStretchSize(int stretchHeight, int stretchWidth)
|
| -{
|
| -
|
| - _owner->LockAGLCntx();
|
| - _stretchedHeight = stretchHeight;
|
| - _stretchedWidth = stretchWidth;
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoChannelAGL::FrameSizeChange(int width, int height, int numberOfStreams)
|
| -{
|
| - // We'll get a new frame size from VideoAPI, prepare the buffer
|
| -
|
| - _owner->LockAGLCntx();
|
| -
|
| - if (width == _width && _height == height)
|
| - {
|
| - // We already have a correct buffer size
|
| - _numberOfStreams = numberOfStreams;
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| - }
|
| -
|
| - _width = width;
|
| - _height = height;
|
| -
|
| - // Delete the old buffer, create a new one with correct size.
|
| - if (_buffer)
|
| - {
|
| - delete [] _buffer;
|
| - _bufferSize = 0;
|
| - }
|
| -
|
| - _incomingBufferSize = CalcBufferSize(kI420, _width, _height);
|
| - _bufferSize = CalcBufferSize(kARGB, _width, _height);//_width * _height * bytesPerPixel;
|
| - _buffer = new unsigned char [_bufferSize];
|
| - memset(_buffer, 0, _bufferSize * sizeof(unsigned char));
|
| -
|
| - if (aglSetCurrentContext(_aglContext) == false)
|
| - {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Delete a possible old texture
|
| - if (_texture != 0)
|
| - {
|
| - glDeleteTextures(1, (const GLuint*) &_texture);
|
| - _texture = 0;
|
| - }
|
| -
|
| - // Create a new texture
|
| - glGenTextures(1, (GLuint *) &_texture);
|
| -
|
| - GLenum glErr = glGetError();
|
| -
|
| - if (glErr != GL_NO_ERROR)
|
| - {
|
| - }
|
| -
|
| - // Do the setup for both textures
|
| - // Note: we setup two textures even if we're not running full screen
|
| - glBindTexture(GL_TEXTURE_RECTANGLE_EXT, _texture);
|
| -
|
| - // Set texture parameters
|
| - glTexParameterf(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_PRIORITY, 1.0);
|
| -
|
| - glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
| - glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
| -
|
| - glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
| - glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
| - //glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
| - //glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
| -
|
| - glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
|
| -
|
| - glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
|
| -
|
| - glTexParameteri(GL_TEXTURE_RECTANGLE_EXT, GL_TEXTURE_STORAGE_HINT_APPLE, GL_STORAGE_SHARED_APPLE);
|
| -
|
| - // Maximum width/height for a texture
|
| - GLint texSize;
|
| - glGetIntegerv(GL_MAX_TEXTURE_SIZE, &texSize);
|
| -
|
| - if (texSize < _width || texSize < _height)
|
| - {
|
| - // Image too big for memory
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Set up th texture type and size
|
| - glTexImage2D(GL_TEXTURE_RECTANGLE_EXT, // target
|
| - 0, // level
|
| - GL_RGBA, // internal format
|
| - _width, // width
|
| - _height, // height
|
| - 0, // border 0/1 = off/on
|
| - _pixelFormat, // format, GL_BGRA
|
| - _pixelDataType, // data type, GL_UNSIGNED_INT_8_8_8_8
|
| - _buffer); // pixel data
|
| -
|
| - glErr = glGetError();
|
| - if (glErr != GL_NO_ERROR)
|
| - {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -// Called from video engine when a new frame should be rendered.
|
| -int VideoChannelAGL::DeliverFrame(const VideoFrame& videoFrame) {
|
| - _owner->LockAGLCntx();
|
| -
|
| - if (_texture == 0) {
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| - }
|
| -
|
| - if (CalcBufferSize(kI420, videoFrame.width(), videoFrame.height()) !=
|
| - _incomingBufferSize) {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Setting stride = width.
|
| - int rgbret = ConvertFromYV12(videoFrame, kBGRA, 0, _buffer);
|
| - if (rgbret < 0) {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - aglSetCurrentContext(_aglContext);
|
| -
|
| - // Put the new frame into the graphic card texture.
|
| - // Make sure this texture is the active one
|
| - glBindTexture(GL_TEXTURE_RECTANGLE_EXT, _texture);
|
| - GLenum glErr = glGetError();
|
| - if (glErr != GL_NO_ERROR) {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Copy buffer to texture
|
| - glTexSubImage2D(GL_TEXTURE_RECTANGLE_EXT,
|
| - 0, // Level, not use
|
| - 0, // start point x, (low left of pic)
|
| - 0, // start point y,
|
| - _width, // width
|
| - _height, // height
|
| - _pixelFormat, // pictue format for _buffer
|
| - _pixelDataType, // data type of _buffer
|
| - (const GLvoid*) _buffer); // the pixel data
|
| -
|
| - if (glGetError() != GL_NO_ERROR) {
|
| - _owner->UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - _bufferIsUpdated = true;
|
| - _owner->UnlockAGLCntx();
|
| -
|
| - return 0;
|
| -}
|
| -
|
| -int VideoChannelAGL::RenderOffScreenBuffer()
|
| -{
|
| -
|
| - _owner->LockAGLCntx();
|
| -
|
| - if (_texture == 0)
|
| - {
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| - }
|
| -
|
| - GLfloat xStart = 2.0f * _startWidth - 1.0f;
|
| - GLfloat xStop = 2.0f * _stopWidth - 1.0f;
|
| - GLfloat yStart = 1.0f - 2.0f * _stopHeight;
|
| - GLfloat yStop = 1.0f - 2.0f * _startHeight;
|
| -
|
| - aglSetCurrentContext(_aglContext);
|
| - glBindTexture(GL_TEXTURE_RECTANGLE_EXT, _texture);
|
| -
|
| - if(_stretchedWidth != _oldStretchedWidth || _stretchedHeight != _oldStretchedHeight)
|
| - {
|
| - glViewport(0, 0, _stretchedWidth, _stretchedHeight);
|
| - }
|
| - _oldStretchedHeight = _stretchedHeight;
|
| - _oldStretchedWidth = _stretchedWidth;
|
| -
|
| - // Now really put the texture into the framebuffer
|
| - glLoadIdentity();
|
| -
|
| - glEnable(GL_TEXTURE_RECTANGLE_EXT);
|
| -
|
| - glBegin(GL_POLYGON);
|
| - {
|
| - glTexCoord2f(0.0, 0.0); glVertex2f(xStart, yStop);
|
| - glTexCoord2f(_width, 0.0); glVertex2f(xStop, yStop);
|
| - glTexCoord2f(_width, _height); glVertex2f(xStop, yStart);
|
| - glTexCoord2f(0.0, _height); glVertex2f(xStart, yStart);
|
| - }
|
| - glEnd();
|
| -
|
| - glDisable(GL_TEXTURE_RECTANGLE_EXT);
|
| -
|
| - _bufferIsUpdated = false;
|
| -
|
| - _owner->UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoChannelAGL::IsUpdated(bool& isUpdated)
|
| -{
|
| - _owner->LockAGLCntx();
|
| - isUpdated = _bufferIsUpdated;
|
| - _owner->UnlockAGLCntx();
|
| -
|
| - return 0;
|
| -}
|
| -
|
| -int VideoChannelAGL::SetStreamSettings(int /*streamId*/, float startWidth, float startHeight, float stopWidth, float stopHeight)
|
| -{
|
| -
|
| - _owner->LockAGLCntx();
|
| -
|
| - _startWidth = startWidth;
|
| - _stopWidth = stopWidth;
|
| - _startHeight = startHeight;
|
| - _stopHeight = stopHeight;
|
| -
|
| - int oldWidth = _width;
|
| - int oldHeight = _height;
|
| - int oldNumberOfStreams = _numberOfStreams;
|
| -
|
| - _width = 0;
|
| - _height = 0;
|
| -
|
| - int retVal = FrameSizeChange(oldWidth, oldHeight, oldNumberOfStreams);
|
| -
|
| - _owner->UnlockAGLCntx();
|
| -
|
| - return retVal;
|
| -}
|
| -
|
| -int VideoChannelAGL::SetStreamCropSettings(int /*streamId*/, float /*startWidth*/, float /*startHeight*/, float /*stopWidth*/, float /*stopHeight*/)
|
| -{
|
| - return -1;
|
| -}
|
| -
|
| -#pragma mark VideoRenderAGL WindowRef constructor
|
| -
|
| -VideoRenderAGL::VideoRenderAGL(WindowRef windowRef, bool fullscreen, int iId) :
|
| -_hiviewRef( 0),
|
| -_windowRef( windowRef),
|
| -_fullScreen( fullscreen),
|
| -_id( iId),
|
| -_renderCritSec(*CriticalSectionWrapper::CreateCriticalSection()),
|
| -_screenUpdateEvent( 0),
|
| -_isHIViewRef( false),
|
| -_aglContext( 0),
|
| -_windowWidth( 0),
|
| -_windowHeight( 0),
|
| -_lastWindowWidth( -1),
|
| -_lastWindowHeight( -1),
|
| -_lastHiViewWidth( -1),
|
| -_lastHiViewHeight( -1),
|
| -_currentParentWindowHeight( 0),
|
| -_currentParentWindowWidth( 0),
|
| -_currentParentWindowBounds( ),
|
| -_windowHasResized( false),
|
| -_lastParentWindowBounds( ),
|
| -_currentHIViewBounds( ),
|
| -_lastHIViewBounds( ),
|
| -_windowRect( ),
|
| -_aglChannels( ),
|
| -_zOrderToChannel( ),
|
| -_hiviewEventHandlerRef( NULL),
|
| -_windowEventHandlerRef( NULL),
|
| -_currentViewBounds( ),
|
| -_lastViewBounds( ),
|
| -_renderingIsPaused( false),
|
| -
|
| -{
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s");
|
| -
|
| - _screenUpdateThread.reset(
|
| - new rtc::PlatformThread(ScreenUpdateThreadProc, this, "ScreenUpdate"));
|
| - _screenUpdateEvent = EventWrapper::Create();
|
| -
|
| - if(!IsValidWindowPtr(_windowRef))
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, kTraceVideoRenderer, _id, "%s:%d Invalid WindowRef:0x%x", __FUNCTION__, __LINE__, _windowRef);
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, kTraceVideoRenderer, _id, "%s:%d WindowRef 0x%x is valid", __FUNCTION__, __LINE__, _windowRef);
|
| - }
|
| -
|
| - GetWindowRect(_windowRect);
|
| -
|
| - _lastViewBounds.origin.x = 0;
|
| - _lastViewBounds.origin.y = 0;
|
| - _lastViewBounds.size.width = 0;
|
| - _lastViewBounds.size.height = 0;
|
| -
|
| -}
|
| -
|
| -// this is a static function. It has been registered (in class constructor) to be called on various window redrawing or resizing.
|
| -// Since it is a static method, I have passed in "this" as the userData (one and only allowed) parameter, then calling member methods on it.
|
| -#pragma mark WindowRef Event Handler
|
| -pascal OSStatus VideoRenderAGL::sHandleWindowResized (EventHandlerCallRef /*nextHandler*/,
|
| - EventRef theEvent,
|
| - void* userData)
|
| -{
|
| - WindowRef windowRef = NULL;
|
| -
|
| - int eventType = GetEventKind(theEvent);
|
| -
|
| - // see https://dcs.sourcerepo.com/dcs/tox_view/trunk/tox/libraries/i686-win32/include/quicktime/CarbonEvents.h for a list of codes
|
| - GetEventParameter (theEvent,
|
| - kEventParamDirectObject,
|
| - typeWindowRef,
|
| - NULL,
|
| - sizeof (WindowRef),
|
| - NULL,
|
| - &windowRef);
|
| -
|
| - VideoRenderAGL* obj = (VideoRenderAGL*)(userData);
|
| -
|
| - bool updateUI = true;
|
| - if(kEventWindowBoundsChanged == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowBoundsChanging == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowZoomed == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowExpanding == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowExpanded == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowClickResizeRgn == eventType)
|
| - {
|
| - }
|
| - else if(kEventWindowClickDragRgn == eventType)
|
| - {
|
| - }
|
| - else
|
| - {
|
| - updateUI = false;
|
| - }
|
| -
|
| - if(true == updateUI)
|
| - {
|
| - obj->ParentWindowResized(windowRef);
|
| - obj->UpdateClipping();
|
| - obj->RenderOffScreenBuffers();
|
| - }
|
| -
|
| - return noErr;
|
| -}
|
| -
|
| -#pragma mark VideoRenderAGL HIViewRef constructor
|
| -
|
| -VideoRenderAGL::VideoRenderAGL(HIViewRef windowRef, bool fullscreen, int iId) :
|
| -_hiviewRef( windowRef),
|
| -_windowRef( 0),
|
| -_fullScreen( fullscreen),
|
| -_id( iId),
|
| -_renderCritSec(*CriticalSectionWrapper::CreateCriticalSection()),
|
| -_screenUpdateEvent( 0),
|
| -_isHIViewRef( false),
|
| -_aglContext( 0),
|
| -_windowWidth( 0),
|
| -_windowHeight( 0),
|
| -_lastWindowWidth( -1),
|
| -_lastWindowHeight( -1),
|
| -_lastHiViewWidth( -1),
|
| -_lastHiViewHeight( -1),
|
| -_currentParentWindowHeight( 0),
|
| -_currentParentWindowWidth( 0),
|
| -_currentParentWindowBounds( ),
|
| -_windowHasResized( false),
|
| -_lastParentWindowBounds( ),
|
| -_currentHIViewBounds( ),
|
| -_lastHIViewBounds( ),
|
| -_windowRect( ),
|
| -_aglChannels( ),
|
| -_zOrderToChannel( ),
|
| -_hiviewEventHandlerRef( NULL),
|
| -_windowEventHandlerRef( NULL),
|
| -_currentViewBounds( ),
|
| -_lastViewBounds( ),
|
| -_renderingIsPaused( false),
|
| -{
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Constructor", __FUNCTION__, __LINE__);
|
| - // _renderCritSec = CriticalSectionWrapper::CreateCriticalSection();
|
| -
|
| - _screenUpdateThread.reset(new rtc::PlatformThread(
|
| - ScreenUpdateThreadProc, this, "ScreenUpdateThread"));
|
| - _screenUpdateEvent = EventWrapper::Create();
|
| -
|
| - GetWindowRect(_windowRect);
|
| -
|
| - _lastViewBounds.origin.x = 0;
|
| - _lastViewBounds.origin.y = 0;
|
| - _lastViewBounds.size.width = 0;
|
| - _lastViewBounds.size.height = 0;
|
| -
|
| -#ifdef NEW_HIVIEW_PARENT_EVENT_HANDLER
|
| - // This gets the parent window of the HIViewRef that's passed in and installs a WindowRef event handler on it
|
| - // The event handler looks for window resize events and adjusts the offset of the controls.
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Installing Eventhandler for hiviewRef's parent window", __FUNCTION__, __LINE__);
|
| -
|
| -
|
| - static const EventTypeSpec windowEventTypes[] =
|
| - {
|
| - kEventClassWindow, kEventWindowBoundsChanged,
|
| - kEventClassWindow, kEventWindowBoundsChanging,
|
| - kEventClassWindow, kEventWindowZoomed,
|
| - kEventClassWindow, kEventWindowExpanded,
|
| - kEventClassWindow, kEventWindowClickResizeRgn,
|
| - kEventClassWindow, kEventWindowClickDragRgn
|
| - };
|
| -
|
| - WindowRef parentWindow = HIViewGetWindow(windowRef);
|
| -
|
| - InstallWindowEventHandler (parentWindow,
|
| - NewEventHandlerUPP (sHandleWindowResized),
|
| - GetEventTypeCount(windowEventTypes),
|
| - windowEventTypes,
|
| - (void *) this, // this is an arbitrary parameter that will be passed on to your event handler when it is called later
|
| - &_windowEventHandlerRef);
|
| -
|
| -#endif
|
| -
|
| -#ifdef NEW_HIVIEW_EVENT_HANDLER
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Installing Eventhandler for hiviewRef", __FUNCTION__, __LINE__);
|
| -
|
| - static const EventTypeSpec hiviewEventTypes[] =
|
| - {
|
| - kEventClassControl, kEventControlBoundsChanged,
|
| - kEventClassControl, kEventControlDraw
|
| - // kEventControlDragLeave
|
| - // kEventControlDragReceive
|
| - // kEventControlGetFocusPart
|
| - // kEventControlApplyBackground
|
| - // kEventControlDraw
|
| - // kEventControlHit
|
| -
|
| - };
|
| -
|
| - HIViewInstallEventHandler(_hiviewRef,
|
| - NewEventHandlerUPP(sHandleHiViewResized),
|
| - GetEventTypeCount(hiviewEventTypes),
|
| - hiviewEventTypes,
|
| - (void *) this,
|
| - &_hiviewEventHandlerRef);
|
| -
|
| -#endif
|
| -}
|
| -
|
| -// this is a static function. It has been registered (in constructor) to be called on various window redrawing or resizing.
|
| -// Since it is a static method, I have passed in "this" as the userData (one and only allowed) parameter, then calling member methods on it.
|
| -#pragma mark HIViewRef Event Handler
|
| -pascal OSStatus VideoRenderAGL::sHandleHiViewResized (EventHandlerCallRef nextHandler, EventRef theEvent, void* userData)
|
| -{
|
| - //static int callbackCounter = 1;
|
| - HIViewRef hiviewRef = NULL;
|
| -
|
| - // see https://dcs.sourcerepo.com/dcs/tox_view/trunk/tox/libraries/i686-win32/include/quicktime/CarbonEvents.h for a list of codes
|
| - int eventType = GetEventKind(theEvent);
|
| - OSStatus status = noErr;
|
| - status = GetEventParameter (theEvent,
|
| - kEventParamDirectObject,
|
| - typeControlRef,
|
| - NULL,
|
| - sizeof (ControlRef),
|
| - NULL,
|
| - &hiviewRef);
|
| -
|
| - VideoRenderAGL* obj = (VideoRenderAGL*)(userData);
|
| - WindowRef parentWindow = HIViewGetWindow(hiviewRef);
|
| - bool updateUI = true;
|
| -
|
| - if(kEventControlBoundsChanged == eventType)
|
| - {
|
| - }
|
| - else if(kEventControlDraw == eventType)
|
| - {
|
| - }
|
| - else
|
| - {
|
| - updateUI = false;
|
| - }
|
| -
|
| - if(true == updateUI)
|
| - {
|
| - obj->ParentWindowResized(parentWindow);
|
| - obj->UpdateClipping();
|
| - obj->RenderOffScreenBuffers();
|
| - }
|
| -
|
| - return status;
|
| -}
|
| -
|
| -VideoRenderAGL::~VideoRenderAGL()
|
| -{
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Destructor", __FUNCTION__, __LINE__);
|
| -
|
| -
|
| -#ifdef USE_EVENT_HANDLERS
|
| - // remove event handlers
|
| - OSStatus status;
|
| - if(_isHIViewRef)
|
| - {
|
| - status = RemoveEventHandler(_hiviewEventHandlerRef);
|
| - }
|
| - else
|
| - {
|
| - status = RemoveEventHandler(_windowEventHandlerRef);
|
| - }
|
| - if(noErr != status)
|
| - {
|
| - if(_isHIViewRef)
|
| - {
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Failed to remove hiview event handler: %d", __FUNCTION__, __LINE__, (int)_hiviewEventHandlerRef);
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Failed to remove window event handler %d", __FUNCTION__, __LINE__, (int)_windowEventHandlerRef);
|
| - }
|
| - }
|
| -
|
| -#endif
|
| -
|
| - OSStatus status;
|
| -#ifdef NEW_HIVIEW_PARENT_EVENT_HANDLER
|
| - if(_windowEventHandlerRef)
|
| - {
|
| - status = RemoveEventHandler(_windowEventHandlerRef);
|
| - if(status != noErr)
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d failed to remove window event handler %d", __FUNCTION__, __LINE__, (int)_windowEventHandlerRef);
|
| - }
|
| - }
|
| -#endif
|
| -
|
| -#ifdef NEW_HIVIEW_EVENT_HANDLER
|
| - if(_hiviewEventHandlerRef)
|
| - {
|
| - status = RemoveEventHandler(_hiviewEventHandlerRef);
|
| - if(status != noErr)
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Failed to remove hiview event handler: %d", __FUNCTION__, __LINE__, (int)_hiviewEventHandlerRef);
|
| - }
|
| - }
|
| -#endif
|
| -
|
| - // Signal event to exit thread, then delete it
|
| - rtc::PlatformThread* tmpPtr = _screenUpdateThread.release();
|
| -
|
| - if (tmpPtr)
|
| - {
|
| - _screenUpdateEvent->Set();
|
| - _screenUpdateEvent->StopTimer();
|
| -
|
| - tmpPtr->Stop();
|
| - delete tmpPtr;
|
| - delete _screenUpdateEvent;
|
| - _screenUpdateEvent = NULL;
|
| - }
|
| -
|
| - if (_aglContext != 0)
|
| - {
|
| - aglSetCurrentContext(_aglContext);
|
| - aglDestroyContext(_aglContext);
|
| - _aglContext = 0;
|
| - }
|
| -
|
| - // Delete all channels
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.begin();
|
| - while (it!= _aglChannels.end())
|
| - {
|
| - delete it->second;
|
| - _aglChannels.erase(it);
|
| - it = _aglChannels.begin();
|
| - }
|
| - _aglChannels.clear();
|
| -
|
| - // Clean the zOrder map
|
| - std::multimap<int, int>::iterator zIt = _zOrderToChannel.begin();
|
| - while(zIt != _zOrderToChannel.end())
|
| - {
|
| - _zOrderToChannel.erase(zIt);
|
| - zIt = _zOrderToChannel.begin();
|
| - }
|
| - _zOrderToChannel.clear();
|
| -
|
| - //delete _renderCritSec;
|
| -
|
| -
|
| -}
|
| -
|
| -int VideoRenderAGL::GetOpenGLVersion(int& aglMajor, int& aglMinor)
|
| -{
|
| - aglGetVersion((GLint *) &aglMajor, (GLint *) &aglMinor);
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::Init()
|
| -{
|
| - LockAGLCntx();
|
| -
|
| - // Start rendering thread...
|
| - if (!_screenUpdateThread)
|
| - {
|
| - UnlockAGLCntx();
|
| - //WEBRTC_TRACE(kTraceError, "%s:%d Thread not created", __FUNCTION__, __LINE__);
|
| - return -1;
|
| - }
|
| - _screenUpdateThread->Start();
|
| - _screenUpdateThread->SetPriority(rtc::kRealtimePriority);
|
| -
|
| - // Start the event triggering the render process
|
| - unsigned int monitorFreq = 60;
|
| - _screenUpdateEvent->StartTimer(true, 1000/monitorFreq);
|
| -
|
| - // Create mixing textures
|
| - if (CreateMixingContext() == -1)
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, "%s:%d Could not create a mixing context", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -VideoChannelAGL* VideoRenderAGL::CreateAGLChannel(int channel, int zOrder, float startWidth, float startHeight, float stopWidth, float stopHeight)
|
| -{
|
| -
|
| - LockAGLCntx();
|
| -
|
| - //WEBRTC_TRACE(kTraceInfo, "%s:%d Creating AGL channel: %d", __FUNCTION__, __LINE__, channel);
|
| -
|
| - if (HasChannel(channel))
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, "%s:%d Channel already exists", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();k
|
| - return NULL;
|
| - }
|
| -
|
| - if (_zOrderToChannel.find(zOrder) != _zOrderToChannel.end())
|
| - {
|
| - // There are already one channel using this zOrder
|
| - // TODO: Allow multiple channels with same zOrder
|
| - }
|
| -
|
| - VideoChannelAGL* newAGLChannel = new VideoChannelAGL(_aglContext, _id, this);
|
| -
|
| - if (newAGLChannel->SetStreamSettings(0, startWidth, startHeight, stopWidth, stopHeight) == -1)
|
| - {
|
| - if (newAGLChannel)
|
| - {
|
| - delete newAGLChannel;
|
| - newAGLChannel = NULL;
|
| - }
|
| - //WEBRTC_LOG(kTraceError, "Could not create AGL channel");
|
| - //WEBRTC_TRACE(kTraceError, "%s:%d Could not create AGL channel", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return NULL;
|
| - }
|
| -k
|
| - _aglChannels[channel] = newAGLChannel;
|
| - _zOrderToChannel.insert(std::pair<int, int>(zOrder, channel));
|
| -
|
| - UnlockAGLCntx();
|
| - return newAGLChannel;
|
| -}
|
| -
|
| -int VideoRenderAGL::DeleteAllAGLChannels()
|
| -{
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| -
|
| - //WEBRTC_TRACE(kTraceInfo, "%s:%d Deleting all AGL channels", __FUNCTION__, __LINE__);
|
| - //int i = 0 ;
|
| - std::map<int, VideoChannelAGL*>::iterator it;
|
| - it = _aglChannels.begin();
|
| -
|
| - while (it != _aglChannels.end())
|
| - {
|
| - VideoChannelAGL* channel = it->second;
|
| - if (channel)
|
| - delete channel;
|
| -
|
| - _aglChannels.erase(it);
|
| - it = _aglChannels.begin();
|
| - }
|
| - _aglChannels.clear();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::DeleteAGLChannel(int channel)
|
| -{
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Deleting AGL channel %d", __FUNCTION__, __LINE__, channel);
|
| -
|
| - std::map<int, VideoChannelAGL*>::iterator it;
|
| - it = _aglChannels.find(channel);
|
| - if (it != _aglChannels.end())
|
| - {
|
| - delete it->second;
|
| - _aglChannels.erase(it);
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_TRACE(kTraceWarning, "%s:%d Channel not found", __FUNCTION__, __LINE__);
|
| - return -1;
|
| - }
|
| -
|
| - std::multimap<int, int>::iterator zIt = _zOrderToChannel.begin();
|
| - while( zIt != _zOrderToChannel.end())
|
| - {
|
| - if (zIt->second == channel)
|
| - {
|
| - _zOrderToChannel.erase(zIt);
|
| - break;
|
| - }
|
| - zIt++;// = _zOrderToChannel.begin();
|
| - }
|
| -
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::StopThread()
|
| -{
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| - rtc::PlatformThread* tmpPtr = _screenUpdateThread.release();
|
| -
|
| - if (tmpPtr)
|
| - {
|
| - _screenUpdateEvent->Set();
|
| - _renderCritSec.Leave();
|
| - tmpPtr->Stop();
|
| - delete tmpPtr;
|
| - _renderCritSec.Enter();
|
| - }
|
| -
|
| - delete _screenUpdateEvent;
|
| - _screenUpdateEvent = NULL;
|
| -
|
| - return 0;
|
| -}
|
| -
|
| -bool VideoRenderAGL::IsFullScreen()
|
| -{
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| - return _fullScreen;
|
| -}
|
| -
|
| -bool VideoRenderAGL::HasChannels()
|
| -{
|
| -
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| -
|
| - if (_aglChannels.begin() != _aglChannels.end())
|
| - {
|
| - return true;
|
| - }
|
| -
|
| - return false;
|
| -}
|
| -
|
| -bool VideoRenderAGL::HasChannel(int channel)
|
| -{
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| -
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.find(channel);
|
| - if (it != _aglChannels.end())
|
| - {
|
| - return true;
|
| - }
|
| -
|
| - return false;
|
| -}
|
| -
|
| -int VideoRenderAGL::GetChannels(std::list<int>& channelList)
|
| -{
|
| -
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.begin();
|
| -
|
| - while (it != _aglChannels.end())
|
| - {
|
| - channelList.push_back(it->first);
|
| - it++;
|
| - }
|
| -
|
| - return 0;
|
| -}
|
| -
|
| -VideoChannelAGL* VideoRenderAGL::ConfigureAGLChannel(int channel, int zOrder, float startWidth, float startHeight, float stopWidth, float stopHeight)
|
| -{
|
| -
|
| - CriticalSectionScoped cs(&_renderCritSec);
|
| -
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.find(channel);
|
| -
|
| - if (it != _aglChannels.end())
|
| - {
|
| - VideoChannelAGL* aglChannel = it->second;
|
| - if (aglChannel->SetStreamSettings(0, startWidth, startHeight, stopWidth, stopHeight) == -1)
|
| - {
|
| - return NULL;
|
| - }
|
| -
|
| - std::multimap<int, int>::iterator it = _zOrderToChannel.begin();
|
| - while(it != _zOrderToChannel.end())
|
| - {
|
| - if (it->second == channel)
|
| - {
|
| - if (it->first != zOrder)
|
| - {
|
| - _zOrderToChannel.erase(it);
|
| - _zOrderToChannel.insert(std::pair<int, int>(zOrder, channel));
|
| - }
|
| - break;
|
| - }
|
| - it++;
|
| - }
|
| - return aglChannel;
|
| - }
|
| -
|
| - return NULL;
|
| -}
|
| -
|
| -bool VideoRenderAGL::ScreenUpdateThreadProc(void* obj)
|
| -{
|
| - return static_cast<VideoRenderAGL*>(obj)->ScreenUpdateProcess();
|
| -}
|
| -
|
| -bool VideoRenderAGL::ScreenUpdateProcess()
|
| -{
|
| - _screenUpdateEvent->Wait(100);
|
| -
|
| - LockAGLCntx();
|
| -
|
| - if (!_screenUpdateThread)
|
| - {
|
| - UnlockAGLCntx();
|
| - return false;
|
| - }
|
| -
|
| - if (aglSetCurrentContext(_aglContext) == GL_FALSE)
|
| - {
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| -
|
| - if (GetWindowRect(_windowRect) == -1)
|
| - {
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| -
|
| - if (_windowWidth != (_windowRect.right - _windowRect.left)
|
| - || _windowHeight != (_windowRect.bottom - _windowRect.top))
|
| - {
|
| - // We have a new window size, update the context.
|
| - if (aglUpdateContext(_aglContext) == GL_FALSE)
|
| - {
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| - _windowWidth = _windowRect.right - _windowRect.left;
|
| - _windowHeight = _windowRect.bottom - _windowRect.top;
|
| - }
|
| -
|
| - // this section will poll to see if the window size has changed
|
| - // this is causing problem w/invalid windowRef
|
| - // this code has been modified and exists now in the window event handler
|
| -#ifndef NEW_HIVIEW_PARENT_EVENT_HANDLER
|
| - if (_isHIViewRef)
|
| - {
|
| -
|
| - if(FALSE == HIViewIsValid(_hiviewRef))
|
| - {
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Invalid windowRef", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| - WindowRef window = HIViewGetWindow(_hiviewRef);
|
| -
|
| - if(FALSE == IsValidWindowPtr(window))
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Invalide hiviewRef", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| - if (window == NULL)
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d WindowRef = NULL", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| -
|
| - if(FALSE == MacIsWindowVisible(window))
|
| - {
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d MacIsWindowVisible == FALSE. Returning early", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return true;
|
| - }
|
| -
|
| - HIRect viewBounds; // Placement and size for HIView
|
| - int windowWidth = 0; // Parent window width
|
| - int windowHeight = 0; // Parent window height
|
| -
|
| - // NOTE: Calling GetWindowBounds with kWindowStructureRgn will crash intermittentaly if the OS decides it needs to push it into the back for a moment.
|
| - // To counter this, we get the titlebar height on class construction and then add it to the content region here. Content regions seems not to crash
|
| - Rect contentBounds =
|
| - { 0, 0, 0, 0}; // The bounds for the parent window
|
| -
|
| -#if defined(USE_CONTENT_RGN)
|
| - GetWindowBounds(window, kWindowContentRgn, &contentBounds);
|
| -#elif defined(USE_STRUCT_RGN)
|
| - GetWindowBounds(window, kWindowStructureRgn, &contentBounds);
|
| -#endif
|
| -
|
| - Rect globalBounds =
|
| - { 0, 0, 0, 0}; // The bounds for the parent window
|
| - globalBounds.top = contentBounds.top;
|
| - globalBounds.right = contentBounds.right;
|
| - globalBounds.bottom = contentBounds.bottom;
|
| - globalBounds.left = contentBounds.left;
|
| -
|
| - windowHeight = globalBounds.bottom - globalBounds.top;
|
| - windowWidth = globalBounds.right - globalBounds.left;
|
| -
|
| - // Get the size of the HIViewRef
|
| - HIViewGetBounds(_hiviewRef, &viewBounds);
|
| - HIViewConvertRect(&viewBounds, _hiviewRef, NULL);
|
| -
|
| - // Check if this is the first call..
|
| - if (_lastWindowHeight == -1 &&
|
| - _lastWindowWidth == -1)
|
| - {
|
| - _lastWindowWidth = windowWidth;
|
| - _lastWindowHeight = windowHeight;
|
| -
|
| - _lastViewBounds.origin.x = viewBounds.origin.x;
|
| - _lastViewBounds.origin.y = viewBounds.origin.y;
|
| - _lastViewBounds.size.width = viewBounds.size.width;
|
| - _lastViewBounds.size.height = viewBounds.size.height;
|
| - }
|
| - sfasdfasdf
|
| -
|
| - bool resized = false;
|
| -
|
| - // Check if parent window size has changed
|
| - if (windowHeight != _lastWindowHeight ||
|
| - windowWidth != _lastWindowWidth)
|
| - {
|
| - resized = true;
|
| - }
|
| -
|
| - // Check if the HIView has new size or is moved in the parent window
|
| - if (_lastViewBounds.origin.x != viewBounds.origin.x ||
|
| - _lastViewBounds.origin.y != viewBounds.origin.y ||
|
| - _lastViewBounds.size.width != viewBounds.size.width ||
|
| - _lastViewBounds.size.height != viewBounds.size.height)
|
| - {
|
| - // The HiView is resized or has moved.
|
| - resized = true;
|
| - }
|
| -
|
| - if (resized)
|
| - {
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d Window has resized", __FUNCTION__, __LINE__);
|
| -
|
| - // Calculate offset between the windows
|
| - // {x, y, widht, height}, x,y = lower left corner
|
| - const GLint offs[4] =
|
| - { (int)(0.5f + viewBounds.origin.x),
|
| - (int)(0.5f + windowHeight - (viewBounds.origin.y + viewBounds.size.height)),
|
| - viewBounds.size.width, viewBounds.size.height};
|
| -
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d contentBounds t:%d r:%d b:%d l:%d", __FUNCTION__, __LINE__,
|
| - contentBounds.top, contentBounds.right, contentBounds.bottom, contentBounds.left);
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d windowHeight=%d", __FUNCTION__, __LINE__, windowHeight);
|
| - //WEBRTC_TRACE(kTraceDebug, "%s:%d offs[4] = %d, %d, %d, %d", __FUNCTION__, __LINE__, offs[0], offs[1], offs[2], offs[3]);
|
| -
|
| - aglSetDrawable (_aglContext, GetWindowPort(window));
|
| - aglSetInteger(_aglContext, AGL_BUFFER_RECT, offs);
|
| - aglEnable(_aglContext, AGL_BUFFER_RECT);
|
| -
|
| - // We need to change the viewport too if the HIView size has changed
|
| - glViewport(0.0f, 0.0f, (GLsizei) viewBounds.size.width, (GLsizei) viewBounds.size.height);
|
| -
|
| - }
|
| - _lastWindowWidth = windowWidth;
|
| - _lastWindowHeight = windowHeight;
|
| -
|
| - _lastViewBounds.origin.x = viewBounds.origin.x;
|
| - _lastViewBounds.origin.y = viewBounds.origin.y;
|
| - _lastViewBounds.size.width = viewBounds.size.width;
|
| - _lastViewBounds.size.height = viewBounds.size.height;
|
| -
|
| - }
|
| -#endif
|
| - if (_fullScreen)
|
| - {
|
| - // TODO
|
| - // We use double buffers, must always update
|
| - //RenderOffScreenBuffersToBackBuffer();
|
| - }
|
| - else
|
| - {
|
| - // Check if there are any updated buffers
|
| - bool updated = false;
|
| -
|
| - // TODO: check if window size is updated!
|
| - // TODO Improvement: Walk through the zOrder Map to only render the ones in need of update
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.begin();
|
| - while (it != _aglChannels.end())
|
| - {
|
| -
|
| - VideoChannelAGL* aglChannel = it->second;
|
| - aglChannel->UpdateStretchSize(_windowHeight, _windowWidth);
|
| - aglChannel->IsUpdated(updated);
|
| - if (updated)
|
| - {
|
| - break;
|
| - }
|
| - it++;
|
| - }
|
| -
|
| - if (updated)
|
| - {
|
| - // At least on buffers is updated, we need to repaint the texture
|
| - if (RenderOffScreenBuffers() != -1)
|
| - {
|
| - // MF
|
| - //SwapAndDisplayBuffers();
|
| - }
|
| - else
|
| - {
|
| - // Error updating the mixing texture, don't swap.
|
| - }
|
| - }
|
| - }
|
| -
|
| - UnlockAGLCntx();
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Leaving ScreenUpdateProcess()");
|
| - return true;
|
| -}
|
| -
|
| -void VideoRenderAGL::ParentWindowResized(WindowRef window)
|
| -{
|
| - //WEBRTC_LOG(kTraceDebug, "%s HIViewRef:%d owner window has resized", __FUNCTION__, (int)_hiviewRef);
|
| -
|
| - LockAGLCntx();
|
| -k
|
| - // set flag
|
| - _windowHasResized = false;
|
| -
|
| - if(FALSE == HIViewIsValid(_hiviewRef))
|
| - {
|
| - //WEBRTC_LOG(kTraceDebug, "invalid windowRef");
|
| - UnlockAGLCntx();
|
| - return;
|
| - }
|
| -
|
| - if(FALSE == IsValidWindowPtr(window))
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "invalid windowRef");
|
| - UnlockAGLCntx();
|
| - return;
|
| - }
|
| -
|
| - if (window == NULL)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "windowRef = NULL");
|
| - UnlockAGLCntx();
|
| - return;
|
| - }
|
| -
|
| - if(FALSE == MacIsWindowVisible(window))
|
| - {
|
| - //WEBRTC_LOG(kTraceDebug, "MacIsWindowVisible = FALSE. Returning early.");
|
| - UnlockAGLCntx();
|
| - return;
|
| - }
|
| -
|
| - Rect contentBounds =
|
| - { 0, 0, 0, 0};
|
| -
|
| -#if defined(USE_CONTENT_RGN)
|
| - GetWindowBounds(window, kWindowContentRgn, &contentBounds);
|
| -#elif defined(USE_STRUCT_RGN)
|
| - GetWindowBounds(window, kWindowStructureRgn, &contentBounds);
|
| -#endif
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "%s contentBounds t:%d r:%d b:%d l:%d", __FUNCTION__, contentBounds.top, contentBounds.right, contentBounds.bottom, contentBounds.left);
|
| -
|
| - // update global vars
|
| - _currentParentWindowBounds.top = contentBounds.top;
|
| - _currentParentWindowBounds.left = contentBounds.left;
|
| - _currentParentWindowBounds.bottom = contentBounds.bottom;
|
| - _currentParentWindowBounds.right = contentBounds.right;
|
| -
|
| - _currentParentWindowWidth = _currentParentWindowBounds.right - _currentParentWindowBounds.left;
|
| - _currentParentWindowHeight = _currentParentWindowBounds.bottom - _currentParentWindowBounds.top;
|
| -
|
| - _windowHasResized = true;
|
| -
|
| - // ********* update AGL offsets
|
| - HIRect viewBounds;
|
| - HIViewGetBounds(_hiviewRef, &viewBounds);
|
| - HIViewConvertRect(&viewBounds, _hiviewRef, NULL);
|
| -
|
| - const GLint offs[4] =
|
| - { (int)(0.5f + viewBounds.origin.x),
|
| - (int)(0.5f + _currentParentWindowHeight - (viewBounds.origin.y + viewBounds.size.height)),
|
| - viewBounds.size.width, viewBounds.size.height};
|
| - //WEBRTC_LOG(kTraceDebug, "%s _currentParentWindowHeight=%d", __FUNCTION__, _currentParentWindowHeight);
|
| - //WEBRTC_LOG(kTraceDebug, "%s offs[4] = %d, %d, %d, %d", __FUNCTION__, offs[0], offs[1], offs[2], offs[3]);
|
| -
|
| - aglSetCurrentContext(_aglContext);
|
| - aglSetDrawable (_aglContext, GetWindowPort(window));
|
| - aglSetInteger(_aglContext, AGL_BUFFER_RECT, offs);
|
| - aglEnable(_aglContext, AGL_BUFFER_RECT);
|
| -
|
| - // We need to change the viewport too if the HIView size has changed
|
| - glViewport(0.0f, 0.0f, (GLsizei) viewBounds.size.width, (GLsizei) viewBounds.size.height);
|
| -
|
| - UnlockAGLCntx();
|
| -
|
| - return;
|
| -}
|
| -
|
| -int VideoRenderAGL::CreateMixingContext()
|
| -{
|
| -
|
| - LockAGLCntx();
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Entering CreateMixingContext()");
|
| -
|
| - // Use both AGL_ACCELERATED and AGL_NO_RECOVERY to make sure
|
| - // a hardware renderer is used and not a software renderer.
|
| -
|
| - GLint attributes[] =
|
| - {
|
| - AGL_DOUBLEBUFFER,
|
| - AGL_WINDOW,
|
| - AGL_RGBA,
|
| - AGL_NO_RECOVERY,
|
| - AGL_ACCELERATED,
|
| - AGL_RED_SIZE, 8,
|
| - AGL_GREEN_SIZE, 8,
|
| - AGL_BLUE_SIZE, 8,
|
| - AGL_ALPHA_SIZE, 8,
|
| - AGL_DEPTH_SIZE, 24,
|
| - AGL_NONE,
|
| - };
|
| -
|
| - AGLPixelFormat aglPixelFormat;
|
| -
|
| - // ***** Set up the OpenGL Context *****
|
| -
|
| - // Get a pixel format for the attributes above
|
| - aglPixelFormat = aglChoosePixelFormat(NULL, 0, attributes);
|
| - if (NULL == aglPixelFormat)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not create pixel format");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Create an AGL context
|
| - _aglContext = aglCreateContext(aglPixelFormat, NULL);
|
| - if (_aglContext == NULL)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could no create AGL context");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Release the pixel format memory
|
| - aglDestroyPixelFormat(aglPixelFormat);
|
| -
|
| - // Set the current AGL context for the rest of the settings
|
| - if (aglSetCurrentContext(_aglContext) == false)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set current context: %d", aglGetError());
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - if (_isHIViewRef)
|
| - {
|
| - //---------------------------
|
| - // BEGIN: new test code
|
| -#if 0
|
| - // Don't use this one!
|
| - // There seems to be an OS X bug that can't handle
|
| - // movements and resizing of the parent window
|
| - // and or the HIView
|
| - if (aglSetHIViewRef(_aglContext,_hiviewRef) == false)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set WindowRef: %d", aglGetError());
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -#else
|
| -
|
| - // Get the parent window for this control
|
| - WindowRef window = GetControlOwner(_hiviewRef);
|
| -
|
| - Rect globalBounds =
|
| - { 0,0,0,0}; // The bounds for the parent window
|
| - HIRect viewBounds; // Placemnt in the parent window and size.
|
| - int windowHeight = 0;
|
| -
|
| - // Rect titleBounds = {0,0,0,0};
|
| - // GetWindowBounds(window, kWindowTitleBarRgn, &titleBounds);
|
| - // _titleBarHeight = titleBounds.top - titleBounds.bottom;
|
| - // if(0 == _titleBarHeight)
|
| - // {
|
| - // //WEBRTC_LOG(kTraceError, "Titlebar height = 0");
|
| - // //return -1;
|
| - // }
|
| -
|
| -
|
| - // Get the bounds for the parent window
|
| -#if defined(USE_CONTENT_RGN)
|
| - GetWindowBounds(window, kWindowContentRgn, &globalBounds);
|
| -#elif defined(USE_STRUCT_RGN)
|
| - GetWindowBounds(window, kWindowStructureRgn, &globalBounds);
|
| -#endif
|
| - windowHeight = globalBounds.bottom - globalBounds.top;
|
| -
|
| - // Get the bounds for the HIView
|
| - HIViewGetBounds(_hiviewRef, &viewBounds);
|
| -
|
| - HIViewConvertRect(&viewBounds, _hiviewRef, NULL);
|
| -
|
| - const GLint offs[4] =
|
| - { (int)(0.5f + viewBounds.origin.x),
|
| - (int)(0.5f + windowHeight - (viewBounds.origin.y + viewBounds.size.height)),
|
| - viewBounds.size.width, viewBounds.size.height};
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "%s offs[4] = %d, %d, %d, %d", __FUNCTION__, offs[0], offs[1], offs[2], offs[3]);
|
| -
|
| -
|
| - aglSetDrawable (_aglContext, GetWindowPort(window));
|
| - aglSetInteger(_aglContext, AGL_BUFFER_RECT, offs);
|
| - aglEnable(_aglContext, AGL_BUFFER_RECT);
|
| -
|
| - GLint surfaceOrder = 1; // 1: above window, -1 below.
|
| - //OSStatus status = aglSetInteger(_aglContext, AGL_SURFACE_ORDER, &surfaceOrder);
|
| - aglSetInteger(_aglContext, AGL_SURFACE_ORDER, &surfaceOrder);
|
| -
|
| - glViewport(0.0f, 0.0f, (GLsizei) viewBounds.size.width, (GLsizei) viewBounds.size.height);
|
| -#endif
|
| -
|
| - }
|
| - else
|
| - {
|
| - if(GL_FALSE == aglSetDrawable (_aglContext, GetWindowPort(_windowRef)))
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set WindowRef: %d", aglGetError());
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| - }
|
| -
|
| - _windowWidth = _windowRect.right - _windowRect.left;
|
| - _windowHeight = _windowRect.bottom - _windowRect.top;
|
| -
|
| - // opaque surface
|
| - int surfaceOpacity = 1;
|
| - if (aglSetInteger(_aglContext, AGL_SURFACE_OPACITY, (const GLint *) &surfaceOpacity) == false)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set surface opacity: %d", aglGetError());
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // 1 -> sync to screen rat, slow...
|
| - //int swapInterval = 0; // 0 don't sync with vertical trace
|
| - int swapInterval = 0; // 1 sync with vertical trace
|
| - if (aglSetInteger(_aglContext, AGL_SWAP_INTERVAL, (const GLint *) &swapInterval) == false)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set swap interval: %d", aglGetError());
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Update the rect with the current size
|
| - if (GetWindowRect(_windowRect) == -1)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not get window size");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // Disable not needed functionality to increase performance
|
| - glDisable(GL_DITHER);
|
| - glDisable(GL_ALPHA_TEST);
|
| - glDisable(GL_STENCIL_TEST);
|
| - glDisable(GL_FOG);
|
| - glDisable(GL_TEXTURE_2D);
|
| - glPixelZoom(1.0, 1.0);
|
| -
|
| - glDisable(GL_BLEND);
|
| - glDisable(GL_DEPTH_TEST);
|
| - glDepthMask(GL_FALSE);
|
| - glDisable(GL_CULL_FACE);
|
| -
|
| - glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
|
| - glClear(GL_COLOR_BUFFER_BIT);
|
| -
|
| - GLenum glErr = glGetError();
|
| -
|
| - if (glErr)
|
| - {
|
| - }
|
| -
|
| - UpdateClipping();
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Leaving CreateMixingContext()");
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::RenderOffScreenBuffers()
|
| -{
|
| - LockAGLCntx();
|
| -
|
| - // Get the current window size, it might have changed since last render.
|
| - if (GetWindowRect(_windowRect) == -1)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not get window rect");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - if (aglSetCurrentContext(_aglContext) == false)
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "Could not set current context for rendering");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - // HERE - onl if updated!
|
| - glClear(GL_COLOR_BUFFER_BIT);
|
| -
|
| - // Loop through all channels starting highest zOrder ending with lowest.
|
| - for (std::multimap<int, int>::reverse_iterator rIt = _zOrderToChannel.rbegin();
|
| - rIt != _zOrderToChannel.rend();
|
| - rIt++)
|
| - {
|
| - int channelId = rIt->second;
|
| - std::map<int, VideoChannelAGL*>::iterator it = _aglChannels.find(channelId);
|
| -
|
| - VideoChannelAGL* aglChannel = it->second;
|
| -
|
| - aglChannel->RenderOffScreenBuffer();
|
| - }
|
| -
|
| - SwapAndDisplayBuffers();
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::SwapAndDisplayBuffers()
|
| -{
|
| -
|
| - LockAGLCntx();
|
| - if (_fullScreen)
|
| - {
|
| - // TODO:
|
| - // Swap front and back buffers, rendering taking care of in the same call
|
| - //aglSwapBuffers(_aglContext);
|
| - // Update buffer index to the idx for the next rendering!
|
| - //_textureIdx = (_textureIdx + 1) & 1;
|
| - }
|
| - else
|
| - {
|
| - // Single buffer rendering, only update context.
|
| - glFlush();
|
| - aglSwapBuffers(_aglContext);
|
| - HIViewSetNeedsDisplay(_hiviewRef, true);
|
| - }
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int VideoRenderAGL::GetWindowRect(Rect& rect)
|
| -{
|
| -
|
| - LockAGLCntx();
|
| -
|
| - if (_isHIViewRef)
|
| - {
|
| - if (_hiviewRef)
|
| - {
|
| - HIRect HIViewRect1;
|
| - if(FALSE == HIViewIsValid(_hiviewRef))
|
| - {
|
| - rect.top = 0;
|
| - rect.left = 0;
|
| - rect.right = 0;
|
| - rect.bottom = 0;
|
| - //WEBRTC_LOG(kTraceError,"GetWindowRect() HIViewIsValid() returned false");
|
| - UnlockAGLCntx();
|
| - }
|
| - HIViewGetBounds(_hiviewRef,&HIViewRect1);
|
| - HIRectConvert(&HIViewRect1, 1, NULL, 2, NULL);
|
| - if(HIViewRect1.origin.x < 0)
|
| - {
|
| - rect.top = 0;
|
| - //WEBRTC_LOG(kTraceDebug, "GetWindowRect() rect.top = 0");
|
| - }
|
| - else
|
| - {
|
| - rect.top = HIViewRect1.origin.x;
|
| - }
|
| -
|
| - if(HIViewRect1.origin.y < 0)
|
| - {
|
| - rect.left = 0;
|
| - //WEBRTC_LOG(kTraceDebug, "GetWindowRect() rect.left = 0");
|
| - }
|
| - else
|
| - {
|
| - rect.left = HIViewRect1.origin.y;
|
| - }
|
| -
|
| - if(HIViewRect1.size.width < 0)
|
| - {
|
| - rect.right = 0;
|
| - //WEBRTC_LOG(kTraceDebug, "GetWindowRect() rect.right = 0");
|
| - }
|
| - else
|
| - {
|
| - rect.right = HIViewRect1.size.width;
|
| - }
|
| -
|
| - if(HIViewRect1.size.height < 0)
|
| - {
|
| - rect.bottom = 0;
|
| - //WEBRTC_LOG(kTraceDebug, "GetWindowRect() rect.bottom = 0");
|
| - }
|
| - else
|
| - {
|
| - rect.bottom = HIViewRect1.size.height;
|
| - }
|
| -
|
| - ////WEBRTC_LOG(kTraceDebug,"GetWindowRect() HIViewRef: rect.top = %d, rect.left = %d, rect.right = %d, rect.bottom =%d in GetWindowRect", rect.top,rect.left,rect.right,rect.bottom);
|
| - UnlockAGLCntx();
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "invalid HIViewRef");
|
| - UnlockAGLCntx();
|
| - }
|
| - }
|
| - else
|
| - {
|
| - if (_windowRef)
|
| - {
|
| - GetWindowBounds(_windowRef, kWindowContentRgn, &rect);
|
| - UnlockAGLCntx();
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "No WindowRef");
|
| - UnlockAGLCntx();
|
| - }
|
| - }
|
| -}
|
| -
|
| -int VideoRenderAGL::UpdateClipping()
|
| -{
|
| - //WEBRTC_LOG(kTraceDebug, "Entering UpdateClipping()");
|
| - LockAGLCntx();
|
| -
|
| - if(_isHIViewRef)
|
| - {
|
| - if(FALSE == HIViewIsValid(_hiviewRef))
|
| - {
|
| - //WEBRTC_LOG(kTraceError, "UpdateClipping() _isHIViewRef is invalid. Returning -1");
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - RgnHandle visibleRgn = NewRgn();
|
| - SetEmptyRgn (visibleRgn);
|
| -
|
| - if(-1 == CalculateVisibleRegion((ControlRef)_hiviewRef, visibleRgn, true))
|
| - {
|
| - }
|
| -
|
| - if(GL_FALSE == aglSetCurrentContext(_aglContext))
|
| - {
|
| - GLenum glErr = aglGetError();
|
| - //WEBRTC_LOG(kTraceError, "aglSetCurrentContext returned FALSE with error code %d at line %d", glErr, __LINE__);
|
| - }
|
| -
|
| - if(GL_FALSE == aglEnable(_aglContext, AGL_CLIP_REGION))
|
| - {
|
| - GLenum glErr = aglGetError();
|
| - //WEBRTC_LOG(kTraceError, "aglEnable returned FALSE with error code %d at line %d\n", glErr, __LINE__);
|
| - }
|
| -
|
| - if(GL_FALSE == aglSetInteger(_aglContext, AGL_CLIP_REGION, (const GLint*)visibleRgn))
|
| - {
|
| - GLenum glErr = aglGetError();
|
| - //WEBRTC_LOG(kTraceError, "aglSetInteger returned FALSE with error code %d at line %d\n", glErr, __LINE__);
|
| - }
|
| -
|
| - DisposeRgn(visibleRgn);
|
| - }
|
| - else
|
| - {
|
| - //WEBRTC_LOG(kTraceDebug, "Not using a hiviewref!\n");
|
| - }
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Leaving UpdateClipping()");
|
| - UnlockAGLCntx();
|
| - return true;
|
| -}
|
| -
|
| -int VideoRenderAGL::CalculateVisibleRegion(ControlRef control, RgnHandle &visibleRgn, bool clipChildren)
|
| -{
|
| -
|
| - // LockAGLCntx();
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Entering CalculateVisibleRegion()");
|
| - OSStatus osStatus = 0;
|
| - OSErr osErr = 0;
|
| -
|
| - RgnHandle tempRgn = NewRgn();
|
| - if (IsControlVisible(control))
|
| - {
|
| - RgnHandle childRgn = NewRgn();
|
| - WindowRef window = GetControlOwner(control);
|
| - ControlRef rootControl;
|
| - GetRootControl(window, &rootControl); // 'wvnc'
|
| - ControlRef masterControl;
|
| - osStatus = GetSuperControl(rootControl, &masterControl);
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM GetSuperControl=%d", osStatus);
|
| -
|
| - if (masterControl != NULL)
|
| - {
|
| - CheckValidRegion(visibleRgn);
|
| - // init visibleRgn with region of 'wvnc'
|
| - osStatus = GetControlRegion(rootControl, kControlStructureMetaPart, visibleRgn);
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM GetControlRegion=%d : %d", osStatus, __LINE__);
|
| - //GetSuperControl(rootControl, &rootControl);
|
| - ControlRef tempControl = control, lastControl = 0;
|
| - while (tempControl != masterControl) // current control != master
|
| -
|
| - {
|
| - CheckValidRegion(tempRgn);
|
| -
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM tempControl=%d masterControl=%d", tempControl, masterControl);
|
| - ControlRef subControl;
|
| -
|
| - osStatus = GetControlRegion(tempControl, kControlStructureMetaPart, tempRgn); // intersect the region of the current control with visibleRgn
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM GetControlRegion=%d : %d", osStatus, __LINE__);
|
| - CheckValidRegion(tempRgn);
|
| -
|
| - osErr = HIViewConvertRegion(tempRgn, tempControl, rootControl);
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM HIViewConvertRegion=%d : %d", osErr, __LINE__);
|
| - CheckValidRegion(tempRgn);
|
| -
|
| - SectRgn(tempRgn, visibleRgn, visibleRgn);
|
| - CheckValidRegion(tempRgn);
|
| - CheckValidRegion(visibleRgn);
|
| - if (EmptyRgn(visibleRgn)) // if the region is empty, bail
|
| - break;
|
| -
|
| - if (clipChildren || tempControl != control) // clip children if true, cut out the tempControl if it's not one passed to this function
|
| -
|
| - {
|
| - UInt16 numChildren;
|
| - osStatus = CountSubControls(tempControl, &numChildren); // count the subcontrols
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM CountSubControls=%d : %d", osStatus, __LINE__);
|
| -
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM numChildren=%d", numChildren);
|
| - for (int i = 0; i < numChildren; i++)
|
| - {
|
| - osErr = GetIndexedSubControl(tempControl, numChildren - i, &subControl); // retrieve the subcontrol in order by zorder
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM GetIndexedSubControls=%d : %d", osErr, __LINE__);
|
| - if ( subControl == lastControl ) // break because of zorder
|
| -
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM breaking because of zorder %d", __LINE__);
|
| - break;
|
| - }
|
| -
|
| - if (!IsControlVisible(subControl)) // dont' clip invisible controls
|
| -
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM continue. Control is not visible %d", __LINE__);
|
| - continue;
|
| - }
|
| -
|
| - if(!subControl) continue;
|
| -
|
| - osStatus = GetControlRegion(subControl, kControlStructureMetaPart, tempRgn); //get the region of the current control and union to childrg
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM GetControlRegion=%d %d", osStatus, __LINE__);
|
| - CheckValidRegion(tempRgn);
|
| - if(osStatus != 0)
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM ERROR! osStatus=%d. Continuing. %d", osStatus, __LINE__);
|
| - continue;
|
| - }
|
| - if(!tempRgn)
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM ERROR! !tempRgn %d", osStatus, __LINE__);
|
| - continue;
|
| - }
|
| -
|
| - osStatus = HIViewConvertRegion(tempRgn, subControl, rootControl);
|
| - CheckValidRegion(tempRgn);
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM HIViewConvertRegion=%d %d", osStatus, __LINE__);
|
| - if(osStatus != 0)
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM ERROR! osStatus=%d. Continuing. %d", osStatus, __LINE__);
|
| - continue;
|
| - }
|
| - if(!rootControl)
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM ERROR! !rootControl %d", osStatus, __LINE__);
|
| - continue;
|
| - }
|
| -
|
| - UnionRgn(tempRgn, childRgn, childRgn);
|
| - CheckValidRegion(tempRgn);
|
| - CheckValidRegion(childRgn);
|
| - CheckValidRegion(visibleRgn);
|
| - if(!childRgn)
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM ERROR! !childRgn %d", osStatus, __LINE__);
|
| - continue;
|
| - }
|
| -
|
| - } // next child control
|
| - }
|
| - lastControl = tempControl;
|
| - GetSuperControl(tempControl, &subControl);
|
| - tempControl = subControl;
|
| - }
|
| -
|
| - DiffRgn(visibleRgn, childRgn, visibleRgn);
|
| - CheckValidRegion(visibleRgn);
|
| - CheckValidRegion(childRgn);
|
| - DisposeRgn(childRgn);
|
| - }
|
| - else
|
| - {
|
| - CopyRgn(tempRgn, visibleRgn);
|
| - CheckValidRegion(tempRgn);
|
| - CheckValidRegion(visibleRgn);
|
| - }
|
| - DisposeRgn(tempRgn);
|
| - }
|
| -
|
| - //WEBRTC_LOG(kTraceDebug, "Leaving CalculateVisibleRegion()");
|
| - //_aglCritPtr->Leave();
|
| - return 0;
|
| -}
|
| -
|
| -bool VideoRenderAGL::CheckValidRegion(RgnHandle rHandle)
|
| -{
|
| -
|
| - Handle hndSize = (Handle)rHandle;
|
| - long size = GetHandleSize(hndSize);
|
| - if(0 == size)
|
| - {
|
| -
|
| - OSErr memErr = MemError();
|
| - if(noErr != memErr)
|
| - {
|
| - // //WEBRTC_LOG(kTraceError, "IBM ERROR Could not get size of handle. MemError() returned %d", memErr);
|
| - }
|
| - else
|
| - {
|
| - // //WEBRTC_LOG(kTraceError, "IBM ERROR Could not get size of handle yet MemError() returned noErr");
|
| - }
|
| -
|
| - }
|
| - else
|
| - {
|
| - // //WEBRTC_LOG(kTraceDebug, "IBM handleSize = %d", size);
|
| - }
|
| -
|
| - if(false == IsValidRgnHandle(rHandle))
|
| - {
|
| - // //WEBRTC_LOG(kTraceError, "IBM ERROR Invalid Region found : $%d", rHandle);
|
| - assert(false);
|
| - }
|
| -
|
| - int err = QDError();
|
| - switch(err)
|
| - {
|
| - case 0:
|
| - break;
|
| - case -147:
|
| - //WEBRTC_LOG(kTraceError, "ERROR region too big");
|
| - assert(false);
|
| - break;
|
| -
|
| - case -149:
|
| - //WEBRTC_LOG(kTraceError, "ERROR not enough stack");
|
| - assert(false);
|
| - break;
|
| -
|
| - default:
|
| - //WEBRTC_LOG(kTraceError, "ERROR Unknown QDError %d", err);
|
| - assert(false);
|
| - break;
|
| - }
|
| -
|
| - return true;
|
| -}
|
| -
|
| -int VideoRenderAGL::ChangeWindow(void* newWindowRef)
|
| -{
|
| -
|
| - LockAGLCntx();
|
| -
|
| - UnlockAGLCntx();
|
| - return -1;
|
| -}
|
| -
|
| -int32_t VideoRenderAGL::StartRender()
|
| -{
|
| -
|
| - LockAGLCntx();
|
| - const unsigned int MONITOR_FREQ = 60;
|
| - if(TRUE == _renderingIsPaused)
|
| - {
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Rendering is paused. Restarting now", __FUNCTION__, __LINE__);
|
| -
|
| - // we already have the thread. Most likely StopRender() was called and they were paused
|
| - if(FALSE == _screenUpdateThread->Start())
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, kTraceVideoRenderer, _id, "%s:%d Failed to start screenUpdateThread", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| - _screenUpdateThread->SetPriority(rtc::kRealtimePriority);
|
| - if(FALSE == _screenUpdateEvent->StartTimer(true, 1000/MONITOR_FREQ))
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, kTraceVideoRenderer, _id, "%s:%d Failed to start screenUpdateEvent", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - return 0;
|
| - }
|
| -
|
| - _screenUpdateThread.reset(
|
| - new rtc::PlatformThread(ScreenUpdateThreadProc, this, "ScreenUpdate"));
|
| - _screenUpdateEvent = EventWrapper::Create();
|
| -
|
| - if (!_screenUpdateThread)
|
| - {
|
| - //WEBRTC_TRACE(kTraceError, kTraceVideoRenderer, _id, "%s:%d Failed to start screenUpdateThread", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - _screenUpdateThread->Start();
|
| - _screenUpdateThread->SetPriority(rtc::kRealtimePriority);
|
| - _screenUpdateEvent->StartTimer(true, 1000/MONITOR_FREQ);
|
| -
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Started screenUpdateThread", __FUNCTION__, __LINE__);
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int32_t VideoRenderAGL::StopRender()
|
| -{
|
| - LockAGLCntx();
|
| -
|
| - if(!_screenUpdateThread || !_screenUpdateEvent)
|
| - {
|
| - _renderingIsPaused = TRUE;
|
| - UnlockAGLCntx();
|
| - return 0;
|
| - }
|
| -
|
| - if(FALSE == _screenUpdateThread->Stop() || FALSE == _screenUpdateEvent->StopTimer())
|
| - {
|
| - _renderingIsPaused = FALSE;
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Could not stop either: screenUpdateThread or screenUpdateEvent", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return -1;
|
| - }
|
| -
|
| - _renderingIsPaused = TRUE;
|
| -
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Stopped screenUpdateThread", __FUNCTION__, __LINE__);
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int32_t VideoRenderAGL::DeleteAGLChannel(const uint32_t streamID)
|
| -{
|
| -
|
| - LockAGLCntx();
|
| -
|
| - std::map<int, VideoChannelAGL*>::iterator it;
|
| - it = _aglChannels.begin();
|
| -
|
| - while (it != _aglChannels.end())
|
| - {
|
| - VideoChannelAGL* channel = it->second;
|
| - //WEBRTC_TRACE(kTraceInfo, kTraceVideoRenderer, _id, "%s:%d Deleting channel %d", __FUNCTION__, __LINE__, streamID);
|
| - delete channel;
|
| - it++;
|
| - }
|
| - _aglChannels.clear();
|
| -
|
| - UnlockAGLCntx();
|
| - return 0;
|
| -}
|
| -
|
| -int32_t VideoRenderAGL::GetChannelProperties(const uint16_t streamId,
|
| - uint32_t& zOrder,
|
| - float& left,
|
| - float& top,
|
| - float& right,
|
| - float& bottom)
|
| -{
|
| -
|
| - LockAGLCntx();
|
| - UnlockAGLCntx();
|
| - return -1;
|
| -
|
| -}
|
| -
|
| -void VideoRenderAGL::LockAGLCntx()
|
| -{
|
| - _renderCritSec.Enter();
|
| -}
|
| -void VideoRenderAGL::UnlockAGLCntx()
|
| -{
|
| - _renderCritSec.Leave();
|
| -}
|
| -
|
| -} // namespace webrtc
|
| -
|
| -#endif // CARBON_RENDERING
|
|
|