Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
# Daniel Nachbaur <daniel.nachbaur@epfl.ch>

cmake_minimum_required(VERSION 3.1 FATAL_ERROR)
project(Deflect VERSION 0.11.0)
project(Deflect VERSION 0.11.1)
set(Deflect_VERSION_ABI 4)

list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/CMake
Expand Down
15 changes: 6 additions & 9 deletions apps/DesktopStreamer/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ set(DESKTOPSTREAMER_SOURCES
set(DESKTOPSTREAMER_LINK_LIBRARIES
Deflect
Qt5::Core
Qt5::Network
Qt5::Widgets
)

Expand All @@ -36,12 +37,11 @@ if(APPLE)
list(APPEND DESKTOPSTREAMER_SOURCES AppNapSuspender.mm)
list(APPEND DESKTOPSTREAMER_LINK_LIBRARIES "-framework Foundation")
if(TARGET Qt5::MacExtras)
option(DESKTOPSTREAMER_ENABLE_MULTIWINDOW "Enable support for streaming multiple windows" OFF)
if(DESKTOPSTREAMER_ENABLE_MULTIWINDOW)
list(APPEND DESKTOPSTREAMER_SOURCES DesktopWindowsModel.mm)
list(APPEND DESKTOPSTREAMER_LINK_LIBRARIES
Qt5::MacExtras "-framework AppKit")
endif()
list(APPEND DESKTOPSTREAMER_HEADERS DesktopWindowsModel.h)
list(APPEND DESKTOPSTREAMER_SOURCES DesktopWindowsModel.mm)
list(APPEND DESKTOPSTREAMER_LINK_LIBRARIES
Qt5::MacExtras "-framework AppKit"
)
endif()
if(OSX_VERSION VERSION_LESS 10.9)
list(APPEND DESKTOPSTREAMER_LINK_LIBRARIES "-framework ApplicationServices")
Expand All @@ -55,9 +55,6 @@ endif()
common_application(${DESKTOPSTREAMER_APP_NAME} GUI)

if(APPLE)
if(TARGET Qt5::MacExtras AND DESKTOPSTREAMER_ENABLE_MULTIWINDOW)
target_compile_definitions(${DESKTOPSTREAMER_APP_NAME} PRIVATE DESKTOPSTREAMER_ENABLE_MULTIWINDOW)
endif()
# create a zip for Puppet deployment
install(CODE "execute_process(COMMAND zip -r
${DESKTOPSTREAMER_APP_NAME}-${PROJECT_VERSION}.zip ${DESKTOPSTREAMER_APP_NAME}.app
Expand Down
178 changes: 119 additions & 59 deletions apps/DesktopStreamer/MainWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@

#include <deflect/version.h>

#include <QHostInfo>
#include <QMessageBox>
#include <QPainter>
#include <QScreen>
Expand All @@ -56,37 +57,38 @@ typedef __int32 int32_t;
# include <windows.h>
#else
# include <stdint.h>
# include <unistd.h>
#endif

#ifdef DESKTOPSTREAMER_ENABLE_MULTIWINDOW
#ifdef DEFLECT_USE_QT5MACEXTRAS
# include "DesktopWindowsModel.h"
#endif

#define SHARE_DESKTOP_UPDATE_DELAY 0
#define FAILURE_UPDATE_DELAY 100
#define FRAME_RATE_DAMPING 0.1f // influence of new value between 0-1

namespace
{
const std::vector< std::pair< QString, QString > > defaultHosts = {
{ "DisplayWall Ground floor", "bbpav02.epfl.ch" },
{ "DisplayWall 3rd floor", "bbpav04.epfl.ch" },
{ "DisplayWall 5th floor", "bbpav05.epfl.ch" },
{ "DisplayWall 6th floor", "bbpav06.epfl.ch" }
};

const QString streamButtonDefaultText = "Stream";
const QString streamSelected = "Stream selected item(s)";
}

MainWindow::MainWindow()
: _streamID( 0 )
, _averageUpdate( 0 )
{
setupUi( this );

#ifndef __APPLE__
// Event injection support is currently limited to OSX
_remoteControlLabel->setVisible( false );
_remoteControlCheckBox->setVisible( false );
#endif
for( const auto& entry : defaultHosts )
_hostComboBox->addItem( entry.first, entry.second );

_hostComboBox->setCurrentIndex( -1 ); // no default host selected initially

connect( _hostComboBox, &QComboBox::currentTextChanged,
[&]( const QString& text )
Expand All @@ -95,47 +97,42 @@ MainWindow::MainWindow()
_listView->setEnabled( !text.isEmpty( ));
});

for( const auto& entry : defaultHosts )
_hostComboBox->addItem( entry.first, entry.second );

// no default host selected initially
_hostComboBox->setCurrentIndex( -1 );
_streamIdLineEdit->setText( QHostInfo::localHostName( ));

char hostname[256] = { 0 };
gethostname( hostname, 256 );
_streamIdLineEdit->setText( QString( "%1" ).arg( hostname ));

#ifdef DESKTOPSTREAMER_ENABLE_MULTIWINDOW
_listView->setModel( new DesktopWindowsModel );

// select 'Desktop' item as initial default stream item
_listView->setCurrentIndex( _listView->model()->index( 0, 0 ));
_streamButton->setText( streamSelected );

const int itemsHorizontal = std::min( 3.f,
std::ceil( std::sqrt( float(_listView->model()->rowCount( )))));
const int itemsVertical = std::min( 3.f,
std::ceil(float( _listView->model()->rowCount( )) / itemsHorizontal ));

// 230 (itemSize + spacing), frameWidth for decorations
resize( QSize( 230 * itemsHorizontal + 2 * _listView->frameWidth(),
230 * itemsVertical + 2 * _listView->frameWidth() + 50 ));
#else
_listView->setHidden( true );
adjustSize();
#endif
connect( _streamButton, &QPushButton::clicked,
this, &MainWindow::_update );
connect( _streamButton, &QPushButton::clicked,
_actionMultiWindowMode, &QAction::setDisabled );

connect( _remoteControlCheckBox, &QCheckBox::clicked,
this, &MainWindow::_onStreamEventsBoxClicked );

connect( _streamButton, &QPushButton::clicked,
this, &MainWindow::_update );
connect( _actionAdvancedSettings, &QAction::triggered,
this, &MainWindow::_showAdvancedSettings );

connect( _actionMultiWindowMode, &QAction::triggered,
[this]( const bool checked )
{
if( checked )
_showMultiWindowMode();
else
_showSingleWindowMode();
});

connect( _actionAbout, &QAction::triggered,
this, &MainWindow::_openAboutWidget );

// Update timer
connect( &_updateTimer, &QTimer::timeout, this, &MainWindow::_update );

#ifndef __APPLE__
// Event injection support is currently limited to OSX
_showRemoteControl( false );
#endif
#ifndef DEFLECT_USE_QT5MACEXTRAS
_actionMultiWindowMode->setVisible( false );
#endif
_showAdvancedSettings( false );
_showSingleWindowMode();
}

MainWindow::~MainWindow() {}
Expand Down Expand Up @@ -193,11 +190,69 @@ void MainWindow::_update()
_stopStreaming();
}

