summaryrefslogtreecommitdiff
path: root/avmedia
diff options
context:
space:
mode:
Diffstat (limited to 'avmedia')
-rw-r--r--avmedia/Library_avmedia.mk43
-rw-r--r--avmedia/Library_avmediaMacAVF.mk2
-rw-r--r--avmedia/Library_avmediagst.mk3
-rw-r--r--avmedia/Library_avmediagtk.mk48
-rw-r--r--avmedia/Library_avmediawin.mk2
-rw-r--r--avmedia/Module_avmedia.mk11
-rw-r--r--avmedia/README.md (renamed from avmedia/README)16
-rw-r--r--avmedia/inc/bitmaps.hlst4
-rw-r--r--avmedia/inc/helpids.h24
-rw-r--r--avmedia/inc/mediacontrol.hxx3
-rw-r--r--avmedia/inc/strings.hrc9
-rw-r--r--avmedia/source/avmediadummy.cxx92
-rw-r--r--avmedia/source/framework/MediaControlBase.cxx80
-rw-r--r--avmedia/source/framework/mediacontrol.cxx18
-rw-r--r--avmedia/source/framework/mediaitem.cxx186
-rw-r--r--avmedia/source/framework/mediaplayer.cxx1
-rw-r--r--avmedia/source/framework/mediatoolbox.cxx6
-rw-r--r--avmedia/source/framework/soundhandler.cxx30
-rw-r--r--avmedia/source/framework/soundhandler.hxx8
-rw-r--r--avmedia/source/gstreamer/gstframegrabber.cxx26
-rw-r--r--avmedia/source/gstreamer/gstframegrabber.hxx3
-rw-r--r--avmedia/source/gstreamer/gstmanager.cxx10
-rw-r--r--avmedia/source/gstreamer/gstplayer.cxx130
-rw-r--r--avmedia/source/gstreamer/gstplayer.hxx1
-rw-r--r--avmedia/source/gstreamer/gstwindow.cxx5
-rw-r--r--avmedia/source/gstreamer/gstwindow.hxx2
-rw-r--r--avmedia/source/gtk/avmediagtk.component16
-rw-r--r--avmedia/source/gtk/gstwindow.cxx12
-rw-r--r--avmedia/source/gtk/gtkmanager.cxx58
-rw-r--r--avmedia/source/gtk/gtkmanager.hxx34
-rw-r--r--avmedia/source/gtk/gtkplayer.cxx469
-rw-r--r--avmedia/source/gtk/gtkplayer.hxx89
-rw-r--r--avmedia/source/inc/mediamisc.hxx10
-rw-r--r--avmedia/source/macavf/framegrabber.mm2
-rw-r--r--avmedia/source/macavf/manager.mm2
-rw-r--r--avmedia/source/macavf/player.mm2
-rw-r--r--avmedia/source/macavf/window.hxx4
-rw-r--r--avmedia/source/viewer/mediaevent_impl.cxx32
-rw-r--r--avmedia/source/viewer/mediaevent_impl.hxx4
-rw-r--r--avmedia/source/viewer/mediawindow.cxx206
-rw-r--r--avmedia/source/viewer/mediawindow_impl.cxx67
-rw-r--r--avmedia/source/viewer/mediawindow_impl.hxx1
-rw-r--r--avmedia/source/win/framegrabber.cxx45
-rw-r--r--avmedia/source/win/framegrabber.hxx5
-rw-r--r--avmedia/source/win/manager.cxx8
-rw-r--r--avmedia/source/win/player.cxx72
-rw-r--r--avmedia/source/win/player.hxx23
-rw-r--r--avmedia/source/win/window.cxx91
-rw-r--r--avmedia/source/win/window.hxx13
49 files changed, 1386 insertions, 642 deletions
diff --git a/avmedia/Library_avmedia.mk b/avmedia/Library_avmedia.mk
index b27b9bae8c80..3b57e564a530 100644
--- a/avmedia/Library_avmedia.mk
+++ b/avmedia/Library_avmedia.mk
@@ -9,15 +9,21 @@
$(eval $(call gb_Library_Library,avmedia))
-$(eval $(call gb_Library_set_componentfile,avmedia,avmedia/util/avmedia))
-
$(eval $(call gb_Library_set_include,avmedia,\
$$(INCLUDE) \
-I$(SRCDIR)/avmedia/inc \
-I$(SRCDIR)/avmedia/source/inc \
))
-$(eval $(call gb_Library_set_componentfile,avmedia,avmedia/util/avmedia))
+$(eval $(call gb_Library_use_libraries,avmedia,\
+ comphelper \
+ cppu \
+ cppuhelper \
+ sal \
+ svl \
+ ucbhelper \
+ vcl \
+))
$(eval $(call gb_Library_use_sdk_api,avmedia,))
@@ -25,45 +31,29 @@ $(eval $(call gb_Library_use_externals,avmedia,\
boost_headers \
))
-ifeq ($(USE_AVMEDIA_DUMMY),TRUE)
-$(eval $(call gb_Library_add_exception_objects,avmedia,\
- avmedia/source/avmediadummy \
-))
-
-
-else
-
-
$(eval $(call gb_Library_add_defs,avmedia,\
- -DAVMEDIA_DLLIMPLEMENTATION \
+ -DAVMEDIA_DLLIMPLEMENTATION \
))
-ifeq ($(DISABLE_GUI),)
-$(eval $(call gb_Library_use_externals,avmedia,\
- epoxy \
+$(eval $(call gb_Library_add_exception_objects,avmedia,\
+ avmedia/source/framework/mediaitem \
))
-endif
+ifneq (,$(filter AVMEDIA,$(BUILD_TYPE)))
+
+$(eval $(call gb_Library_set_componentfile,avmedia,avmedia/util/avmedia,services))
$(eval $(call gb_Library_use_libraries,avmedia,\
- comphelper \
- ucbhelper \
- cppu \
- cppuhelper \
- sal \
i18nlangtag \
sfx \
- svl \
svt \
tl \
utl \
- vcl \
))
$(eval $(call gb_Library_add_exception_objects,avmedia,\
avmedia/source/framework/mediacontrol \
avmedia/source/framework/MediaControlBase \
- avmedia/source/framework/mediaitem \
avmedia/source/framework/mediaplayer \
avmedia/source/framework/mediatoolbox \
avmedia/source/framework/soundhandler \
@@ -71,6 +61,7 @@ $(eval $(call gb_Library_add_exception_objects,avmedia,\
avmedia/source/viewer/mediawindow \
avmedia/source/viewer/mediawindow_impl \
))
-endif
+
+endif # AVMEDIA
# vim: set noet sw=4 ts=4:
diff --git a/avmedia/Library_avmediaMacAVF.mk b/avmedia/Library_avmediaMacAVF.mk
index de6373632df7..388a9fba1386 100644
--- a/avmedia/Library_avmediaMacAVF.mk
+++ b/avmedia/Library_avmediaMacAVF.mk
@@ -9,7 +9,7 @@
$(eval $(call gb_Library_Library,avmediaMacAVF))
-$(eval $(call gb_Library_set_componentfile,avmediaMacAVF,avmedia/source/macavf/avmediaMacAVF))
+$(eval $(call gb_Library_set_componentfile,avmediaMacAVF,avmedia/source/macavf/avmediaMacAVF,services))
$(eval $(call gb_Library_set_include,avmediaMacAVF,\
$$(INCLUDE) \
diff --git a/avmedia/Library_avmediagst.mk b/avmedia/Library_avmediagst.mk
index 699d0197b50e..fcbaeebbc7ee 100644
--- a/avmedia/Library_avmediagst.mk
+++ b/avmedia/Library_avmediagst.mk
@@ -9,7 +9,7 @@
$(eval $(call gb_Library_Library,avmediagst))
-$(eval $(call gb_Library_set_componentfile,avmediagst,avmedia/source/gstreamer/avmediagstreamer))
+$(eval $(call gb_Library_set_componentfile,avmediagst,avmedia/source/gstreamer/avmediagstreamer,services))
$(eval $(call gb_Library_set_include,avmediagst,\
$$(INCLUDE) \
@@ -33,6 +33,7 @@ $(eval $(call gb_Library_use_libraries,avmediagst,\
salhelper \
tl \
vcl \
+ avmedia \
))
$(eval $(call gb_Library_add_exception_objects,avmediagst,\
diff --git a/avmedia/Library_avmediagtk.mk b/avmedia/Library_avmediagtk.mk
new file mode 100644
index 000000000000..08d30d3259dc
--- /dev/null
+++ b/avmedia/Library_avmediagtk.mk
@@ -0,0 +1,48 @@
+# -*- Mode: makefile-gmake; tab-width: 4; indent-tabs-mode: t -*-
+#
+# This file is part of the LibreOffice project.
+#
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+#
+
+$(eval $(call gb_Library_Library,avmediagtk))
+
+$(eval $(call gb_Library_set_componentfile,avmediagtk,avmedia/source/gtk/avmediagtk,services))
+
+$(eval $(call gb_Library_set_include,avmediagtk,\
+ $$(INCLUDE) \
+ -I$(SRCDIR)/avmedia/source/inc \
+ -I$(SRCDIR)/avmedia/source/gstreamer \
+))
+
+$(eval $(call gb_Library_use_external,avmediagtk,boost_headers))
+
+$(eval $(call gb_Library_add_cxxflags,avmediagtk,\
+ $$(GTK4_CFLAGS) \
+))
+
+$(eval $(call gb_Library_use_sdk_api,avmediagtk))
+
+$(eval $(call gb_Library_use_libraries,avmediagtk,\
+ comphelper \
+ cppu \
+ cppuhelper \
+ sal \
+ salhelper \
+ tl \
+ vcl \
+))
+
+$(eval $(call gb_Library_add_libs,avmediagtk,\
+ $(GTK4_LIBS) \
+))
+
+$(eval $(call gb_Library_add_exception_objects,avmediagtk,\
+ avmedia/source/gtk/gstwindow \
+ avmedia/source/gtk/gtkmanager \
+ avmedia/source/gtk/gtkplayer \
+))
+
+# vim: set noet sw=4 ts=4:
diff --git a/avmedia/Library_avmediawin.mk b/avmedia/Library_avmediawin.mk
index 320ba2b36073..318e28265530 100644
--- a/avmedia/Library_avmediawin.mk
+++ b/avmedia/Library_avmediawin.mk
@@ -9,7 +9,7 @@
$(eval $(call gb_Library_Library,avmediawin))
-$(eval $(call gb_Library_set_componentfile,avmediawin,avmedia/source/win/avmediawin))
+$(eval $(call gb_Library_set_componentfile,avmediawin,avmedia/source/win/avmediawin,services))
$(eval $(call gb_Library_use_external,avmediawin,boost_headers))
diff --git a/avmedia/Module_avmedia.mk b/avmedia/Module_avmedia.mk
index aeb3176544bf..8a1132077210 100644
--- a/avmedia/Module_avmedia.mk
+++ b/avmedia/Module_avmedia.mk
@@ -13,7 +13,8 @@ $(eval $(call gb_Module_add_targets,avmedia,\
Library_avmedia \
))
-ifneq ($(USE_AVMEDIA_DUMMY),TRUE)
+ifneq (,$(filter AVMEDIA,$(BUILD_TYPE)))
+
$(eval $(call gb_Module_add_l10n_targets,avmedia,\
AllLangMoTarget_avmedia \
))
@@ -24,6 +25,12 @@ $(eval $(call gb_Module_add_targets,avmedia,\
))
endif
+ifneq ($(ENABLE_GTK4),)
+$(eval $(call gb_Module_add_targets,avmedia,\
+ Library_avmediagtk \
+))
+endif
+
ifeq ($(OS),MACOSX)
$(eval $(call gb_Module_add_targets,avmedia,\
Library_avmediaMacAVF \
@@ -36,6 +43,6 @@ $(eval $(call gb_Module_add_targets,avmedia,\
))
endif
-endif
+endif # AVMEDIA
# vim: set noet sw=4 ts=4:
diff --git a/avmedia/README b/avmedia/README.md
index 32155b2ac1cf..51202cbe34b2 100644
--- a/avmedia/README
+++ b/avmedia/README.md
@@ -1,18 +1,18 @@
-Audio/Video media implementation.
+# Audio / video Media Implementation.
Provides per-platform implementations of multimedia functionality.
Currently no stream API is provided, only a URI based one, so
streaming has to be wrapped around it via temp files.
-Also provides (in source/framework/mediacontrol.cxx) an implementation
+Also provides (in `source/framework/mediacontrol.cxx`) an implementation
of the graphical media playback control that appears in the toolbar /
-mediaobject bar when media is selected under the .uno:AVMediaToolBox
+mediaobject bar when media is selected under the `.uno:AVMediaToolBox`
item.
-== avmedia/gstreamer ==
+## avmedia / gstreamer
-The avmedia component is implementation of manager service defined in
-offapi/com/sun/star/media/. Radek has added implementation based on
+The `avmedia` component is implementation of manager service defined in
+`offapi/com/sun/star/media/`. Radek has added implementation based on
gstreamer so that we can add audio and video files into impress
presentation on Linux with gstreamer.
@@ -22,4 +22,6 @@ problems when gstreamer installation is incomplete.
In the beginning the media files were not embedded, Thorsten added
support for that later.
-FUTURE work: it might be worthwhile to revamp the avmedia UI
+## Future Works
+
+it might be worthwhile to revamp the avmedia UI.
diff --git a/avmedia/inc/bitmaps.hlst b/avmedia/inc/bitmaps.hlst
index 0ce3ca1f77c0..2730761ecb64 100644
--- a/avmedia/inc/bitmaps.hlst
+++ b/avmedia/inc/bitmaps.hlst
@@ -9,7 +9,7 @@
#pragma once
-#define AVMEDIA_BMP_AUDIOLOGO "avmedia/res/avaudiologo.png"
-#define AVMEDIA_BMP_EMPTYLOGO "avmedia/res/avemptylogo.png"
+inline constexpr OUString AVMEDIA_BMP_AUDIOLOGO = u"avmedia/res/avaudiologo.png"_ustr;
+inline constexpr OUString AVMEDIA_BMP_EMPTYLOGO = u"avmedia/res/avemptylogo.png"_ustr;
/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/avmedia/inc/helpids.h b/avmedia/inc/helpids.h
index c21ba79c9016..a20267998a00 100644
--- a/avmedia/inc/helpids.h
+++ b/avmedia/inc/helpids.h
@@ -19,16 +19,18 @@
#pragma once
-#define HID_AVMEDIA_TOOLBOXITEM_PLAY "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_PLAY"
-#define HID_AVMEDIA_TOOLBOXITEM_PAUSE "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_PAUSE"
-#define HID_AVMEDIA_TOOLBOXITEM_STOP "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_STOP"
-#define HID_AVMEDIA_TOOLBOXITEM_MUTE "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_MUTE"
-#define HID_AVMEDIA_TOOLBOXITEM_LOOP "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_LOOP"
-#define HID_AVMEDIA_TOOLBOXITEM_OPEN "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_OPEN"
-#define HID_AVMEDIA_TOOLBOXITEM_INSERT "AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_INSERT"
-#define HID_AVMEDIA_ZOOMLISTBOX "AVMEDIA_HID_AVMEDIA_ZOOMLISTBOX"
-#define HID_AVMEDIA_TIMEEDIT "AVMEDIA_HID_AVMEDIA_TIMEEDIT"
-#define HID_AVMEDIA_VOLUMESLIDER "AVMEDIA_HID_AVMEDIA_VOLUMESLIDER"
-#define HID_AVMEDIA_PLAYERWINDOW "AVMEDIA_HID_AVMEDIA_PLAYERWINDOW"
+#include <rtl/ustring.hxx>
+
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_PLAY = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_PLAY"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_PAUSE = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_PAUSE"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_STOP = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_STOP"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_MUTE = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_MUTE"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_LOOP = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_LOOP"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_OPEN = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_OPEN"_ustr;
+inline constexpr OUString HID_AVMEDIA_TOOLBOXITEM_INSERT = u"AVMEDIA_HID_AVMEDIA_TOOLBOXITEM_INSERT"_ustr;
+inline constexpr OUString HID_AVMEDIA_ZOOMLISTBOX = u"AVMEDIA_HID_AVMEDIA_ZOOMLISTBOX"_ustr;
+inline constexpr OUString HID_AVMEDIA_TIMEEDIT = u"AVMEDIA_HID_AVMEDIA_TIMEEDIT"_ustr;
+inline constexpr OUString HID_AVMEDIA_VOLUMESLIDER = u"AVMEDIA_HID_AVMEDIA_VOLUMESLIDER"_ustr;
+inline constexpr OUString HID_AVMEDIA_PLAYERWINDOW = u"AVMEDIA_HID_AVMEDIA_PLAYERWINDOW"_ustr;
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/avmedia/inc/mediacontrol.hxx b/avmedia/inc/mediacontrol.hxx
index 33c063fc9dad..f168ef566807 100644
--- a/avmedia/inc/mediacontrol.hxx
+++ b/avmedia/inc/mediacontrol.hxx
@@ -57,7 +57,7 @@ private:
DECL_LINK(implTimeHdl, weld::Scale&, void);
DECL_LINK(implTimeEndHdl, Timer*, void);
DECL_LINK(implVolumeHdl, weld::Scale&, void);
- DECL_LINK(implSelectHdl, const OString&, void);
+ DECL_LINK(implSelectHdl, const OUString&, void);
DECL_LINK(implZoomSelectHdl, weld::ComboBox&, void);
DECL_LINK(implTimeoutHdl, Timer*, void);
@@ -66,7 +66,6 @@ private:
MediaItem maItem;
bool mbLocked;
MediaControlStyle meControlStyle;
- double mfTime;
};
}
diff --git a/avmedia/inc/strings.hrc b/avmedia/inc/strings.hrc
index 26e6b8fbd478..1edbe24a00f4 100644
--- a/avmedia/inc/strings.hrc
+++ b/avmedia/inc/strings.hrc
@@ -19,15 +19,8 @@
#pragma once
-#define NC_(Context, String) reinterpret_cast<char const *>(Context "\004" u8##String)
+#define NC_(Context, String) TranslateId(Context, u8##String)
-#define AVMEDIA_STR_OPEN NC_("AVMEDIA_STR_OPEN", "Open")
-#define AVMEDIA_STR_INSERT NC_("AVMEDIA_STR_INSERT", "Apply")
-#define AVMEDIA_STR_PLAY NC_("AVMEDIA_STR_PLAY", "Play")
-#define AVMEDIA_STR_PAUSE NC_("AVMEDIA_STR_PAUSE", "Pause")
-#define AVMEDIA_STR_STOP NC_("AVMEDIA_STR_STOP", "Stop")
-#define AVMEDIA_STR_LOOP NC_("AVMEDIA_STR_LOOP", "Repeat")
-#define AVMEDIA_STR_MUTE NC_("AVMEDIA_STR_MUTE", "Mute")
#define AVMEDIA_STR_ZOOM_50 NC_("AVMEDIA_STR_ZOOM_50", "50%")
#define AVMEDIA_STR_ZOOM_100 NC_("AVMEDIA_STR_ZOOM_100", "100%")
#define AVMEDIA_STR_ZOOM_200 NC_("AVMEDIA_STR_ZOOM_200", "200%")
diff --git a/avmedia/source/avmediadummy.cxx b/avmedia/source/avmediadummy.cxx
deleted file mode 100644
index 6c6ada0163e9..000000000000
--- a/avmedia/source/avmediadummy.cxx
+++ /dev/null
@@ -1,92 +0,0 @@
-/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
-/*
- * This file is part of the LibreOffice project.
- *
- * This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- *
- * This file incorporates work covered by the following license notice:
- *
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed
- * with this work for additional information regarding copyright
- * ownership. The ASF licenses this file to you under the Apache
- * License, Version 2.0 (the "License"); you may not use this file
- * except in compliance with the License. You may obtain a copy of
- * the License at http://www.apache.org/licenses/LICENSE-2.0 .
- */
-
-#include <avmedia/mediaitem.hxx>
-
-#include <com/sun/star/uno/Sequence.hxx>
-#include <com/sun/star/uno/XComponentContext.hpp>
-
-using namespace ::com::sun::star;
-
-namespace avmedia
-{
-MediaItem::MediaItem( sal_uInt16 i_nWhich, AVMediaSetMask )
- : SfxPoolItem( i_nWhich )
-{
-}
-
-MediaItem::MediaItem( const MediaItem& rItem )
- : SfxPoolItem( rItem )
-{
-}
-
-MediaItem::~MediaItem()
-{
-}
-
-struct MediaItem::Impl
-{
-};
-
-bool MediaItem::QueryValue( css::uno::Any&, sal_uInt8 ) const
-{
- return false;
-}
-
-bool MediaItem::GetPresentation( SfxItemPresentation, MapUnit, MapUnit, OUString&, const IntlWrapper& ) const
-{
- return false;
-}
-
-bool MediaItem::PutValue( const css::uno::Any&, sal_uInt8 )
-{
- return false;
-}
-
-AVMediaSetMask MediaItem::getMaskSet() const
-{
- return AVMediaSetMask::NONE;
-}
-
-SfxPoolItem* MediaItem::CreateDefault()
-{
- return new MediaItem;
-}
-
-
-MediaItem* MediaItem::Clone( SfxItemPool*) const
-{
- return nullptr;
-}
-
-bool MediaItem::operator==( const SfxPoolItem& rItem ) const
-{
- assert(SfxPoolItem::operator==(rItem)); (void)rItem;
- return false;
-}
-
-} // namespace avmedia
-
-extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface* SAL_CALL
-com_sun_star_comp_framework_SoundHandler_get_implementation(css::uno::XComponentContext*,
- css::uno::Sequence<css::uno::Any> const &)
-{
- return NULL;
-}
-/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/avmedia/source/framework/MediaControlBase.cxx b/avmedia/source/framework/MediaControlBase.cxx
index 890bb04d805b..fb8f91066b67 100644
--- a/avmedia/source/framework/MediaControlBase.cxx
+++ b/avmedia/source/framework/MediaControlBase.cxx
@@ -20,16 +20,15 @@
#include <avmedia/mediaplayer.hxx>
#include <avmedia/mediaitem.hxx>
#include <tools/time.hxx>
+#include <tools/duration.hxx>
#include <unotools/localedatawrapper.hxx>
#include <strings.hrc>
#include <helpids.h>
#include <mediamisc.hxx>
-using ::rtl::OUString;
-
constexpr sal_Int32 AVMEDIA_DB_RANGE = -40;
-#define AVMEDIA_LINEINCREMENT 1.0
-#define AVMEDIA_PAGEINCREMENT 10.0
+constexpr double AVMEDIA_LINEINCREMENT = 1.0;
+constexpr double AVMEDIA_PAGEINCREMENT = 10.0;
namespace avmedia {
@@ -48,9 +47,11 @@ void MediaControlBase::UpdateTimeField( MediaItem const & aMediaItem, double fTi
SvtSysLocale aSysLocale;
const LocaleDataWrapper& rLocaleData = aSysLocale.GetLocaleData();
- aTimeString += rLocaleData.getDuration( tools::Time( 0, 0, static_cast< sal_uInt32 >( floor( fTime ) ) ) ) +
+ aTimeString += rLocaleData.getDuration(
+ tools::Duration( 0, 0, 0, static_cast<sal_uInt32>( floor( fTime )), 0)) +
" / " +
- rLocaleData.getDuration( tools::Time( 0, 0, static_cast< sal_uInt32 >( floor( aMediaItem.getDuration() ) )) );
+ rLocaleData.getDuration(
+ tools::Duration( 0, 0, 0, static_cast<sal_uInt32>( floor( aMediaItem.getDuration())), 0));
if( mxTimeEdit->get_text() != aTimeString )
mxTimeEdit->set_text( aTimeString );
@@ -84,6 +85,7 @@ void MediaControlBase::UpdateTimeSlider( MediaItem const & aMediaItem )
bool bChanged(false);
int nStep(0), nPage(0);
+ mxTimeSlider->get_increments(nStep, nPage);
if (!nStep)
{
nStep = AVMEDIA_TIME_RANGE * AVMEDIA_LINEINCREMENT / fDuration;
@@ -105,15 +107,10 @@ void MediaControlBase::UpdateTimeSlider( MediaItem const & aMediaItem )
void MediaControlBase::InitializeWidgets()
{
mxPlayToolBox->set_item_help_id("play", HID_AVMEDIA_TOOLBOXITEM_PLAY);
- mxPlayToolBox->set_item_label("play", AvmResId(AVMEDIA_STR_PLAY));
mxPlayToolBox->set_item_help_id("pause", HID_AVMEDIA_TOOLBOXITEM_PAUSE);
- mxPlayToolBox->set_item_label("pause", AvmResId(AVMEDIA_STR_PAUSE));
mxPlayToolBox->set_item_help_id("stop", HID_AVMEDIA_TOOLBOXITEM_STOP);
- mxPlayToolBox->set_item_label("stop", AvmResId(AVMEDIA_STR_STOP));
mxPlayToolBox->set_item_help_id("loop", HID_AVMEDIA_TOOLBOXITEM_LOOP);
- mxPlayToolBox->set_item_label("loop", AvmResId(AVMEDIA_STR_LOOP));
mxMuteToolBox->set_item_help_id("mute", HID_AVMEDIA_TOOLBOXITEM_MUTE);
- mxMuteToolBox->set_item_label("mute", AvmResId(AVMEDIA_STR_MUTE));
mxZoomListBox->append(OUString::number(AVMEDIA_ZOOMLEVEL_50), AvmResId( AVMEDIA_STR_ZOOM_50 ));
mxZoomListBox->append(OUString::number(AVMEDIA_ZOOMLEVEL_100), AvmResId( AVMEDIA_STR_ZOOM_100 ));
@@ -134,6 +131,28 @@ void MediaControlBase::InitializeWidgets()
mxTimeSlider->set_tooltip_text( AvmResId( AVMEDIA_STR_POSITION ));
}
+void MediaControlBase::UpdatePlayState(const MediaItem& rMediaItem)
+{
+ if (rMediaItem.getState() == MediaState::Play)
+ {
+ mxPlayToolBox->set_item_active("play", true);
+ mxPlayToolBox->set_item_active("pause", false);
+ mxPlayToolBox->set_item_active("stop", false);
+ }
+ else if( rMediaItem.getState() == MediaState::Pause )
+ {
+ mxPlayToolBox->set_item_active("play", false);
+ mxPlayToolBox->set_item_active("pause", true);
+ mxPlayToolBox->set_item_active("stop", false);
+ }
+ else
+ {
+ mxPlayToolBox->set_item_active("play", false);
+ mxPlayToolBox->set_item_active("pause", false);
+ mxPlayToolBox->set_item_active("stop", true);
+ }
+}
+
void MediaControlBase::UpdateToolBoxes(const MediaItem& rMediaItem)
{
const bool bValidURL = !rMediaItem.getURL().isEmpty();
@@ -151,24 +170,7 @@ void MediaControlBase::UpdateToolBoxes(const MediaItem& rMediaItem)
{
mxPlayToolBox->set_sensitive(true);
mxMuteToolBox->set_sensitive(true);
- if( rMediaItem.getState() == MediaState::Play )
- {
- mxPlayToolBox->set_item_active("play", true);
- mxPlayToolBox->set_item_active("pause", false);
- mxPlayToolBox->set_item_active("stop", false);
- }
- else if( rMediaItem.getState() == MediaState::Pause )
- {
- mxPlayToolBox->set_item_active("play", false);
- mxPlayToolBox->set_item_active("pause", true);
- mxPlayToolBox->set_item_active("stop", false);
- }
- else
- {
- mxPlayToolBox->set_item_active("play", false);
- mxPlayToolBox->set_item_active("pause", false);
- mxPlayToolBox->set_item_active("stop", true);
- }
+ UpdatePlayState(rMediaItem);
mxPlayToolBox->set_item_active("loop", rMediaItem.isLoop());
mxMuteToolBox->set_item_active("mute", rMediaItem.isMute());
if (!mbCurrentlySettingZoom)
@@ -210,16 +212,16 @@ void MediaControlBase::UpdateToolBoxes(const MediaItem& rMediaItem)
}
}
-void MediaControlBase::SelectPlayToolBoxItem( MediaItem& aExecItem, MediaItem const & aItem, std::string_view rId)
+void MediaControlBase::SelectPlayToolBoxItem( MediaItem& aExecItem, MediaItem const & aItem, std::u16string_view rId)
{
- if (rId == "apply")
+ if (rId == u"apply")
{
MediaFloater* pFloater = avmedia::getMediaFloater();
if( pFloater )
pFloater->dispatchCurrentURL();
}
- else if (rId == "play")
+ else if (rId == u"play")
{
aExecItem.setState( MediaState::Play );
@@ -227,21 +229,27 @@ void MediaControlBase::SelectPlayToolBoxItem( MediaItem& aExecItem, MediaItem co
aExecItem.setTime( 0.0 );
else
aExecItem.setTime( aItem.getTime() );
+
+ UpdatePlayState(aExecItem);
}
- else if (rId == "pause")
+ else if (rId == u"pause")
{
aExecItem.setState( MediaState::Pause );
+
+ UpdatePlayState(aExecItem);
}
- else if (rId == "stop")
+ else if (rId == u"stop")
{
aExecItem.setState( MediaState::Stop );
aExecItem.setTime( 0.0 );
+
+ UpdatePlayState(aExecItem);
}
- else if (rId == "mute")
+ else if (rId == u"mute")
{
aExecItem.setMute( mxMuteToolBox->get_item_active("mute") );
}
- else if (rId == "loop")
+ else if (rId == u"loop")
{
aExecItem.setLoop( mxPlayToolBox->get_item_active("loop") );
}
diff --git a/avmedia/source/framework/mediacontrol.cxx b/avmedia/source/framework/mediacontrol.cxx
index 035430ab9089..a9c33ff45455 100644
--- a/avmedia/source/framework/mediacontrol.cxx
+++ b/avmedia/source/framework/mediacontrol.cxx
@@ -35,13 +35,11 @@ MediaControl::MediaControl( vcl::Window* pParent, MediaControlStyle eControlStyl
OUString("svx/ui/mediawindow.ui") :
OUString("svx/ui/medialine.ui"),
"MediaWindow"),
- MediaControlBase(),
maIdle( "avmedia MediaControl Idle" ),
maChangeTimeIdle( "avmedia MediaControl Change Time Idle" ),
maItem( 0, AVMediaSetMask::ALL ),
mbLocked( false ),
- meControlStyle( eControlStyle ),
- mfTime(0.0)
+ meControlStyle( eControlStyle )
{
mxPlayToolBox = m_xBuilder->weld_toolbar("playtoolbox");
mxTimeSlider = m_xBuilder->weld_scale("timeslider");
@@ -51,8 +49,6 @@ MediaControl::MediaControl( vcl::Window* pParent, MediaControlStyle eControlStyl
mxTimeEdit = m_xBuilder->weld_entry("timeedit");
mxMediaPath = m_xBuilder->weld_label("url");
- // TODO SetParentClipMode( ParentClipMode::NoClip );
-
InitializeWidgets();
mxPlayToolBox->connect_clicked( LINK( this, MediaControl, implSelectHdl ) );
@@ -90,9 +86,7 @@ void MediaControl::InitializeWidgets()
if( meControlStyle != MediaControlStyle::SingleLine )
{
mxPlayToolBox->set_item_help_id("open", HID_AVMEDIA_TOOLBOXITEM_OPEN);
- mxPlayToolBox->set_item_label("open", AvmResId(AVMEDIA_STR_OPEN));
mxPlayToolBox->set_item_help_id("apply", HID_AVMEDIA_TOOLBOXITEM_INSERT);
- mxPlayToolBox->set_item_label("apply", AvmResId(AVMEDIA_STR_INSERT));
}
avmedia::MediaControlBase::InitializeWidgets();
}
@@ -117,11 +111,11 @@ void MediaControl::UpdateURLField(MediaItem const & tempItem)
void MediaControl::setState( const MediaItem& rItem )
{
- double fTime = rItem.getTime();
- if( !mbLocked && fTime != mfTime)
+ if (mbLocked)
+ return;
+ bool bChanged = maItem.merge(rItem);
+ if (bChanged)
{
- mfTime = fTime;
- maItem.merge( rItem );
if( rItem.getURL().isEmpty() && meControlStyle == MediaControlStyle::SingleLine )
mxPlayToolBox->set_sensitive(false);
UpdateToolBoxes( maItem );
@@ -162,7 +156,7 @@ IMPL_LINK( MediaControl, implVolumeHdl, weld::Scale&, rSlider, void )
update();
}
-IMPL_LINK( MediaControl, implSelectHdl, const OString&, rIdent, void )
+IMPL_LINK( MediaControl, implSelectHdl, const OUString&, rIdent, void )
{
MediaItem aExecItem;
if (rIdent == "open")
diff --git a/avmedia/source/framework/mediaitem.cxx b/avmedia/source/framework/mediaitem.cxx
index 54db2e3bc6bf..320a24bc9bfe 100644
--- a/avmedia/source/framework/mediaitem.cxx
+++ b/avmedia/source/framework/mediaitem.cxx
@@ -30,16 +30,18 @@
#include <com/sun/star/uri/UriReferenceFactory.hpp>
#include <com/sun/star/uri/XUriReference.hpp>
#include <com/sun/star/uri/XUriReferenceFactory.hpp>
+#include <com/sun/star/text/GraphicCrop.hpp>
#include <sal/log.hxx>
#include <ucbhelper/content.hxx>
+#include <comphelper/mediamimetype.hxx>
#include <comphelper/processfactory.hxx>
#include <comphelper/storagehelper.hxx>
#include <mediamisc.hxx>
#include <osl/file.hxx>
-#include <tools/diagnose_ex.h>
+#include <comphelper/diagnose_ex.hxx>
#include <vcl/graph.hxx>
using namespace ::com::sun::star;
@@ -64,6 +66,7 @@ struct MediaItem::Impl
bool m_bMute;
css::media::ZoomLevel m_eZoom;
Graphic m_aGraphic;
+ text::GraphicCrop m_aCrop;
explicit Impl(AVMediaSetMask nMaskSet)
: m_nMaskSet( nMaskSet )
@@ -107,6 +110,7 @@ bool MediaItem::operator==( const SfxPoolItem& rItem ) const
&& m_pImpl->m_Referer == rOther.m_pImpl->m_Referer
&& m_pImpl->m_sMimeType == rOther.m_pImpl->m_sMimeType
&& m_pImpl->m_aGraphic == rOther.m_pImpl->m_aGraphic
+ && m_pImpl->m_aCrop == rOther.m_pImpl->m_aCrop
&& m_pImpl->m_eState == rOther.m_pImpl->m_eState
&& m_pImpl->m_fDuration == rOther.m_pImpl->m_fDuration
&& m_pImpl->m_fTime == rOther.m_pImpl->m_fTime
@@ -133,18 +137,16 @@ bool MediaItem::GetPresentation( SfxItemPresentation,
bool MediaItem::QueryValue( css::uno::Any& rVal, sal_uInt8 ) const
{
- uno::Sequence< uno::Any > aSeq( 10 );
-
- aSeq[ 0 ] <<= m_pImpl->m_URL;
- aSeq[ 1 ] <<= static_cast<sal_uInt32>(m_pImpl->m_nMaskSet);
- aSeq[ 2 ] <<= static_cast< sal_Int32 >( m_pImpl->m_eState );
- aSeq[ 3 ] <<= m_pImpl->m_fTime;
- aSeq[ 4 ] <<= m_pImpl->m_fDuration;
- aSeq[ 5 ] <<= m_pImpl->m_nVolumeDB;
- aSeq[ 6 ] <<= m_pImpl->m_bLoop;
- aSeq[ 7 ] <<= m_pImpl->m_bMute;
- aSeq[ 8 ] <<= m_pImpl->m_eZoom;
- aSeq[ 9 ] <<= m_pImpl->m_sMimeType;
+ uno::Sequence< uno::Any > aSeq{ uno::Any(m_pImpl->m_URL),
+ uno::Any(static_cast<sal_uInt32>(m_pImpl->m_nMaskSet)),
+ uno::Any(static_cast< sal_Int32 >( m_pImpl->m_eState )),
+ uno::Any(m_pImpl->m_fTime),
+ uno::Any(m_pImpl->m_fDuration),
+ uno::Any(m_pImpl->m_nVolumeDB),
+ uno::Any(m_pImpl->m_bLoop),
+ uno::Any(m_pImpl->m_bMute),
+ uno::Any(m_pImpl->m_eZoom),
+ uno::Any(m_pImpl->m_sMimeType) };
rVal <<= aSeq;
@@ -180,187 +182,216 @@ bool MediaItem::PutValue( const css::uno::Any& rVal, sal_uInt8 )
return bRet;
}
-
-void MediaItem::merge( const MediaItem& rMediaItem )
+bool MediaItem::merge(const MediaItem& rMediaItem)
{
+ bool bChanged = false;
+
const AVMediaSetMask nMaskSet = rMediaItem.getMaskSet();
if( AVMediaSetMask::URL & nMaskSet )
- setURL( rMediaItem.getURL(), rMediaItem.getTempURL(), rMediaItem.getReferer() );
+ bChanged |= setURL(rMediaItem.getURL(), rMediaItem.getTempURL(), rMediaItem.getReferer());
if( AVMediaSetMask::MIME_TYPE & nMaskSet )
- setMimeType( rMediaItem.getMimeType() );
+ bChanged |= setMimeType(rMediaItem.getMimeType());
if (nMaskSet & AVMediaSetMask::GRAPHIC)
- setGraphic(rMediaItem.getGraphic());
+ bChanged |= setGraphic(rMediaItem.getGraphic());
+
+ if (nMaskSet & AVMediaSetMask::CROP)
+ bChanged |= setCrop(rMediaItem.getCrop());
if( AVMediaSetMask::STATE & nMaskSet )
- setState( rMediaItem.getState() );
+ bChanged |= setState( rMediaItem.getState() );
if( AVMediaSetMask::DURATION & nMaskSet )
- setDuration( rMediaItem.getDuration() );
+ bChanged |= setDuration(rMediaItem.getDuration());
if( AVMediaSetMask::TIME & nMaskSet )
- setTime( rMediaItem.getTime() );
+ bChanged |= setTime(rMediaItem.getTime());
if( AVMediaSetMask::LOOP & nMaskSet )
- setLoop( rMediaItem.isLoop() );
+ bChanged |= setLoop(rMediaItem.isLoop());
if( AVMediaSetMask::MUTE & nMaskSet )
- setMute( rMediaItem.isMute() );
+ bChanged |= setMute(rMediaItem.isMute());
if( AVMediaSetMask::VOLUMEDB & nMaskSet )
- setVolumeDB( rMediaItem.getVolumeDB() );
+ bChanged |= setVolumeDB(rMediaItem.getVolumeDB());
if( AVMediaSetMask::ZOOM & nMaskSet )
- setZoom( rMediaItem.getZoom() );
-}
+ bChanged |= setZoom(rMediaItem.getZoom());
+ return bChanged;
+}
AVMediaSetMask MediaItem::getMaskSet() const
{
return m_pImpl->m_nMaskSet;
}
-
-void MediaItem::setURL( const OUString& rURL, const OUString& rTempURL, const OUString& rReferer )
+bool MediaItem::setURL(const OUString& rURL, const OUString& rTempURL, const OUString& rReferer)
{
m_pImpl->m_nMaskSet |= AVMediaSetMask::URL;
- m_pImpl->m_URL = rURL;
- m_pImpl->m_TempFileURL = rTempURL;
- m_pImpl->m_Referer = rReferer;
+ bool bChanged = rURL != m_pImpl->m_URL || rTempURL != m_pImpl->m_TempFileURL || rReferer != m_pImpl->m_Referer;
+ if (bChanged)
+ {
+ m_pImpl->m_URL = rURL;
+ m_pImpl->m_TempFileURL = rTempURL;
+ m_pImpl->m_Referer = rReferer;
+ setMimeType(::comphelper::GuessMediaMimeType(GetFilename(rURL)));
+ }
+ return bChanged;
}
-
const OUString& MediaItem::getURL() const
{
return m_pImpl->m_URL;
}
-
const OUString& MediaItem::getTempURL() const
{
return m_pImpl->m_TempFileURL;
}
-
const OUString& MediaItem::getReferer() const
{
return m_pImpl->m_Referer;
}
-
-void MediaItem::setMimeType( const OUString& rMimeType )
+bool MediaItem::setMimeType(const OUString& rMimeType)
{
m_pImpl->m_nMaskSet |= AVMediaSetMask::MIME_TYPE;
- m_pImpl->m_sMimeType = rMimeType;
+ bool bChanged = rMimeType != m_pImpl->m_sMimeType;
+ if (bChanged)
+ m_pImpl->m_sMimeType = rMimeType;
+ return bChanged;
}
-
OUString MediaItem::getMimeType() const
{
return !m_pImpl->m_sMimeType.isEmpty() ? m_pImpl->m_sMimeType : AVMEDIA_MIMETYPE_COMMON;
}
-void MediaItem::setGraphic(const Graphic& rGraphic)
+bool MediaItem::setGraphic(const Graphic& rGraphic)
{
m_pImpl->m_nMaskSet |= AVMediaSetMask::GRAPHIC;
- m_pImpl->m_aGraphic = rGraphic;
+ bool bChanged = rGraphic != m_pImpl->m_aGraphic;
+ if (bChanged)
+ m_pImpl->m_aGraphic = rGraphic;
+ return bChanged;
}
-Graphic MediaItem::getGraphic() const { return m_pImpl->m_aGraphic; }
+const Graphic & MediaItem::getGraphic() const { return m_pImpl->m_aGraphic; }
-void MediaItem::setState( MediaState eState )
+bool MediaItem::setCrop(const text::GraphicCrop& rCrop)
{
- m_pImpl->m_eState = eState;
- m_pImpl->m_nMaskSet |= AVMediaSetMask::STATE;
+ m_pImpl->m_nMaskSet |= AVMediaSetMask::CROP;
+ bool bChanged = rCrop != m_pImpl->m_aCrop;
+ if (bChanged)
+ m_pImpl->m_aCrop = rCrop;
+ return bChanged;
}
+const text::GraphicCrop& MediaItem::getCrop() const { return m_pImpl->m_aCrop; }
+
+bool MediaItem::setState(MediaState eState)
+{
+ m_pImpl->m_nMaskSet |= AVMediaSetMask::STATE;
+ bool bChanged = eState != m_pImpl->m_eState;
+ if (bChanged)
+ m_pImpl->m_eState = eState;
+ return bChanged;
+}
MediaState MediaItem::getState() const
{
return m_pImpl->m_eState;
}
-
-void MediaItem::setDuration( double fDuration )
+bool MediaItem::setDuration(double fDuration)
{
- m_pImpl->m_fDuration = fDuration;
m_pImpl->m_nMaskSet |= AVMediaSetMask::DURATION;
+ bool bChanged = fDuration != m_pImpl->m_fDuration;
+ if (bChanged)
+ m_pImpl->m_fDuration = fDuration;
+ return bChanged;
}
-
double MediaItem::getDuration() const
{
return m_pImpl->m_fDuration;
}
-
-void MediaItem::setTime( double fTime )
+bool MediaItem::setTime(double fTime)
{
- m_pImpl->m_fTime = fTime;
m_pImpl->m_nMaskSet |= AVMediaSetMask::TIME;
+ bool bChanged = fTime != m_pImpl->m_fTime;
+ if (bChanged)
+ m_pImpl->m_fTime = fTime;
+ return bChanged;
}
-
double MediaItem::getTime() const
{
return m_pImpl->m_fTime;
}
-
-void MediaItem::setLoop( bool bLoop )
+bool MediaItem::setLoop(bool bLoop)
{
- m_pImpl->m_bLoop = bLoop;
m_pImpl->m_nMaskSet |= AVMediaSetMask::LOOP;
+ bool bChanged = bLoop != m_pImpl->m_bLoop;
+ if (bChanged)
+ m_pImpl->m_bLoop = bLoop;
+ return bChanged;
}
-
bool MediaItem::isLoop() const
{
return m_pImpl->m_bLoop;
}
-
-void MediaItem::setMute( bool bMute )
+bool MediaItem::setMute(bool bMute)
{
- m_pImpl->m_bMute = bMute;
m_pImpl->m_nMaskSet |= AVMediaSetMask::MUTE;
+ bool bChanged = bMute != m_pImpl->m_bMute;
+ if (bChanged)
+ m_pImpl->m_bMute = bMute;
+ return bChanged;
}
-
bool MediaItem::isMute() const
{
return m_pImpl->m_bMute;
}
-
-void MediaItem::setVolumeDB( sal_Int16 nDB )
+bool MediaItem::setVolumeDB(sal_Int16 nDB)
{
- m_pImpl->m_nVolumeDB = nDB;
m_pImpl->m_nMaskSet |= AVMediaSetMask::VOLUMEDB;
+ bool bChanged = nDB != m_pImpl->m_nVolumeDB;
+ if (bChanged)
+ m_pImpl->m_nVolumeDB = nDB;
+ return bChanged;
}
-
sal_Int16 MediaItem::getVolumeDB() const
{
return m_pImpl->m_nVolumeDB;
}
-
-void MediaItem::setZoom( css::media::ZoomLevel eZoom )
+bool MediaItem::setZoom(css::media::ZoomLevel eZoom)
{
- m_pImpl->m_eZoom = eZoom;
m_pImpl->m_nMaskSet |= AVMediaSetMask::ZOOM;
+ bool bChanged = eZoom != m_pImpl->m_eZoom;
+ if (bChanged)
+ m_pImpl->m_eZoom = eZoom;
+ return bChanged;
}
-
css::media::ZoomLevel MediaItem::getZoom() const
{
return m_pImpl->m_eZoom;
}
-
OUString GetFilename(OUString const& rSourceURL)
{
uno::Reference<uri::XUriReferenceFactory> const xUriFactory(
@@ -394,13 +425,13 @@ CreateStream(uno::Reference<embed::XStorage> const& xStorage,
if (xStorage->hasByName(filename))
{
- OUString basename;
- OUString suffix;
+ std::u16string_view basename;
+ std::u16string_view suffix;
sal_Int32 const nIndex(rFilename.lastIndexOf('.'));
if (0 < nIndex)
{
- basename = rFilename.copy(0, nIndex);
- suffix = rFilename.copy(nIndex);
+ basename = rFilename.subView(0, nIndex);
+ suffix = rFilename.subView(nIndex);
}
sal_Int32 count(0); // sigh... try to generate non-existent name
do
@@ -418,10 +449,9 @@ CreateStream(uno::Reference<embed::XStorage> const& xStorage,
uno::Reference< beans::XPropertySet > const xStreamProps(xStream,
uno::UNO_QUERY);
if (xStreamProps.is()) { // this is NOT supported in FileSystemStorage
- xStreamProps->setPropertyValue("MediaType", uno::Any(OUString(
- //FIXME how to detect real media type?
- //but currently xmloff has this one hardcoded anyway...
- "application/vnd.sun.star.media")));
+ OUString const guessed(::comphelper::GuessMediaMimeType(filename));
+ xStreamProps->setPropertyValue("MediaType",
+ uno::Any(guessed.isEmpty() ? AVMEDIA_MIMETYPE_COMMON : guessed));
xStreamProps->setPropertyValue( // turn off compression
"Compressed", uno::Any(false));
}
@@ -439,7 +469,7 @@ bool EmbedMedia(uno::Reference<frame::XModel> const& xModel,
uno::Reference<embed::XStorage> const xStorage(
xSBD->getDocumentStorage(), uno::UNO_SET_THROW);
- OUString const media("Media");
+ static constexpr OUString media(u"Media"_ustr);
uno::Reference<embed::XStorage> const xSubStorage(
xStorage->openStorageElement(media, embed::ElementModes::WRITE));
diff --git a/avmedia/source/framework/mediaplayer.cxx b/avmedia/source/framework/mediaplayer.cxx
index 258f23ff4645..b4acad37c741 100644
--- a/avmedia/source/framework/mediaplayer.cxx
+++ b/avmedia/source/framework/mediaplayer.cxx
@@ -25,6 +25,7 @@
#include <helpids.h>
#include <svl/stritem.hxx>
+#include <svl/itemset.hxx>
#include <sfx2/sfxsids.hrc>
#include <sfx2/bindings.hxx>
#include <sfx2/dispatch.hxx>
diff --git a/avmedia/source/framework/mediatoolbox.cxx b/avmedia/source/framework/mediatoolbox.cxx
index a109113a78fe..55a19ac6601d 100644
--- a/avmedia/source/framework/mediatoolbox.cxx
+++ b/avmedia/source/framework/mediatoolbox.cxx
@@ -65,10 +65,10 @@ void MediaToolBoxControl_Impl::execute( const MediaItem& rItem )
}
-SFX_IMPL_TOOLBOX_CONTROL( ::avmedia::MediaToolBoxControl, ::avmedia::MediaItem );
+SFX_IMPL_TOOLBOX_CONTROL( MediaToolBoxControl, ::avmedia::MediaItem );
-MediaToolBoxControl::MediaToolBoxControl( sal_uInt16 nSlotId, sal_uInt16 nId, ToolBox& rTbx ) :
+MediaToolBoxControl::MediaToolBoxControl( sal_uInt16 nSlotId, ToolBoxItemId nId, ToolBox& rTbx ) :
SfxToolBoxControl( nSlotId, nId, rTbx )
{
rTbx.Invalidate();
@@ -80,7 +80,7 @@ MediaToolBoxControl::~MediaToolBoxControl()
}
-void MediaToolBoxControl::StateChanged( sal_uInt16, SfxItemState eState, const SfxPoolItem* pState )
+void MediaToolBoxControl::StateChangedAtToolBoxControl( sal_uInt16, SfxItemState eState, const SfxPoolItem* pState )
{
MediaToolBoxControl_Impl* pCtrl = static_cast< MediaToolBoxControl_Impl* >( GetToolBox().GetItemWindow( GetId() ) );
diff --git a/avmedia/source/framework/soundhandler.cxx b/avmedia/source/framework/soundhandler.cxx
index cf341f7226a5..d3cc8b724d39 100644
--- a/avmedia/source/framework/soundhandler.cxx
+++ b/avmedia/source/framework/soundhandler.cxx
@@ -36,13 +36,13 @@ namespace avmedia{
// XInterface, XTypeProvider, XServiceInfo
-void SAL_CALL SoundHandler::acquire() throw()
+void SAL_CALL SoundHandler::acquire() noexcept
{
/* Don't use mutex in methods of XInterface! */
OWeakObject::acquire();
}
-void SAL_CALL SoundHandler::release() throw()
+void SAL_CALL SoundHandler::release() noexcept
{
/* Don't use mutex in methods of XInterface! */
OWeakObject::release();
@@ -85,14 +85,12 @@ css::uno::Sequence< css::uno::Type > SAL_CALL SoundHandler::getTypes()
return aTypeCollection.getTypes();
}
-#define IMPLEMENTATIONNAME_SOUNDHANDLER "com.sun.star.comp.framework.SoundHandler"
-
/*===========================================================================================================*/
/* XServiceInfo */
/*===========================================================================================================*/
OUString SAL_CALL SoundHandler::getImplementationName()
{
- return IMPLEMENTATIONNAME_SOUNDHANDLER;
+ return u"com.sun.star.comp.framework.SoundHandler"_ustr;
}
// XServiceInfo
@@ -104,7 +102,7 @@ sal_Bool SAL_CALL SoundHandler::supportsService( const OUString& sServiceName )
// XServiceInfo
css::uno::Sequence< OUString > SAL_CALL SoundHandler::getSupportedServiceNames()
{
- return { "com.sun.star.frame.ContentHandler" };
+ return { u"com.sun.star.frame.ContentHandler"_ustr };
}
/*-************************************************************************************************************
@@ -144,7 +142,7 @@ SoundHandler::~SoundHandler()
@short try to load audio file
@descr This method try to load given audio file by URL and play it. We use vcl/Sound class to do that.
- Playing of sound is asynchron every time.
+ Playing of sound is asynchronous every time.
@attention We must hold us alive by ourself ... because we use async. vcl sound player ... but playing is started
in async interface call "dispatch()" too. And caller forget us immediately. But then our uno ref count
@@ -164,7 +162,7 @@ void SAL_CALL SoundHandler::dispatchWithNotification(const css::util::URL&
const css::uno::Reference< css::frame::XDispatchResultListener >& xListener )
{
// SAFE {
- const ::osl::MutexGuard aLock( GetMutex() );
+ const ::osl::MutexGuard aLock( m_aMutex );
utl::MediaDescriptor aDescriptor(lDescriptor);
@@ -172,7 +170,7 @@ void SAL_CALL SoundHandler::dispatchWithNotification(const css::util::URL&
//close streams otherwise on windows we can't reopen the file in the
//media player when we pass the url to directx as it'll already be open
css::uno::Reference< css::io::XInputStream > xInputStream =
- aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_INPUTSTREAM(),
+ aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_INPUTSTREAM,
css::uno::Reference< css::io::XInputStream >());
if (xInputStream.is()) xInputStream->closeInput();
}
@@ -192,10 +190,10 @@ void SAL_CALL SoundHandler::dispatchWithNotification(const css::util::URL&
try
{
m_bError = false;
- m_xPlayer.set( avmedia::MediaWindow::createPlayer( aURL.Complete, aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_REFERRER(), OUString()) ), css::uno::UNO_SET_THROW );
+ m_xPlayer.set( avmedia::MediaWindow::createPlayer( aURL.Complete, aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_REFERRER, OUString()) ), css::uno::UNO_SET_THROW );
// OK- we can start async playing ...
// Count this request and initialize self-holder against dying by uno ref count ...
- m_xSelfHold.set(static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY);
+ m_xSelfHold.set(getXWeak());
m_xPlayer->start();
m_aUpdateIdle.SetPriority( TaskPriority::HIGH_IDLE );
m_aUpdateIdle.Start();
@@ -243,8 +241,8 @@ OUString SAL_CALL SoundHandler::detect( css::uno::Sequence< css::beans::Property
// Analyze given descriptor to find filename or input stream or ...
utl::MediaDescriptor aDescriptor(lDescriptor);
- OUString sURL = aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_URL(), OUString());
- OUString sReferer = aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_REFERRER(), OUString());
+ OUString sURL = aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_URL, OUString());
+ OUString sReferer = aDescriptor.getUnpackedValueOrDefault(utl::MediaDescriptor::PROP_REFERRER, OUString());
if (
!sURL.isEmpty() &&
@@ -255,8 +253,8 @@ OUString SAL_CALL SoundHandler::detect( css::uno::Sequence< css::beans::Property
// I think we can the following ones:
// a) look for given extension of url to map our type decision HARD CODED!!!
// b) return preferred type every time... it's easy :-)
- sTypeName = "wav_Wave_Audio_File";
- aDescriptor[utl::MediaDescriptor::PROP_TYPENAME()] <<= sTypeName;
+ sTypeName = u"wav_Wave_Audio_File"_ustr;
+ aDescriptor[utl::MediaDescriptor::PROP_TYPENAME] <<= sTypeName;
aDescriptor >> lDescriptor;
}
@@ -276,7 +274,7 @@ OUString SAL_CALL SoundHandler::detect( css::uno::Sequence< css::beans::Property
IMPL_LINK_NOARG(SoundHandler, implts_PlayerNotify, Timer *, void)
{
// SAFE {
- ::osl::ClearableMutexGuard aLock( GetMutex() );
+ ::osl::ClearableMutexGuard aLock( m_aMutex );
if (m_xPlayer.is() && m_xPlayer->isPlaying() && m_xPlayer->getMediaTime() < m_xPlayer->getDuration())
{
diff --git a/avmedia/source/framework/soundhandler.hxx b/avmedia/source/framework/soundhandler.hxx
index 8a1dfde2e457..648cbe59dd4b 100644
--- a/avmedia/source/framework/soundhandler.hxx
+++ b/avmedia/source/framework/soundhandler.hxx
@@ -29,12 +29,12 @@
#include <com/sun/star/lang/XServiceInfo.hpp>
+#include <cppuhelper/basemutex.hxx>
#include <cppuhelper/weak.hxx>
#include <vcl/timer.hxx>
#include <vcl/idle.hxx>
#include <tools/link.hxx>
-#include <toolkit/helper/mutexhelper.hxx>
namespace avmedia{
@@ -56,7 +56,7 @@ class SoundHandler : // interfaces
, public css::document::XExtendedFilterDetection
// baseclasses
// Order is necessary for right initialization!
- , private MutexHelper
+ , private cppu::BaseMutex
, public ::cppu::OWeakObject
{
// public methods
@@ -68,8 +68,8 @@ class SoundHandler : // interfaces
// XInterface, XTypeProvider, XServiceInfo
virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type& aType ) override;
- virtual void SAL_CALL acquire() throw() override;
- virtual void SAL_CALL release() throw() override;
+ virtual void SAL_CALL acquire() noexcept override;
+ virtual void SAL_CALL release() noexcept override;
virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes () override;
virtual css::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId() override;
diff --git a/avmedia/source/gstreamer/gstframegrabber.cxx b/avmedia/source/gstreamer/gstframegrabber.cxx
index c1341d8d6ad4..d8f96bd5e568 100644
--- a/avmedia/source/gstreamer/gstframegrabber.cxx
+++ b/avmedia/source/gstreamer/gstframegrabber.cxx
@@ -31,8 +31,7 @@
#include <string>
-#define AVMEDIA_GST_FRAMEGRABBER_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.FrameGrabber_GStreamer"
-#define AVMEDIA_GST_FRAMEGRABBER_SERVICENAME "com.sun.star.media.FrameGrabber_GStreamer"
+constexpr OUString AVMEDIA_GST_FRAMEGRABBER_SERVICENAME = u"com.sun.star.media.FrameGrabber_GStreamer"_ustr;
using namespace ::com::sun::star;
@@ -48,14 +47,11 @@ void FrameGrabber::disposePipeline()
}
}
-FrameGrabber::FrameGrabber( std::u16string_view rURL ) :
- FrameGrabber_BASE()
+FrameGrabber::FrameGrabber( std::u16string_view rURL )
{
- gchar *pPipelineStr;
- pPipelineStr = g_strdup_printf(
- "uridecodebin uri=%s ! videoconvert ! videoscale ! appsink "
- "name=sink caps=\"video/x-raw,format=RGB,pixel-aspect-ratio=1/1\"",
- OUStringToOString( rURL, RTL_TEXTENCODING_UTF8 ).getStr() );
+ const char pPipelineStr[] =
+ "uridecodebin name=source ! videoconvert ! videoscale ! appsink "
+ "name=sink caps=\"video/x-raw,format=RGB,pixel-aspect-ratio=1/1\"";
GError *pError = nullptr;
mpPipeline = gst_parse_launch( pPipelineStr, &pError );
@@ -66,6 +62,12 @@ FrameGrabber::FrameGrabber( std::u16string_view rURL ) :
}
if( mpPipeline ) {
+
+ if (GstElement *pUriDecode = gst_bin_get_by_name(GST_BIN(mpPipeline), "source"))
+ g_object_set(pUriDecode, "uri", OUStringToOString(rURL, RTL_TEXTENCODING_UTF8).getStr(), nullptr);
+ else
+ g_warning("Missing 'source' element in gstreamer pipeline");
+
// pre-roll
switch( gst_element_set_state( mpPipeline, GST_STATE_PAUSED ) ) {
case GST_STATE_CHANGE_FAILURE:
@@ -87,7 +89,7 @@ FrameGrabber::~FrameGrabber()
disposePipeline();
}
-FrameGrabber* FrameGrabber::create( std::u16string_view rURL )
+rtl::Reference<FrameGrabber> FrameGrabber::create( std::u16string_view rURL )
{
return new FrameGrabber( rURL );
}
@@ -147,7 +149,7 @@ uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMe
pData = aMapInfo.data;
int nStride = GST_ROUND_UP_4( nWidth * 3 );
- BitmapEx aBmp = vcl::bitmap::CreateFromData(pData, nWidth, nHeight, nStride, 24 );
+ BitmapEx aBmp = vcl::bitmap::CreateFromData(pData, nWidth, nHeight, nStride, /*nBitsPerPixel*/24);
gst_buffer_unmap( pBuf, &aMapInfo );
xRet = Graphic( aBmp ).GetXGraphic();
@@ -158,7 +160,7 @@ uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMe
OUString SAL_CALL FrameGrabber::getImplementationName( )
{
- return AVMEDIA_GST_FRAMEGRABBER_IMPLEMENTATIONNAME;
+ return u"com.sun.star.comp.avmedia.FrameGrabber_GStreamer"_ustr;
}
sal_Bool SAL_CALL FrameGrabber::supportsService( const OUString& ServiceName )
diff --git a/avmedia/source/gstreamer/gstframegrabber.hxx b/avmedia/source/gstreamer/gstframegrabber.hxx
index b99401526506..c706192efd7d 100644
--- a/avmedia/source/gstreamer/gstframegrabber.hxx
+++ b/avmedia/source/gstreamer/gstframegrabber.hxx
@@ -26,6 +26,7 @@
#include "gstplayer.hxx"
#include <com/sun/star/media/XFrameGrabber.hpp>
#include <cppuhelper/implbase.hxx>
+#include <rtl/ref.hxx>
namespace avmedia::gstreamer {
@@ -43,7 +44,7 @@ public:
const FrameGrabber& operator=(const FrameGrabber&) =delete;
// static create method instead of public Ctor
- static FrameGrabber* create( std::u16string_view rURL );
+ static rtl::Reference<FrameGrabber> create( std::u16string_view rURL );
virtual ~FrameGrabber() override;
diff --git a/avmedia/source/gstreamer/gstmanager.cxx b/avmedia/source/gstreamer/gstmanager.cxx
index bc7c917dc99d..54d23541676e 100644
--- a/avmedia/source/gstreamer/gstmanager.cxx
+++ b/avmedia/source/gstreamer/gstmanager.cxx
@@ -23,6 +23,7 @@
#include "gstplayer.hxx"
#include <tools/urlobj.hxx>
+#include <rtl/ref.hxx>
using namespace ::com::sun::star;
@@ -38,19 +39,18 @@ Manager::~Manager()
uno::Reference< media::XPlayer > SAL_CALL Manager::createPlayer( const OUString& rURL )
{
- Player* pPlayer( new Player );
- uno::Reference< media::XPlayer > xRet( pPlayer );
+ rtl::Reference<Player> pPlayer( new Player );
const INetURLObject aURL( rURL );
if( !pPlayer->create( aURL.GetMainURL( INetURLObject::DecodeMechanism::Unambiguous ) ) )
- xRet.clear();
+ pPlayer.clear();
- return xRet;
+ return pPlayer;
}
OUString SAL_CALL Manager::getImplementationName( )
{
- return "com.sun.star.comp.avmedia.Manager_GStreamer";
+ return "com.sun.star.comp.media.Manager_GStreamer";
}
sal_Bool SAL_CALL Manager::supportsService( const OUString& ServiceName )
diff --git a/avmedia/source/gstreamer/gstplayer.cxx b/avmedia/source/gstreamer/gstplayer.cxx
index 4efbc6497b09..1a91a689299e 100644
--- a/avmedia/source/gstreamer/gstplayer.cxx
+++ b/avmedia/source/gstreamer/gstplayer.cxx
@@ -25,10 +25,13 @@
#include <cstddef>
#include <cstring>
#include <map>
+#include <mutex>
#include <set>
#include <vector>
#include <math.h>
+#include <com/sun/star/text/GraphicCrop.hpp>
+
#include <cppuhelper/supportsservice.hxx>
#include <sal/log.hxx>
#include <rtl/string.hxx>
@@ -36,15 +39,14 @@
#include <vcl/svapp.hxx>
#include <vcl/syschild.hxx>
#include <vcl/sysdata.hxx>
+#include <vcl/graph.hxx>
+#include <avmedia/mediaitem.hxx>
#include "gstplayer.hxx"
#include "gstframegrabber.hxx"
#include "gstwindow.hxx"
#include <gst/video/videooverlay.h>
-#define AVMEDIA_GST_PLAYER_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Player_GStreamer"
-#define AVMEDIA_GST_PLAYER_SERVICENAME "com.sun.star.media.Player_GStreamer"
-
#include <gst/pbutils/missing-plugins.h>
#include <gst/pbutils/pbutils.h>
@@ -95,7 +97,7 @@ private:
DECL_STATIC_LINK(MissingPluginInstaller, launchUi, void*, void);
- osl::Mutex mutex_;
+ std::recursive_mutex mutex_;
std::set<OString> reported_;
std::map<OString, std::set<rtl::Reference<Player>>> queued_;
rtl::Reference<MissingPluginInstallerThread> currentThread_;
@@ -107,7 +109,7 @@ private:
MissingPluginInstaller::~MissingPluginInstaller() {
- osl::MutexGuard g(mutex_);
+ std::unique_lock g(mutex_);
SAL_WARN_IF(currentThread_.is(), "avmedia.gstreamer", "unjoined thread");
inCleanUp_ = true;
}
@@ -135,7 +137,7 @@ void MissingPluginInstaller::report(
rtl::Reference<MissingPluginInstallerThread> join;
rtl::Reference<MissingPluginInstallerThread> launch;
{
- osl::MutexGuard g(mutex_);
+ std::unique_lock g(mutex_);
if (reported_.find(detStr) != reported_.end()) {
return;
}
@@ -180,7 +182,7 @@ void eraseSource(std::set<rtl::Reference<Player>> & set, Player const * source)
void MissingPluginInstaller::detach(Player const * source) {
rtl::Reference<MissingPluginInstallerThread> join;
{
- osl::MutexGuard g(mutex_);
+ std::unique_lock g(mutex_);
if (inCleanUp_) {
// Guard against ~MissingPluginInstaller with erroneously un-joined
// currentThread_ (thus non-empty currentSources_) calling
@@ -242,17 +244,19 @@ IMPL_STATIC_LINK(MissingPluginInstaller, launchUi, void *, p, void)
}
-struct TheMissingPluginInstaller:
- public rtl::Static<MissingPluginInstaller, TheMissingPluginInstaller>
-{};
+MissingPluginInstaller& TheMissingPluginInstaller()
+{
+ static MissingPluginInstaller theInstaller;
+ return theInstaller;
+}
void MissingPluginInstallerThread::execute() {
- MissingPluginInstaller & inst = TheMissingPluginInstaller::get();
+ MissingPluginInstaller & inst = TheMissingPluginInstaller();
for (;;) {
std::vector<OString> details;
{
- osl::MutexGuard g(inst.mutex_);
+ std::unique_lock g(inst.mutex_);
assert(!inst.currentDetails_.empty());
details.swap(inst.currentDetails_);
}
@@ -265,7 +269,7 @@ void MissingPluginInstallerThread::execute() {
args.push_back(nullptr);
gst_install_plugins_sync(args.data(), nullptr);
{
- osl::MutexGuard g(inst.mutex_);
+ std::unique_lock g(inst.mutex_);
if (inst.queued_.empty() || inst.launchNewThread_) {
inst.launchNewThread_ = true;
break;
@@ -285,7 +289,6 @@ Player::Player() :
mbUseGtkSink( false ),
mbFakeVideo (false ),
mnUnmutedVolume( 0 ),
- mbPlayPending ( false ),
mbMuted( false ),
mbLooping( false ),
mbInitialized( false ),
@@ -328,7 +331,7 @@ Player::~Player()
void SAL_CALL Player::disposing()
{
- TheMissingPluginInstaller::get().detach(this);
+ TheMissingPluginInstaller().detach(this);
::osl::MutexGuard aGuard(m_aMutex);
@@ -385,7 +388,6 @@ void Player::processMessage( GstMessage *message )
switch( GST_MESSAGE_TYPE( message ) ) {
case GST_MESSAGE_EOS:
gst_element_set_state( mpPlaybin, GST_STATE_READY );
- mbPlayPending = false;
if (mbLooping)
start();
break;
@@ -401,9 +403,6 @@ void Player::processMessage( GstMessage *message )
{
gst_video_overlay_expose(mpXOverlay);
}
-
- if (mbPlayPending)
- mbPlayPending = ((newstate == GST_STATE_READY) || (newstate == GST_STATE_PAUSED));
}
break;
default:
@@ -447,6 +446,28 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
"error: '" << error->message << "' debug: '"
<< error_debug << "'");
}
+ else if ( GST_MESSAGE_TYPE( message ) == GST_MESSAGE_WARNING )
+ {
+ GError* error;
+ gchar* error_debug;
+
+ gst_message_parse_warning( message, &error, &error_debug );
+ SAL_WARN(
+ "avmedia.gstreamer",
+ "warning: '" << error->message << "' debug: '"
+ << error_debug << "'");
+ }
+ else if ( GST_MESSAGE_TYPE( message ) == GST_MESSAGE_INFO )
+ {
+ GError* error;
+ gchar* error_debug;
+
+ gst_message_parse_info( message, &error, &error_debug );
+ SAL_WARN(
+ "avmedia.gstreamer",
+ "info: '" << error->message << "' debug: '"
+ << error_debug << "'");
+ }
#endif
if (!mbUseGtkSink)
@@ -512,7 +533,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
maSizeCondition.set();
}
} else if (gst_is_missing_plugin_message(message)) {
- TheMissingPluginInstaller::get().report(this, message);
+ TheMissingPluginInstaller().report(this, message);
if( mnWidth == 0 ) {
// an error occurred, set condition so that OOo thread doesn't wait for us
maSizeCondition.set();
@@ -532,7 +553,6 @@ void Player::preparePlaybin( std::u16string_view rURL, GstElement *pSink )
if (mpPlaybin != nullptr)
{
gst_element_set_state( mpPlaybin, GST_STATE_NULL );
- mbPlayPending = false;
g_object_unref( mpPlaybin );
}
@@ -597,7 +617,6 @@ bool Player::create( const OUString& rURL )
preparePlaybin( rURL, gst_element_factory_make( "fakesink", nullptr ) );
gst_element_set_state( mpPlaybin, GST_STATE_PAUSED );
- mbPlayPending = false;
bRet = true;
}
@@ -610,7 +629,6 @@ bool Player::create( const OUString& rURL )
return bRet;
}
-
void SAL_CALL Player::start()
{
::osl::MutexGuard aGuard(m_aMutex);
@@ -619,10 +637,10 @@ void SAL_CALL Player::start()
if( mbInitialized && mpPlaybin != nullptr )
{
gst_element_set_state( mpPlaybin, GST_STATE_PLAYING );
- mbPlayPending = true;
}
-}
+ SAL_INFO( "avmedia.gstreamer", AVVERSION "start " << mpPlaybin );
+}
void SAL_CALL Player::stop()
{
@@ -632,29 +650,24 @@ void SAL_CALL Player::stop()
if( mpPlaybin )
gst_element_set_state( mpPlaybin, GST_STATE_PAUSED );
- mbPlayPending = false;
SAL_INFO( "avmedia.gstreamer", AVVERSION "stop " << mpPlaybin );
}
-
sal_Bool SAL_CALL Player::isPlaying()
{
::osl::MutexGuard aGuard(m_aMutex);
- bool bRet = mbPlayPending;
+ bool bRet = false;
- // return whether the pipeline is in PLAYING STATE or not
- if( !mbPlayPending && mbInitialized && mpPlaybin )
+ // return whether the pipeline target is PLAYING STATE or not
+ if (mbInitialized && mpPlaybin)
{
- bRet = GST_STATE( mpPlaybin ) == GST_STATE_PLAYING;
+ bRet = GST_STATE_TARGET(mpPlaybin) == GST_STATE_PLAYING;
}
- SAL_INFO( "avmedia.gstreamer", AVVERSION "isPlaying " << bRet );
-
return bRet;
}
-
double SAL_CALL Player::getDuration()
{
::osl::MutexGuard aGuard(m_aMutex);
@@ -850,7 +863,7 @@ uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( co
// tdf#124027: the position of embedded window is identical w/ the position
// of media object in all other vclplugs (kf5, gen), in gtk3 w/o gtksink it
// needs to be translated
- if (pEnvData->toolkit == SystemEnvData::Toolkit::Gtk3)
+ if (pEnvData->toolkit == SystemEnvData::Toolkit::Gtk)
{
Point aPoint = pParentWindow->GetPosPixel();
maArea.X = aPoint.getX();
@@ -862,7 +875,7 @@ uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( co
GstElement *pVideosink = static_cast<GstElement*>(pParentWindow->CreateGStreamerSink());
if (pVideosink)
{
- if (pEnvData->toolkit == SystemEnvData::Toolkit::Gtk3)
+ if (pEnvData->toolkit == SystemEnvData::Toolkit::Gtk)
mbUseGtkSink = true;
}
else
@@ -880,11 +893,40 @@ uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( co
g_object_set(G_OBJECT(mpPlaybin), "video-sink", pVideosink, nullptr);
g_object_set(G_OBJECT(mpPlaybin), "force-aspect-ratio", FALSE, nullptr);
- mnWindowID = pEnvData->aWindow;
- mpDisplay = pEnvData->pDisplay;
- SAL_INFO( "avmedia.gstreamer", AVVERSION "set window id to " << static_cast<int>(mnWindowID) << " XOverlay " << mpXOverlay);
+ if ((rArguments.getLength() >= 4) && (rArguments[3] >>= pIntPtr) && pIntPtr)
+ {
+ auto pItem = reinterpret_cast<const avmedia::MediaItem*>(pIntPtr);
+ Graphic aGraphic = pItem->getGraphic();
+ const text::GraphicCrop& rCrop = pItem->getCrop();
+ if (!aGraphic.IsNone() && (rCrop.Bottom > 0 || rCrop.Left > 0 || rCrop.Right > 0 || rCrop.Top > 0))
+ {
+ // The media item has a non-empty cropping set. Try to crop the video accordingly.
+ Size aPref = aGraphic.GetPrefSize();
+ Size aPixel = aGraphic.GetSizePixel();
+ tools::Long nLeft = aPixel.getWidth() * rCrop.Left / aPref.getWidth();
+ tools::Long nTop = aPixel.getHeight() * rCrop.Top / aPref.getHeight();
+ tools::Long nRight = aPixel.getWidth() * rCrop.Right / aPref.getWidth();
+ tools::Long nBottom = aPixel.getHeight() * rCrop.Bottom / aPref.getHeight();
+ GstElement* pVideoFilter = gst_element_factory_make("videocrop", nullptr);
+ if (pVideoFilter)
+ {
+ g_object_set(G_OBJECT(pVideoFilter), "left", nLeft, nullptr);
+ g_object_set(G_OBJECT(pVideoFilter), "top", nTop, nullptr);
+ g_object_set(G_OBJECT(pVideoFilter), "right", nRight, nullptr);
+ g_object_set(G_OBJECT(pVideoFilter), "bottom", nBottom, nullptr);
+ g_object_set(G_OBJECT(mpPlaybin), "video-filter", pVideoFilter, nullptr);
+ }
+ }
+ }
+
+ if (!mbUseGtkSink)
+ {
+ mnWindowID = pEnvData->GetWindowHandle(pParentWindow->ImplGetFrame());
+ mpDisplay = pEnvData->pDisplay;
+ SAL_INFO( "avmedia.gstreamer", AVVERSION "set window id to " << static_cast<int>(mnWindowID) << " XOverlay " << mpXOverlay);
+ }
gst_element_set_state( mpPlaybin, GST_STATE_PAUSED );
- if ( mpXOverlay != nullptr )
+ if (!mbUseGtkSink && mpXOverlay)
gst_video_overlay_set_window_handle( mpXOverlay, mnWindowID );
}
@@ -894,12 +936,12 @@ uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( co
uno::Reference< media::XFrameGrabber > SAL_CALL Player::createFrameGrabber()
{
::osl::MutexGuard aGuard(m_aMutex);
- FrameGrabber* pFrameGrabber = nullptr;
+ rtl::Reference<FrameGrabber> pFrameGrabber;
const awt::Size aPrefSize( getPreferredPlayerWindowSize() );
if( ( aPrefSize.Width > 0 ) && ( aPrefSize.Height > 0 ) )
pFrameGrabber = FrameGrabber::create( maURL );
- SAL_INFO( "avmedia.gstreamer", AVVERSION "created FrameGrabber " << pFrameGrabber );
+ SAL_INFO( "avmedia.gstreamer", AVVERSION "created FrameGrabber " << pFrameGrabber.get() );
return pFrameGrabber;
}
@@ -907,7 +949,7 @@ uno::Reference< media::XFrameGrabber > SAL_CALL Player::createFrameGrabber()
OUString SAL_CALL Player::getImplementationName()
{
- return AVMEDIA_GST_PLAYER_IMPLEMENTATIONNAME;
+ return u"com.sun.star.comp.avmedia.Player_GStreamer"_ustr;
}
@@ -919,7 +961,7 @@ sal_Bool SAL_CALL Player::supportsService( const OUString& ServiceName )
uno::Sequence< OUString > SAL_CALL Player::getSupportedServiceNames()
{
- return { AVMEDIA_GST_PLAYER_SERVICENAME };
+ return { u"com.sun.star.media.Player_GStreamer"_ustr };
}
} // namespace
diff --git a/avmedia/source/gstreamer/gstplayer.hxx b/avmedia/source/gstreamer/gstplayer.hxx
index a82dac3f2b39..2694ac00ce7e 100644
--- a/avmedia/source/gstreamer/gstplayer.hxx
+++ b/avmedia/source/gstreamer/gstplayer.hxx
@@ -86,7 +86,6 @@ private:
bool mbFakeVideo;
gdouble mnUnmutedVolume;
- bool mbPlayPending;
bool mbMuted;
bool mbLooping;
bool mbInitialized;
diff --git a/avmedia/source/gstreamer/gstwindow.cxx b/avmedia/source/gstreamer/gstwindow.cxx
index 61f1b6a4cb61..2d9aec0418b3 100644
--- a/avmedia/source/gstreamer/gstwindow.cxx
+++ b/avmedia/source/gstreamer/gstwindow.cxx
@@ -22,10 +22,9 @@
#include <cppuhelper/supportsservice.hxx>
#include "gstwindow.hxx"
-#include "gstplayer.hxx"
-#define AVMEDIA_GST_WINDOW_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Window_GStreamer"
-#define AVMEDIA_GST_WINDOW_SERVICENAME "com.sun.star.media.Window_GStreamer"
+constexpr OUString AVMEDIA_GST_WINDOW_IMPLEMENTATIONNAME = u"com.sun.star.comp.avmedia.Window_GStreamer"_ustr;
+constexpr OUString AVMEDIA_GST_WINDOW_SERVICENAME = u"com.sun.star.media.Window_GStreamer"_ustr;
using namespace ::com::sun::star;
diff --git a/avmedia/source/gstreamer/gstwindow.hxx b/avmedia/source/gstreamer/gstwindow.hxx
index c9d633d5434f..ff8a7cc91566 100644
--- a/avmedia/source/gstreamer/gstwindow.hxx
+++ b/avmedia/source/gstreamer/gstwindow.hxx
@@ -19,10 +19,10 @@
#pragma once
-#include "gstcommon.hxx"
#include <cppuhelper/implbase.hxx>
#include <cppuhelper/interfacecontainer.h>
+#include <com/sun/star/lang/XServiceInfo.hpp>
#include <com/sun/star/media/XPlayerWindow.hpp>
namespace avmedia::gstreamer {
diff --git a/avmedia/source/gtk/avmediagtk.component b/avmedia/source/gtk/avmediagtk.component
new file mode 100644
index 000000000000..e3930dc9e65d
--- /dev/null
+++ b/avmedia/source/gtk/avmediagtk.component
@@ -0,0 +1,16 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+-->
+<component loader="com.sun.star.loader.SharedLibrary" environment="@CPPU_ENV@"
+ xmlns="http://openoffice.org/2010/uno-components">
+ <implementation name="com.sun.star.comp.media.Manager_Gtk"
+ constructor="com_sun_star_comp_media_Manager_Gtk_get_implementation">
+ <service name="com.sun.star.comp.avmedia.Manager_Gtk"/>
+ </implementation>
+</component>
diff --git a/avmedia/source/gtk/gstwindow.cxx b/avmedia/source/gtk/gstwindow.cxx
new file mode 100644
index 000000000000..48c70df98e7d
--- /dev/null
+++ b/avmedia/source/gtk/gstwindow.cxx
@@ -0,0 +1,12 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include "../gstreamer/gstwindow.cxx"
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/avmedia/source/gtk/gtkmanager.cxx b/avmedia/source/gtk/gtkmanager.cxx
new file mode 100644
index 000000000000..fe823c1f49ed
--- /dev/null
+++ b/avmedia/source/gtk/gtkmanager.cxx
@@ -0,0 +1,58 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include <cppuhelper/supportsservice.hxx>
+
+#include "gtkmanager.hxx"
+#include "gtkplayer.hxx"
+
+#include <tools/urlobj.hxx>
+#include <rtl/ref.hxx>
+
+using namespace ::com::sun::star;
+
+namespace avmedia::gtk
+{
+Manager::Manager() {}
+
+Manager::~Manager() {}
+
+uno::Reference<media::XPlayer> SAL_CALL Manager::createPlayer(const OUString& rURL)
+{
+ const INetURLObject aURL(rURL);
+ OUString sMainURL = aURL.GetMainURL(INetURLObject::DecodeMechanism::Unambiguous);
+
+ rtl::Reference<GtkPlayer> xPlayer(new GtkPlayer);
+ if (!xPlayer->create(sMainURL))
+ xPlayer.clear();
+ return xPlayer;
+}
+
+OUString SAL_CALL Manager::getImplementationName() { return "com.sun.star.comp.media.Manager_Gtk"; }
+
+sal_Bool SAL_CALL Manager::supportsService(const OUString& ServiceName)
+{
+ return cppu::supportsService(this, ServiceName);
+}
+
+uno::Sequence<OUString> SAL_CALL Manager::getSupportedServiceNames()
+{
+ return { "com.sun.star.media.Manager" };
+}
+
+} // namespace
+
+extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface*
+com_sun_star_comp_media_Manager_Gtk_get_implementation(css::uno::XComponentContext*,
+ css::uno::Sequence<css::uno::Any> const&)
+{
+ return cppu::acquire(new avmedia::gtk::Manager());
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/avmedia/source/gtk/gtkmanager.hxx b/avmedia/source/gtk/gtkmanager.hxx
new file mode 100644
index 000000000000..9cf6d93f5b68
--- /dev/null
+++ b/avmedia/source/gtk/gtkmanager.hxx
@@ -0,0 +1,34 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#pragma once
+
+#include <cppuhelper/implbase.hxx>
+#include <com/sun/star/lang/XServiceInfo.hpp>
+#include <com/sun/star/media/XManager.hpp>
+#include <com/sun/star/uno/XComponentContext.hpp>
+
+namespace avmedia::gtk
+{
+class Manager : public cppu::WeakImplHelper<css::media::XManager, css::lang::XServiceInfo>
+{
+public:
+ explicit Manager();
+ virtual ~Manager() override;
+
+ virtual css::uno::Reference<css::media::XPlayer>
+ SAL_CALL createPlayer(const OUString& aURL) override;
+
+ virtual OUString SAL_CALL getImplementationName() override;
+ virtual sal_Bool SAL_CALL supportsService(const OUString& ServiceName) override;
+ virtual css::uno::Sequence<OUString> SAL_CALL getSupportedServiceNames() override;
+};
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/avmedia/source/gtk/gtkplayer.cxx b/avmedia/source/gtk/gtkplayer.cxx
new file mode 100644
index 000000000000..4dca3e202a24
--- /dev/null
+++ b/avmedia/source/gtk/gtkplayer.cxx
@@ -0,0 +1,469 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include <sal/config.h>
+
+#include <mutex>
+
+#include <cppuhelper/supportsservice.hxx>
+#include <sal/log.hxx>
+#include <rtl/string.hxx>
+#include <tools/link.hxx>
+#include <vcl/BitmapTools.hxx>
+#include <vcl/graph.hxx>
+#include <vcl/svapp.hxx>
+#include <vcl/syschild.hxx>
+#include <vcl/sysdata.hxx>
+#include <vcl/timer.hxx>
+
+#include <gstwindow.hxx>
+#include "gtkplayer.hxx"
+
+#include <gtk/gtk.h>
+
+constexpr OUStringLiteral AVMEDIA_GTK_PLAYER_IMPLEMENTATIONNAME
+ = u"com.sun.star.comp.avmedia.Player_Gtk";
+constexpr OUString AVMEDIA_GTK_PLAYER_SERVICENAME = u"com.sun.star.media.Player_Gtk"_ustr;
+
+using namespace ::com::sun::star;
+
+namespace avmedia::gtk
+{
+GtkPlayer::GtkPlayer()
+ : GtkPlayer_BASE(m_aMutex)
+ , m_lListener(m_aMutex)
+ , m_pStream(nullptr)
+ , m_pVideo(nullptr)
+ , m_nNotifySignalId(0)
+ , m_nInvalidateSizeSignalId(0)
+ , m_nTimeoutId(0)
+ , m_nUnmutedVolume(0)
+{
+}
+
+GtkPlayer::~GtkPlayer() { disposing(); }
+
+static gboolean gtk_media_stream_unref(gpointer user_data)
+{
+ g_object_unref(user_data);
+ return FALSE;
+}
+
+void GtkPlayer::cleanup()
+{
+ if (m_pVideo)
+ {
+ gtk_widget_unparent(m_pVideo);
+ m_pVideo = nullptr;
+ }
+
+ if (m_pStream)
+ {
+ uninstallNotify();
+
+ // shouldn't have to attempt this unref on idle, but with gtk4-4.4.1 I get
+ // intermittent "instance of invalid non-instantiable type '(null)'"
+ // on some mysterious gst dbus callback
+ if (g_main_context_default())
+ g_idle_add_full(G_PRIORITY_DEFAULT_IDLE, gtk_media_stream_unref, m_pStream, nullptr);
+ else
+ g_object_unref(m_pStream);
+ m_pStream = nullptr;
+ }
+}
+
+void SAL_CALL GtkPlayer::disposing()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ stop();
+
+ cleanup();
+}
+
+static void do_notify(GtkPlayer* pThis)
+{
+ rtl::Reference<GtkPlayer> xThis(pThis);
+ xThis->notifyListeners();
+ xThis->uninstallNotify();
+}
+
+static void invalidate_size_cb(GdkPaintable* /*pPaintable*/, GtkPlayer* pThis) { do_notify(pThis); }
+
+static void notify_cb(GtkMediaStream* /*pStream*/, GParamSpec* pspec, GtkPlayer* pThis)
+{
+ if (g_str_equal(pspec->name, "prepared") || g_str_equal(pspec->name, "error"))
+ do_notify(pThis);
+}
+
+static bool timeout_cb(GtkPlayer* pThis)
+{
+ do_notify(pThis);
+ return false;
+}
+
+void GtkPlayer::installNotify()
+{
+ if (m_nNotifySignalId)
+ return;
+ m_nNotifySignalId = g_signal_connect(m_pStream, "notify", G_CALLBACK(notify_cb), this);
+ // notify should be enough, but there is an upstream bug so also try "invalidate-size" and add a timeout for
+ // audio-only case where that won't happen, see: https://gitlab.gnome.org/GNOME/gtk/-/merge_requests/4513
+ m_nInvalidateSizeSignalId
+ = g_signal_connect(m_pStream, "invalidate-size", G_CALLBACK(invalidate_size_cb), this);
+ m_nTimeoutId = g_timeout_add_seconds(10, G_SOURCE_FUNC(timeout_cb), this);
+}
+
+void GtkPlayer::uninstallNotify()
+{
+ if (!m_nNotifySignalId)
+ return;
+ g_signal_handler_disconnect(m_pStream, m_nNotifySignalId);
+ m_nNotifySignalId = 0;
+ g_signal_handler_disconnect(m_pStream, m_nInvalidateSizeSignalId);
+ m_nInvalidateSizeSignalId = 0;
+ g_source_remove(m_nTimeoutId);
+ m_nTimeoutId = 0;
+}
+
+bool GtkPlayer::create(const OUString& rURL)
+{
+ bool bRet = false;
+
+ cleanup();
+
+ if (!rURL.isEmpty())
+ {
+ GFile* pFile = g_file_new_for_uri(OUStringToOString(rURL, RTL_TEXTENCODING_UTF8).getStr());
+ m_pStream = gtk_media_file_new_for_file(pFile);
+ g_object_unref(pFile);
+
+ bRet = gtk_media_stream_get_error(m_pStream) == nullptr;
+ }
+
+ if (bRet)
+ m_aURL = rURL;
+ else
+ m_aURL.clear();
+
+ return bRet;
+}
+
+void GtkPlayer::notifyListeners()
+{
+ comphelper::OInterfaceContainerHelper2* pContainer
+ = m_lListener.getContainer(cppu::UnoType<css::media::XPlayerListener>::get());
+ if (!pContainer)
+ return;
+
+ css::lang::EventObject aEvent;
+ aEvent.Source = getXWeak();
+
+ comphelper::OInterfaceIteratorHelper2 pIterator(*pContainer);
+ while (pIterator.hasMoreElements())
+ {
+ css::uno::Reference<css::media::XPlayerListener> xListener(
+ static_cast<css::media::XPlayerListener*>(pIterator.next()));
+ xListener->preferredPlayerWindowSizeAvailable(aEvent);
+ }
+}
+
+void SAL_CALL GtkPlayer::start()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ if (m_pStream)
+ gtk_media_stream_play(m_pStream);
+}
+
+void SAL_CALL GtkPlayer::stop()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ if (m_pStream)
+ gtk_media_stream_pause(m_pStream);
+}
+
+sal_Bool SAL_CALL GtkPlayer::isPlaying()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ bool bRet = false;
+
+ if (m_pStream)
+ bRet = gtk_media_stream_get_playing(m_pStream);
+
+ return bRet;
+}
+
+double SAL_CALL GtkPlayer::getDuration()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ double duration = 0.0;
+
+ if (m_pStream)
+ duration = gtk_media_stream_get_duration(m_pStream) / 1000000.0;
+
+ return duration;
+}
+
+void SAL_CALL GtkPlayer::setMediaTime(double fTime)
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ if (!m_pStream)
+ return;
+
+ gint64 gst_position = llround(fTime * 1000000);
+
+ gtk_media_stream_seek(m_pStream, gst_position);
+
+ // on resetting back to zero the reported timestamp doesn't seem to get
+ // updated in a reasonable time, so on zero just force an update of
+ // timestamp to 0
+ if (gst_position == 0 && gtk_media_stream_is_prepared(m_pStream))
+ gtk_media_stream_update(m_pStream, gst_position);
+}
+
+double SAL_CALL GtkPlayer::getMediaTime()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ double position = 0.0;
+
+ if (m_pStream)
+ position = gtk_media_stream_get_timestamp(m_pStream) / 1000000.0;
+
+ return position;
+}
+
+void SAL_CALL GtkPlayer::setPlaybackLoop(sal_Bool bSet)
+{
+ osl::MutexGuard aGuard(m_aMutex);
+ gtk_media_stream_set_loop(m_pStream, bSet);
+}
+
+sal_Bool SAL_CALL GtkPlayer::isPlaybackLoop()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+ return gtk_media_stream_get_loop(m_pStream);
+}
+
+// gtk4-4.4.1 docs state: "Muting a stream will cause no audio to be played, but
+// it does not modify the volume. This means that muting and then unmuting the
+// stream will restore the volume settings." but that doesn't seem to be my
+// experience at all
+void SAL_CALL GtkPlayer::setMute(sal_Bool bSet)
+{
+ osl::MutexGuard aGuard(m_aMutex);
+ bool bMuted = gtk_media_stream_get_muted(m_pStream);
+ if (bMuted == static_cast<bool>(bSet))
+ return;
+ gtk_media_stream_set_muted(m_pStream, bSet);
+ if (!bSet)
+ setVolumeDB(m_nUnmutedVolume);
+}
+
+sal_Bool SAL_CALL GtkPlayer::isMute()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+ return gtk_media_stream_get_muted(m_pStream);
+}
+
+void SAL_CALL GtkPlayer::setVolumeDB(sal_Int16 nVolumeDB)
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ // range is -40 for silence to 0 for full volume
+ m_nUnmutedVolume = std::clamp<sal_Int16>(nVolumeDB, -40, 0);
+ double fValue = (m_nUnmutedVolume + 40) / 40.0;
+ gtk_media_stream_set_volume(m_pStream, fValue);
+}
+
+sal_Int16 SAL_CALL GtkPlayer::getVolumeDB()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ if (gtk_media_stream_get_muted(m_pStream))
+ return m_nUnmutedVolume;
+
+ double fVolume = gtk_media_stream_get_volume(m_pStream);
+
+ m_nUnmutedVolume = (fVolume * 40) - 40;
+
+ return m_nUnmutedVolume;
+}
+
+awt::Size SAL_CALL GtkPlayer::getPreferredPlayerWindowSize()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ awt::Size aSize(0, 0);
+
+ if (m_pStream)
+ {
+ aSize.Width = gdk_paintable_get_intrinsic_width(GDK_PAINTABLE(m_pStream));
+ aSize.Height = gdk_paintable_get_intrinsic_height(GDK_PAINTABLE(m_pStream));
+ }
+
+ return aSize;
+}
+
+uno::Reference<::media::XPlayerWindow>
+ SAL_CALL GtkPlayer::createPlayerWindow(const uno::Sequence<uno::Any>& rArguments)
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ uno::Reference<::media::XPlayerWindow> xRet;
+
+ if (rArguments.getLength() > 1)
+ rArguments[1] >>= m_aArea;
+
+ if (rArguments.getLength() <= 2)
+ {
+ xRet = new ::avmedia::gstreamer::Window;
+ return xRet;
+ }
+
+ sal_IntPtr pIntPtr = 0;
+ rArguments[2] >>= pIntPtr;
+ SystemChildWindow* pParentWindow = reinterpret_cast<SystemChildWindow*>(pIntPtr);
+ if (!pParentWindow)
+ return nullptr;
+
+ const SystemEnvData* pEnvData = pParentWindow->GetSystemData();
+ if (!pEnvData)
+ return nullptr;
+
+ m_pVideo = gtk_picture_new_for_paintable(GDK_PAINTABLE(m_pStream));
+#if GTK_CHECK_VERSION(4, 7, 2)
+ gtk_picture_set_content_fit(GTK_PICTURE(m_pVideo), GTK_CONTENT_FIT_FILL);
+#else
+ gtk_picture_set_keep_aspect_ratio(GTK_PICTURE(m_pVideo), false);
+#endif
+ gtk_widget_set_can_target(m_pVideo, false);
+ gtk_widget_set_vexpand(m_pVideo, true);
+ gtk_widget_set_hexpand(m_pVideo, true);
+
+ GtkWidget* pParent = static_cast<GtkWidget*>(pEnvData->pWidget);
+ gtk_widget_set_can_target(pParent, false);
+ gtk_grid_attach(GTK_GRID(pParent), m_pVideo, 0, 0, 1, 1);
+ // "‘void gtk_widget_show(GtkWidget*)’ is deprecated: Use 'gtk_widget_set_visible or
+ // gtk_window_present' instead":
+ SAL_WNODEPRECATED_DECLARATIONS_PUSH
+ gtk_widget_show(m_pVideo);
+ gtk_widget_show(pParent);
+ SAL_WNODEPRECATED_DECLARATIONS_POP
+
+ xRet = new ::avmedia::gstreamer::Window;
+
+ return xRet;
+}
+
+void SAL_CALL
+GtkPlayer::addPlayerListener(const css::uno::Reference<css::media::XPlayerListener>& rListener)
+{
+ m_lListener.addInterface(cppu::UnoType<css::media::XPlayerListener>::get(), rListener);
+ if (gtk_media_stream_is_prepared(m_pStream))
+ {
+ css::lang::EventObject aEvent;
+ aEvent.Source = getXWeak();
+ rListener->preferredPlayerWindowSizeAvailable(aEvent);
+ }
+ else
+ installNotify();
+}
+
+void SAL_CALL
+GtkPlayer::removePlayerListener(const css::uno::Reference<css::media::XPlayerListener>& rListener)
+{
+ m_lListener.removeInterface(cppu::UnoType<css::media::XPlayerListener>::get(), rListener);
+}
+
+namespace
+{
+class GtkFrameGrabber : public ::cppu::WeakImplHelper<css::media::XFrameGrabber>
+{
+private:
+ awt::Size m_aSize;
+ GtkMediaStream* m_pStream;
+
+public:
+ GtkFrameGrabber(GtkMediaStream* pStream, const awt::Size& rSize)
+ : m_aSize(rSize)
+ , m_pStream(pStream)
+ {
+ g_object_ref(m_pStream);
+ }
+
+ virtual ~GtkFrameGrabber() override { g_object_unref(m_pStream); }
+
+ // XFrameGrabber
+ virtual css::uno::Reference<css::graphic::XGraphic>
+ SAL_CALL grabFrame(double fMediaTime) override
+ {
+ gint64 gst_position = llround(fMediaTime * 1000000);
+ gtk_media_stream_seek(m_pStream, gst_position);
+
+ cairo_surface_t* surface
+ = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, m_aSize.Width, m_aSize.Height);
+
+ GtkSnapshot* snapshot = gtk_snapshot_new();
+ gdk_paintable_snapshot(GDK_PAINTABLE(m_pStream), snapshot, m_aSize.Width, m_aSize.Height);
+ GskRenderNode* node = gtk_snapshot_free_to_node(snapshot);
+
+ cairo_t* cr = cairo_create(surface);
+ gsk_render_node_draw(node, cr);
+ cairo_destroy(cr);
+
+ gsk_render_node_unref(node);
+
+ std::unique_ptr<BitmapEx> xBitmap(
+ vcl::bitmap::CreateFromCairoSurface(Size(m_aSize.Width, m_aSize.Height), surface));
+
+ cairo_surface_destroy(surface);
+
+ return Graphic(*xBitmap).GetXGraphic();
+ }
+};
+}
+
+uno::Reference<media::XFrameGrabber> SAL_CALL GtkPlayer::createFrameGrabber()
+{
+ osl::MutexGuard aGuard(m_aMutex);
+
+ rtl::Reference<GtkFrameGrabber> xFrameGrabber;
+
+ const awt::Size aPrefSize(getPreferredPlayerWindowSize());
+
+ if (aPrefSize.Width > 0 && aPrefSize.Height > 0)
+ xFrameGrabber.set(new GtkFrameGrabber(m_pStream, aPrefSize));
+
+ return xFrameGrabber;
+}
+
+OUString SAL_CALL GtkPlayer::getImplementationName()
+{
+ return AVMEDIA_GTK_PLAYER_IMPLEMENTATIONNAME;
+}
+
+sal_Bool SAL_CALL GtkPlayer::supportsService(const OUString& ServiceName)
+{
+ return cppu::supportsService(this, ServiceName);
+}
+
+uno::Sequence<OUString> SAL_CALL GtkPlayer::getSupportedServiceNames()
+{
+ return { AVMEDIA_GTK_PLAYER_SERVICENAME };
+}
+
+} // namespace
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/avmedia/source/gtk/gtkplayer.hxx b/avmedia/source/gtk/gtkplayer.hxx
new file mode 100644
index 000000000000..46e416e79e25
--- /dev/null
+++ b/avmedia/source/gtk/gtkplayer.hxx
@@ -0,0 +1,89 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#pragma once
+
+#include <sal/config.h>
+
+#include <string_view>
+
+#include <com/sun/star/lang/XServiceInfo.hpp>
+#include <com/sun/star/media/XPlayer.hpp>
+#include <com/sun/star/media/XPlayerNotifier.hpp>
+#include <comphelper/multicontainer2.hxx>
+#include <cppuhelper/compbase.hxx>
+#include <cppuhelper/basemutex.hxx>
+
+typedef struct _GtkMediaStream GtkMediaStream;
+typedef struct _GtkWidget GtkWidget;
+
+namespace avmedia::gtk
+{
+typedef cppu::WeakComponentImplHelper<css::media::XPlayer, css::media::XPlayerNotifier,
+ css::lang::XServiceInfo>
+ GtkPlayer_BASE;
+
+class GtkPlayer final : public cppu::BaseMutex, public GtkPlayer_BASE
+{
+public:
+ explicit GtkPlayer();
+ virtual ~GtkPlayer() override;
+
+ bool create(const OUString& rURL);
+
+ virtual void SAL_CALL start() override;
+ virtual void SAL_CALL stop() override;
+ virtual sal_Bool SAL_CALL isPlaying() override;
+ virtual double SAL_CALL getDuration() override;
+ virtual void SAL_CALL setMediaTime(double fTime) override;
+ virtual double SAL_CALL getMediaTime() override;
+ virtual void SAL_CALL setPlaybackLoop(sal_Bool bSet) override;
+ virtual sal_Bool SAL_CALL isPlaybackLoop() override;
+ virtual void SAL_CALL setMute(sal_Bool bSet) override;
+ virtual sal_Bool SAL_CALL isMute() override;
+ virtual void SAL_CALL setVolumeDB(sal_Int16 nVolumeDB) override;
+ virtual sal_Int16 SAL_CALL getVolumeDB() override;
+ virtual css::awt::Size SAL_CALL getPreferredPlayerWindowSize() override;
+ virtual css::uno::Reference<css::media::XPlayerWindow>
+ SAL_CALL createPlayerWindow(const css::uno::Sequence<css::uno::Any>& rArgs) override;
+ virtual css::uno::Reference<css::media::XFrameGrabber> SAL_CALL createFrameGrabber() override;
+
+ virtual OUString SAL_CALL getImplementationName() override;
+ virtual sal_Bool SAL_CALL supportsService(const OUString& ServiceName) override;
+ virtual css::uno::Sequence<OUString> SAL_CALL getSupportedServiceNames() override;
+
+ virtual void SAL_CALL
+ addPlayerListener(const css::uno::Reference<css::media::XPlayerListener>& rListener) override;
+ virtual void SAL_CALL removePlayerListener(
+ const css::uno::Reference<css::media::XPlayerListener>& rListener) override;
+
+ virtual void SAL_CALL disposing() final override;
+
+ void notifyListeners();
+ void installNotify();
+ void uninstallNotify();
+
+private:
+ void cleanup();
+
+ comphelper::OMultiTypeInterfaceContainerHelper2 m_lListener;
+
+ OUString m_aURL;
+ css::awt::Rectangle m_aArea; // Area of the player window.
+ GtkMediaStream* m_pStream;
+ GtkWidget* m_pVideo;
+ unsigned long m_nNotifySignalId;
+ unsigned long m_nInvalidateSizeSignalId;
+ unsigned long m_nTimeoutId;
+ sal_Int16 m_nUnmutedVolume;
+};
+
+} // namespace avmedia::gtk
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/avmedia/source/inc/mediamisc.hxx b/avmedia/source/inc/mediamisc.hxx
index 79c46ab404c4..f45f5b50da0b 100644
--- a/avmedia/source/inc/mediamisc.hxx
+++ b/avmedia/source/inc/mediamisc.hxx
@@ -19,9 +19,10 @@
#pragma once
+#include <comphelper/mediamimetype.hxx>
+
#include <unotools/resmgr.hxx>
-#define AVMEDIA_MANAGER_SERVICE_PREFERRED "com.sun.star.comp.avmedia.Manager_GStreamer"
#ifdef _WIN32
#define AVMEDIA_MANAGER_SERVICE_NAME "com.sun.star.comp.avmedia.Manager_DirectX"
#else
@@ -32,12 +33,9 @@
#endif
#endif
-// Mime types
-#define AVMEDIA_MIMETYPE_COMMON "application/vnd.sun.star.media"
-
-inline OUString AvmResId(const char* pId)
+inline OUString AvmResId(TranslateId aId)
{
- return Translate::get(pId, Translate::Create("avmedia"));
+ return Translate::get(aId, Translate::Create("avmedia"));
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/avmedia/source/macavf/framegrabber.mm b/avmedia/source/macavf/framegrabber.mm
index 7803fa4f1063..e0b8bad61171 100644
--- a/avmedia/source/macavf/framegrabber.mm
+++ b/avmedia/source/macavf/framegrabber.mm
@@ -67,7 +67,9 @@ uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMe
// convert the image to a TIFF-formatted byte-array
CFMutableDataRef pCFData = CFDataCreateMutable( kCFAllocatorDefault, 0 );
+ SAL_WNODEPRECATED_DECLARATIONS_PUSH // kUTTypeTIFF (12.0)
CGImageDestination* pCGImgDest = CGImageDestinationCreateWithData( pCFData, kUTTypeTIFF, 1, nullptr );
+ SAL_WNODEPRECATED_DECLARATIONS_POP
CGImageDestinationAddImage( pCGImgDest, pCGImage, nullptr );
CGImageDestinationFinalize( pCGImgDest );
CFRelease( pCGImgDest );
diff --git a/avmedia/source/macavf/manager.mm b/avmedia/source/macavf/manager.mm
index 44768b54c4e3..d240bb27a8d1 100644
--- a/avmedia/source/macavf/manager.mm
+++ b/avmedia/source/macavf/manager.mm
@@ -44,7 +44,7 @@ uno::Reference< media::XPlayer > SAL_CALL Manager::createPlayer( const OUString&
if( !xPlayer->create( aURL.GetMainURL( INetURLObject::DecodeMechanism::Unambiguous ) ) )
return {};
- return uno::Reference<media::XPlayer>(xPlayer.get());
+ return uno::Reference<media::XPlayer>(xPlayer);
}
diff --git a/avmedia/source/macavf/player.mm b/avmedia/source/macavf/player.mm
index 7fdc58247f50..401cba74c2d2 100644
--- a/avmedia/source/macavf/player.mm
+++ b/avmedia/source/macavf/player.mm
@@ -333,7 +333,7 @@ uno::Reference< media::XFrameGrabber > SAL_CALL Player::createFrameGrabber()
if( !pGrabber->create( pMovie ) )
return {};
- return pGrabber.get();
+ return pGrabber;
}
diff --git a/avmedia/source/macavf/window.hxx b/avmedia/source/macavf/window.hxx
index cfaae6f47d3b..14fdaf389811 100644
--- a/avmedia/source/macavf/window.hxx
+++ b/avmedia/source/macavf/window.hxx
@@ -21,7 +21,7 @@
#include "macavfcommon.hxx"
#include <cppuhelper/implbase.hxx>
-#include <cppuhelper/interfacecontainer.h>
+#include <comphelper/multicontainer2.hxx>
#include <com/sun/star/media/XPlayerWindow.hpp>
@@ -92,7 +92,7 @@ public:
private:
::osl::Mutex maMutex;
- ::cppu::OMultiTypeInterfaceContainerHelper maListeners;
+ comphelper::OMultiTypeInterfaceContainerHelper2 maListeners;
css::media::ZoomLevel meZoomLevel;
Player& mrPlayer;
int mnPointerType;
diff --git a/avmedia/source/viewer/mediaevent_impl.cxx b/avmedia/source/viewer/mediaevent_impl.cxx
index 9fbaceea1145..d6a2c082c246 100644
--- a/avmedia/source/viewer/mediaevent_impl.cxx
+++ b/avmedia/source/viewer/mediaevent_impl.cxx
@@ -21,6 +21,7 @@
#include <osl/mutex.hxx>
#include <vcl/svapp.hxx>
#include <vcl/event.hxx>
+#include <vcl/window.hxx>
using namespace ::com::sun::star;
@@ -39,7 +40,7 @@ MediaEventListenersImpl::~MediaEventListenersImpl()
void MediaEventListenersImpl::cleanUp()
{
- Application::RemoveMouseAndKeyEvents( reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ) );
+ Application::RemoveMouseAndKeyEvents( mpNotifyWindow.get() );
mpNotifyWindow = nullptr;
}
@@ -51,8 +52,7 @@ void SAL_CALL MediaEventListenersImpl::disposing( const css::lang::EventObject&
void SAL_CALL MediaEventListenersImpl::keyPressed( const css::awt::KeyEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
- const SolarMutexGuard aAppGuard;
+ const std::unique_lock aGuard( maMutex );
if( mpNotifyWindow )
{
@@ -62,15 +62,14 @@ void SAL_CALL MediaEventListenersImpl::keyPressed( const css::awt::KeyEvent& e )
( ( e.Modifiers & 4 ) ? KEY_MOD2 : 0 ) );
KeyEvent aVCLKeyEvt( e.KeyChar, aVCLKeyCode );
- Application::PostKeyEvent( VclEventId::WindowKeyInput, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLKeyEvt );
+ Application::PostKeyEvent( VclEventId::WindowKeyInput, mpNotifyWindow.get(), &aVCLKeyEvt );
}
}
void SAL_CALL MediaEventListenersImpl::keyReleased( const css::awt::KeyEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
- const SolarMutexGuard aAppGuard;
+ const std::unique_lock aGuard( maMutex );
if( mpNotifyWindow )
{
@@ -79,15 +78,14 @@ void SAL_CALL MediaEventListenersImpl::keyReleased( const css::awt::KeyEvent& e
( ( e.Modifiers & 2 ) ? KEY_MOD1 : 0 ) |
( ( e.Modifiers & 4 ) ? KEY_MOD2 : 0 ) );
KeyEvent aVCLKeyEvt( e.KeyChar, aVCLKeyCode );
- Application::PostKeyEvent( VclEventId::WindowKeyUp, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLKeyEvt );
+ Application::PostKeyEvent( VclEventId::WindowKeyUp, mpNotifyWindow.get(), &aVCLKeyEvt );
}
}
void SAL_CALL MediaEventListenersImpl::mousePressed( const css::awt::MouseEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
- const SolarMutexGuard aAppGuard;
+ const std::unique_lock aGuard( maMutex );
if( mpNotifyWindow )
{
@@ -98,14 +96,14 @@ void SAL_CALL MediaEventListenersImpl::mousePressed( const css::awt::MouseEvent&
( ( e.Buttons & 2 ) ? MOUSE_RIGHT : 0 ) |
( ( e.Buttons & 4 ) ? MOUSE_MIDDLE : 0 ),
e.Modifiers );
- Application::PostMouseEvent( VclEventId::WindowMouseButtonDown, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLMouseEvt );
+ Application::PostMouseEvent( VclEventId::WindowMouseButtonDown, mpNotifyWindow.get(), &aVCLMouseEvt );
}
}
void SAL_CALL MediaEventListenersImpl::mouseReleased( const css::awt::MouseEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
+ const std::unique_lock aGuard( maMutex );
const SolarMutexGuard aAppGuard;
if( mpNotifyWindow )
@@ -117,7 +115,7 @@ void SAL_CALL MediaEventListenersImpl::mouseReleased( const css::awt::MouseEvent
( ( e.Buttons & 2 ) ? MOUSE_RIGHT : 0 ) |
( ( e.Buttons & 4 ) ? MOUSE_MIDDLE : 0 ),
e.Modifiers );
- Application::PostMouseEvent( VclEventId::WindowMouseButtonUp, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLMouseEvt );
+ Application::PostMouseEvent( VclEventId::WindowMouseButtonUp, mpNotifyWindow.get(), &aVCLMouseEvt );
}
}
@@ -134,26 +132,24 @@ void SAL_CALL MediaEventListenersImpl::mouseExited( const css::awt::MouseEvent&
void SAL_CALL MediaEventListenersImpl::mouseDragged( const css::awt::MouseEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
- const SolarMutexGuard aAppGuard;
+ const std::unique_lock aGuard( maMutex );
if( mpNotifyWindow )
{
MouseEvent aVCLMouseEvt( Point( e.X, e.Y ), 0, MouseEventModifiers::NONE, e.Buttons, e.Modifiers );
- Application::PostMouseEvent( VclEventId::WindowMouseMove, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLMouseEvt );
+ Application::PostMouseEvent( VclEventId::WindowMouseMove, mpNotifyWindow.get(), &aVCLMouseEvt );
}
}
void SAL_CALL MediaEventListenersImpl::mouseMoved( const css::awt::MouseEvent& e )
{
- const ::osl::MutexGuard aGuard( maMutex );
- const SolarMutexGuard aAppGuard;
+ const std::unique_lock aGuard( maMutex );
if( mpNotifyWindow )
{
MouseEvent aVCLMouseEvt( Point( e.X, e.Y ), 0, MouseEventModifiers::NONE, e.Buttons, e.Modifiers );
- Application::PostMouseEvent( VclEventId::WindowMouseMove, reinterpret_cast< vcl::Window* >( mpNotifyWindow.get() ), &aVCLMouseEvt );
+ Application::PostMouseEvent( VclEventId::WindowMouseMove, mpNotifyWindow.get(), &aVCLMouseEvt );
}
}
diff --git a/avmedia/source/viewer/mediaevent_impl.hxx b/avmedia/source/viewer/mediaevent_impl.hxx
index 1dc1c20ec2ff..682eff1d7970 100644
--- a/avmedia/source/viewer/mediaevent_impl.hxx
+++ b/avmedia/source/viewer/mediaevent_impl.hxx
@@ -27,6 +27,8 @@
#include <com/sun/star/awt/XFocusListener.hpp>
#include <vcl/vclptr.hxx>
+#include <mutex>
+
namespace avmedia::priv
{
@@ -68,7 +70,7 @@ namespace avmedia::priv
private:
VclPtr<vcl::Window> mpNotifyWindow;
- mutable ::osl::Mutex maMutex;
+ mutable std::mutex maMutex;
};
}
diff --git a/avmedia/source/viewer/mediawindow.cxx b/avmedia/source/viewer/mediawindow.cxx
index e823c2e8dac5..cc369bed6264 100644
--- a/avmedia/source/viewer/mediawindow.cxx
+++ b/avmedia/source/viewer/mediawindow.cxx
@@ -23,18 +23,25 @@
#include <bitmaps.hlst>
#include <strings.hrc>
#include <tools/urlobj.hxx>
+#include <utility>
#include <vcl/graph.hxx>
#include <vcl/svapp.hxx>
#include <vcl/weld.hxx>
#include <sfx2/filedlghelper.hxx>
#include <com/sun/star/awt/Size.hpp>
+#include <com/sun/star/frame/XDispatchHelper.hpp>
#include <com/sun/star/media/XPlayer.hpp>
+#include <com/sun/star/media/XPlayerNotifier.hpp>
#include <com/sun/star/ui/dialogs/ExtendedFilePickerElementIds.hpp>
#include <com/sun/star/ui/dialogs/TemplateDescription.hpp>
#include <com/sun/star/ui/dialogs/XFilePicker3.hpp>
#include <com/sun/star/ui/dialogs/XFilePickerControlAccess.hpp>
+#include <com/sun/star/util/URLTransformer.hpp>
+#include <comphelper/processfactory.hxx>
+#include <comphelper/propertysequence.hxx>
#include <memory>
#include <sal/log.hxx>
+#include <o3tl/string_view.hxx>
#define AVMEDIA_FRAMEGRABBER_DEFAULTFRAME_MEDIATIME 3.0
@@ -142,30 +149,30 @@ bool MediaWindow::start()
return mpImpl->start();
}
-
void MediaWindow::updateMediaItem( MediaItem& rItem ) const
{
mpImpl->updateMediaItem( rItem );
}
-
void MediaWindow::executeMediaItem( const MediaItem& rItem )
{
mpImpl->executeMediaItem( rItem );
}
-
void MediaWindow::show()
{
mpImpl->Show();
}
-
void MediaWindow::hide()
{
mpImpl->Hide();
}
+bool MediaWindow::isVisible() const
+{
+ return mpImpl->IsVisible();
+}
vcl::Window* MediaWindow::getWindow() const
{
@@ -215,24 +222,25 @@ bool MediaWindow::executeMediaURLDialog(weld::Window* pParent, OUString& rURL, b
static const char aSeparator[] = ";";
OUStringBuffer aAllTypes;
+ aDlg.SetContext(sfx2::FileDialogHelper::InsertMedia);
aDlg.SetTitle( AvmResId( o_pbLink != nullptr
? AVMEDIA_STR_INSERTMEDIA_DLG : AVMEDIA_STR_OPENMEDIA_DLG ) );
- for( FilterNameVector::size_type i = 0; i < aFilters.size(); ++i )
+ for( const auto &filter : aFilters )
{
for( sal_Int32 nIndex = 0; nIndex >= 0; )
{
if( !aAllTypes.isEmpty() )
aAllTypes.append(aSeparator);
- aAllTypes.append(aWildcard).append(aFilters[ i ].second.getToken( 0, ';', nIndex ));
+ aAllTypes.append(OUString::Concat(aWildcard) + o3tl::getToken(filter.second, 0, ';', nIndex ));
}
}
// add filter for all media types
aDlg.AddFilter( AvmResId( AVMEDIA_STR_ALL_MEDIAFILES ), aAllTypes.makeStringAndClear() );
- for( FilterNameVector::size_type i = 0; i < aFilters.size(); ++i )
+ for( const auto &filter : aFilters )
{
OUStringBuffer aTypes;
@@ -241,11 +249,11 @@ bool MediaWindow::executeMediaURLDialog(weld::Window* pParent, OUString& rURL, b
if( !aTypes.isEmpty() )
aTypes.append(aSeparator);
- aTypes.append(aWildcard).append(aFilters[ i ].second.getToken( 0, ';', nIndex ));
+ aTypes.append(OUString::Concat(aWildcard) + o3tl::getToken(filter.second, 0, ';', nIndex ));
}
// add single filters
- aDlg.AddFilter( aFilters[ i ].first, aTypes.makeStringAndClear() );
+ aDlg.AddFilter( filter.first, aTypes.makeStringAndClear() );
}
// add filter for all types
@@ -295,49 +303,55 @@ void MediaWindow::executeFormatErrorBox(weld::Window* pParent)
xBox->run();
}
-bool MediaWindow::isMediaURL( const OUString& rURL, const OUString& rReferer, bool bDeep, Size* pPreferredSizePixel )
+bool MediaWindow::isMediaURL(std::u16string_view rURL, const OUString& rReferer, bool bDeep, const rtl::Reference<PlayerListener>& xPreferredPixelSizeListener)
{
const INetURLObject aURL( rURL );
- if( aURL.GetProtocol() != INetProtocol::NotValid )
+ if( aURL.GetProtocol() == INetProtocol::NotValid )
+ return false;
+
+ if (bDeep || xPreferredPixelSizeListener)
{
- if( bDeep || pPreferredSizePixel )
+ try
{
- try
- {
- uno::Reference< media::XPlayer > xPlayer( priv::MediaWindowImpl::createPlayer(
- aURL.GetMainURL( INetURLObject::DecodeMechanism::Unambiguous ),
- rReferer, nullptr ) );
+ uno::Reference< media::XPlayer > xPlayer( priv::MediaWindowImpl::createPlayer(
+ aURL.GetMainURL( INetURLObject::DecodeMechanism::Unambiguous ),
+ rReferer, nullptr ) );
- if( xPlayer.is() )
+ if( xPlayer.is() )
+ {
+ if (xPreferredPixelSizeListener)
{
- if( pPreferredSizePixel )
+ uno::Reference<media::XPlayerNotifier> xPlayerNotifier(xPlayer, css::uno::UNO_QUERY);
+ if (xPlayerNotifier)
{
- const awt::Size aAwtSize( xPlayer->getPreferredPlayerWindowSize() );
-
- pPreferredSizePixel->setWidth( aAwtSize.Width );
- pPreferredSizePixel->setHeight( aAwtSize.Height );
+ // wait until it's possible to query this to get a sensible answer
+ xPreferredPixelSizeListener->startListening(xPlayerNotifier);
+ }
+ else
+ {
+ // assume the size is possible to query immediately
+ xPreferredPixelSizeListener->callPlayerWindowSizeAvailable(xPlayer);
}
-
- return true;
}
- }
- catch( ... )
- {
+ return true;
}
}
- else
+ catch( ... )
{
- FilterNameVector aFilters = getMediaFilters();
- const OUString aExt( aURL.getExtension() );
+ }
+ }
+ else
+ {
+ FilterNameVector aFilters = getMediaFilters();
+ const OUString aExt( aURL.getExtension() );
- for( FilterNameVector::size_type i = 0; i < aFilters.size(); ++i )
+ for( const auto &filter : aFilters )
+ {
+ for( sal_Int32 nIndex = 0; nIndex >= 0; )
{
- for( sal_Int32 nIndex = 0; nIndex >= 0; )
- {
- if( aExt.equalsIgnoreAsciiCase( aFilters[ i ].second.getToken( 0, ';', nIndex ) ) )
- return true;
- }
+ if( aExt.equalsIgnoreAsciiCase( o3tl::getToken(filter.second, 0, ';', nIndex ) ) )
+ return true;
}
}
}
@@ -345,20 +359,17 @@ bool MediaWindow::isMediaURL( const OUString& rURL, const OUString& rReferer, bo
return false;
}
-
uno::Reference< media::XPlayer > MediaWindow::createPlayer( const OUString& rURL, const OUString& rReferer, const OUString* pMimeType )
{
return priv::MediaWindowImpl::createPlayer( rURL, rReferer, pMimeType );
}
-
-uno::Reference< graphic::XGraphic > MediaWindow::grabFrame( const OUString& rURL,
- const OUString& rReferer,
- const OUString& sMimeType )
+uno::Reference<graphic::XGraphic>
+MediaWindow::grabFrame(const uno::Reference<media::XPlayer>& xPlayer,
+ const uno::Reference<graphic::XGraphic>& rGraphic)
{
- uno::Reference< media::XPlayer > xPlayer( createPlayer( rURL, rReferer, &sMimeType ) );
uno::Reference< graphic::XGraphic > xRet;
- std::unique_ptr< Graphic > xGraphic;
+ std::optional< Graphic > oGraphic;
if( xPlayer.is() )
{
@@ -381,23 +392,120 @@ uno::Reference< graphic::XGraphic > MediaWindow::grabFrame( const OUString& rURL
if( !aPrefSize.Width && !aPrefSize.Height )
{
const BitmapEx aBmpEx(AVMEDIA_BMP_AUDIOLOGO);
- xGraphic.reset( new Graphic( aBmpEx ) );
+ oGraphic.emplace( aBmpEx );
}
}
}
- if (!xRet.is() && !xGraphic)
+ if (!xRet.is() && !oGraphic)
{
const BitmapEx aBmpEx(AVMEDIA_BMP_EMPTYLOGO);
- xGraphic.reset( new Graphic( aBmpEx ) );
+ oGraphic.emplace( aBmpEx );
}
- if (xGraphic)
- xRet = xGraphic->GetXGraphic();
+ if (oGraphic)
+ {
+ if (rGraphic)
+ oGraphic.emplace(rGraphic);
+ xRet = oGraphic->GetXGraphic();
+ }
return xRet;
}
+uno::Reference< graphic::XGraphic > MediaWindow::grabFrame(const OUString& rURL,
+ const OUString& rReferer,
+ const OUString& sMimeType,
+ const rtl::Reference<PlayerListener>& xPreferredPixelSizeListener)
+{
+ uno::Reference<media::XPlayer> xPlayer(createPlayer(rURL, rReferer, &sMimeType));
+
+ if (xPreferredPixelSizeListener)
+ {
+ uno::Reference<media::XPlayerNotifier> xPlayerNotifier(xPlayer, css::uno::UNO_QUERY);
+ if (xPlayerNotifier)
+ {
+ // set a callback to call when a more sensible result is available, which
+ // might be called immediately if already available
+ xPreferredPixelSizeListener->startListening(xPlayerNotifier);
+ }
+ else
+ {
+ // assume the size is possible to query immediately
+ xPreferredPixelSizeListener->callPlayerWindowSizeAvailable(xPlayer);
+ }
+
+ return nullptr;
+ }
+
+ return grabFrame(xPlayer);
+}
+
+void MediaWindow::dispatchInsertAVMedia(const css::uno::Reference<css::frame::XDispatchProvider>& rDispatchProvider,
+ const css::awt::Size& rSize, const OUString& rURL, bool bLink)
+{
+ util::URL aDispatchURL;
+ aDispatchURL.Complete = ".uno:InsertAVMedia";
+
+ css::uno::Reference<css::util::XURLTransformer> xTrans(css::util::URLTransformer::create(::comphelper::getProcessComponentContext()));
+ xTrans->parseStrict(aDispatchURL);
+
+ css::uno::Reference<css::frame::XDispatch> xDispatch = rDispatchProvider->queryDispatch(aDispatchURL, "", 0);
+ css::uno::Sequence<css::beans::PropertyValue> aArgs(comphelper::InitPropertySequence({
+ { "URL", css::uno::Any(rURL) },
+ { "Size.Width", uno::Any(rSize.Width)},
+ { "Size.Height", uno::Any(rSize.Height)},
+ { "IsLink", css::uno::Any(bLink) },
+ }));
+ xDispatch->dispatch(aDispatchURL, aArgs);
+}
+
+PlayerListener::PlayerListener(std::function<void(const css::uno::Reference<css::media::XPlayer>&)> fn)
+ : m_aFn(std::move(fn))
+{
+}
+
+void PlayerListener::disposing(std::unique_lock<std::mutex>& rGuard)
+{
+ stopListening(rGuard);
+ WeakComponentImplHelperBase::disposing(rGuard);
+}
+
+void PlayerListener::startListening(const css::uno::Reference<media::XPlayerNotifier>& rNotifier)
+{
+ std::unique_lock aGuard(m_aMutex);
+
+ m_xNotifier = rNotifier;
+ m_xNotifier->addPlayerListener(this);
+}
+
+void PlayerListener::stopListening(std::unique_lock<std::mutex>&)
+{
+ if (!m_xNotifier)
+ return;
+ m_xNotifier->removePlayerListener(this);
+ m_xNotifier.clear();
+}
+
+void SAL_CALL PlayerListener::preferredPlayerWindowSizeAvailable(const css::lang::EventObject&)
+{
+ std::unique_lock aGuard(m_aMutex);
+
+ css::uno::Reference<media::XPlayer> xPlayer(m_xNotifier, css::uno::UNO_QUERY_THROW);
+ aGuard.unlock();
+ callPlayerWindowSizeAvailable(xPlayer);
+ aGuard.lock();
+
+ stopListening(aGuard);
+}
+
+void SAL_CALL PlayerListener::disposing(const css::lang::EventObject&)
+{
+}
+
+PlayerListener::~PlayerListener()
+{
+}
} // namespace avmedia
diff --git a/avmedia/source/viewer/mediawindow_impl.cxx b/avmedia/source/viewer/mediawindow_impl.cxx
index 50110cfd1748..82ca1b92821c 100644
--- a/avmedia/source/viewer/mediawindow_impl.cxx
+++ b/avmedia/source/viewer/mediawindow_impl.cxx
@@ -29,14 +29,16 @@
#include <sal/log.hxx>
#include <comphelper/processfactory.hxx>
-#include <tools/diagnose_ex.h>
+#include <comphelper/diagnose_ex.hxx>
+#include <comphelper/scopeguard.hxx>
#include <tools/urlobj.hxx>
#include <unotools/securityoptions.hxx>
#include <vcl/bitmapex.hxx>
-#include <vcl/svapp.hxx>
+#include <vcl/sysdata.hxx>
#include <vcl/commandevent.hxx>
#include <vcl/event.hxx>
#include <vcl/ptrstyle.hxx>
+#include <vcl/svapp.hxx>
#include <com/sun/star/awt/SystemPointer.hpp>
#include <com/sun/star/lang/XComponent.hpp>
@@ -143,10 +145,9 @@ void MediaWindowImpl::dispose()
if (mxPlayerWindow.is())
{
- auto pEventsIf = static_cast<cppu::OWeakObject*>(mxEvents.get());
- mxPlayerWindow->removeKeyListener( uno::Reference< awt::XKeyListener >( pEventsIf, uno::UNO_QUERY ) );
- mxPlayerWindow->removeMouseListener( uno::Reference< awt::XMouseListener >( pEventsIf, uno::UNO_QUERY ) );
- mxPlayerWindow->removeMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( pEventsIf, uno::UNO_QUERY ) );
+ mxPlayerWindow->removeKeyListener( uno::Reference< awt::XKeyListener >( mxEvents ) );
+ mxPlayerWindow->removeMouseListener( uno::Reference< awt::XMouseListener >( mxEvents ) );
+ mxPlayerWindow->removeMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( mxEvents ) );
mxPlayerWindow->dispose();
mxPlayerWindow.clear();
}
@@ -167,34 +168,26 @@ void MediaWindowImpl::dispose()
Control::dispose();
}
-uno::Reference<media::XPlayer> MediaWindowImpl::createPlayer(const OUString& rURL, const OUString& rReferer, const OUString* pMimeType)
+uno::Reference<media::XPlayer> MediaWindowImpl::createPlayer(const OUString& rURL, const OUString& rReferer, const OUString*)
{
uno::Reference<media::XPlayer> xPlayer;
if( rURL.isEmpty() )
return xPlayer;
- if (SvtSecurityOptions().isUntrustedReferer(rReferer))
+ if (SvtSecurityOptions::isUntrustedReferer(rReferer))
{
return xPlayer;
}
- if (!pMimeType || *pMimeType == AVMEDIA_MIMETYPE_COMMON)
+ // currently there isn't anything else, throw any mime type to the media players
+ //if (!pMimeType || *pMimeType == AVMEDIA_MIMETYPE_COMMON)
{
uno::Reference<uno::XComponentContext> xContext(::comphelper::getProcessComponentContext());
-
- static std::u16string_view aServiceManagers[] =
- {
- u"" AVMEDIA_MANAGER_SERVICE_PREFERRED,
- u"" AVMEDIA_MANAGER_SERVICE_NAME,
- };
-
- for (const auto& rServiceName : aServiceManagers)
- {
- xPlayer = createPlayer(rURL, OUString(rServiceName), xContext);
- if (xPlayer)
- break;
- }
+ if (Application::GetToolkitName() == "gtk4")
+ xPlayer = createPlayer(rURL, "com.sun.star.comp.avmedia.Manager_Gtk", xContext);
+ else
+ xPlayer = createPlayer(rURL, AVMEDIA_MANAGER_SERVICE_NAME, xContext);
}
return xPlayer;
@@ -307,6 +300,9 @@ void MediaWindowImpl::updateMediaItem( MediaItem& rItem ) const
void MediaWindowImpl::executeMediaItem( const MediaItem& rItem )
{
+ mpItem = &rItem;
+ comphelper::ScopeGuard g([this] { this->mpItem = nullptr; });
+
const AVMediaSetMask nMaskSet = rItem.getMaskSet();
// set URL first
@@ -402,7 +398,7 @@ void MediaWindowImpl::stopPlayingInternal(bool bStop)
void MediaWindowImpl::onURLChanged()
{
- if (m_sMimeType == AVMEDIA_MIMETYPE_COMMON)
+ //if (m_sMimeType == AVMEDIA_MIMETYPE_COMMON)
{
mpChildWindow.disposeAndClear();
mpChildWindow.reset(VclPtr<MediaChildWindow>::Create(this));
@@ -415,14 +411,22 @@ void MediaWindowImpl::onURLChanged()
if (mxPlayer.is())
{
Resize();
- uno::Sequence<uno::Any> aArgs( 3 );
uno::Reference<media::XPlayerWindow> xPlayerWindow;
const Point aPoint;
const Size aSize(mpChildWindow->GetSizePixel());
- aArgs[0] <<= mpChildWindow->GetParentWindowHandle();
- aArgs[1] <<= awt::Rectangle(aPoint.X(), aPoint.Y(), aSize.Width(), aSize.Height());
- aArgs[2] <<= reinterpret_cast<sal_IntPtr>(mpChildWindow.get());
+ sal_IntPtr nParentWindowHandle(0);
+ const SystemEnvData* pEnvData = mpChildWindow->GetSystemData();
+ // tdf#139609 gtk doesn't need the handle, and fetching it is undesirable
+ if (!pEnvData || pEnvData->toolkit != SystemEnvData::Toolkit::Gtk)
+ nParentWindowHandle = mpChildWindow->GetParentWindowHandle();
+ uno::Sequence<uno::Any> aArgs{
+ uno::Any(nParentWindowHandle),
+ uno::Any(awt::Rectangle(aPoint.X(), aPoint.Y(), aSize.Width(), aSize.Height())),
+ uno::Any(reinterpret_cast<sal_IntPtr>(mpChildWindow.get())),
+ // Media item contains media properties, e.g. cropping.
+ uno::Any(reinterpret_cast<sal_IntPtr>(mpItem))
+ };
try
{
@@ -437,11 +441,10 @@ void MediaWindowImpl::onURLChanged()
if( xPlayerWindow.is() )
{
- auto pEventsIf = static_cast<cppu::OWeakObject*>(mxEvents.get());
- xPlayerWindow->addKeyListener( uno::Reference< awt::XKeyListener >( pEventsIf, uno::UNO_QUERY ) );
- xPlayerWindow->addMouseListener( uno::Reference< awt::XMouseListener >( pEventsIf, uno::UNO_QUERY ) );
- xPlayerWindow->addMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( pEventsIf, uno::UNO_QUERY ) );
- xPlayerWindow->addFocusListener( uno::Reference< awt::XFocusListener >( pEventsIf, uno::UNO_QUERY ) );
+ xPlayerWindow->addKeyListener( uno::Reference< awt::XKeyListener >( mxEvents ) );
+ xPlayerWindow->addMouseListener( uno::Reference< awt::XMouseListener >( mxEvents ) );
+ xPlayerWindow->addMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( mxEvents ) );
+ xPlayerWindow->addFocusListener( uno::Reference< awt::XFocusListener >( mxEvents ) );
}
}
else
diff --git a/avmedia/source/viewer/mediawindow_impl.hxx b/avmedia/source/viewer/mediawindow_impl.hxx
index 8bceebb08d15..aa95fde22444 100644
--- a/avmedia/source/viewer/mediawindow_impl.hxx
+++ b/avmedia/source/viewer/mediawindow_impl.hxx
@@ -150,6 +150,7 @@ private:
VclPtr<MediaWindowControl> mpMediaWindowControl;
std::unique_ptr<BitmapEx> mpEmptyBmpEx;
std::unique_ptr<BitmapEx> mpAudioBmpEx;
+ const MediaItem* mpItem = nullptr;
};
}} // end namespace avmedia::priv
diff --git a/avmedia/source/win/framegrabber.cxx b/avmedia/source/win/framegrabber.cxx
index 249648f04f96..84e9d1b187e8 100644
--- a/avmedia/source/win/framegrabber.cxx
+++ b/avmedia/source/win/framegrabber.cxx
@@ -38,9 +38,10 @@
#include <vcl/graph.hxx>
#include <vcl/dibtools.hxx>
#include <o3tl/char16_t2wchar_t.hxx>
+#include <systools/win32/oleauto.hxx>
-#define AVMEDIA_WIN_FRAMEGRABBER_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.FrameGrabber_DirectX"
-#define AVMEDIA_WIN_FRAMEGRABBER_SERVICENAME "com.sun.star.media.FrameGrabber_DirectX"
+constexpr OUStringLiteral AVMEDIA_WIN_FRAMEGRABBER_IMPLEMENTATIONNAME = u"com.sun.star.comp.avmedia.FrameGrabber_DirectX";
+constexpr OUString AVMEDIA_WIN_FRAMEGRABBER_SERVICENAME = u"com.sun.star.media.FrameGrabber_DirectX"_ustr;
using namespace ::com::sun::star;
@@ -48,39 +49,29 @@ namespace avmedia::win {
FrameGrabber::FrameGrabber()
+ : sal::systools::CoInitializeGuard(COINIT_APARTMENTTHREADED, false,
+ sal::systools::CoInitializeGuard::WhenFailed::NoThrow)
{
- ::CoInitializeEx( nullptr, COINIT_APARTMENTTHREADED );
}
-FrameGrabber::~FrameGrabber()
-{
- ::CoUninitialize();
-}
+FrameGrabber::~FrameGrabber() = default;
namespace {
-IMediaDet* implCreateMediaDet( const OUString& rURL )
+sal::systools::COMReference<IMediaDet> implCreateMediaDet( const OUString& rURL )
{
- IMediaDet* pDet = nullptr;
+ sal::systools::COMReference<IMediaDet> pDet;
- if( SUCCEEDED( CoCreateInstance( CLSID_MediaDet, nullptr, CLSCTX_INPROC_SERVER, IID_IMediaDet, reinterpret_cast<void**>(&pDet) ) ) )
+ if( SUCCEEDED(pDet.CoCreateInstance(CLSID_MediaDet, nullptr, CLSCTX_INPROC_SERVER)) )
{
OUString aLocalStr;
if( osl::FileBase::getSystemPathFromFileURL( rURL, aLocalStr )
== osl::FileBase::E_None )
{
- BSTR bstrFilename = SysAllocString(o3tl::toW(aLocalStr.getStr()));
- if( !SUCCEEDED( pDet->put_Filename( bstrFilename ) ) )
- {
- // Shouldn't we free this string unconditionally, not only in case of failure?
- // I cannot find information why do we pass a newly allocated BSTR to the put_Filename
- // and if it frees the string internally
- SysFreeString(bstrFilename);
- pDet->Release();
- pDet = nullptr;
- }
+ if( !SUCCEEDED( pDet->put_Filename(sal::systools::BStr(aLocalStr)) ) )
+ pDet.clear();
}
}
@@ -92,14 +83,8 @@ IMediaDet* implCreateMediaDet( const OUString& rURL )
bool FrameGrabber::create( const OUString& rURL )
{
// just check if a MediaDet interface can be created with the given URL
- IMediaDet* pDet = implCreateMediaDet( rURL );
-
- if( pDet )
- {
+ if (implCreateMediaDet(rURL))
maURL = rURL;
- pDet->Release();
- pDet = nullptr;
- }
else
maURL.clear();
@@ -110,9 +95,7 @@ bool FrameGrabber::create( const OUString& rURL )
uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMediaTime )
{
uno::Reference< graphic::XGraphic > xRet;
- IMediaDet* pDet = implCreateMediaDet( maURL );
-
- if( pDet )
+ if (sal::systools::COMReference<IMediaDet> pDet = implCreateMediaDet(maURL))
{
double fLength;
long nStreamCount;
@@ -195,8 +178,6 @@ uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMe
}
}
}
-
- pDet->Release();
}
return xRet;
diff --git a/avmedia/source/win/framegrabber.hxx b/avmedia/source/win/framegrabber.hxx
index fb4fda35905d..d1ca48e84230 100644
--- a/avmedia/source/win/framegrabber.hxx
+++ b/avmedia/source/win/framegrabber.hxx
@@ -21,6 +21,8 @@
#include "wincommon.hxx"
#include <cppuhelper/implbase.hxx>
+#include <systools/win32/comtools.hxx>
+
#include <com/sun/star/media/XFrameGrabber.hpp>
struct IMediaDet;
@@ -28,7 +30,8 @@ struct IMediaDet;
namespace avmedia::win {
class FrameGrabber : public ::cppu::WeakImplHelper< css::media::XFrameGrabber,
- css::lang::XServiceInfo >
+ css::lang::XServiceInfo >,
+ public sal::systools::CoInitializeGuard
{
public:
explicit FrameGrabber();
diff --git a/avmedia/source/win/manager.cxx b/avmedia/source/win/manager.cxx
index 731effd5f80f..578ec9d2a5af 100644
--- a/avmedia/source/win/manager.cxx
+++ b/avmedia/source/win/manager.cxx
@@ -21,6 +21,7 @@
#include "player.hxx"
#include <cppuhelper/supportsservice.hxx>
+#include <rtl/ref.hxx>
#include <tools/urlobj.hxx>
using namespace ::com::sun::star;
@@ -39,14 +40,13 @@ Manager::~Manager()
uno::Reference< media::XPlayer > SAL_CALL Manager::createPlayer( const OUString& rURL )
{
- Player* pPlayer( new Player() );
- uno::Reference< media::XPlayer > xRet( pPlayer );
+ rtl::Reference<Player> pPlayer( new Player() );
const INetURLObject aURL( rURL );
if( !pPlayer->create( aURL.GetMainURL( INetURLObject::DecodeMechanism::Unambiguous ) ) )
- xRet.clear();
+ pPlayer.clear();
- return xRet;
+ return pPlayer;
}
diff --git a/avmedia/source/win/player.cxx b/avmedia/source/win/player.cxx
index 7990e7aecdfe..b52ac8171dfc 100644
--- a/avmedia/source/win/player.cxx
+++ b/avmedia/source/win/player.cxx
@@ -29,9 +29,10 @@
#include <cppuhelper/supportsservice.hxx>
#include <o3tl/char16_t2wchar_t.hxx>
#include <osl/file.hxx>
+#include <rtl/ref.hxx>
-#define AVMEDIA_WIN_PLAYER_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Player_DirectX"
-#define AVMEDIA_WIN_PLAYER_SERVICENAME "com.sun.star.media.Player_DirectX"
+constexpr OUStringLiteral AVMEDIA_WIN_PLAYER_IMPLEMENTATIONNAME = u"com.sun.star.comp.avmedia.Player_DirectX";
+constexpr OUString AVMEDIA_WIN_PLAYER_SERVICENAME = u"com.sun.star.media.Player_DirectX"_ustr;
using namespace ::com::sun::star;
@@ -63,23 +64,14 @@ static LRESULT CALLBACK MediaPlayerWndProc_2( HWND hWnd,UINT nMsg, WPARAM nPar1,
Player::Player() :
Player_BASE(m_aMutex),
- mpGB( nullptr ),
- mpOMF( nullptr ),
- mpMC( nullptr ),
- mpME( nullptr ),
- mpMS( nullptr ),
- mpMP( nullptr ),
- mpBA( nullptr ),
- mpBV( nullptr ),
- mpVW( nullptr ),
- mpEV( nullptr ),
+ sal::systools::CoInitializeGuard(COINIT_APARTMENTTHREADED, false,
+ sal::systools::CoInitializeGuard::WhenFailed::NoThrow),
mnUnmutedVolume( 0 ),
mnFrameWnd( nullptr ),
mbMuted( false ),
mbLooping( false ),
mbAddWindow( true )
{
- ::CoInitializeEx( nullptr, COINIT_APARTMENTTHREADED );
}
@@ -87,8 +79,6 @@ Player::~Player()
{
if( mnFrameWnd )
::DestroyWindow( mnFrameWnd );
-
- ::CoUninitialize();
}
@@ -96,47 +86,16 @@ void SAL_CALL Player::disposing()
{
::osl::MutexGuard aGuard(m_aMutex);
stop();
- if( mpBA )
- mpBA->Release();
-
- if( mpBV )
- mpBV->Release();
-
- if( mpVW )
- mpVW->Release();
-
- if( mpMP )
- mpMP->Release();
-
- if( mpMS )
- mpMS->Release();
-
if( mpME )
- {
mpME->SetNotifyWindow( 0, WM_GRAPHNOTIFY, 0);
- mpME->Release();
- }
-
- if( mpMC )
- mpMC->Release();
-
- if( mpEV )
- mpEV->Release();
-
- if( mpOMF )
- mpOMF->Release();
-
- if( mpGB )
- mpGB->Release();
}
bool Player::create( const OUString& rURL )
{
- HRESULT hR;
bool bRet = false;
- if( SUCCEEDED( hR = CoCreateInstance( CLSID_FilterGraph, nullptr, CLSCTX_INPROC_SERVER, IID_IGraphBuilder, reinterpret_cast<void**>(&mpGB) ) ) )
+ if( SUCCEEDED(mpGB.CoCreateInstance(CLSID_FilterGraph, nullptr, CLSCTX_INPROC_SERVER)) )
{
// Don't use the overlay mixer on Windows Vista
// It disables the desktop composition as soon as RenderFile is called
@@ -148,18 +107,17 @@ bool Player::create( const OUString& rURL )
if (aFile.startsWithIgnoreAsciiCase("file:"))
osl::FileBase::getSystemPathFromFileURL(rURL, aFile);
- if( SUCCEEDED( hR = mpGB->RenderFile( o3tl::toW(aFile.getStr()), nullptr ) ) &&
- SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaControl, reinterpret_cast<void**>(&mpMC) ) ) &&
- SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaEventEx, reinterpret_cast<void**>(&mpME) ) ) &&
- SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaSeeking, reinterpret_cast<void**>(&mpMS) ) ) &&
- SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaPosition, reinterpret_cast<void**>(&mpMP) ) ) )
+ if( SUCCEEDED( mpGB->RenderFile( o3tl::toW(aFile.getStr()), nullptr ) ) &&
+ mpMC.set(mpGB, sal::systools::COM_QUERY) &&
+ mpME.set(mpGB, sal::systools::COM_QUERY) &&
+ mpMP.set(mpGB, sal::systools::COM_QUERY) )
{
// Video interfaces
- mpGB->QueryInterface( IID_IVideoWindow, reinterpret_cast<void**>(&mpVW) );
- mpGB->QueryInterface( IID_IBasicVideo, reinterpret_cast<void**>(&mpBV) );
+ mpVW.set(mpGB, sal::systools::COM_QUERY);
+ mpBV.set(mpGB, sal::systools::COM_QUERY);
// Audio interface
- mpGB->QueryInterface( IID_IBasicAudio, reinterpret_cast<void**>(&mpBA) );
+ mpBA.set(mpGB, sal::systools::COM_QUERY);
if( mpBA )
mpBA->put_Volume( mnUnmutedVolume );
@@ -407,7 +365,7 @@ uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( co
if( mpVW && aSize.Width > 0 && aSize.Height > 0 )
{
- ::avmedia::win::Window* pWindow = new ::avmedia::win::Window( *this );
+ rtl::Reference<::avmedia::win::Window> pWindow = new ::avmedia::win::Window( *this );
xRet = pWindow;
@@ -425,7 +383,7 @@ uno::Reference< media::XFrameGrabber > SAL_CALL Player::createFrameGrabber( )
if( !maURL.isEmpty() )
{
- FrameGrabber* pGrabber = new FrameGrabber();
+ rtl::Reference<FrameGrabber> pGrabber = new FrameGrabber();
xRet = pGrabber;
diff --git a/avmedia/source/win/player.hxx b/avmedia/source/win/player.hxx
index 84e2689c0397..1563d549a85e 100644
--- a/avmedia/source/win/player.hxx
+++ b/avmedia/source/win/player.hxx
@@ -29,6 +29,7 @@
#include <cppuhelper/compbase.hxx>
#include <cppuhelper/basemutex.hxx>
+#include <systools/win32/comtools.hxx>
struct IGraphBuilder;
struct IBaseFilter;
@@ -50,7 +51,8 @@ typedef ::cppu::WeakComponentImplHelper< css::media::XPlayer,
class Player : public cppu::BaseMutex,
- public Player_BASE
+ public Player_BASE,
+ public sal::systools::CoInitializeGuard
{
public:
@@ -92,23 +94,18 @@ public:
private:
OUString maURL;
- IGraphBuilder* mpGB;
- IBaseFilter* mpOMF;
- IMediaControl* mpMC;
- IMediaEventEx* mpME;
- IMediaSeeking* mpMS;
- IMediaPosition* mpMP;
- IBasicAudio* mpBA;
- IBasicVideo* mpBV;
- IVideoWindow* mpVW;
- IDDrawExclModeVideo* mpEV;
+ sal::systools::COMReference<IGraphBuilder> mpGB;
+ sal::systools::COMReference<IMediaControl> mpMC;
+ sal::systools::COMReference<IMediaEventEx> mpME;
+ sal::systools::COMReference<IMediaPosition> mpMP;
+ sal::systools::COMReference<IBasicAudio> mpBA;
+ sal::systools::COMReference<IBasicVideo> mpBV;
+ sal::systools::COMReference<IVideoWindow> mpVW;
long mnUnmutedVolume;
HWND mnFrameWnd;
bool mbMuted;
bool mbLooping;
bool mbAddWindow;
-
- void ImplLayoutVideoWindow();
};
} // namespace avmedia::win
diff --git a/avmedia/source/win/window.cxx b/avmedia/source/win/window.cxx
index ad770dc691a2..8cf3fee74d3d 100644
--- a/avmedia/source/win/window.cxx
+++ b/avmedia/source/win/window.cxx
@@ -28,8 +28,8 @@
#include "window.hxx"
#include "player.hxx"
-#define AVMEDIA_WIN_WINDOW_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Window_DirectX"
-#define AVMEDIA_WIN_WINDOW_SERVICENAME "com.sun.star.media.Window_DirectX"
+constexpr OUStringLiteral AVMEDIA_WIN_WINDOW_IMPLEMENTATIONNAME = u"com.sun.star.comp.avmedia.Window_DirectX";
+constexpr OUString AVMEDIA_WIN_WINDOW_SERVICENAME = u"com.sun.star.media.Window_DirectX"_ustr;
using namespace ::com::sun::star;
@@ -98,7 +98,6 @@ static WNDCLASSW* lcl_getWndClass()
}
Window::Window( Player& rPlayer ) :
- maListeners( maMutex ),
meZoomLevel( media::ZoomLevel_NOT_AVAILABLE ),
mrPlayer( rPlayer ),
mnFrameWnd( nullptr ),
@@ -349,62 +348,74 @@ void SAL_CALL Window::setFocus( )
void SAL_CALL Window::addWindowListener( const uno::Reference< awt::XWindowListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maWindowListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeWindowListener( const uno::Reference< awt::XWindowListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maWindowListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::addFocusListener( const uno::Reference< awt::XFocusListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maFocusListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeFocusListener( const uno::Reference< awt::XFocusListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maFocusListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::addKeyListener( const uno::Reference< awt::XKeyListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maKeyListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeKeyListener( const uno::Reference< awt::XKeyListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maKeyListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::addMouseListener( const uno::Reference< awt::XMouseListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maMouseListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeMouseListener( const uno::Reference< awt::XMouseListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maMouseListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::addMouseMotionListener( const uno::Reference< awt::XMouseMotionListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maMouseMotionListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeMouseMotionListener( const uno::Reference< awt::XMouseMotionListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maMouseMotionListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::addPaintListener( const uno::Reference< awt::XPaintListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maPaintListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removePaintListener( const uno::Reference< awt::XPaintListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maPaintListeners.removeInterface( g, xListener );
}
void SAL_CALL Window::dispose( )
@@ -413,64 +424,38 @@ void SAL_CALL Window::dispose( )
void SAL_CALL Window::addEventListener( const uno::Reference< lang::XEventListener >& xListener )
{
- maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maEventListeners.addInterface( g, xListener );
}
void SAL_CALL Window::removeEventListener( const uno::Reference< lang::XEventListener >& xListener )
{
- maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
+ std::unique_lock g(maMutex);
+ maEventListeners.removeInterface( g, xListener );
}
void Window::fireMousePressedEvent( const css::awt::MouseEvent& rEvt )
{
- ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseListener>::get());
-
- if( pContainer )
- {
- ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
-
- while( aIter.hasMoreElements() )
- uno::Reference< awt::XMouseListener >( aIter.next(), uno::UNO_QUERY_THROW )->mousePressed( rEvt );
- }
+ std::unique_lock g(maMutex);
+ maMouseListeners.notifyEach(g, &awt::XMouseListener::mousePressed, rEvt);
}
void Window::fireMouseReleasedEvent( const css::awt::MouseEvent& rEvt )
{
- ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseListener>::get());
-
- if( pContainer )
- {
- ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
-
- while( aIter.hasMoreElements() )
- uno::Reference< awt::XMouseListener >( aIter.next(), uno::UNO_QUERY_THROW )->mouseReleased( rEvt );
- }
+ std::unique_lock g(maMutex);
+ maMouseListeners.notifyEach(g, &awt::XMouseListener::mouseReleased, rEvt);
}
void Window::fireMouseMovedEvent( const css::awt::MouseEvent& rEvt )
{
- ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseMotionListener>::get());
-
- if( pContainer )
- {
- ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
-
- while( aIter.hasMoreElements() )
- uno::Reference< awt::XMouseMotionListener >( aIter.next(), uno::UNO_QUERY_THROW )->mouseMoved( rEvt );
- }
+ std::unique_lock g(maMutex);
+ maMouseMotionListeners.notifyEach(g, &awt::XMouseMotionListener::mouseMoved, rEvt);
}
void Window::fireSetFocusEvent( const css::awt::FocusEvent& rEvt )
{
- ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XFocusListener>::get());
-
- if( pContainer )
- {
- ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
-
- while( aIter.hasMoreElements() )
- uno::Reference< awt::XFocusListener >( aIter.next(), uno::UNO_QUERY_THROW )->focusGained( rEvt );
- }
+ std::unique_lock g(maMutex);
+ maFocusListeners.notifyEach(g, &awt::XFocusListener::focusGained, rEvt);
}
OUString SAL_CALL Window::getImplementationName( )
diff --git a/avmedia/source/win/window.hxx b/avmedia/source/win/window.hxx
index c13bd8b62ea4..0ab691ffbb82 100644
--- a/avmedia/source/win/window.hxx
+++ b/avmedia/source/win/window.hxx
@@ -25,7 +25,8 @@
#include "wincommon.hxx"
#include <cppuhelper/implbase.hxx>
-#include <cppuhelper/interfacecontainer.h>
+#include <comphelper/interfacecontainer4.hxx>
+#include <mutex>
#include <com/sun/star/media/XPlayerWindow.hpp>
@@ -95,8 +96,14 @@ public:
private:
- ::osl::Mutex maMutex;
- ::cppu::OMultiTypeInterfaceContainerHelper maListeners;
+ std::mutex maMutex;
+ comphelper::OInterfaceContainerHelper4<css::awt::XWindowListener> maWindowListeners;
+ comphelper::OInterfaceContainerHelper4<css::awt::XFocusListener> maFocusListeners;
+ comphelper::OInterfaceContainerHelper4<css::awt::XKeyListener> maKeyListeners;
+ comphelper::OInterfaceContainerHelper4<css::awt::XMouseListener> maMouseListeners;
+ comphelper::OInterfaceContainerHelper4<css::awt::XMouseMotionListener> maMouseMotionListeners;
+ comphelper::OInterfaceContainerHelper4<css::awt::XPaintListener> maPaintListeners;
+ comphelper::OInterfaceContainerHelper4<css::lang::XEventListener> maEventListeners;
css::media::ZoomLevel meZoomLevel;
Player& mrPlayer;
HWND mnFrameWnd;