- cleanup
This commit is contained in:
parent
32e387ed1d
commit
5d26986064
@ -1,369 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
|
||||
<!--
|
||||
BigBlueButton open source conferencing system - http://www.bigbluebutton.org
|
||||
|
||||
Copyright (c) 2010 BigBlueButton Inc. and by respective authors (see below).
|
||||
|
||||
BigBlueButton is free software; you can redistribute it and/or modify it under the
|
||||
terms of the GNU Lesser General Public License as published by the Free Software
|
||||
Foundation; either version 2.1 of the License, or (at your option) any later
|
||||
version.
|
||||
|
||||
BigBlueButton 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 for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with BigBlueButton; if not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
$Id: $
|
||||
-->
|
||||
|
||||
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
|
||||
xmlns:mate="http://mate.asfusion.com/"
|
||||
creationComplete="onCreationComplete()"
|
||||
backgroundColor="white"
|
||||
width="100%" height="100%"
|
||||
layout="absolute">
|
||||
|
||||
<mate:Listener type="{EventConstants.USER_TALKING}" method="handleUserTalkingEvent" />
|
||||
<mate:Listener type="{EventConstants.NEW_ROLE}" method="handleNewRoleEvent" />
|
||||
<mate:Listener type="{CloseAllWindowsEvent.CLOSE_ALL_WINDOWS}" method="closeWindow" />
|
||||
|
||||
<mx:Script>
|
||||
<![CDATA[
|
||||
import flexlib.mdi.events.MDIWindowEvent;
|
||||
import mx.core.UIComponent;
|
||||
import mx.events.ResizeEvent;
|
||||
import org.bigbluebutton.common.Images;
|
||||
import org.bigbluebutton.common.LogUtil;
|
||||
import org.bigbluebutton.common.Role;
|
||||
import org.bigbluebutton.common.events.CloseWindowEvent;
|
||||
import org.bigbluebutton.common.events.LocaleChangeEvent;
|
||||
import org.bigbluebutton.core.EventConstants;
|
||||
import org.bigbluebutton.core.UsersUtil;
|
||||
import org.bigbluebutton.core.events.CoreEvent;
|
||||
import org.bigbluebutton.core.managers.UserManager;
|
||||
import org.bigbluebutton.main.views.MainCanvas;
|
||||
import org.bigbluebutton.modules.videoconf.business.TalkingButtonOverlay;
|
||||
import org.bigbluebutton.modules.videoconf.events.CloseAllWindowsEvent;
|
||||
import org.bigbluebutton.modules.videoconf.events.OpenVideoWindowEvent;
|
||||
import org.bigbluebutton.modules.videoconf.events.StartBroadcastEvent;
|
||||
import org.bigbluebutton.modules.videoconf.events.StopBroadcastEvent;
|
||||
import org.bigbluebutton.modules.videoconf.model.VideoConfOptions;
|
||||
import org.bigbluebutton.util.i18n.ResourceUtil;
|
||||
|
||||
[Bindable] private var defaultWidth:Number = 320;
|
||||
[Bindable] private var defaultHeight:Number = 240;
|
||||
|
||||
private var _video:Video;
|
||||
private var _videoHolder:UIComponent;
|
||||
private var camIndex:int = 0;
|
||||
private var camWidth:Number = 320;
|
||||
private var camHeight:Number = 240;
|
||||
private var _camera:Camera = null;
|
||||
private var quality:Number = 0;
|
||||
private var PADDING_HORIZONTAL:Number = 6;
|
||||
private var PADDING_VERTICAL:Number = 29;
|
||||
private var _minWidth:int = 160 + PADDING_HORIZONTAL;
|
||||
private var _minHeight:int = 120 + PADDING_VERTICAL;
|
||||
private var aspectRatio:Number = 1;
|
||||
|
||||
private var userID:String;
|
||||
|
||||
// Timer to auto-publish webcam. We need this timer to delay
|
||||
// the auto-publishing until after the Viewers's window has loaded
|
||||
// to receive the publishing events. Otherwise, the user joining next
|
||||
// won't be able to view the webcam.
|
||||
private var autoPublishTimer:Timer = null;
|
||||
|
||||
// Timer used to enable the start publishing button, only after get
|
||||
// any activity on the camera. It avoids the problem of publishing
|
||||
// a blank video
|
||||
private var _activationTimer:Timer = null;
|
||||
private var _waitingForActivation:Boolean = false;
|
||||
|
||||
static private var _cameraAccessDenied:Boolean = false;
|
||||
|
||||
[Bindable]
|
||||
public var videoOptions:VideoConfOptions;
|
||||
|
||||
private var windowType:String = "PublishWindowType";
|
||||
|
||||
override public function getWindowType():String {
|
||||
return windowType;
|
||||
}
|
||||
|
||||
private function onCreationComplete():void{
|
||||
_videoHolder = new UIComponent();
|
||||
_videoHolder.width = camWidth;
|
||||
_videoHolder.height = camHeight;
|
||||
this.addChild(_videoHolder);
|
||||
|
||||
this.minWidth = _minWidth;
|
||||
this.minHeight = _minHeight;
|
||||
|
||||
|
||||
this.visible = videoOptions.publishWindowVisible;
|
||||
|
||||
updateCamera();
|
||||
}
|
||||
|
||||
private function autopublishTimerHandler(event:TimerEvent):void {
|
||||
startPublishing();
|
||||
autoPublishTimer.stop();
|
||||
}
|
||||
|
||||
private function handleNewRoleEvent(event:CoreEvent):void {
|
||||
switchRole(event.message.role == Role.PRESENTER)
|
||||
}
|
||||
|
||||
private function handleUserTalkingEvent(event:CoreEvent):void {
|
||||
if (event.message.userID == userID) {
|
||||
if (event.message.talking) {
|
||||
notTalkingEffect.end();
|
||||
talkingEffect.play([_videoHolder]);
|
||||
} else {
|
||||
talkingEffect.end();
|
||||
notTalkingEffect.play([_videoHolder]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private function updateCamera():void {
|
||||
stopCamera();
|
||||
|
||||
if (Camera.names.length == 0) {
|
||||
showWarning('bbb.video.publish.hint.noCamera');
|
||||
return;
|
||||
}
|
||||
|
||||
_camera = Camera.getCamera();
|
||||
if (_camera == null) {
|
||||
showWarning('bbb.video.publish.hint.cantOpenCamera');
|
||||
return;
|
||||
}
|
||||
|
||||
_camera.setMotionLevel(5, 1000);
|
||||
|
||||
if (_camera.muted) {
|
||||
if (_cameraAccessDenied) {
|
||||
onCameraAccessDisallowed();
|
||||
return;
|
||||
} else {
|
||||
showWarning('bbb.video.publish.hint.waitingApproval');
|
||||
}
|
||||
} else {
|
||||
// if the camera isn't muted, that is because the user has
|
||||
// previously allowed the camera capture on the flash privacy box
|
||||
onCameraAccessAllowed();
|
||||
}
|
||||
|
||||
_camera.addEventListener(ActivityEvent.ACTIVITY, onActivityEvent);
|
||||
_camera.addEventListener(StatusEvent.STATUS, onStatusEvent);
|
||||
|
||||
_camera.setKeyFrameInterval(videoOptions.camKeyFrameInterval);
|
||||
_camera.setMode(camWidth, camHeight, videoOptions.camModeFps);
|
||||
_camera.setQuality(videoOptions.camQualityBandwidth, videoOptions.camQualityPicture);
|
||||
|
||||
if (_camera.width != camWidth || _camera.height != camHeight) {
|
||||
trace("Resolution " + camWidth + "x" + camHeight + " is not supported, using " + _camera.width + "x" + _camera.height + " instead");
|
||||
setResolution(_camera.width, _camera.height);
|
||||
}
|
||||
|
||||
_video = new Video;
|
||||
_video.attachCamera(_camera);
|
||||
|
||||
if (aspectRatio > _videoHolder.width / _videoHolder.height) {
|
||||
_video.width = _videoHolder.width;
|
||||
_video.height = _videoHolder.width / aspectRatio;
|
||||
_video.x = 0;
|
||||
_video.y = (_videoHolder.height - _video.height) / 2;
|
||||
} else {
|
||||
_video.width = _videoHolder.height * aspectRatio;
|
||||
_video.height = _videoHolder.height;
|
||||
_video.x = (_videoHolder.width - _video.width) / 2;
|
||||
_video.y = 0;
|
||||
}
|
||||
|
||||
_videoHolder.addChild(_video);
|
||||
|
||||
}
|
||||
|
||||
private function onActivityEvent(e:ActivityEvent):void {
|
||||
if (_waitingForActivation && e.activating) {
|
||||
trace("Cam activity event: waitingForActivation = [" + _waitingForActivation + "] activating = [" + e.activating + "]");
|
||||
_activationTimer.stop();
|
||||
showWarning('bbb.video.publish.hint.videoPreview', false, "0xFFFF00");
|
||||
_waitingForActivation = false;
|
||||
|
||||
trace("Starting auto-publisher timer.");
|
||||
autoPublishTimer = new Timer(3000, 1);
|
||||
autoPublishTimer.addEventListener(TimerEvent.TIMER, autopublishTimerHandler);
|
||||
autoPublishTimer.start();
|
||||
}
|
||||
}
|
||||
|
||||
private function onStatusEvent(e:StatusEvent):void {
|
||||
if (e.code == "Camera.Unmuted") {
|
||||
onCameraAccessAllowed();
|
||||
// this is just to overwrite the message of waiting for approval
|
||||
showWarning('bbb.video.publish.hint.openingCamera');
|
||||
} else if (e.code == "Camera.Muted") {
|
||||
onCameraAccessDisallowed();
|
||||
}
|
||||
}
|
||||
|
||||
private function onCameraAccessAllowed():void {
|
||||
// set timer to ensure that the camera activates. If not, it might be in use by another application
|
||||
_waitingForActivation = true;
|
||||
if (_activationTimer != null) {
|
||||
_activationTimer.stop();
|
||||
}
|
||||
|
||||
_activationTimer = new Timer(10000, 1);
|
||||
_activationTimer.addEventListener(TimerEvent.TIMER, activationTimeout);
|
||||
_activationTimer.start();
|
||||
}
|
||||
|
||||
private function onCameraAccessDisallowed():void {
|
||||
showWarning('bbb.video.publish.hint.cameraDenied');
|
||||
_cameraAccessDenied = true;
|
||||
}
|
||||
|
||||
private function activationTimeout(e:TimerEvent):void {
|
||||
showWarning('bbb.video.publish.hint.cameraIsBeingUsed');
|
||||
// it will try to reopen the camera after the timeout
|
||||
updateCamera();
|
||||
}
|
||||
|
||||
private function startPublishing():void{
|
||||
if (_camera == null) return;
|
||||
|
||||
if (autoPublishTimer != null) {
|
||||
autoPublishTimer.stop();
|
||||
}
|
||||
|
||||
showWarning('bbb.video.publish.hint.publishing', true, "0xFFFF00");
|
||||
|
||||
defaultWidth = originalWidth;
|
||||
defaultHeight = originalHeight;
|
||||
|
||||
var e:StartBroadcastEvent = new StartBroadcastEvent();
|
||||
e.stream = this.streamName;
|
||||
e.camera = _camera;
|
||||
dispatchEvent(e);
|
||||
|
||||
this.resizable = true;
|
||||
onResize();
|
||||
|
||||
addEventListener(MDIWindowEvent.RESIZE_START, onResizeStart);
|
||||
addEventListener(MDIWindowEvent.RESIZE_END, onResizeEnd);
|
||||
addEventListener(MouseEvent.MOUSE_OVER, showButtons);
|
||||
addEventListener(MouseEvent.MOUSE_OUT, hideButtons);
|
||||
addEventListener(MouseEvent.DOUBLE_CLICK, onDoubleClick);
|
||||
|
||||
// Store the userid for the publisher. This allows us to control
|
||||
// the user's status from the video window
|
||||
userID = UsersUtil.getMyUserID();
|
||||
|
||||
createButtons();
|
||||
addControlButtons();
|
||||
|
||||
}
|
||||
|
||||
private var _isClosing:Boolean = false;
|
||||
|
||||
override public function close(event:MouseEvent=null):void{
|
||||
trace("PublishWindow::close");
|
||||
if (!_isClosing) {
|
||||
_isClosing = true;
|
||||
stopPublishing();
|
||||
}
|
||||
}
|
||||
|
||||
private function stopCamera():void {
|
||||
_camera = null;
|
||||
if (_video != null) {
|
||||
_videoHolder.removeChild(_video);
|
||||
_video.attachCamera(null);
|
||||
_video.clear();
|
||||
_video = null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private function stopPublishing():void{
|
||||
trace("PublishWindow::stopPublishing");
|
||||
stopCamera();
|
||||
var e:StopBroadcastEvent = new StopBroadcastEvent()
|
||||
e.stream = streamName;
|
||||
dispatchEvent(e);
|
||||
}
|
||||
|
||||
|
||||
public function setResolution(width:int, height:int):void {
|
||||
camWidth = originalWidth = width;
|
||||
camHeight = originalHeight = height;
|
||||
setAspectRatio(camWidth, camHeight);
|
||||
|
||||
/**
|
||||
* Add timestamp to create a unique stream name. This way we can record
|
||||
* stream without overwriting previously recorded streams.
|
||||
*/
|
||||
var curTime:Number = new Date().getTime();
|
||||
var uid:String = UserManager.getInstance().getConference().getMyUserId();
|
||||
var res:String = camWidth + "x" + camHeight;
|
||||
this.streamName = res.concat("-" + uid) + "-" + curTime;
|
||||
}
|
||||
|
||||
private function isPresenter():Boolean{
|
||||
if (UsersUtil.amIModerator() || UsersUtil.amIPresenter()) return true;
|
||||
else return false;
|
||||
}
|
||||
|
||||
private function closeWindow(e:CloseAllWindowsEvent):void{
|
||||
trace("PublishWindow::closeWindow");
|
||||
stopCamera();
|
||||
}
|
||||
|
||||
private var hideWarningTimer:Timer = null;
|
||||
|
||||
private function showWarning(resourceName:String, autoHide:Boolean=false, color:String="0xFF0000"):void {
|
||||
const text:String = ResourceUtil.getInstance().getString(resourceName);
|
||||
|
||||
if (hideWarningTimer != null)
|
||||
hideWarningTimer.stop();
|
||||
if (autoHide) {
|
||||
hideWarningTimer = new Timer(3000, 1);
|
||||
hideWarningTimer.addEventListener(TimerEvent.TIMER, hideWarning);
|
||||
hideWarningTimer.start();
|
||||
}
|
||||
|
||||
// bring the label to front
|
||||
setChildIndex(lblWarning, getChildren().length - 1);
|
||||
lblWarning.text = text;
|
||||
lblWarning.setStyle("color", color);
|
||||
lblWarning.visible = true;
|
||||
LogUtil.debug("Showing warning: " + text);
|
||||
}
|
||||
|
||||
private function hideWarning(e:TimerEvent):void {
|
||||
lblWarning.visible = false;
|
||||
}
|
||||
|
||||
]]>
|
||||
</mx:Script>
|
||||
|
||||
<mx:Glow id="talkingEffect" duration="500" alphaFrom="1.0" alphaTo="0.3"
|
||||
blurXFrom="0.0" blurXTo="30.0" blurYFrom="0.0" blurYTo="30.0" color="0xFF0000"/>
|
||||
<mx:Glow id="notTalkingEffect" duration="500" alphaFrom="0.3" alphaTo="1.0"
|
||||
blurXFrom="30.0" blurXTo="0.0" blurYFrom="30.0" blurYTo="0.0" color="0xFF0000"/>
|
||||
|
||||
<mx:Fade id="dissolveOut" duration="1000" alphaFrom="1.0" alphaTo="0.0"/>
|
||||
<mx:Fade id="dissolveIn" duration="1000" alphaFrom="0.0" alphaTo="1.0"/>
|
||||
<mx:Text id="lblWarning" width="100%" textAlign="right" fontSize="14" fontWeight="bold" y="{this.height - lblWarning.height - 30}"
|
||||
visible="false" selectable="false" hideEffect="{dissolveOut}" showEffect="{dissolveIn}"/>
|
||||
<mx:Label text="Foo!!!"/>
|
||||
</mx:Application>
|
Loading…
Reference in New Issue
Block a user