void MainWindow::_showRemoteControl( const bool visible )
{
_remoteControlLabel->setVisible( visible );
_remoteControlCheckBox->setVisible( visible );
}

void MainWindow::_showMultiWindowMode()
{
#ifdef DEFLECT_USE_QT5MACEXTRAS
if( !_listView->model( ))
{
auto model = new DesktopWindowsModel();
model->setParent( _listView );
_listView->setModel( model );
}

_listView->setVisible( true );

// select 'Desktop' item as initial default stream item
_listView->setCurrentIndex( _listView->model()->index( 0, 0 ));
_streamButton->setText( streamSelected );

const int itemsHorizontal = std::min( 3.f,
std::ceil( std::sqrt( float(_listView->model()->rowCount( )))));
const int itemsVertical = std::min( 3.f,
std::ceil(float( _listView->model()->rowCount( )) / itemsHorizontal ));

layout()->setSizeConstraint( QLayout::SetDefaultConstraint );
setFixedSize( QWIDGETSIZE_MAX, QWIDGETSIZE_MAX );
// 230 (itemSize + spacing), frameWidth for decorations
resize( QSize( 230 * itemsHorizontal + 2 * _listView->frameWidth(),
230 * itemsVertical + 2 * _listView->frameWidth() + 50 ));
#endif
}

void MainWindow::_showSingleWindowMode()
{
_listView->setHidden( true );
_streamButton->setText( streamButtonDefaultText );

layout()->setSizeConstraint( QLayout::SetFixedSize );
}

