aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCharles Kerr <charles.kerr@canonical.com>2015-01-28 19:15:59 +0000
committerCI Train Bot <ci-train-bot@canonical.com>2015-01-28 19:15:59 +0000
commite1f1be9e181a3d00506b77c6201178e030fc0168 (patch)
tree5a0d7e2b25bc47903452446be831a9b6495f7238
parentfe5d8d46225d9144e2c756c9d206d2ac73f6ad77 (diff)
parent12c742122d34578b23da54d49d4ae1b9bb6af87e (diff)
downloadayatana-indicator-datetime-e1f1be9e181a3d00506b77c6201178e030fc0168.tar.gz
ayatana-indicator-datetime-e1f1be9e181a3d00506b77c6201178e030fc0168.tar.bz2
ayatana-indicator-datetime-e1f1be9e181a3d00506b77c6201178e030fc0168.zip
Don't play calendar alarm sounds if Silent Mode is enabled. Use the alarm sound role for both clock and calendar alarms. Fixes: #1410874
Approved by: Antti Kaijanmäki, PS Jenkins bot
-rw-r--r--include/notifications/sound.h2
-rw-r--r--src/CMakeLists.txt3
-rw-r--r--src/com.ubuntu.touch.AccountsService.Sound.xml42
-rw-r--r--src/snap.cpp63
-rw-r--r--src/sound.cpp19
-rw-r--r--tests/manual13
6 files changed, 128 insertions, 14 deletions
diff --git a/include/notifications/sound.h b/include/notifications/sound.h
index f5f549c..d08c2e7 100644
--- a/include/notifications/sound.h
+++ b/include/notifications/sound.h
@@ -41,7 +41,7 @@ namespace notifications {
class Sound
{
public:
- Sound(const std::string& uri, unsigned int volume, bool loop);
+ Sound(const std::string& role, const std::string& uri, unsigned int volume, bool loop);
~Sound();
private:
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 512cc5c..5fc822c 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -47,6 +47,9 @@ set(SERVICE_GENERATED_SOURCES)
add_gdbus_codegen(SERVICE_GENERATED_SOURCES dbus-alarm-properties
com.canonical.indicator
${CMAKE_SOURCE_DIR}/data/com.canonical.indicator.datetime.AlarmProperties.xml)
+add_gdbus_codegen(SERVICE_GENERATED_SOURCES dbus-accounts-sound
+ com.ubuntu.touch
+ ${CMAKE_SOURCE_DIR}/src/com.ubuntu.touch.AccountsService.Sound.xml)
# add warnings/coverage info on handwritten files
# but not the autogenerated ones...
diff --git a/src/com.ubuntu.touch.AccountsService.Sound.xml b/src/com.ubuntu.touch.AccountsService.Sound.xml
new file mode 100644
index 0000000..91d71dc
--- /dev/null
+++ b/src/com.ubuntu.touch.AccountsService.Sound.xml
@@ -0,0 +1,42 @@
+<node>
+ <interface name="com.ubuntu.touch.AccountsService.Sound">
+
+ <annotation name="org.freedesktop.Accounts.VendorExtension" value="true"/>
+
+ <!-- Muted is all sound, SilentMode is only non-user-initiated sounds -->
+ <property name="SilentMode" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="false"/>
+ </property>
+
+ <property name="IncomingCallSound" type="s" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue.String"
+ value="/usr/share/sounds/ubuntu/ringtones/Ubuntu.ogg"/>
+ </property>
+
+ <property name="IncomingMessageSound" type="s" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue.String"
+ value="/usr/share/sounds/ubuntu/notifications/Xylo.ogg"/>
+ </property>
+
+ <property name="IncomingCallVibrate" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="true"/>
+ </property>
+
+ <property name="IncomingCallVibrateSilentMode" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="true"/>
+ </property>
+
+ <property name="IncomingMessageVibrate" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="true"/>
+ </property>
+
+ <property name="IncomingMessageVibrateSilentMode" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="true"/>
+ </property>
+
+ <property name="DialpadSoundsEnabled" type="b" access="readwrite">
+ <annotation name="org.freedesktop.Accounts.DefaultValue" value="true"/>
+ </property>
+
+ </interface>
+</node>
diff --git a/src/snap.cpp b/src/snap.cpp
index ee96007..e655d2d 100644
--- a/src/snap.cpp
+++ b/src/snap.cpp
@@ -17,6 +17,8 @@
* Charles Kerr <charles.kerr@canonical.com>
*/
+#include "dbus-accounts-sound.h"
+
#include <datetime/snap.h>
#include <datetime/utils.h> // is_locale_12h()
@@ -32,6 +34,9 @@
#include <set>
#include <string>
+#include <unistd.h> // getuid()
+#include <sys/types.h> // getuid()
+
namespace uin = unity::indicator::notifications;
namespace unity {
@@ -49,12 +54,26 @@ public:
Impl(const std::shared_ptr<unity::indicator::notifications::Engine>& engine,
const std::shared_ptr<const Settings>& settings):
m_engine(engine),
- m_settings(settings)
+ m_settings(settings),
+ m_cancellable(g_cancellable_new())
{
+ auto object_path = g_strdup_printf("/org/freedesktop/Accounts/User%lu", (gulong)getuid());
+ accounts_service_sound_proxy_new_for_bus(G_BUS_TYPE_SYSTEM,
+ G_DBUS_PROXY_FLAGS_GET_INVALIDATED_PROPERTIES,
+ "org.freedesktop.Accounts",
+ object_path,
+ m_cancellable,
+ on_sound_proxy_ready,
+ this);
+ g_free(object_path);
}
~Impl()
{
+ g_cancellable_cancel(m_cancellable);
+ g_clear_object(&m_cancellable);
+ g_clear_object(&m_accounts_service_sound_proxy);
+
for (const auto& key : m_notifications)
m_engine->close (key);
}
@@ -72,11 +91,16 @@ public:
// force the system to stay awake
auto awake = std::make_shared<uin::Awake>(m_engine->app_name());
- // create the sound...
- const auto uri = get_alarm_uri(appointment, m_settings);
- const auto volume = m_settings->alarm_volume.get();
- const bool loop = interactive;
- auto sound = std::make_shared<uin::Sound>(uri, volume, loop);
+ // calendar events are muted in silent mode; alarm clocks never are
+ std::shared_ptr<uin::Sound> sound;
+ if (appointment.is_ubuntu_alarm() || !silent_mode()) {
+ // create the sound.
+ const auto role = appointment.is_ubuntu_alarm() ? "alarm" : "alert";
+ const auto uri = get_alarm_uri(appointment, m_settings);
+ const auto volume = m_settings->alarm_volume.get();
+ const bool loop = interactive;
+ sound = std::make_shared<uin::Sound>(role, uri, volume, loop);
+ }
// create the haptic feedback...
const auto haptic_mode = m_settings->alarm_haptic.get();
@@ -131,6 +155,31 @@ public:
private:
+ static void on_sound_proxy_ready(GObject* /*source_object*/, GAsyncResult* res, gpointer gself)
+ {
+ GError * error;
+
+ error = nullptr;
+ auto proxy = accounts_service_sound_proxy_new_for_bus_finish (res, &error);
+ if (error != nullptr)
+ {
+ if (!g_error_matches(error, G_IO_ERROR, G_IO_ERROR_CANCELLED))
+ g_warning("%s Couldn't find accounts service sound proxy: %s", G_STRLOC, error->message);
+
+ g_clear_error(&error);
+ }
+ else
+ {
+ static_cast<Impl*>(gself)->m_accounts_service_sound_proxy = proxy;
+ }
+ }
+
+ bool silent_mode() const
+ {
+ return (m_accounts_service_sound_proxy != nullptr)
+ && (accounts_service_sound_get_silent_mode(m_accounts_service_sound_proxy));
+ }
+
std::string get_alarm_uri(const Appointment& appointment,
const std::shared_ptr<const Settings>& settings) const
{
@@ -167,6 +216,8 @@ private:
const std::shared_ptr<unity::indicator::notifications::Engine> m_engine;
const std::shared_ptr<const Settings> m_settings;
std::set<int> m_notifications;
+ GCancellable * m_cancellable {nullptr};
+ AccountsServiceSound * m_accounts_service_sound_proxy {nullptr};
};
/***
diff --git a/src/sound.cpp b/src/sound.cpp
index 3a4b26f..a768a29 100644
--- a/src/sound.cpp
+++ b/src/sound.cpp
@@ -38,9 +38,11 @@ class Sound::Impl
{
public:
- Impl(const std::string& uri,
+ Impl(const std::string& role,
+ const std::string& uri,
unsigned int volume,
bool loop):
+ m_role(role),
m_uri(uri),
m_volume(volume),
m_loop(loop)
@@ -98,8 +100,9 @@ private:
static gboolean bus_callback(GstBus*, GstMessage* msg, gpointer gself)
{
auto self = static_cast<Impl*>(gself);
+ const auto message_type = GST_MESSAGE_TYPE(msg);
- if ((GST_MESSAGE_TYPE(msg) == GST_MESSAGE_EOS) && (self->m_loop))
+ if ((message_type == GST_MESSAGE_EOS) && (self->m_loop))
{
gst_element_seek(self->m_play,
1.0,
@@ -110,7 +113,7 @@ private:
GST_SEEK_TYPE_NONE,
(gint64)GST_CLOCK_TIME_NONE);
}
- else if ((GST_MESSAGE_TYPE(msg) == GST_MESSAGE_STREAM_START) && (self->m_loop))
+ else if (message_type == GST_MESSAGE_STREAM_START)
{
/* Set the media role if audio sink is pulsesink */
GstElement *audio_sink = nullptr;
@@ -121,10 +124,11 @@ private:
feature = GST_PLUGIN_FEATURE_CAST(GST_ELEMENT_GET_CLASS(audio_sink)->elementfactory);
if (feature && g_strcmp0(gst_plugin_feature_get_name(feature), "pulsesink") == 0)
{
- std::string role_str("props,media.role=alarm");
- GstStructure *props = gst_structure_from_string(role_str.c_str(), nullptr);
+ auto role_str = g_strdup_printf("props,media.role=%s", self->m_role.c_str());
+ GstStructure *props = gst_structure_from_string(role_str, nullptr);
g_object_set(audio_sink, "stream-properties", props, nullptr);
gst_structure_free(props);
+ g_free(role_str);
}
gst_object_unref(audio_sink);
}
@@ -137,6 +141,7 @@ private:
****
***/
+ const std::string m_role;
const std::string m_uri;
const unsigned int m_volume;
const bool m_loop;
@@ -144,8 +149,8 @@ private:
GstElement* m_play = nullptr;
};
-Sound::Sound(const std::string& uri, unsigned int volume, bool loop):
- impl (new Impl(uri, volume, loop))
+Sound::Sound(const std::string& role, const std::string& uri, unsigned int volume, bool loop):
+ impl (new Impl(role, uri, volume, loop))
{
}
diff --git a/tests/manual b/tests/manual
index c283422..007f967 100644
--- a/tests/manual
+++ b/tests/manual
@@ -124,6 +124,19 @@ Test-case indicator-datetime/change-alarm-sound
<dd>The newly-selected sound should play, rather than the previous sound.</dd>
</dl>
+Test-case indicator-datetime/silent-mode
+<dl>
+ <dt>Set an alarm and wait for it to arrive.</dt>
+ <dt>From the sound indicator, turn on silent mode.</dt>
+ <dd>Alarm should go off at the specified time and play its sound regardless of silent mode.</dd>
+ <dt>From the sound indicator, turn on silent mode.</dt>
+ <dt>Create a calendar event from the calendar app and wait for it to arrive.</dt>
+ <dd>The calendar event notification should be silent.</dd>
+ <dt>From the sound indicator, turn off silent mode.</dt>
+ <dt>Create a calendar event from the calendar app and wait for it to arrive.</dt>
+ <dd>The calendar event notification should play a sound.</dd>
+</dl>
+
<strong>
If all actions produce the expected results listed, please <a href="results#add_result">submit</a> a 'passed' result.
If an action fails, or produces an unexpected result, please <a href="results#add_result">submit</a> a 'failed' result and <a href="../../buginstructions">file a bug</a>. Please be sure to include the bug number when you <a href="results#add_result">submit</a> your result</strong>.