Skip to content

Commit

Permalink
Allow sharing screen with sound on Windows.
Browse files Browse the repository at this point in the history
  • Loading branch information
john-preston committed Jul 13, 2021
1 parent 402729d commit db81638
Show file tree
Hide file tree
Showing 13 changed files with 129 additions and 27 deletions.
1 change: 1 addition & 0 deletions Telegram/Resources/langs/lang.strings
Original file line number Diff line number Diff line change
Expand Up @@ -2021,6 +2021,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_group_call_screen_share_start" = "Share Screen";
"lng_group_call_screen_share_stop" = "Stop Sharing";
"lng_group_call_screen_title" = "Screen {index}";
"lng_group_call_screen_share_audio" = "Share Audio";
"lng_group_call_unmute_small" = "Unmute";
"lng_group_call_more" = "More";
"lng_group_call_unmute" = "Unmute";
Expand Down
10 changes: 10 additions & 0 deletions Telegram/SourceFiles/calls/calls.style
Original file line number Diff line number Diff line change
Expand Up @@ -1184,6 +1184,16 @@ desktopCaptureSubmit: RoundButton(desktopCaptureCancel) {
color: shadowFg;
}
}
desktopCaptureWithAudio: Checkbox(defaultCheckbox) {
textFg: groupCallMembersFg;
textFgActive: groupCallMembersFg;
rippleBg: groupCallMembersBgRipple;
rippleBgActive: groupCallMembersBgRipple;
style: semiboldTextStyle;
}
desktopCaptureWithAudioCheck: Check(defaultCheck) {
untoggledFg: groupCallActiveFg;
}

groupCallNarrowSkip: 9px;
groupCallNarrowMembersWidth: 204px;
Expand Down
16 changes: 12 additions & 4 deletions Telegram/SourceFiles/calls/group/calls_group_call.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -613,6 +613,10 @@ QString GroupCall::screenSharingDeviceId() const {
return isSharingScreen() ? _screenDeviceId : QString();
}

bool GroupCall::screenSharingWithAudio() const {
return isSharingScreen() && _screenWithAudio;
}

