diff --git a/openlp/core/ui/advancedtab.py b/openlp/core/ui/advancedtab.py index fe8c09131..08adc0f29 100644 --- a/openlp/core/ui/advancedtab.py +++ b/openlp/core/ui/advancedtab.py @@ -274,7 +274,7 @@ class AdvancedTab(SettingsTab): self.single_click_preview_check_box.setText(translate('OpenLP.AdvancedTab', 'Preview items when clicked in Media Manager')) self.single_click_service_preview_check_box.setText(translate('OpenLP.AdvancedTab', - 'Preview items when clicked in Service Manager')) + 'Preview items when clicked in Service Manager')) self.expand_service_item_check_box.setText(translate('OpenLP.AdvancedTab', 'Expand new service items on creation')) self.enable_auto_close_check_box.setText(translate('OpenLP.AdvancedTab', diff --git a/openlp/core/ui/servicemanager.py b/openlp/core/ui/servicemanager.py index a90ab1e8b..e75a24d9e 100644 --- a/openlp/core/ui/servicemanager.py +++ b/openlp/core/ui/servicemanager.py @@ -211,7 +211,7 @@ class Ui_ServiceManager(object): self.layout.addWidget(self.order_toolbar) # Connect up our signals and slots self.theme_combo_box.activated.connect(self.on_theme_combo_box_selected) - self.service_manager_list.doubleClicked.connect(self.on_make_live) + self.service_manager_list.doubleClicked.connect(self.on_double_click_live) self.service_manager_list.clicked.connect(self.on_single_click_preview) self.service_manager_list.itemCollapsed.connect(self.collapsed) self.service_manager_list.itemExpanded.connect(self.expanded) @@ -320,6 +320,7 @@ class ServiceManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ServiceMa self._modified = False self._file_name = '' self.service_has_all_original_files = True + self.list_double_clicked = False def bootstrap_initialise(self): """ @@ -1455,19 +1456,34 @@ class ServiceManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ServiceMa else: return self.service_items[item]['service_item'] - def on_make_live(self, field=None): + def on_double_click_live(self, field=None): """ Send the current item to the Live slide controller but triggered by a tablewidget click event. :param field: """ + self.list_double_clicked = True self.make_live() def on_single_click_preview(self, field=None): """ - If single click previewing is enabled, send the current item to the Preview slide controller but triggered by a tablewidget click event. + If single click previewing is enabled, and triggered by a tablewidget click event, start a timeout to verify a double-click hasn't triggered. :param field: """ if Settings().value('advanced/single click service preview'): + if not self.list_double_clicked: + # If a double click has not registered start a timer, otherwise wait for the existing timer to finish. + QtCore.QTimer.singleShot(QtWidgets.QApplication.instance().doubleClickInterval(), self.on_single_click_preview_timeout) + + def on_single_click_preview_timeout(self): + """ + If a single click, but not a double click has been triggered, send the current item to the Preview slide controller. + :param field: + """ + if self.list_double_clicked: + # If a double click has registered, clear it. + self.list_double_clicked = False + else: + # Otherwise preview the item. self.make_preview() def make_live(self, row=-1): diff --git a/tests/functional/openlp_core_ui/test_servicemanager.py b/tests/functional/openlp_core_ui/test_servicemanager.py index f013b9ada..f731f7761 100644 --- a/tests/functional/openlp_core_ui/test_servicemanager.py +++ b/tests/functional/openlp_core_ui/test_servicemanager.py @@ -22,6 +22,7 @@ """ Package to test the openlp.core.ui.slidecontroller package. """ +import PyQt5 from unittest import TestCase from openlp.core.common import Registry, ThemeLevel, Settings @@ -540,12 +541,12 @@ class TestServiceManager(TestCase): self.assertEquals(service_manager.timed_slide_interval.setChecked.call_count, 0, 'Should not be called') self.assertEquals(service_manager.theme_menu.menuAction().setVisible.call_count, 1, 'Should have be called once') - + @patch(u'openlp.core.ui.servicemanager.Settings') - @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_preview') - def single_click_preview_test_true(self, mocked_make_preview, MockedSettings): + @patch(u'PyQt5.QtCore.QTimer.singleShot') + def single_click_preview_test_true(self, mocked_singleShot, MockedSettings): """ - Test that when "Preview items when clicked in Service Manager" is enabled that the item goes to preview + Test that when "Preview items when clicked in Service Manager" enabled the preview timer starts """ # GIVEN: A setting to enable "Preview items when clicked in Service Manager" and a service manager. mocked_settings = MagicMock() @@ -554,14 +555,14 @@ class TestServiceManager(TestCase): service_manager = ServiceManager(None) # WHEN: on_single_click_preview() is called service_manager.on_single_click_preview() - # THEN: make_preview() should have been called - self.assertEquals(mocked_make_preview.call_count, 1, 'Should have been called once') - + # THEN: timer should have been started + mocked_singleShot.assert_called_with(PyQt5.QtWidgets.QApplication.instance().doubleClickInterval(),service_manager.on_single_click_preview_timeout) + @patch(u'openlp.core.ui.servicemanager.Settings') - @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_preview') - def single_click_preview_test_false(self, mocked_make_preview, MockedSettings): + @patch(u'PyQt5.QtCore.QTimer.singleShot') + def single_click_preview_test_false(self, mocked_singleShot, MockedSettings): """ - Test that when "Preview items when clicked in Service Manager" is disabled that the item does not goes to preview + Test that when "Preview items when clicked in Service Manager" disabled the preview timer doesn't start """ # GIVEN: A setting to enable "Preview items when clicked in Service Manager" and a service manager. mocked_settings = MagicMock() @@ -570,5 +571,49 @@ class TestServiceManager(TestCase): service_manager = ServiceManager(None) # WHEN: on_single_click_preview() is called service_manager.on_single_click_preview() + # THEN: timer should not be started + self.assertEquals(mocked_singleShot.call_count, 0, 'Should not be called') + + @patch(u'openlp.core.ui.servicemanager.Settings') + @patch(u'PyQt5.QtCore.QTimer.singleShot') + @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_live') + def single_click_preview_test_double(self, mocked_make_live, mocked_singleShot, MockedSettings): + """ + Test that when a double click has registered the preview timer doesn't start + """ + # GIVEN: A setting to enable "Preview items when clicked in Service Manager" and a service manager. + mocked_settings = MagicMock() + mocked_settings.value.return_value = True + MockedSettings.return_value = mocked_settings + service_manager = ServiceManager(None) + # WHEN: on_single_click_preview() is called following a double click + service_manager.on_double_click_live() + service_manager.on_single_click_preview() + # THEN: timer should not be started + self.assertEquals(mocked_singleShot.call_count, 0, 'Should not be called') + + @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_preview') + def single_click_timeout_test_single(self, mocked_make_preview): + """ + Test that when a single click has been registered, the item is sent to preview + """ + # GIVEN: A service manager. + service_manager = ServiceManager(None) + # WHEN: on_single_click_preview() is called + service_manager.on_single_click_preview_timeout() + # THEN: make_preview() should have been called + self.assertEquals(mocked_make_preview.call_count, 1, 'Should have been called once') + + @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_preview') + @patch(u'openlp.core.ui.servicemanager.ServiceManager.make_live') + def single_click_timeout_test_double(self, mocked_make_live, mocked_make_preview): + """ + Test that when a double click has been registered, the item does not goes to preview + """ + # GIVEN: A service manager. + service_manager = ServiceManager(None) + # WHEN: on_single_click_preview() is called after a double click + service_manager.on_double_click_live() + service_manager.on_single_click_preview_timeout() # THEN: make_preview() should have been called self.assertEquals(mocked_make_preview.call_count, 0, 'Should not be called')