void MainWindow::_showAdvancedSettings( const bool visible )
{
_maxFrameRateSpinBox->setVisible( visible );
_maxFrameRateLabel->setVisible( visible );

_streamIdLineEdit->setVisible( visible );
_streamIdLabel->setVisible( visible );
}

void MainWindow::_updateStreams()
{
const std::string& host = _getStreamHost();
if( _actionMultiWindowMode->isChecked( ))
_updateMultipleStreams();
else
_updateSingleStream();
}

#ifdef DESKTOPSTREAMER_ENABLE_MULTIWINDOW
void MainWindow::_updateMultipleStreams()
{
#ifdef DEFLECT_USE_QT5MACEXTRAS
const QModelIndexList windowIndices =
_listView->selectionModel()->selectedIndexes();

Expand All @@ -219,12 +274,12 @@ void MainWindow::_updateStreams()
const int pid = index.isValid() ?
_listView->model()->data( index,
DesktopWindowsModel::ROLE_PID).toInt(): 0;
const std::string host = _getStreamHost();
StreamPtr stream( new Stream( *this, index, streamId, host, pid ));

if( !stream->isConnected( ))
{
_statusbar->showMessage( QString( "Could not connect to host %1" ).
arg( host.c_str( )));
_showConnectionErrorStatus();
continue;
}

Expand All @@ -240,9 +295,11 @@ void MainWindow::_updateStreams()
_streamButton->setChecked( true );
_startStreaming();
};
#endif
}

#else // No window list: Stream button toggles

void MainWindow::_updateSingleStream()
{
if( !_streamButton->isChecked( ))
{
_stopStreaming();
Expand All @@ -254,7 +311,7 @@ void MainWindow::_updateStreams()
const QPersistentModelIndex index; // default == use desktop
StreamPtr stream( new Stream( *this, index,
_streamIdLineEdit->text().toStdString(),
host ));
_getStreamHost( )));
if( stream->isConnected( ))
{
if( _remoteControlCheckBox->isChecked( ))
Expand All @@ -263,9 +320,14 @@ void MainWindow::_updateStreams()
_startStreaming();
}
else
_statusbar->showMessage( "Could not connect to host" );
_showConnectionErrorStatus();
}
#endif
}

void MainWindow::_showConnectionErrorStatus()
{
_statusbar->showMessage( QString( "Cannot connect to host: '%1'" ).
arg( _getStreamHost().c_str( )));
}

void MainWindow::_processStreamEvents()
Expand Down Expand Up @@ -306,22 +368,20 @@ void MainWindow::_shareDesktopUpdate()
}
}

#ifdef DESKTOPSTREAMER_ENABLE_MULTIWINDOW
void MainWindow::_deselect( ConstStreamPtr stream )
{
const QPersistentModelIndex& index = stream->getIndex();
if( index.isValid( ))
if( _actionMultiWindowMode->isChecked( ))
{
QItemSelectionModel* model = _listView->selectionModel();
model->select( index, QItemSelectionModel::Deselect );
const QPersistentModelIndex& index = stream->getIndex();
if( index.isValid( ))
{
QItemSelectionModel* model = _listView->selectionModel();
model->select( index, QItemSelectionModel::Deselect );
}
}
else
_streamButton->setChecked( false );
}
#else
void MainWindow::_deselect( ConstStreamPtr )
{
_streamButton->setChecked( false );
}
#endif

void MainWindow::_regulateFrameRate()
{
Expand Down
14 changes: 12 additions & 2 deletions apps/DesktopStreamer/MainWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,8 @@
/* or implied, of The University of Texas at Austin. */
/*********************************************************************/

#ifndef MAIN_WINDOW_H
#define MAIN_WINDOW_H
#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <apps/DesktopStreamer/ui_MainWindow.h>

Expand Down Expand Up @@ -92,9 +92,19 @@ private slots:
AppNapSuspender _napSuspender;
#endif

void _showMultiWindowMode();
void _showSingleWindowMode();

void _showRemoteControl( bool visible );
void _showAdvancedSettings( bool visible );

void _startStreaming();
void _stopStreaming();
void _updateStreams();
void _updateMultipleStreams();
void _updateSingleStream();
void _showConnectionErrorStatus();

void _deselect( ConstStreamPtr stream );
void _processStreamEvents();
void _shareDesktopUpdate();
Expand Down
Loading