bool GroupCall::mutedByAdmin() const {
const auto mute = muted();
return mute == MuteState::ForceMuted || mute == MuteState::RaisedHand;
Expand All @@ -635,7 +639,9 @@ void GroupCall::toggleVideo(bool active) {
: Webrtc::VideoState::Inactive;
}

void GroupCall::toggleScreenSharing(std::optional<QString> uniqueId) {
void GroupCall::toggleScreenSharing(
std::optional<QString> uniqueId,
bool withAudio) {
if (!_instance || !_id) {
return;
} else if (!uniqueId) {
Expand All @@ -645,10 +651,14 @@ void GroupCall::toggleScreenSharing(std::optional<QString> uniqueId) {
const auto changed = (_screenDeviceId != *uniqueId);
const auto wasSharing = isSharingScreen();
_screenDeviceId = *uniqueId;
_screenWithAudio = withAudio;
_screenState = Webrtc::VideoState::Active;
if (changed && wasSharing && isSharingScreen()) {
_screenCapture->switchToDevice(uniqueId->toStdString());
}
if (_screenInstance) {
_screenInstance->setIsMuted(!withAudio);
}
}

bool GroupCall::hasVideoWithFrames() const {
Expand Down Expand Up @@ -2281,9 +2291,7 @@ bool GroupCall::tryCreateScreencast() {
_screenInstance = std::make_unique<tgcalls::GroupInstanceCustomImpl>(
std::move(descriptor));

#ifdef Q_OS_WIN
_screenInstance->setIsMuted(false);
#endif // Q_OS_WIN
_screenInstance->setIsMuted(!_screenWithAudio);

return true;
}
Expand Down
6 changes: 5 additions & 1 deletion Telegram/SourceFiles/calls/group/calls_group_call.h
Original file line number Diff line number Diff line change
Expand Up @@ -380,8 +380,11 @@ class GroupCall final : public base::has_weak_ptr {
[[nodiscard]] bool isCameraPaused() const;
[[nodiscard]] const std::string &cameraSharingEndpoint() const;
[[nodiscard]] QString screenSharingDeviceId() const;
[[nodiscard]] bool screenSharingWithAudio() const;
void toggleVideo(bool active);
void toggleScreenSharing(std::optional<QString> uniqueId);
void toggleScreenSharing(
std::optional<QString> uniqueId,
bool withAudio = false);
[[nodiscard]] bool hasVideoWithFrames() const;
[[nodiscard]] rpl::producer<bool> hasVideoWithFramesValue() const;

Expand Down Expand Up @@ -614,6 +617,7 @@ class GroupCall final : public base::has_weak_ptr {
rpl::variable<Webrtc::VideoState> _screenState;
rpl::variable<bool> _isSharingScreen = false;
QString _screenDeviceId;
bool _screenWithAudio = false;

base::flags<SendUpdateType> _pendingSelfUpdates;
bool _requireARGB32 = true;
Expand Down
20 changes: 17 additions & 3 deletions Telegram/SourceFiles/calls/group/calls_group_panel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -260,12 +260,26 @@ QString Panel::chooseSourceActiveDeviceId() {
return _call->screenSharingDeviceId();
}

bool Panel::chooseSourceActiveWithAudio() {
return _call->screenSharingWithAudio();
}

bool Panel::chooseSourceWithAudioSupported() {
#ifdef Q_OS_WIN
return true;
#else // Q_OS_WIN
return false;
#endif // Q_OS_WIN
}

rpl::lifetime &Panel::chooseSourceInstanceLifetime() {
return lifetime();
}

void Panel::chooseSourceAccepted(const QString &deviceId) {
_call->toggleScreenSharing(deviceId);
void Panel::chooseSourceAccepted(
const QString &deviceId,
bool withAudio) {
_call->toggleScreenSharing(deviceId, withAudio);
}

void Panel::chooseSourceStop() {
Expand Down Expand Up @@ -1185,7 +1199,7 @@ void Panel::chooseShareScreenSource() {
if (_call->isSharingScreen()) {
_call->toggleScreenSharing(std::nullopt);
} else {
chooseSourceAccepted(*source);
chooseSourceAccepted(*source, false);
}
} else {
Ui::DesktopCapture::ChooseSource(this);
Expand Down
6 changes: 5 additions & 1 deletion Telegram/SourceFiles/calls/group/calls_group_panel.h
Original file line number Diff line number Diff line change
Expand Up @@ -169,8 +169,12 @@ class Panel final : private Ui::DesktopCapture::ChooseSourceDelegate {

QWidget *chooseSourceParent() override;
QString chooseSourceActiveDeviceId() override;
bool chooseSourceActiveWithAudio() override;
bool chooseSourceWithAudioSupported() override;
rpl::lifetime &chooseSourceInstanceLifetime() override;
void chooseSourceAccepted(const QString &deviceId) override;
void chooseSourceAccepted(
const QString &deviceId,
bool withAudio) override;
void chooseSourceStop() override;

const not_null<GroupCall*> _call;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ For license and copyright information please follow this link:
#include "ui/widgets/scroll_area.h"
#include "ui/widgets/labels.h"
#include "ui/widgets/buttons.h"
#include "ui/widgets/checkbox.h"
#include "ui/effects/ripple_animation.h"
#include "ui/image/image.h"
#include "ui/platform/ui_platform_window_title.h"
Expand Down Expand Up @@ -62,6 +63,8 @@ class Source final {

[[nodiscard]] rpl::producer<> activations() const;
void setActive(bool active);
[[nodiscard]] bool isWindow() const;
[[nodiscard]] QString deviceIdKey() const;
[[nodiscard]] rpl::lifetime &lifetime();

private:
Expand Down Expand Up @@ -94,6 +97,7 @@ class ChooseSourceProcess final {
void setupGeometryWithParent(not_null<QWidget*> parent);
void fillSources();
void setupSourcesGeometry();
void updateButtonsVisibility();
void destroy();

static base::flat_map<
Expand All @@ -107,6 +111,7 @@ class ChooseSourceProcess final {
const not_null<RpWidget*> _bottom;
const not_null<RoundButton*> _submit;
const not_null<RoundButton*> _finish;
const not_null<Checkbox*> _withAudio;

std::vector<std::unique_ptr<Source>> _sources;
Source *_selected = nullptr;
Expand Down Expand Up @@ -166,6 +171,14 @@ rpl::producer<> Source::activations() const {
return _activations.events();
}

bool Source::isWindow() const {
return _source.isWindow();
}

QString Source::deviceIdKey() const {
return QString::fromStdString(_source.deviceIdKey());
}

void Source::setActive(bool active) {
if (_active != active) {
_active = active;
Expand Down Expand Up @@ -255,7 +268,13 @@ ChooseSourceProcess::ChooseSourceProcess(
CreateChild<RoundButton>(
_bottom.get(),
tr::lng_group_call_screen_share_stop(),
st::desktopCaptureFinish)) {
st::desktopCaptureFinish))
, _withAudio(
CreateChild<Checkbox>(
_bottom.get(),
tr::lng_group_call_screen_share_audio(tr::now),
false,
st::desktopCaptureWithAudio)) {
setupPanel();
setupSources();
activate();
Expand Down Expand Up @@ -336,7 +355,9 @@ void ChooseSourceProcess::setupPanel() {
return;
}
const auto weak = MakeWeak(_window.get());
_delegate->chooseSourceAccepted(_selectedId);
_delegate->chooseSourceAccepted(
_selectedId,
!_withAudio->isHidden() && _withAudio->checked());
if (const auto strong = weak.data()) {
strong->close();
}
Expand Down Expand Up @@ -375,6 +396,18 @@ void ChooseSourceProcess::setupPanel() {
bottomSkip);
}, _bottom->lifetime());

_withAudio->widthValue(
) | rpl::start_with_next([=](int width) {
const auto top = (bottomHeight - _withAudio->heightNoMargins()) / 2;
_withAudio->moveToLeft(bottomSkip, top);
}, _withAudio->lifetime());

_withAudio->setChecked(_delegate->chooseSourceActiveWithAudio());
_withAudio->checkedChanges(
) | rpl::start_with_next([=] {
updateButtonsVisibility();
}, _withAudio->lifetime());

const auto sharing = !_delegate->chooseSourceActiveDeviceId().isEmpty();
_finish->setVisible(sharing);
_submit->setVisible(!sharing);
Expand Down Expand Up @@ -420,6 +453,8 @@ void ChooseSourceProcess::fillSources() {
auto screensManager = tgcalls::DesktopCaptureSourceManager(Type::Screen);
auto windowsManager = tgcalls::DesktopCaptureSourceManager(Type::Window);

_withAudio->setVisible(false);

auto screenIndex = 0;
auto windowIndex = 0;
const auto active = _delegate->chooseSourceActiveDeviceId();
Expand All @@ -435,9 +470,13 @@ void ChooseSourceProcess::fillSources() {
const auto id = source.deviceIdKey();
_sources.push_back(std::make_unique<Source>(_inner, source, title));

const auto withAudioSupported = !source.isWindow()
&& _delegate->chooseSourceWithAudioSupported();

const auto raw = _sources.back().get();
if (!active.isEmpty() && active.toStdString() == id) {
_selected = raw;
_withAudio->setVisible(withAudioSupported);
raw->setActive(true);
}
_sources.back()->activations(
Expand All @@ -448,15 +487,8 @@ void ChooseSourceProcess::fillSources() {
_selected->setActive(false);
}
_selected = raw;
_selectedId = QString::fromStdString(id);
if (_selectedId == _delegate->chooseSourceActiveDeviceId()) {
_selectedId = QString();
_finish->setVisible(true);
_submit->setVisible(false);
} else {
_finish->setVisible(false);
_submit->setVisible(true);
}
_withAudio->setVisible(withAudioSupported);
updateButtonsVisibility();
}, raw->lifetime());
};
for (const auto &source : screensManager.sources()) {
Expand All @@ -467,6 +499,27 @@ void ChooseSourceProcess::fillSources() {
}
}

void ChooseSourceProcess::updateButtonsVisibility() {
const auto withAudioSupported = _selected
&& !_selected->isWindow()
&& _delegate->chooseSourceWithAudioSupported();
const auto selectedId = _selected
? _selected->deviceIdKey()
: QString();
if (selectedId == _delegate->chooseSourceActiveDeviceId()
&& (!withAudioSupported
|| (_withAudio->checked()
== _delegate->chooseSourceActiveWithAudio()))) {
_selectedId = QString();
_finish->setVisible(true);
_submit->setVisible(false);
} else {
_selectedId = selectedId;
_finish->setVisible(false);
_submit->setVisible(true);
}
}

void ChooseSourceProcess::setupSourcesGeometry() {
if (_sources.empty()) {
destroy();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,12 @@ class ChooseSourceDelegate {
public:
virtual QWidget *chooseSourceParent() = 0;
virtual QString chooseSourceActiveDeviceId() = 0;
virtual bool chooseSourceActiveWithAudio() = 0;
virtual bool chooseSourceWithAudioSupported() = 0;
virtual rpl::lifetime &chooseSourceInstanceLifetime() = 0;
virtual void chooseSourceAccepted(const QString &deviceId) = 0;
virtual void chooseSourceAccepted(
const QString &deviceId,
bool withAudio) = 0;
virtual void chooseSourceStop() = 0;
};

Expand Down
4 changes: 4 additions & 0 deletions Telegram/cmake/lib_tgcalls.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,13 @@ PRIVATE
Message.h
NetworkManager.cpp
NetworkManager.h
SctpDataChannelProviderInterfaceImpl.cpp
SctpDataChannelProviderInterfaceImpl.h
StaticThreads.cpp
StaticThreads.h
ThreadLocalObject.h
TurnCustomizerImpl.cpp
TurnCustomizerImpl.h
VideoCaptureInterface.cpp
VideoCaptureInterface.h
VideoCaptureInterfaceImpl.cpp
Expand Down
4 changes: 2 additions & 2 deletions docs/building-msvc-x64.md
Original file line number Diff line number Diff line change
Expand Up @@ -110,9 +110,9 @@ Open **x64 Native Tools Command Prompt for VS 2019.bat**, go to ***BuildPath***
cmake --build . --config Release
cd ..

git clone https://github.com/kcat/openal-soft.git
git clone https://github.com/telegramdesktop/openal-soft.git
cd openal-soft
git checkout openal-soft-1.21.0
git checkout wasapi_exact_device_time
cd build
cmake .. ^
-G "Visual Studio 16 2019" ^
Expand Down
4 changes: 2 additions & 2 deletions docs/building-msvc.md
Original file line number Diff line number Diff line change
Expand Up @@ -110,9 +110,9 @@ Open **x86 Native Tools Command Prompt for VS 2019.bat**, go to ***BuildPath***
cmake --build . --config Release
cd ..

git clone https://github.com/kcat/openal-soft.git
git clone https://github.com/telegramdesktop/openal-soft.git
cd openal-soft
git checkout openal-soft-1.21.0
git checkout wasapi_exact_device_time
cd build
cmake .. ^
-G "Visual Studio 16 2019" ^
Expand Down

0 comments on commit db81638

Please sign in to comment.