Phase 1 complete

This commit is contained in:
Raoul Snyman 2017-10-07 00:05:07 -07:00
parent 63cdc813b0
commit b406cfd5a8
303 changed files with 2036 additions and 2160 deletions

View File

@ -27,16 +27,26 @@ import faulthandler
import multiprocessing import multiprocessing
import sys import sys
from openlp.core import main
from openlp.core.common import is_win, is_macosx from openlp.core.common import is_win, is_macosx
from openlp.core.common.applocation import AppLocation from openlp.core.common.applocation import AppLocation
from openlp.core import main from openlp.core.common.path import create_paths
def set_up_fault_handling():
"""
Set up the Python fault handler
"""
# Create the cache directory if it doesn't exist, and enable the fault handler to log to an error log file
create_paths(AppLocation.get_directory(AppLocation.CacheDir))
faulthandler.enable(open(str(AppLocation.get_directory(AppLocation.CacheDir) / 'error.log'), 'wb'))
faulthandler.enable(open(str(AppLocation.get_directory(AppLocation.CacheDir) / 'error.log'), 'wb'))
if __name__ == '__main__': if __name__ == '__main__':
""" """
Instantiate and run the application. Instantiate and run the application.
""" """
set_up_fault_handling()
# Add support for using multiprocessing from frozen Windows executable (built using PyInstaller), # Add support for using multiprocessing from frozen Windows executable (built using PyInstaller),
# see https://docs.python.org/3/library/multiprocessing.html#multiprocessing.freeze_support # see https://docs.python.org/3/library/multiprocessing.html#multiprocessing.freeze_support
if is_win(): if is_win():

View File

@ -33,11 +33,15 @@ import time
from datetime import datetime from datetime import datetime
from traceback import format_exception from traceback import format_exception
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, OpenLPMixin, AppLocation, LanguageManager, Settings, UiStrings, \ from openlp.core.common import is_macosx, is_win
check_directory_exists, is_macosx, is_win, translate from openlp.core.common.applocation import AppLocation
from openlp.core.common.path import Path, copytree from openlp.core.common.i18n import LanguageManager, UiStrings, translate
from openlp.core.common.mixins import OpenLPMixin
from openlp.core.common.path import create_paths, copytree
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.version import check_for_update, get_version from openlp.core.version import check_for_update, get_version
from openlp.core.lib import ScreenList from openlp.core.lib import ScreenList
from openlp.core.resources import qInitResources from openlp.core.resources import qInitResources
@ -316,7 +320,7 @@ def set_up_logging(log_path):
:param openlp.core.common.path.Path log_path: The file to save the log to. :param openlp.core.common.path.Path log_path: The file to save the log to.
:rtype: None :rtype: None
""" """
check_directory_exists(log_path, True) create_paths(log_path, True)
file_path = log_path / 'openlp.log' file_path = log_path / 'openlp.log'
# TODO: FileHandler accepts a Path object in Py3.6 # TODO: FileHandler accepts a Path object in Py3.6
logfile = logging.FileHandler(str(file_path), 'w', encoding='UTF-8') logfile = logging.FileHandler(str(file_path), 'w', encoding='UTF-8')

View File

@ -25,7 +25,8 @@ Download and "install" the remote web client
import os import os
from zipfile import ZipFile from zipfile import ZipFile
from openlp.core.common import AppLocation, Registry from openlp.core.common.applocation import AppLocation
from openlp.core.common.registry import Registry
from openlp.core.common.httputils import url_get_file, get_web_page, get_url_file_size from openlp.core.common.httputils import url_get_file, get_web_page, get_url_file_size

View File

@ -27,7 +27,9 @@ import json
from openlp.core.api.http.endpoint import Endpoint from openlp.core.api.http.endpoint import Endpoint
from openlp.core.api.http import requires_auth from openlp.core.api.http import requires_auth
from openlp.core.common import Registry, AppLocation, Settings from openlp.core.common.applocation import AppLocation
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import ItemCapabilities, create_thumb from openlp.core.lib import ItemCapabilities, create_thumb
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -19,13 +19,17 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
"""
The :mod:`~openlp.core.api.endpoint.core` module contains the core API endpoints
"""
import logging import logging
import os import os
from openlp.core.api.http.endpoint import Endpoint
from openlp.core.api.http import requires_auth from openlp.core.api.http import requires_auth
from openlp.core.common import Registry, UiStrings, translate from openlp.core.api.http.endpoint import Endpoint
from openlp.core.lib import image_to_byte, PluginStatus, StringContent from openlp.core.common.registry import Registry
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import PluginStatus, StringContent, image_to_byte
template_dir = 'templates' template_dir = 'templates'

View File

@ -24,11 +24,11 @@ import json
import re import re
import urllib import urllib
from urllib.parse import urlparse
from webob import Response from webob import Response
from openlp.core.api.http.errors import NotFound from openlp.core.api.http.errors import NotFound
from openlp.core.common import Registry, AppLocation from openlp.core.common.applocation import AppLocation
from openlp.core.common.registry import Registry
from openlp.core.lib import PluginStatus, image_to_byte from openlp.core.lib import PluginStatus, image_to_byte

View File

@ -22,9 +22,9 @@
import logging import logging
import json import json
from openlp.core.api.http.endpoint import Endpoint
from openlp.core.api.http import requires_auth from openlp.core.api.http import requires_auth
from openlp.core.common import Registry from openlp.core.api.http.endpoint import Endpoint
from openlp.core.common.registry import Registry
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -22,12 +22,12 @@
""" """
The Endpoint class, which provides plugins with a way to serve their own portion of the API The Endpoint class, which provides plugins with a way to serve their own portion of the API
""" """
import os import os
from openlp.core.common import AppLocation
from mako.template import Template from mako.template import Template
from openlp.core.common.applocation import AppLocation
class Endpoint(object): class Endpoint(object):
""" """

View File

@ -19,31 +19,31 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
The :mod:`http` module contains the API web server. This is a lightweight web server used by remotes to interact The :mod:`http` module contains the API web server. This is a lightweight web server used by remotes to interact
with OpenLP. It uses JSON to communicate with the remotes. with OpenLP. It uses JSON to communicate with the remotes.
""" """
import logging import logging
import time import time
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from waitress import serve from waitress import serve
from openlp.core.api.http import register_endpoint
from openlp.core.api.http import application
from openlp.core.common import AppLocation, RegistryMixin, RegistryProperties, OpenLPMixin, \
Settings, Registry, UiStrings, check_directory_exists
from openlp.core.lib import translate
from openlp.core.api.deploy import download_and_check, download_sha256 from openlp.core.api.deploy import download_and_check, download_sha256
from openlp.core.api.poll import Poller
from openlp.core.api.endpoint.controller import controller_endpoint, api_controller_endpoint from openlp.core.api.endpoint.controller import controller_endpoint, api_controller_endpoint
from openlp.core.api.endpoint.core import chords_endpoint, stage_endpoint, blank_endpoint, main_endpoint from openlp.core.api.endpoint.core import chords_endpoint, stage_endpoint, blank_endpoint, main_endpoint
from openlp.core.api.endpoint.service import service_endpoint, api_service_endpoint from openlp.core.api.endpoint.service import service_endpoint, api_service_endpoint
from openlp.core.api.endpoint.remote import remote_endpoint from openlp.core.api.endpoint.remote import remote_endpoint
from openlp.core.api.http import register_endpoint
from openlp.core.api.http import application
from openlp.core.api.poll import Poller
from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import UiStrings
from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.path import create_paths
from openlp.core.common.registry import RegistryProperties, Registry
from openlp.core.common.settings import Settings
from openlp.core.common.i18n import translate
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
@ -115,11 +115,11 @@ class HttpServer(RegistryMixin, RegistryProperties, OpenLPMixin):
Create the internal file structure if it does not exist Create the internal file structure if it does not exist
:return: :return:
""" """
check_directory_exists(AppLocation.get_section_data_path('remotes') / 'assets') create_paths(AppLocation.get_section_data_path('remotes') / 'assets',
check_directory_exists(AppLocation.get_section_data_path('remotes') / 'images') AppLocation.get_section_data_path('remotes') / 'images',
check_directory_exists(AppLocation.get_section_data_path('remotes') / 'static') AppLocation.get_section_data_path('remotes') / 'static',
check_directory_exists(AppLocation.get_section_data_path('remotes') / 'static' / 'index') AppLocation.get_section_data_path('remotes') / 'static' / 'index',
check_directory_exists(AppLocation.get_section_data_path('remotes') / 'templates') AppLocation.get_section_data_path('remotes') / 'templates')
def first_time(self): def first_time(self):
""" """

View File

@ -31,7 +31,7 @@ import re
from webob import Request, Response from webob import Request, Response
from webob.static import DirectoryApp from webob.static import DirectoryApp
from openlp.core.common import AppLocation from openlp.core.common.applocation import AppLocation
from openlp.core.api.http.errors import HttpError, NotFound, ServerError from openlp.core.api.http.errors import HttpError, NotFound, ServerError

View File

@ -22,8 +22,9 @@
import json import json
from openlp.core.common import RegistryProperties, Settings
from openlp.core.common.httputils import get_web_page from openlp.core.common.httputils import get_web_page
from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
class Poller(RegistryProperties): class Poller(RegistryProperties):

View File

@ -19,10 +19,14 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
"""
The :mod:`~openlp.core.api.tab` module contains the settings tab for the API
"""
from PyQt5 import QtCore, QtGui, QtNetwork, QtWidgets from PyQt5 import QtCore, QtGui, QtNetwork, QtWidgets
from openlp.core.common import UiStrings, Registry, Settings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab from openlp.core.lib import SettingsTab
ZERO_URL = '0.0.0.0' ZERO_URL = '0.0.0.0'

View File

@ -19,12 +19,10 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
The :mod:`http` module contains the API web server. This is a lightweight web server used by remotes to interact The :mod:`http` module contains the API web server. This is a lightweight web server used by remotes to interact
with OpenLP. It uses JSON to communicate with the remotes. with OpenLP. It uses JSON to communicate with the remotes.
""" """
import asyncio import asyncio
import websockets import websockets
import json import json
@ -33,7 +31,9 @@ import time
from PyQt5 import QtCore from PyQt5 import QtCore
from openlp.core.common import Settings, RegistryProperties, OpenLPMixin, Registry from openlp.core.common.mixins import OpenLPMixin
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -35,7 +35,7 @@ from ipaddress import IPv4Address, IPv6Address, AddressValueError
from shutil import which from shutil import which
from subprocess import check_output, CalledProcessError, STDOUT from subprocess import check_output, CalledProcessError, STDOUT
from PyQt5 import QtCore, QtGui from PyQt5 import QtGui
from PyQt5.QtCore import QCryptographicHash as QHash from PyQt5.QtCore import QCryptographicHash as QHash
log = logging.getLogger(__name__ + '.__init__') log = logging.getLogger(__name__ + '.__init__')
@ -56,30 +56,10 @@ def trace_error_handler(logger):
""" """
log_string = "OpenLP Error trace" log_string = "OpenLP Error trace"
for tb in traceback.extract_stack(): for tb in traceback.extract_stack():
log_string += '\n File {file} at line {line} \n\t called {data}'.format(file=tb[0], log_string += '\n File {file} at line {line} \n\t called {data}'.format(file=tb[0], line=tb[1], data=tb[3])
line=tb[1],
data=tb[3])
logger.error(log_string) logger.error(log_string)
def check_directory_exists(directory, do_not_log=False):
"""
Check a directory exists and if not create it
:param openlp.core.common.path.Path directory: The directory to make sure exists
:param bool do_not_log: To not log anything. This is need for the start up, when the log isn't ready.
:rtype: None
"""
if not do_not_log:
log.debug('check_directory_exists {text}'.format(text=directory))
try:
if not directory.exists():
directory.mkdir(parents=True)
except IOError:
if not do_not_log:
log.exception('failed to check if directory exists or create directory')
def extension_loader(glob_pattern, excluded_files=[]): def extension_loader(glob_pattern, excluded_files=[]):
""" """
A utility function to find and load OpenLP extensions, such as plugins, presentation and media controllers and A utility function to find and load OpenLP extensions, such as plugins, presentation and media controllers and
@ -90,6 +70,7 @@ def extension_loader(glob_pattern, excluded_files=[]):
:param list[str] excluded_files: A list of file names to exclude that the glob pattern may find. :param list[str] excluded_files: A list of file names to exclude that the glob pattern may find.
:rtype: None :rtype: None
""" """
from openlp.core.common.applocation import AppLocation
app_dir = AppLocation.get_directory(AppLocation.AppDir) app_dir = AppLocation.get_directory(AppLocation.AppDir)
for extension_path in app_dir.glob(glob_pattern): for extension_path in app_dir.glob(glob_pattern):
extension_path = extension_path.relative_to(app_dir) extension_path = extension_path.relative_to(app_dir)
@ -137,19 +118,6 @@ class ThemeLevel(object):
Song = 3 Song = 3
def translate(context, text, comment=None, qt_translate=QtCore.QCoreApplication.translate):
"""
A special shortcut method to wrap around the Qt5 translation functions. This abstracts the translation procedure so
that we can change it if at a later date if necessary, without having to redo the whole of OpenLP.
:param context: The translation context, used to give each string a context or a namespace.
:param text: The text to put into the translation tables for translation.
:param comment: An identifying string for when the same text is used in different roles within the same context.
:param qt_translate:
"""
return qt_translate(context, text, comment)
class SlideLimits(object): class SlideLimits(object):
""" """
Provides an enumeration for behaviour of OpenLP at the end limits of each service item when pressing the up/down Provides an enumeration for behaviour of OpenLP at the end limits of each service item when pressing the up/down
@ -203,7 +171,7 @@ def verify_ipv4(addr):
:returns: bool :returns: bool
""" """
try: try:
valid = IPv4Address(addr) IPv4Address(addr)
return True return True
except AddressValueError: except AddressValueError:
return False return False
@ -217,7 +185,7 @@ def verify_ipv6(addr):
:returns: bool :returns: bool
""" """
try: try:
valid = IPv6Address(addr) IPv6Address(addr)
return True return True
except AddressValueError: except AddressValueError:
return False return False
@ -290,20 +258,6 @@ def clean_button_text(button_text):
return button_text.replace('&', '').replace('< ', '').replace(' >', '') return button_text.replace('&', '').replace('< ', '').replace(' >', '')
from .openlpmixin import OpenLPMixin
from .registry import Registry
from .registrymixin import RegistryMixin
from .registryproperties import RegistryProperties
from .uistrings import UiStrings
from .settings import Settings
from .applocation import AppLocation
from .actions import ActionList
from .languagemanager import LanguageManager
if is_win():
from subprocess import STARTUPINFO, STARTF_USESHOWWINDOW
def add_actions(target, actions): def add_actions(target, actions):
""" """
Adds multiple actions to a menu or toolbar in one command. Adds multiple actions to a menu or toolbar in one command.
@ -394,6 +348,7 @@ def get_images_filter():
""" """
Returns a filter string for a file dialog containing all the supported image formats. Returns a filter string for a file dialog containing all the supported image formats.
""" """
from openlp.core.common.i18n import translate
global IMAGES_FILTER global IMAGES_FILTER
if not IMAGES_FILTER: if not IMAGES_FILTER:
log.debug('Generating images filter.') log.debug('Generating images filter.')
@ -446,6 +401,7 @@ def check_binary_exists(program_path):
try: try:
# Setup startupinfo options for check_output to avoid console popping up on windows # Setup startupinfo options for check_output to avoid console popping up on windows
if is_win(): if is_win():
from subprocess import STARTUPINFO, STARTF_USESHOWWINDOW
startupinfo = STARTUPINFO() startupinfo = STARTUPINFO()
startupinfo.dwFlags |= STARTF_USESHOWWINDOW startupinfo.dwFlags |= STARTF_USESHOWWINDOW
else: else:

View File

@ -27,7 +27,7 @@ import logging
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Settings from openlp.core.common.settings import Settings
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -26,8 +26,10 @@ import logging
import os import os
import sys import sys
from openlp.core.common import Settings, is_win, is_macosx import openlp
from openlp.core.common.path import Path from openlp.core.common import get_frozen_path, is_win, is_macosx
from openlp.core.common.path import Path, create_paths
from openlp.core.common.settings import Settings
if not is_win() and not is_macosx(): if not is_win() and not is_macosx():
try: try:
@ -36,10 +38,6 @@ if not is_win() and not is_macosx():
except ImportError: except ImportError:
XDG_BASE_AVAILABLE = False XDG_BASE_AVAILABLE = False
import openlp
from openlp.core.common import check_directory_exists, get_frozen_path
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
FROZEN_APP_PATH = Path(sys.argv[0]).parent FROZEN_APP_PATH = Path(sys.argv[0]).parent
@ -88,7 +86,7 @@ class AppLocation(object):
path = Settings().value('advanced/data path') path = Settings().value('advanced/data path')
else: else:
path = AppLocation.get_directory(AppLocation.DataDir) path = AppLocation.get_directory(AppLocation.DataDir)
check_directory_exists(path) create_paths(path)
return path return path
@staticmethod @staticmethod
@ -121,7 +119,7 @@ class AppLocation(object):
:rtype: openlp.core.common.path.Path :rtype: openlp.core.common.path.Path
""" """
path = AppLocation.get_data_path() / section path = AppLocation.get_data_path() / section
check_directory_exists(path) create_paths(path)
return path return path

View File

@ -30,7 +30,8 @@ from random import randint
import requests import requests
from openlp.core.common import Registry, trace_error_handler from openlp.core.common import trace_error_handler
from openlp.core.common.registry import Registry
log = logging.getLogger(__name__ + '.__init__') log = logging.getLogger(__name__ + '.__init__')

556
openlp/core/common/i18n.py Normal file
View File

@ -0,0 +1,556 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
The :mod:`languages` module provides a list of language names with utility functions.
"""
import itertools
import locale
import logging
import re
from collections import namedtuple
from PyQt5 import QtCore, QtWidgets
from openlp.core.common import is_win, is_macosx
from openlp.core.common.applocation import AppLocation
from openlp.core.common.settings import Settings
log = logging.getLogger(__name__)
# Due to dependency issues, this HAS to be at the top of the file
def translate(context, text, comment=None, qt_translate=QtCore.QCoreApplication.translate):
"""
A special shortcut method to wrap around the Qt5 translation functions. This abstracts the translation procedure so
that we can change it if at a later date if necessary, without having to redo the whole of OpenLP.
:param context: The translation context, used to give each string a context or a namespace.
:param text: The text to put into the translation tables for translation.
:param comment: An identifying string for when the same text is used in different roles within the same context.
:param qt_translate:
"""
return qt_translate(context, text, comment)
Language = namedtuple('Language', ['id', 'name', 'code'])
ICU_COLLATOR = None
DIGITS_OR_NONDIGITS = re.compile(r'\d+|\D+', re.UNICODE)
LANGUAGES = sorted([
Language(1, translate('common.languages', '(Afan) Oromo', 'Language code: om'), 'om'),
Language(2, translate('common.languages', 'Abkhazian', 'Language code: ab'), 'ab'),
Language(3, translate('common.languages', 'Afar', 'Language code: aa'), 'aa'),
Language(4, translate('common.languages', 'Afrikaans', 'Language code: af'), 'af'),
Language(5, translate('common.languages', 'Albanian', 'Language code: sq'), 'sq'),
Language(6, translate('common.languages', 'Amharic', 'Language code: am'), 'am'),
Language(140, translate('common.languages', 'Amuzgo', 'Language code: amu'), 'amu'),
Language(152, translate('common.languages', 'Ancient Greek', 'Language code: grc'), 'grc'),
Language(7, translate('common.languages', 'Arabic', 'Language code: ar'), 'ar'),
Language(8, translate('common.languages', 'Armenian', 'Language code: hy'), 'hy'),
Language(9, translate('common.languages', 'Assamese', 'Language code: as'), 'as'),
Language(10, translate('common.languages', 'Aymara', 'Language code: ay'), 'ay'),
Language(11, translate('common.languages', 'Azerbaijani', 'Language code: az'), 'az'),
Language(12, translate('common.languages', 'Bashkir', 'Language code: ba'), 'ba'),
Language(13, translate('common.languages', 'Basque', 'Language code: eu'), 'eu'),
Language(14, translate('common.languages', 'Bengali', 'Language code: bn'), 'bn'),
Language(15, translate('common.languages', 'Bhutani', 'Language code: dz'), 'dz'),
Language(16, translate('common.languages', 'Bihari', 'Language code: bh'), 'bh'),
Language(17, translate('common.languages', 'Bislama', 'Language code: bi'), 'bi'),
Language(18, translate('common.languages', 'Breton', 'Language code: br'), 'br'),
Language(19, translate('common.languages', 'Bulgarian', 'Language code: bg'), 'bg'),
Language(20, translate('common.languages', 'Burmese', 'Language code: my'), 'my'),
Language(21, translate('common.languages', 'Byelorussian', 'Language code: be'), 'be'),
Language(142, translate('common.languages', 'Cakchiquel', 'Language code: cak'), 'cak'),
Language(22, translate('common.languages', 'Cambodian', 'Language code: km'), 'km'),
Language(23, translate('common.languages', 'Catalan', 'Language code: ca'), 'ca'),
Language(24, translate('common.languages', 'Chinese', 'Language code: zh'), 'zh'),
Language(141, translate('common.languages', 'Comaltepec Chinantec', 'Language code: cco'), 'cco'),
Language(25, translate('common.languages', 'Corsican', 'Language code: co'), 'co'),
Language(26, translate('common.languages', 'Croatian', 'Language code: hr'), 'hr'),
Language(27, translate('common.languages', 'Czech', 'Language code: cs'), 'cs'),
Language(28, translate('common.languages', 'Danish', 'Language code: da'), 'da'),
Language(29, translate('common.languages', 'Dutch', 'Language code: nl'), 'nl'),
Language(30, translate('common.languages', 'English', 'Language code: en'), 'en'),
Language(31, translate('common.languages', 'Esperanto', 'Language code: eo'), 'eo'),
Language(32, translate('common.languages', 'Estonian', 'Language code: et'), 'et'),
Language(33, translate('common.languages', 'Faeroese', 'Language code: fo'), 'fo'),
Language(34, translate('common.languages', 'Fiji', 'Language code: fj'), 'fj'),
Language(35, translate('common.languages', 'Finnish', 'Language code: fi'), 'fi'),
Language(36, translate('common.languages', 'French', 'Language code: fr'), 'fr'),
Language(37, translate('common.languages', 'Frisian', 'Language code: fy'), 'fy'),
Language(38, translate('common.languages', 'Galician', 'Language code: gl'), 'gl'),
Language(39, translate('common.languages', 'Georgian', 'Language code: ka'), 'ka'),
Language(40, translate('common.languages', 'German', 'Language code: de'), 'de'),
Language(41, translate('common.languages', 'Greek', 'Language code: el'), 'el'),
Language(42, translate('common.languages', 'Greenlandic', 'Language code: kl'), 'kl'),
Language(43, translate('common.languages', 'Guarani', 'Language code: gn'), 'gn'),
Language(44, translate('common.languages', 'Gujarati', 'Language code: gu'), 'gu'),
Language(143, translate('common.languages', 'Haitian Creole', 'Language code: ht'), 'ht'),
Language(45, translate('common.languages', 'Hausa', 'Language code: ha'), 'ha'),
Language(46, translate('common.languages', 'Hebrew (former iw)', 'Language code: he'), 'he'),
Language(144, translate('common.languages', 'Hiligaynon', 'Language code: hil'), 'hil'),
Language(47, translate('common.languages', 'Hindi', 'Language code: hi'), 'hi'),
Language(48, translate('common.languages', 'Hungarian', 'Language code: hu'), 'hu'),
Language(49, translate('common.languages', 'Icelandic', 'Language code: is'), 'is'),
Language(50, translate('common.languages', 'Indonesian (former in)', 'Language code: id'), 'id'),
Language(51, translate('common.languages', 'Interlingua', 'Language code: ia'), 'ia'),
Language(52, translate('common.languages', 'Interlingue', 'Language code: ie'), 'ie'),
Language(54, translate('common.languages', 'Inuktitut (Eskimo)', 'Language code: iu'), 'iu'),
Language(53, translate('common.languages', 'Inupiak', 'Language code: ik'), 'ik'),
Language(55, translate('common.languages', 'Irish', 'Language code: ga'), 'ga'),
Language(56, translate('common.languages', 'Italian', 'Language code: it'), 'it'),
Language(145, translate('common.languages', 'Jakalteko', 'Language code: jac'), 'jac'),
Language(57, translate('common.languages', 'Japanese', 'Language code: ja'), 'ja'),
Language(58, translate('common.languages', 'Javanese', 'Language code: jw'), 'jw'),
Language(150, translate('common.languages', 'K\'iche\'', 'Language code: quc'), 'quc'),
Language(59, translate('common.languages', 'Kannada', 'Language code: kn'), 'kn'),
Language(60, translate('common.languages', 'Kashmiri', 'Language code: ks'), 'ks'),
Language(61, translate('common.languages', 'Kazakh', 'Language code: kk'), 'kk'),
Language(146, translate('common.languages', 'Kekchí ', 'Language code: kek'), 'kek'),
Language(62, translate('common.languages', 'Kinyarwanda', 'Language code: rw'), 'rw'),
Language(63, translate('common.languages', 'Kirghiz', 'Language code: ky'), 'ky'),
Language(64, translate('common.languages', 'Kirundi', 'Language code: rn'), 'rn'),
Language(65, translate('common.languages', 'Korean', 'Language code: ko'), 'ko'),
Language(66, translate('common.languages', 'Kurdish', 'Language code: ku'), 'ku'),
Language(67, translate('common.languages', 'Laothian', 'Language code: lo'), 'lo'),
Language(68, translate('common.languages', 'Latin', 'Language code: la'), 'la'),
Language(69, translate('common.languages', 'Latvian, Lettish', 'Language code: lv'), 'lv'),
Language(70, translate('common.languages', 'Lingala', 'Language code: ln'), 'ln'),
Language(71, translate('common.languages', 'Lithuanian', 'Language code: lt'), 'lt'),
Language(72, translate('common.languages', 'Macedonian', 'Language code: mk'), 'mk'),
Language(73, translate('common.languages', 'Malagasy', 'Language code: mg'), 'mg'),
Language(74, translate('common.languages', 'Malay', 'Language code: ms'), 'ms'),
Language(75, translate('common.languages', 'Malayalam', 'Language code: ml'), 'ml'),
Language(76, translate('common.languages', 'Maltese', 'Language code: mt'), 'mt'),
Language(148, translate('common.languages', 'Mam', 'Language code: mam'), 'mam'),
Language(77, translate('common.languages', 'Maori', 'Language code: mi'), 'mi'),
Language(147, translate('common.languages', 'Maori', 'Language code: mri'), 'mri'),
Language(78, translate('common.languages', 'Marathi', 'Language code: mr'), 'mr'),
Language(79, translate('common.languages', 'Moldavian', 'Language code: mo'), 'mo'),
Language(80, translate('common.languages', 'Mongolian', 'Language code: mn'), 'mn'),
Language(149, translate('common.languages', 'Nahuatl', 'Language code: nah'), 'nah'),
Language(81, translate('common.languages', 'Nauru', 'Language code: na'), 'na'),
Language(82, translate('common.languages', 'Nepali', 'Language code: ne'), 'ne'),
Language(83, translate('common.languages', 'Norwegian', 'Language code: no'), 'no'),
Language(84, translate('common.languages', 'Occitan', 'Language code: oc'), 'oc'),
Language(85, translate('common.languages', 'Oriya', 'Language code: or'), 'or'),
Language(86, translate('common.languages', 'Pashto, Pushto', 'Language code: ps'), 'ps'),
Language(87, translate('common.languages', 'Persian', 'Language code: fa'), 'fa'),
Language(151, translate('common.languages', 'Plautdietsch', 'Language code: pdt'), 'pdt'),
Language(88, translate('common.languages', 'Polish', 'Language code: pl'), 'pl'),
Language(89, translate('common.languages', 'Portuguese', 'Language code: pt'), 'pt'),
Language(90, translate('common.languages', 'Punjabi', 'Language code: pa'), 'pa'),
Language(91, translate('common.languages', 'Quechua', 'Language code: qu'), 'qu'),
Language(92, translate('common.languages', 'Rhaeto-Romance', 'Language code: rm'), 'rm'),
Language(93, translate('common.languages', 'Romanian', 'Language code: ro'), 'ro'),
Language(94, translate('common.languages', 'Russian', 'Language code: ru'), 'ru'),
Language(95, translate('common.languages', 'Samoan', 'Language code: sm'), 'sm'),
Language(96, translate('common.languages', 'Sangro', 'Language code: sg'), 'sg'),
Language(97, translate('common.languages', 'Sanskrit', 'Language code: sa'), 'sa'),
Language(98, translate('common.languages', 'Scots Gaelic', 'Language code: gd'), 'gd'),
Language(99, translate('common.languages', 'Serbian', 'Language code: sr'), 'sr'),
Language(100, translate('common.languages', 'Serbo-Croatian', 'Language code: sh'), 'sh'),
Language(101, translate('common.languages', 'Sesotho', 'Language code: st'), 'st'),
Language(102, translate('common.languages', 'Setswana', 'Language code: tn'), 'tn'),
Language(103, translate('common.languages', 'Shona', 'Language code: sn'), 'sn'),
Language(104, translate('common.languages', 'Sindhi', 'Language code: sd'), 'sd'),
Language(105, translate('common.languages', 'Singhalese', 'Language code: si'), 'si'),
Language(106, translate('common.languages', 'Siswati', 'Language code: ss'), 'ss'),
Language(107, translate('common.languages', 'Slovak', 'Language code: sk'), 'sk'),
Language(108, translate('common.languages', 'Slovenian', 'Language code: sl'), 'sl'),
Language(109, translate('common.languages', 'Somali', 'Language code: so'), 'so'),
Language(110, translate('common.languages', 'Spanish', 'Language code: es'), 'es'),
Language(111, translate('common.languages', 'Sudanese', 'Language code: su'), 'su'),
Language(112, translate('common.languages', 'Swahili', 'Language code: sw'), 'sw'),
Language(113, translate('common.languages', 'Swedish', 'Language code: sv'), 'sv'),
Language(114, translate('common.languages', 'Tagalog', 'Language code: tl'), 'tl'),
Language(115, translate('common.languages', 'Tajik', 'Language code: tg'), 'tg'),
Language(116, translate('common.languages', 'Tamil', 'Language code: ta'), 'ta'),
Language(117, translate('common.languages', 'Tatar', 'Language code: tt'), 'tt'),
Language(118, translate('common.languages', 'Tegulu', 'Language code: te'), 'te'),
Language(119, translate('common.languages', 'Thai', 'Language code: th'), 'th'),
Language(120, translate('common.languages', 'Tibetan', 'Language code: bo'), 'bo'),
Language(121, translate('common.languages', 'Tigrinya', 'Language code: ti'), 'ti'),
Language(122, translate('common.languages', 'Tonga', 'Language code: to'), 'to'),
Language(123, translate('common.languages', 'Tsonga', 'Language code: ts'), 'ts'),
Language(124, translate('common.languages', 'Turkish', 'Language code: tr'), 'tr'),
Language(125, translate('common.languages', 'Turkmen', 'Language code: tk'), 'tk'),
Language(126, translate('common.languages', 'Twi', 'Language code: tw'), 'tw'),
Language(127, translate('common.languages', 'Uigur', 'Language code: ug'), 'ug'),
Language(128, translate('common.languages', 'Ukrainian', 'Language code: uk'), 'uk'),
Language(129, translate('common.languages', 'Urdu', 'Language code: ur'), 'ur'),
Language(153, translate('common.languages', 'Uspanteco', 'Language code: usp'), 'usp'),
Language(130, translate('common.languages', 'Uzbek', 'Language code: uz'), 'uz'),
Language(131, translate('common.languages', 'Vietnamese', 'Language code: vi'), 'vi'),
Language(132, translate('common.languages', 'Volapuk', 'Language code: vo'), 'vo'),
Language(133, translate('common.languages', 'Welch', 'Language code: cy'), 'cy'),
Language(134, translate('common.languages', 'Wolof', 'Language code: wo'), 'wo'),
Language(135, translate('common.languages', 'Xhosa', 'Language code: xh'), 'xh'),
Language(136, translate('common.languages', 'Yiddish (former ji)', 'Language code: yi'), 'yi'),
Language(137, translate('common.languages', 'Yoruba', 'Language code: yo'), 'yo'),
Language(138, translate('common.languages', 'Zhuang', 'Language code: za'), 'za'),
Language(139, translate('common.languages', 'Zulu', 'Language code: zu'), 'zu')
], key=lambda language: language.name)
class LanguageManager(object):
"""
Helper for Language selection
"""
__qm_list__ = {}
auto_language = False
@staticmethod
def get_translators(language):
"""
Set up a translator to use in this instance of OpenLP
:param language: The language to load into the translator
"""
if LanguageManager.auto_language:
language = QtCore.QLocale.system().name()
lang_path = str(AppLocation.get_directory(AppLocation.LanguageDir))
app_translator = QtCore.QTranslator()
app_translator.load(language, lang_path)
# A translator for buttons and other default strings provided by Qt.
if not is_win() and not is_macosx():
lang_path = QtCore.QLibraryInfo.location(QtCore.QLibraryInfo.TranslationsPath)
# As of Qt5, the core translations come in 2 files per language
default_translator = QtCore.QTranslator()
default_translator.load('qt_%s' % language, lang_path)
base_translator = QtCore.QTranslator()
base_translator.load('qtbase_%s' % language, lang_path)
return app_translator, default_translator, base_translator
@staticmethod
def find_qm_files():
"""
Find all available language files in this OpenLP install
"""
log.debug('Translation files: {files}'.format(files=AppLocation.get_directory(AppLocation.LanguageDir)))
trans_dir = QtCore.QDir(str(AppLocation.get_directory(AppLocation.LanguageDir)))
file_names = trans_dir.entryList(['*.qm'], QtCore.QDir.Files, QtCore.QDir.Name)
# Remove qm files from the list which start with "qt".
file_names = [file_ for file_ in file_names if not file_.startswith('qt')]
return list(map(trans_dir.filePath, file_names))
@staticmethod
def language_name(qm_file):
"""
Load the language name from a language file
:param qm_file: The file to obtain the name from
"""
translator = QtCore.QTranslator()
translator.load(qm_file)
return translator.translate('OpenLP.MainWindow', 'English', 'Please add the name of your language here')
@staticmethod
def get_language():
"""
Retrieve a saved language to use from settings
"""
language = Settings().value('core/language')
language = str(language)
log.info("Language file: '{language}' Loaded from conf file".format(language=language))
if re.match(r'[[].*[]]', language):
LanguageManager.auto_language = True
language = re.sub(r'[\[\]]', '', language)
return language
@staticmethod
def set_language(action, message=True):
"""
Set the language to translate OpenLP into
:param action: The language menu option
:param message: Display the message option
"""
language = 'en'
if action:
action_name = str(action.objectName())
if action_name == 'autoLanguageItem':
LanguageManager.auto_language = True
else:
LanguageManager.auto_language = False
qm_list = LanguageManager.get_qm_list()
language = str(qm_list[action_name])
if LanguageManager.auto_language:
language = '[{language}]'.format(language=language)
Settings().setValue('core/language', language)
log.info("Language file: '{language}' written to conf file".format(language=language))
if message:
QtWidgets.QMessageBox.information(None,
translate('OpenLP.LanguageManager', 'Language'),
translate('OpenLP.LanguageManager',
'Please restart OpenLP to use your new language setting.'))
@staticmethod
def init_qm_list():
"""
Initialise the list of available translations
"""
LanguageManager.__qm_list__ = {}
qm_files = LanguageManager.find_qm_files()
for counter, qmf in enumerate(qm_files):
reg_ex = QtCore.QRegExp("^.*i18n/(.*).qm")
if reg_ex.exactMatch(qmf):
name = '{regex}'.format(regex=reg_ex.cap(1))
LanguageManager.__qm_list__[
'{count:>2d} {name}'.format(count=counter + 1, name=LanguageManager.language_name(qmf))] = name
@staticmethod
def get_qm_list():
"""
Return the list of available translations
"""
if not LanguageManager.__qm_list__:
LanguageManager.init_qm_list()
return LanguageManager.__qm_list__
class UiStrings(object):
"""
Provide standard strings for objects to use.
"""
__instance__ = None
def __new__(cls):
"""
Override the default object creation method to return a single instance.
"""
if not cls.__instance__:
cls.__instance__ = object.__new__(cls)
return cls.__instance__
def __init__(self):
"""
These strings should need a good reason to be retranslated elsewhere.
Should some/more/less of these have an &amp; attached?
"""
self.About = translate('OpenLP.Ui', 'About')
self.Add = translate('OpenLP.Ui', '&Add')
self.AddGroup = translate('OpenLP.Ui', 'Add group')
self.AddGroupDot = translate('OpenLP.Ui', 'Add group.')
self.Advanced = translate('OpenLP.Ui', 'Advanced')
self.AllFiles = translate('OpenLP.Ui', 'All Files')
self.Automatic = translate('OpenLP.Ui', 'Automatic')
self.BackgroundColor = translate('OpenLP.Ui', 'Background Color')
self.BackgroundColorColon = translate('OpenLP.Ui', 'Background color:')
self.BibleShortSearchTitle = translate('OpenLP.Ui', 'Search is Empty or too Short')
self.BibleShortSearch = translate('OpenLP.Ui', '<strong>The search you have entered is empty or shorter '
'than 3 characters long.</strong><br><br>Please try again with '
'a longer search.')
self.BibleNoBiblesTitle = translate('OpenLP.Ui', 'No Bibles Available')
self.BibleNoBibles = translate('OpenLP.Ui', '<strong>There are no Bibles currently installed.</strong><br><br>'
'Please use the Import Wizard to install one or more Bibles.')
self.Bottom = translate('OpenLP.Ui', 'Bottom')
self.Browse = translate('OpenLP.Ui', 'Browse...')
self.Cancel = translate('OpenLP.Ui', 'Cancel')
self.CCLINumberLabel = translate('OpenLP.Ui', 'CCLI number:')
self.CCLISongNumberLabel = translate('OpenLP.Ui', 'CCLI song number:')
self.CreateService = translate('OpenLP.Ui', 'Create a new service.')
self.ConfirmDelete = translate('OpenLP.Ui', 'Confirm Delete')
self.Continuous = translate('OpenLP.Ui', 'Continuous')
self.Default = translate('OpenLP.Ui', 'Default')
self.DefaultColor = translate('OpenLP.Ui', 'Default Color:')
self.DefaultServiceName = translate('OpenLP.Ui', 'Service %Y-%m-%d %H-%M',
'This may not contain any of the following characters: /\\?*|<>[]":+\n'
'See http://docs.python.org/library/datetime'
'.html#strftime-strptime-behavior for more information.')
self.Delete = translate('OpenLP.Ui', '&Delete')
self.DisplayStyle = translate('OpenLP.Ui', 'Display style:')
self.Duplicate = translate('OpenLP.Ui', 'Duplicate Error')
self.Edit = translate('OpenLP.Ui', '&Edit')
self.EmptyField = translate('OpenLP.Ui', 'Empty Field')
self.Error = translate('OpenLP.Ui', 'Error')
self.Export = translate('OpenLP.Ui', 'Export')
self.File = translate('OpenLP.Ui', 'File')
self.FontSizePtUnit = translate('OpenLP.Ui', 'pt', 'Abbreviated font pointsize unit')
self.Help = translate('OpenLP.Ui', 'Help')
self.Hours = translate('OpenLP.Ui', 'h', 'The abbreviated unit for hours')
self.IFdSs = translate('OpenLP.Ui', 'Invalid Folder Selected', 'Singular')
self.IFSs = translate('OpenLP.Ui', 'Invalid File Selected', 'Singular')
self.IFSp = translate('OpenLP.Ui', 'Invalid Files Selected', 'Plural')
self.Image = translate('OpenLP.Ui', 'Image')
self.Import = translate('OpenLP.Ui', 'Import')
self.LayoutStyle = translate('OpenLP.Ui', 'Layout style:')
self.Live = translate('OpenLP.Ui', 'Live')
self.LiveBGError = translate('OpenLP.Ui', 'Live Background Error')
self.LiveToolbar = translate('OpenLP.Ui', 'Live Toolbar')
self.Load = translate('OpenLP.Ui', 'Load')
self.Manufacturer = translate('OpenLP.Ui', 'Manufacturer', 'Singular')
self.Manufacturers = translate('OpenLP.Ui', 'Manufacturers', 'Plural')
self.Model = translate('OpenLP.Ui', 'Model', 'Singular')
self.Models = translate('OpenLP.Ui', 'Models', 'Plural')
self.Minutes = translate('OpenLP.Ui', 'm', 'The abbreviated unit for minutes')
self.Middle = translate('OpenLP.Ui', 'Middle')
self.New = translate('OpenLP.Ui', 'New')
self.NewService = translate('OpenLP.Ui', 'New Service')
self.NewTheme = translate('OpenLP.Ui', 'New Theme')
self.NextTrack = translate('OpenLP.Ui', 'Next Track')
self.NFdSs = translate('OpenLP.Ui', 'No Folder Selected', 'Singular')
self.NFSs = translate('OpenLP.Ui', 'No File Selected', 'Singular')
self.NFSp = translate('OpenLP.Ui', 'No Files Selected', 'Plural')
self.NISs = translate('OpenLP.Ui', 'No Item Selected', 'Singular')
self.NISp = translate('OpenLP.Ui', 'No Items Selected', 'Plural')
self.NoResults = translate('OpenLP.Ui', 'No Search Results')
self.OpenLP = translate('OpenLP.Ui', 'OpenLP')
self.OpenLPv2AndUp = translate('OpenLP.Ui', 'OpenLP 2.0 and up')
self.OpenLPStart = translate('OpenLP.Ui', 'OpenLP is already running. Do you wish to continue?')
self.OpenService = translate('OpenLP.Ui', 'Open service.')
self.OptionalShowInFooter = translate('OpenLP.Ui', 'Optional, this will be displayed in footer.')
self.OptionalHideInFooter = translate('OpenLP.Ui', 'Optional, this won\'t be displayed in footer.')
self.PlaySlidesInLoop = translate('OpenLP.Ui', 'Play Slides in Loop')
self.PlaySlidesToEnd = translate('OpenLP.Ui', 'Play Slides to End')
self.Preview = translate('OpenLP.Ui', 'Preview')
self.PreviewToolbar = translate('OpenLP.Ui', 'Preview Toolbar')
self.PrintService = translate('OpenLP.Ui', 'Print Service')
self.Projector = translate('OpenLP.Ui', 'Projector', 'Singular')
self.Projectors = translate('OpenLP.Ui', 'Projectors', 'Plural')
self.ReplaceBG = translate('OpenLP.Ui', 'Replace Background')
self.ReplaceLiveBG = translate('OpenLP.Ui', 'Replace live background.')
self.ReplaceLiveBGDisabled = translate('OpenLP.Ui', 'Replace live background is not available when the WebKit '
'player is disabled.')
self.ResetBG = translate('OpenLP.Ui', 'Reset Background')
self.ResetLiveBG = translate('OpenLP.Ui', 'Reset live background.')
self.RequiredShowInFooter = translate('OpenLP.Ui', 'Required, this will be displayed in footer.')
self.Seconds = translate('OpenLP.Ui', 's', 'The abbreviated unit for seconds')
self.SaveAndPreview = translate('OpenLP.Ui', 'Save && Preview')
self.Search = translate('OpenLP.Ui', 'Search')
self.SearchThemes = translate('OpenLP.Ui', 'Search Themes...', 'Search bar place holder text ')
self.SelectDelete = translate('OpenLP.Ui', 'You must select an item to delete.')
self.SelectEdit = translate('OpenLP.Ui', 'You must select an item to edit.')
self.Settings = translate('OpenLP.Ui', 'Settings')
self.SaveService = translate('OpenLP.Ui', 'Save Service')
self.Service = translate('OpenLP.Ui', 'Service')
self.ShortResults = translate('OpenLP.Ui', 'Please type more text to use \'Search As You Type\'')
self.Split = translate('OpenLP.Ui', 'Optional &Split')
self.SplitToolTip = translate('OpenLP.Ui',
'Split a slide into two only if it does not fit on the screen as one slide.')
self.StartingImport = translate('OpenLP.Ui', 'Starting import...')
self.StopPlaySlidesInLoop = translate('OpenLP.Ui', 'Stop Play Slides in Loop')
self.StopPlaySlidesToEnd = translate('OpenLP.Ui', 'Stop Play Slides to End')
self.Theme = translate('OpenLP.Ui', 'Theme', 'Singular')
self.Themes = translate('OpenLP.Ui', 'Themes', 'Plural')
self.Tools = translate('OpenLP.Ui', 'Tools')
self.Top = translate('OpenLP.Ui', 'Top')
self.UnsupportedFile = translate('OpenLP.Ui', 'Unsupported File')
self.VersePerSlide = translate('OpenLP.Ui', 'Verse Per Slide')
self.VersePerLine = translate('OpenLP.Ui', 'Verse Per Line')
self.Version = translate('OpenLP.Ui', 'Version')
self.View = translate('OpenLP.Ui', 'View')
self.ViewMode = translate('OpenLP.Ui', 'View Mode')
self.Video = translate('OpenLP.Ui', 'Video')
self.WebDownloadText = translate('OpenLP.Ui', 'Web Interface, Download and Install latest Version')
book_chapter = translate('OpenLP.Ui', 'Book Chapter')
chapter = translate('OpenLP.Ui', 'Chapter')
verse = translate('OpenLP.Ui', 'Verse')
gap = ' | '
psalm = translate('OpenLP.Ui', 'Psalm')
may_shorten = translate('OpenLP.Ui', 'Book names may be shortened from full names, for an example Ps 23 = '
'Psalm 23')
bible_scripture_items = \
[book_chapter, gap, psalm, ' 23<br>',
book_chapter, '%(range)s', chapter, gap, psalm, ' 23%(range)s24<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, gap, psalm, ' 23%(verse)s1%(range)s2<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, '%(list)s', verse, '%(range)s', verse, gap, psalm,
' 23%(verse)s1%(range)s2%(list)s5%(range)s6<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, '%(list)s', chapter, '%(verse)s', verse, '%(range)s',
verse, gap, psalm, ' 23%(verse)s1%(range)s2%(list)s24%(verse)s1%(range)s3<br>',
book_chapter, '%(verse)s', verse, '%(range)s', chapter, '%(verse)s', verse, gap, psalm,
' 23%(verse)s1%(range)s24%(verse)s1<br><br>', may_shorten]
itertools.chain.from_iterable(itertools.repeat(strings, 1) if isinstance(strings, str)
else strings for strings in bible_scripture_items)
self.BibleScriptureError = ''.join(str(joined) for joined in bible_scripture_items)
def format_time(text, local_time):
"""
Workaround for Python built-in time formatting function time.strftime().
time.strftime() accepts only ascii characters. This function accepts
unicode string and passes individual % placeholders to time.strftime().
This ensures only ascii characters are passed to time.strftime().
:param text: The text to be processed.
:param local_time: The time to be used to add to the string. This is a time object
"""
def match_formatting(match):
"""
Format the match
"""
return local_time.strftime(match.group())
return re.sub(r'\%[a-zA-Z]', match_formatting, text)
def get_locale_key(string):
"""
Creates a key for case insensitive, locale aware string sorting.
:param string: The corresponding string.
"""
string = string.lower()
# ICU is the prefered way to handle locale sort key, we fallback to locale.strxfrm which will work in most cases.
global ICU_COLLATOR
try:
if ICU_COLLATOR is None:
import icu
language = LanguageManager.get_language()
icu_locale = icu.Locale(language)
ICU_COLLATOR = icu.Collator.createInstance(icu_locale)
return ICU_COLLATOR.getSortKey(string)
except:
return locale.strxfrm(string).encode()
def get_natural_key(string):
"""
Generate a key for locale aware natural string sorting.
:param string: string to be sorted by
Returns a list of string compare keys and integers.
"""
key = DIGITS_OR_NONDIGITS.findall(string)
key = [int(part) if part.isdigit() else get_locale_key(part) for part in key]
# Python 3 does not support comparison of different types anymore. So make sure, that we do not compare str
# and int.
if string and string[0].isdigit():
return [b''] + key
return key
def get_language(name):
"""
Find the language by its name or code.
:param name: The name or abbreviation of the language.
:return: The first match as a Language namedtuple or None
"""
if name:
name_lower = name.lower()
name_title = name_lower[:1].upper() + name_lower[1:]
for language in LANGUAGES:
if language.name == name_title or language.code == name_lower:
return language
return None

View File

@ -1,210 +0,0 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
The :mod:`languagemanager` module provides all the translation settings and language file loading for OpenLP.
"""
import locale
import logging
import re
from PyQt5 import QtCore, QtWidgets
from openlp.core.common import AppLocation, Settings, translate, is_win, is_macosx
log = logging.getLogger(__name__)
ICU_COLLATOR = None
DIGITS_OR_NONDIGITS = re.compile(r'\d+|\D+', re.UNICODE)
class LanguageManager(object):
"""
Helper for Language selection
"""
__qm_list__ = {}
auto_language = False
@staticmethod
def get_translators(language):
"""
Set up a translator to use in this instance of OpenLP
:param language: The language to load into the translator
"""
if LanguageManager.auto_language:
language = QtCore.QLocale.system().name()
lang_path = str(AppLocation.get_directory(AppLocation.LanguageDir))
app_translator = QtCore.QTranslator()
app_translator.load(language, lang_path)
# A translator for buttons and other default strings provided by Qt.
if not is_win() and not is_macosx():
lang_path = QtCore.QLibraryInfo.location(QtCore.QLibraryInfo.TranslationsPath)
# As of Qt5, the core translations come in 2 files per language
default_translator = QtCore.QTranslator()
default_translator.load('qt_%s' % language, lang_path)
base_translator = QtCore.QTranslator()
base_translator.load('qtbase_%s' % language, lang_path)
return app_translator, default_translator, base_translator
@staticmethod
def find_qm_files():
"""
Find all available language files in this OpenLP install
"""
log.debug('Translation files: {files}'.format(files=AppLocation.get_directory(AppLocation.LanguageDir)))
trans_dir = QtCore.QDir(str(AppLocation.get_directory(AppLocation.LanguageDir)))
file_names = trans_dir.entryList(['*.qm'], QtCore.QDir.Files, QtCore.QDir.Name)
# Remove qm files from the list which start with "qt".
file_names = [file_ for file_ in file_names if not file_.startswith('qt')]
return list(map(trans_dir.filePath, file_names))
@staticmethod
def language_name(qm_file):
"""
Load the language name from a language file
:param qm_file: The file to obtain the name from
"""
translator = QtCore.QTranslator()
translator.load(qm_file)
return translator.translate('OpenLP.MainWindow', 'English', 'Please add the name of your language here')
@staticmethod
def get_language():
"""
Retrieve a saved language to use from settings
"""
language = Settings().value('core/language')
language = str(language)
log.info("Language file: '{language}' Loaded from conf file".format(language=language))
if re.match(r'[[].*[]]', language):
LanguageManager.auto_language = True
language = re.sub(r'[\[\]]', '', language)
return language
@staticmethod
def set_language(action, message=True):
"""
Set the language to translate OpenLP into
:param action: The language menu option
:param message: Display the message option
"""
language = 'en'
if action:
action_name = str(action.objectName())
if action_name == 'autoLanguageItem':
LanguageManager.auto_language = True
else:
LanguageManager.auto_language = False
qm_list = LanguageManager.get_qm_list()
language = str(qm_list[action_name])
if LanguageManager.auto_language:
language = '[{language}]'.format(language=language)
Settings().setValue('core/language', language)
log.info("Language file: '{language}' written to conf file".format(language=language))
if message:
QtWidgets.QMessageBox.information(None,
translate('OpenLP.LanguageManager', 'Language'),
translate('OpenLP.LanguageManager',
'Please restart OpenLP to use your new language setting.'))
@staticmethod
def init_qm_list():
"""
Initialise the list of available translations
"""
LanguageManager.__qm_list__ = {}
qm_files = LanguageManager.find_qm_files()
for counter, qmf in enumerate(qm_files):
reg_ex = QtCore.QRegExp("^.*i18n/(.*).qm")
if reg_ex.exactMatch(qmf):
name = '{regex}'.format(regex=reg_ex.cap(1))
LanguageManager.__qm_list__[
'{count:>2d} {name}'.format(count=counter + 1, name=LanguageManager.language_name(qmf))] = name
@staticmethod
def get_qm_list():
"""
Return the list of available translations
"""
if not LanguageManager.__qm_list__:
LanguageManager.init_qm_list()
return LanguageManager.__qm_list__
def format_time(text, local_time):
"""
Workaround for Python built-in time formatting function time.strftime().
time.strftime() accepts only ascii characters. This function accepts
unicode string and passes individual % placeholders to time.strftime().
This ensures only ascii characters are passed to time.strftime().
:param text: The text to be processed.
:param local_time: The time to be used to add to the string. This is a time object
"""
def match_formatting(match):
"""
Format the match
"""
return local_time.strftime(match.group())
return re.sub(r'\%[a-zA-Z]', match_formatting, text)
def get_locale_key(string):
"""
Creates a key for case insensitive, locale aware string sorting.
:param string: The corresponding string.
"""
string = string.lower()
# ICU is the prefered way to handle locale sort key, we fallback to locale.strxfrm which will work in most cases.
global ICU_COLLATOR
try:
if ICU_COLLATOR is None:
import icu
language = LanguageManager.get_language()
icu_locale = icu.Locale(language)
ICU_COLLATOR = icu.Collator.createInstance(icu_locale)
return ICU_COLLATOR.getSortKey(string)
except:
return locale.strxfrm(string).encode()
def get_natural_key(string):
"""
Generate a key for locale aware natural string sorting.
:param string: string to be sorted by
Returns a list of string compare keys and integers.
"""
key = DIGITS_OR_NONDIGITS.findall(string)
key = [int(part) if part.isdigit() else get_locale_key(part) for part in key]
# Python 3 does not support comparison of different types anymore. So make sure, that we do not compare str
# and int.
if string and string[0].isdigit():
return [b''] + key
return key

View File

@ -1,201 +0,0 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
The :mod:`languages` module provides a list of language names with utility functions.
"""
from collections import namedtuple
from openlp.core.common import translate
Language = namedtuple('Language', ['id', 'name', 'code'])
languages = sorted([
Language(1, translate('common.languages', '(Afan) Oromo', 'Language code: om'), 'om'),
Language(2, translate('common.languages', 'Abkhazian', 'Language code: ab'), 'ab'),
Language(3, translate('common.languages', 'Afar', 'Language code: aa'), 'aa'),
Language(4, translate('common.languages', 'Afrikaans', 'Language code: af'), 'af'),
Language(5, translate('common.languages', 'Albanian', 'Language code: sq'), 'sq'),
Language(6, translate('common.languages', 'Amharic', 'Language code: am'), 'am'),
Language(140, translate('common.languages', 'Amuzgo', 'Language code: amu'), 'amu'),
Language(152, translate('common.languages', 'Ancient Greek', 'Language code: grc'), 'grc'),
Language(7, translate('common.languages', 'Arabic', 'Language code: ar'), 'ar'),
Language(8, translate('common.languages', 'Armenian', 'Language code: hy'), 'hy'),
Language(9, translate('common.languages', 'Assamese', 'Language code: as'), 'as'),
Language(10, translate('common.languages', 'Aymara', 'Language code: ay'), 'ay'),
Language(11, translate('common.languages', 'Azerbaijani', 'Language code: az'), 'az'),
Language(12, translate('common.languages', 'Bashkir', 'Language code: ba'), 'ba'),
Language(13, translate('common.languages', 'Basque', 'Language code: eu'), 'eu'),
Language(14, translate('common.languages', 'Bengali', 'Language code: bn'), 'bn'),
Language(15, translate('common.languages', 'Bhutani', 'Language code: dz'), 'dz'),
Language(16, translate('common.languages', 'Bihari', 'Language code: bh'), 'bh'),
Language(17, translate('common.languages', 'Bislama', 'Language code: bi'), 'bi'),
Language(18, translate('common.languages', 'Breton', 'Language code: br'), 'br'),
Language(19, translate('common.languages', 'Bulgarian', 'Language code: bg'), 'bg'),
Language(20, translate('common.languages', 'Burmese', 'Language code: my'), 'my'),
Language(21, translate('common.languages', 'Byelorussian', 'Language code: be'), 'be'),
Language(142, translate('common.languages', 'Cakchiquel', 'Language code: cak'), 'cak'),
Language(22, translate('common.languages', 'Cambodian', 'Language code: km'), 'km'),
Language(23, translate('common.languages', 'Catalan', 'Language code: ca'), 'ca'),
Language(24, translate('common.languages', 'Chinese', 'Language code: zh'), 'zh'),
Language(141, translate('common.languages', 'Comaltepec Chinantec', 'Language code: cco'), 'cco'),
Language(25, translate('common.languages', 'Corsican', 'Language code: co'), 'co'),
Language(26, translate('common.languages', 'Croatian', 'Language code: hr'), 'hr'),
Language(27, translate('common.languages', 'Czech', 'Language code: cs'), 'cs'),
Language(28, translate('common.languages', 'Danish', 'Language code: da'), 'da'),
Language(29, translate('common.languages', 'Dutch', 'Language code: nl'), 'nl'),
Language(30, translate('common.languages', 'English', 'Language code: en'), 'en'),
Language(31, translate('common.languages', 'Esperanto', 'Language code: eo'), 'eo'),
Language(32, translate('common.languages', 'Estonian', 'Language code: et'), 'et'),
Language(33, translate('common.languages', 'Faeroese', 'Language code: fo'), 'fo'),
Language(34, translate('common.languages', 'Fiji', 'Language code: fj'), 'fj'),
Language(35, translate('common.languages', 'Finnish', 'Language code: fi'), 'fi'),
Language(36, translate('common.languages', 'French', 'Language code: fr'), 'fr'),
Language(37, translate('common.languages', 'Frisian', 'Language code: fy'), 'fy'),
Language(38, translate('common.languages', 'Galician', 'Language code: gl'), 'gl'),
Language(39, translate('common.languages', 'Georgian', 'Language code: ka'), 'ka'),
Language(40, translate('common.languages', 'German', 'Language code: de'), 'de'),
Language(41, translate('common.languages', 'Greek', 'Language code: el'), 'el'),
Language(42, translate('common.languages', 'Greenlandic', 'Language code: kl'), 'kl'),
Language(43, translate('common.languages', 'Guarani', 'Language code: gn'), 'gn'),
Language(44, translate('common.languages', 'Gujarati', 'Language code: gu'), 'gu'),
Language(143, translate('common.languages', 'Haitian Creole', 'Language code: ht'), 'ht'),
Language(45, translate('common.languages', 'Hausa', 'Language code: ha'), 'ha'),
Language(46, translate('common.languages', 'Hebrew (former iw)', 'Language code: he'), 'he'),
Language(144, translate('common.languages', 'Hiligaynon', 'Language code: hil'), 'hil'),
Language(47, translate('common.languages', 'Hindi', 'Language code: hi'), 'hi'),
Language(48, translate('common.languages', 'Hungarian', 'Language code: hu'), 'hu'),
Language(49, translate('common.languages', 'Icelandic', 'Language code: is'), 'is'),
Language(50, translate('common.languages', 'Indonesian (former in)', 'Language code: id'), 'id'),
Language(51, translate('common.languages', 'Interlingua', 'Language code: ia'), 'ia'),
Language(52, translate('common.languages', 'Interlingue', 'Language code: ie'), 'ie'),
Language(54, translate('common.languages', 'Inuktitut (Eskimo)', 'Language code: iu'), 'iu'),
Language(53, translate('common.languages', 'Inupiak', 'Language code: ik'), 'ik'),
Language(55, translate('common.languages', 'Irish', 'Language code: ga'), 'ga'),
Language(56, translate('common.languages', 'Italian', 'Language code: it'), 'it'),
Language(145, translate('common.languages', 'Jakalteko', 'Language code: jac'), 'jac'),
Language(57, translate('common.languages', 'Japanese', 'Language code: ja'), 'ja'),
Language(58, translate('common.languages', 'Javanese', 'Language code: jw'), 'jw'),
Language(150, translate('common.languages', 'K\'iche\'', 'Language code: quc'), 'quc'),
Language(59, translate('common.languages', 'Kannada', 'Language code: kn'), 'kn'),
Language(60, translate('common.languages', 'Kashmiri', 'Language code: ks'), 'ks'),
Language(61, translate('common.languages', 'Kazakh', 'Language code: kk'), 'kk'),
Language(146, translate('common.languages', 'Kekchí ', 'Language code: kek'), 'kek'),
Language(62, translate('common.languages', 'Kinyarwanda', 'Language code: rw'), 'rw'),
Language(63, translate('common.languages', 'Kirghiz', 'Language code: ky'), 'ky'),
Language(64, translate('common.languages', 'Kirundi', 'Language code: rn'), 'rn'),
Language(65, translate('common.languages', 'Korean', 'Language code: ko'), 'ko'),
Language(66, translate('common.languages', 'Kurdish', 'Language code: ku'), 'ku'),
Language(67, translate('common.languages', 'Laothian', 'Language code: lo'), 'lo'),
Language(68, translate('common.languages', 'Latin', 'Language code: la'), 'la'),
Language(69, translate('common.languages', 'Latvian, Lettish', 'Language code: lv'), 'lv'),
Language(70, translate('common.languages', 'Lingala', 'Language code: ln'), 'ln'),
Language(71, translate('common.languages', 'Lithuanian', 'Language code: lt'), 'lt'),
Language(72, translate('common.languages', 'Macedonian', 'Language code: mk'), 'mk'),
Language(73, translate('common.languages', 'Malagasy', 'Language code: mg'), 'mg'),
Language(74, translate('common.languages', 'Malay', 'Language code: ms'), 'ms'),
Language(75, translate('common.languages', 'Malayalam', 'Language code: ml'), 'ml'),
Language(76, translate('common.languages', 'Maltese', 'Language code: mt'), 'mt'),
Language(148, translate('common.languages', 'Mam', 'Language code: mam'), 'mam'),
Language(77, translate('common.languages', 'Maori', 'Language code: mi'), 'mi'),
Language(147, translate('common.languages', 'Maori', 'Language code: mri'), 'mri'),
Language(78, translate('common.languages', 'Marathi', 'Language code: mr'), 'mr'),
Language(79, translate('common.languages', 'Moldavian', 'Language code: mo'), 'mo'),
Language(80, translate('common.languages', 'Mongolian', 'Language code: mn'), 'mn'),
Language(149, translate('common.languages', 'Nahuatl', 'Language code: nah'), 'nah'),
Language(81, translate('common.languages', 'Nauru', 'Language code: na'), 'na'),
Language(82, translate('common.languages', 'Nepali', 'Language code: ne'), 'ne'),
Language(83, translate('common.languages', 'Norwegian', 'Language code: no'), 'no'),
Language(84, translate('common.languages', 'Occitan', 'Language code: oc'), 'oc'),
Language(85, translate('common.languages', 'Oriya', 'Language code: or'), 'or'),
Language(86, translate('common.languages', 'Pashto, Pushto', 'Language code: ps'), 'ps'),
Language(87, translate('common.languages', 'Persian', 'Language code: fa'), 'fa'),
Language(151, translate('common.languages', 'Plautdietsch', 'Language code: pdt'), 'pdt'),
Language(88, translate('common.languages', 'Polish', 'Language code: pl'), 'pl'),
Language(89, translate('common.languages', 'Portuguese', 'Language code: pt'), 'pt'),
Language(90, translate('common.languages', 'Punjabi', 'Language code: pa'), 'pa'),
Language(91, translate('common.languages', 'Quechua', 'Language code: qu'), 'qu'),
Language(92, translate('common.languages', 'Rhaeto-Romance', 'Language code: rm'), 'rm'),
Language(93, translate('common.languages', 'Romanian', 'Language code: ro'), 'ro'),
Language(94, translate('common.languages', 'Russian', 'Language code: ru'), 'ru'),
Language(95, translate('common.languages', 'Samoan', 'Language code: sm'), 'sm'),
Language(96, translate('common.languages', 'Sangro', 'Language code: sg'), 'sg'),
Language(97, translate('common.languages', 'Sanskrit', 'Language code: sa'), 'sa'),
Language(98, translate('common.languages', 'Scots Gaelic', 'Language code: gd'), 'gd'),
Language(99, translate('common.languages', 'Serbian', 'Language code: sr'), 'sr'),
Language(100, translate('common.languages', 'Serbo-Croatian', 'Language code: sh'), 'sh'),
Language(101, translate('common.languages', 'Sesotho', 'Language code: st'), 'st'),
Language(102, translate('common.languages', 'Setswana', 'Language code: tn'), 'tn'),
Language(103, translate('common.languages', 'Shona', 'Language code: sn'), 'sn'),
Language(104, translate('common.languages', 'Sindhi', 'Language code: sd'), 'sd'),
Language(105, translate('common.languages', 'Singhalese', 'Language code: si'), 'si'),
Language(106, translate('common.languages', 'Siswati', 'Language code: ss'), 'ss'),
Language(107, translate('common.languages', 'Slovak', 'Language code: sk'), 'sk'),
Language(108, translate('common.languages', 'Slovenian', 'Language code: sl'), 'sl'),
Language(109, translate('common.languages', 'Somali', 'Language code: so'), 'so'),
Language(110, translate('common.languages', 'Spanish', 'Language code: es'), 'es'),
Language(111, translate('common.languages', 'Sudanese', 'Language code: su'), 'su'),
Language(112, translate('common.languages', 'Swahili', 'Language code: sw'), 'sw'),
Language(113, translate('common.languages', 'Swedish', 'Language code: sv'), 'sv'),
Language(114, translate('common.languages', 'Tagalog', 'Language code: tl'), 'tl'),
Language(115, translate('common.languages', 'Tajik', 'Language code: tg'), 'tg'),
Language(116, translate('common.languages', 'Tamil', 'Language code: ta'), 'ta'),
Language(117, translate('common.languages', 'Tatar', 'Language code: tt'), 'tt'),
Language(118, translate('common.languages', 'Tegulu', 'Language code: te'), 'te'),
Language(119, translate('common.languages', 'Thai', 'Language code: th'), 'th'),
Language(120, translate('common.languages', 'Tibetan', 'Language code: bo'), 'bo'),
Language(121, translate('common.languages', 'Tigrinya', 'Language code: ti'), 'ti'),
Language(122, translate('common.languages', 'Tonga', 'Language code: to'), 'to'),
Language(123, translate('common.languages', 'Tsonga', 'Language code: ts'), 'ts'),
Language(124, translate('common.languages', 'Turkish', 'Language code: tr'), 'tr'),
Language(125, translate('common.languages', 'Turkmen', 'Language code: tk'), 'tk'),
Language(126, translate('common.languages', 'Twi', 'Language code: tw'), 'tw'),
Language(127, translate('common.languages', 'Uigur', 'Language code: ug'), 'ug'),
Language(128, translate('common.languages', 'Ukrainian', 'Language code: uk'), 'uk'),
Language(129, translate('common.languages', 'Urdu', 'Language code: ur'), 'ur'),
Language(153, translate('common.languages', 'Uspanteco', 'Language code: usp'), 'usp'),
Language(130, translate('common.languages', 'Uzbek', 'Language code: uz'), 'uz'),
Language(131, translate('common.languages', 'Vietnamese', 'Language code: vi'), 'vi'),
Language(132, translate('common.languages', 'Volapuk', 'Language code: vo'), 'vo'),
Language(133, translate('common.languages', 'Welch', 'Language code: cy'), 'cy'),
Language(134, translate('common.languages', 'Wolof', 'Language code: wo'), 'wo'),
Language(135, translate('common.languages', 'Xhosa', 'Language code: xh'), 'xh'),
Language(136, translate('common.languages', 'Yiddish (former ji)', 'Language code: yi'), 'yi'),
Language(137, translate('common.languages', 'Yoruba', 'Language code: yo'), 'yo'),
Language(138, translate('common.languages', 'Zhuang', 'Language code: za'), 'za'),
Language(139, translate('common.languages', 'Zulu', 'Language code: zu'), 'zu')
], key=lambda language: language.name)
def get_language(name):
"""
Find the language by its name or code.
:param name: The name or abbreviation of the language.
:return: The first match as a Language namedtuple or None
"""
if name:
name_lower = name.lower()
name_title = name_lower[:1].upper() + name_lower[1:]
for language in languages:
if language.name == name_title or language.code == name_lower:
return language
return None

View File

@ -25,7 +25,8 @@ Provide Error Handling and login Services
import logging import logging
import inspect import inspect
from openlp.core.common import trace_error_handler from openlp.core.common import trace_error_handler, de_hump
from openlp.core.common.registry import Registry
DO_NOT_TRACE_EVENTS = ['timerEvent', 'paintEvent', 'drag_enter_event', 'drop_event', 'on_controller_size_changed', DO_NOT_TRACE_EVENTS = ['timerEvent', 'paintEvent', 'drag_enter_event', 'drop_event', 'on_controller_size_changed',
'preview_size_changed', 'resizeEvent'] 'preview_size_changed', 'resizeEvent']
@ -90,3 +91,32 @@ class OpenLPMixin(object):
""" """
trace_error_handler(self.logger) trace_error_handler(self.logger)
self.logger.exception(message) self.logger.exception(message)
class RegistryMixin(object):
"""
This adds registry components to classes to use at run time.
"""
def __init__(self, parent):
"""
Register the class and bootstrap hooks.
"""
try:
super(RegistryMixin, self).__init__(parent)
except TypeError:
super(RegistryMixin, self).__init__()
Registry().register(de_hump(self.__class__.__name__), self)
Registry().register_function('bootstrap_initialise', self.bootstrap_initialise)
Registry().register_function('bootstrap_post_set_up', self.bootstrap_post_set_up)
def bootstrap_initialise(self):
"""
Dummy method to be overridden
"""
pass
def bootstrap_post_set_up(self):
"""
Dummy method to be overridden
"""
pass

View File

@ -19,6 +19,7 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
import logging
import shutil import shutil
from contextlib import suppress from contextlib import suppress
@ -29,6 +30,45 @@ if is_win():
else: else:
from pathlib import PosixPath as PathVariant from pathlib import PosixPath as PathVariant
log = logging.getLogger(__name__)
class Path(PathVariant):
"""
Subclass pathlib.Path, so we can add json conversion methods
"""
@staticmethod
def encode_json(obj, base_path=None, **kwargs):
"""
Create a Path object from a dictionary representation. The dictionary has been constructed by JSON encoding of
a JSON reprensation of a Path object.
:param dict[str] obj: The dictionary representation
:param openlp.core.common.path.Path base_path: If specified, an absolute path to base the relative path off of.
:param kwargs: Contains any extra parameters. Not used!
:return: The reconstructed Path object
:rtype: openlp.core.common.path.Path
"""
path = Path(*obj['__Path__'])
if base_path and not path.is_absolute():
return base_path / path
return path
def json_object(self, base_path=None, **kwargs):
"""
Create a dictionary that can be JSON decoded.
:param openlp.core.common.path.Path base_path: If specified, an absolute path to make a relative path from.
:param kwargs: Contains any extra parameters. Not used!
:return: The dictionary representation of this Path object.
:rtype: dict[tuple]
"""
path = self
if base_path:
with suppress(ValueError):
path = path.relative_to(base_path)
return {'__Path__': path.parts}
def replace_params(args, kwargs, params): def replace_params(args, kwargs, params):
""" """
@ -179,38 +219,32 @@ def str_to_path(string):
return Path(string) return Path(string)
class Path(PathVariant): def create_paths(*paths, **kwargs):
""" """
Subclass pathlib.Path, so we can add json conversion methods Create one or more paths
:param openlp.core.common.path.Path paths: The paths to create
:param bool do_not_log: To not log anything. This is need for the start up, when the log isn't ready.
:rtype: None
""" """
@staticmethod for path in paths:
def encode_json(obj, base_path=None, **kwargs): if not kwargs.get('do_not_log', False):
""" log.debug('create_path {path}'.format(path=path))
Create a Path object from a dictionary representation. The dictionary has been constructed by JSON encoding of try:
a JSON reprensation of a Path object. if not path.exists():
path.mkdir(parents=True)
except IOError:
if not kwargs.get('do_not_log', False):
log.exception('failed to check if directory exists or create directory')
:param dict[str] obj: The dictionary representation
:param openlp.core.common.path.Path base_path: If specified, an absolute path to base the relative path off of.
:param kwargs: Contains any extra parameters. Not used!
:return: The reconstructed Path object
:rtype: openlp.core.common.path.Path
"""
path = Path(*obj['__Path__'])
if base_path and not path.is_absolute():
return base_path / path
return path
def json_object(self, base_path=None, **kwargs): def files_to_paths(file_names):
""" """
Create a dictionary that can be JSON decoded. Convert a list of file names in to a list of file paths.
:param openlp.core.common.path.Path base_path: If specified, an absolute path to make a relative path from. :param list[str] file_names: The list of file names to convert.
:param kwargs: Contains any extra parameters. Not used! :return: The list converted to file paths
:return: The dictionary representation of this Path object. :rtype: openlp.core.common.path.Path
:rtype: dict[tuple] """
""" if file_names:
path = self return [str_to_path(file_name) for file_name in file_names]
if base_path:
with suppress(ValueError):
path = path.relative_to(base_path)
return {'__Path__': path.parts}

View File

@ -25,7 +25,7 @@ Provide Registry Services
import logging import logging
import sys import sys
from openlp.core.common import trace_error_handler from openlp.core.common import is_win, trace_error_handler
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
@ -176,3 +176,130 @@ class Registry(object):
""" """
if key in self.working_flags: if key in self.working_flags:
del self.working_flags[key] del self.working_flags[key]
class RegistryProperties(object):
"""
This adds registry components to classes to use at run time.
"""
@property
def application(self):
"""
Adds the openlp to the class dynamically.
Windows needs to access the application in a dynamic manner.
"""
if is_win():
return Registry().get('application')
else:
if not hasattr(self, '_application') or not self._application:
self._application = Registry().get('application')
return self._application
@property
def plugin_manager(self):
"""
Adds the plugin manager to the class dynamically
"""
if not hasattr(self, '_plugin_manager') or not self._plugin_manager:
self._plugin_manager = Registry().get('plugin_manager')
return self._plugin_manager
@property
def image_manager(self):
"""
Adds the image manager to the class dynamically
"""
if not hasattr(self, '_image_manager') or not self._image_manager:
self._image_manager = Registry().get('image_manager')
return self._image_manager
@property
def media_controller(self):
"""
Adds the media controller to the class dynamically
"""
if not hasattr(self, '_media_controller') or not self._media_controller:
self._media_controller = Registry().get('media_controller')
return self._media_controller
@property
def service_manager(self):
"""
Adds the service manager to the class dynamically
"""
if not hasattr(self, '_service_manager') or not self._service_manager:
self._service_manager = Registry().get('service_manager')
return self._service_manager
@property
def preview_controller(self):
"""
Adds the preview controller to the class dynamically
"""
if not hasattr(self, '_preview_controller') or not self._preview_controller:
self._preview_controller = Registry().get('preview_controller')
return self._preview_controller
@property
def live_controller(self):
"""
Adds the live controller to the class dynamically
"""
if not hasattr(self, '_live_controller') or not self._live_controller:
self._live_controller = Registry().get('live_controller')
return self._live_controller
@property
def main_window(self):
"""
Adds the main window to the class dynamically
"""
if not hasattr(self, '_main_window') or not self._main_window:
self._main_window = Registry().get('main_window')
return self._main_window
@property
def renderer(self):
"""
Adds the Renderer to the class dynamically
"""
if not hasattr(self, '_renderer') or not self._renderer:
self._renderer = Registry().get('renderer')
return self._renderer
@property
def theme_manager(self):
"""
Adds the theme manager to the class dynamically
"""
if not hasattr(self, '_theme_manager') or not self._theme_manager:
self._theme_manager = Registry().get('theme_manager')
return self._theme_manager
@property
def settings_form(self):
"""
Adds the settings form to the class dynamically
"""
if not hasattr(self, '_settings_form') or not self._settings_form:
self._settings_form = Registry().get('settings_form')
return self._settings_form
@property
def alerts_manager(self):
"""
Adds the alerts manager to the class dynamically
"""
if not hasattr(self, '_alerts_manager') or not self._alerts_manager:
self._alerts_manager = Registry().get('alerts_manager')
return self._alerts_manager
@property
def projector_manager(self):
"""
Adds the projector manager to the class dynamically
"""
if not hasattr(self, '_projector_manager') or not self._projector_manager:
self._projector_manager = Registry().get('projector_manager')
return self._projector_manager

View File

@ -1,54 +0,0 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
Provide Registry Services
"""
from openlp.core.common import Registry, de_hump
class RegistryMixin(object):
"""
This adds registry components to classes to use at run time.
"""
def __init__(self, parent):
"""
Register the class and bootstrap hooks.
"""
try:
super(RegistryMixin, self).__init__(parent)
except TypeError:
super(RegistryMixin, self).__init__()
Registry().register(de_hump(self.__class__.__name__), self)
Registry().register_function('bootstrap_initialise', self.bootstrap_initialise)
Registry().register_function('bootstrap_post_set_up', self.bootstrap_post_set_up)
def bootstrap_initialise(self):
"""
Dummy method to be overridden
"""
pass
def bootstrap_post_set_up(self):
"""
Dummy method to be overridden
"""
pass

View File

@ -1,152 +0,0 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
Provide Registry values for adding to classes
"""
from openlp.core.common import Registry, is_win
class RegistryProperties(object):
"""
This adds registry components to classes to use at run time.
"""
@property
def application(self):
"""
Adds the openlp to the class dynamically.
Windows needs to access the application in a dynamic manner.
"""
if is_win():
return Registry().get('application')
else:
if not hasattr(self, '_application') or not self._application:
self._application = Registry().get('application')
return self._application
@property
def plugin_manager(self):
"""
Adds the plugin manager to the class dynamically
"""
if not hasattr(self, '_plugin_manager') or not self._plugin_manager:
self._plugin_manager = Registry().get('plugin_manager')
return self._plugin_manager
@property
def image_manager(self):
"""
Adds the image manager to the class dynamically
"""
if not hasattr(self, '_image_manager') or not self._image_manager:
self._image_manager = Registry().get('image_manager')
return self._image_manager
@property
def media_controller(self):
"""
Adds the media controller to the class dynamically
"""
if not hasattr(self, '_media_controller') or not self._media_controller:
self._media_controller = Registry().get('media_controller')
return self._media_controller
@property
def service_manager(self):
"""
Adds the service manager to the class dynamically
"""
if not hasattr(self, '_service_manager') or not self._service_manager:
self._service_manager = Registry().get('service_manager')
return self._service_manager
@property
def preview_controller(self):
"""
Adds the preview controller to the class dynamically
"""
if not hasattr(self, '_preview_controller') or not self._preview_controller:
self._preview_controller = Registry().get('preview_controller')
return self._preview_controller
@property
def live_controller(self):
"""
Adds the live controller to the class dynamically
"""
if not hasattr(self, '_live_controller') or not self._live_controller:
self._live_controller = Registry().get('live_controller')
return self._live_controller
@property
def main_window(self):
"""
Adds the main window to the class dynamically
"""
if not hasattr(self, '_main_window') or not self._main_window:
self._main_window = Registry().get('main_window')
return self._main_window
@property
def renderer(self):
"""
Adds the Renderer to the class dynamically
"""
if not hasattr(self, '_renderer') or not self._renderer:
self._renderer = Registry().get('renderer')
return self._renderer
@property
def theme_manager(self):
"""
Adds the theme manager to the class dynamically
"""
if not hasattr(self, '_theme_manager') or not self._theme_manager:
self._theme_manager = Registry().get('theme_manager')
return self._theme_manager
@property
def settings_form(self):
"""
Adds the settings form to the class dynamically
"""
if not hasattr(self, '_settings_form') or not self._settings_form:
self._settings_form = Registry().get('settings_form')
return self._settings_form
@property
def alerts_manager(self):
"""
Adds the alerts manager to the class dynamically
"""
if not hasattr(self, '_alerts_manager') or not self._alerts_manager:
self._alerts_manager = Registry().get('alerts_manager')
return self._alerts_manager
@property
def projector_manager(self):
"""
Adds the projector manager to the class dynamically
"""
if not hasattr(self, '_projector_manager') or not self._projector_manager:
self._projector_manager = Registry().get('projector_manager')
return self._projector_manager

View File

@ -28,11 +28,11 @@ import json
import os import os
from tempfile import gettempdir from tempfile import gettempdir
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui
from openlp.core.common import SlideLimits, ThemeLevel, UiStrings, is_linux, is_win, translate from openlp.core.common import SlideLimits, ThemeLevel, is_linux, is_win
from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder
from openlp.core.common.path import Path, str_to_path from openlp.core.common.path import Path, str_to_path, files_to_paths
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
@ -62,18 +62,6 @@ def media_players_conv(string):
return string return string
def file_names_conv(file_names):
"""
Convert a list of file names in to a list of file paths.
:param list[str] file_names: The list of file names to convert.
:return: The list converted to file paths
:rtype: openlp.core.common.path.Path
"""
if file_names:
return [str_to_path(file_name) for file_name in file_names]
class Settings(QtCore.QSettings): class Settings(QtCore.QSettings):
""" """
Class to wrap QSettings. Class to wrap QSettings.
@ -116,7 +104,7 @@ class Settings(QtCore.QSettings):
'advanced/default service enabled': True, 'advanced/default service enabled': True,
'advanced/default service hour': 11, 'advanced/default service hour': 11,
'advanced/default service minute': 0, 'advanced/default service minute': 0,
'advanced/default service name': UiStrings().DefaultServiceName, 'advanced/default service name': 'Service %Y-%m-%d %H-%M',
'advanced/display size': 0, 'advanced/display size': 0,
'advanced/double click live': False, 'advanced/double click live': False,
'advanced/enable exit confirmation': True, 'advanced/enable exit confirmation': True,
@ -261,9 +249,9 @@ class Settings(QtCore.QSettings):
('songs/last directory import', 'songs/last directory import', [(str_to_path, None)]), ('songs/last directory import', 'songs/last directory import', [(str_to_path, None)]),
('songs/last directory export', 'songs/last directory export', [(str_to_path, None)]), ('songs/last directory export', 'songs/last directory export', [(str_to_path, None)]),
('songusage/last directory export', 'songusage/last directory export', [(str_to_path, None)]), ('songusage/last directory export', 'songusage/last directory export', [(str_to_path, None)]),
('core/recent files', 'core/recent files', [(file_names_conv, None)]), ('core/recent files', 'core/recent files', [(files_to_paths, None)]),
('media/media files', 'media/media files', [(file_names_conv, None)]), ('media/media files', 'media/media files', [(files_to_paths, None)]),
('presentations/presentations files', 'presentations/presentations files', [(file_names_conv, None)]), ('presentations/presentations files', 'presentations/presentations files', [(files_to_paths, None)]),
('core/logo file', 'core/logo file', [(str_to_path, None)]), ('core/logo file', 'core/logo file', [(str_to_path, None)]),
('presentations/last directory', 'presentations/last directory', [(str_to_path, None)]), ('presentations/last directory', 'presentations/last directory', [(str_to_path, None)]),
('images/last directory', 'images/last directory', [(str_to_path, None)]), ('images/last directory', 'images/last directory', [(str_to_path, None)]),
@ -298,6 +286,7 @@ class Settings(QtCore.QSettings):
""" """
# Make sure the string is translated (when building the dict the string is not translated because the translate # Make sure the string is translated (when building the dict the string is not translated because the translate
# function was not set up as this stage). # function was not set up as this stage).
from openlp.core.common.i18n import UiStrings
Settings.__default_settings__['advanced/default service name'] = UiStrings().DefaultServiceName Settings.__default_settings__['advanced/default service name'] = UiStrings().DefaultServiceName
def __init__(self, *args): def __init__(self, *args):
@ -609,11 +598,5 @@ class Settings(QtCore.QSettings):
if file_record.find('@Invalid()') == -1: if file_record.find('@Invalid()') == -1:
file_record = file_record.replace('%20', ' ') file_record = file_record.replace('%20', ' ')
export_conf_file.write(file_record) export_conf_file.write(file_record)
except OSError as ose:
QtWidgets.QMessageBox.critical(self, translate('OpenLP.MainWindow', 'Export setting error'),
translate('OpenLP.MainWindow',
'An error occurred while exporting the settings: {err}'
).format(err=ose.strerror),
QtWidgets.QMessageBox.StandardButtons(QtWidgets.QMessageBox.Ok))
finally: finally:
temp_path.unlink() temp_path.unlink()

View File

@ -1,187 +0,0 @@
# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=120 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
# Copyright (c) 2008-2017 OpenLP Developers #
# --------------------------------------------------------------------------- #
# This program is free software; you can redistribute it and/or modify it #
# under the terms of the GNU General Public License as published by the Free #
# Software Foundation; version 2 of the License. #
# #
# This program is distributed in the hope that it will be useful, but WITHOUT #
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
# more details. #
# #
# You should have received a copy of the GNU General Public License along #
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
"""
The :mod:`uistrings` module provides standard strings for OpenLP.
"""
import logging
import itertools
from openlp.core.common import translate
log = logging.getLogger(__name__)
class UiStrings(object):
"""
Provide standard strings for objects to use.
"""
__instance__ = None
def __new__(cls):
"""
Override the default object creation method to return a single instance.
"""
if not cls.__instance__:
cls.__instance__ = object.__new__(cls)
return cls.__instance__
def __init__(self):
"""
These strings should need a good reason to be retranslated elsewhere.
Should some/more/less of these have an &amp; attached?
"""
self.About = translate('OpenLP.Ui', 'About')
self.Add = translate('OpenLP.Ui', '&Add')
self.AddGroup = translate('OpenLP.Ui', 'Add group')
self.AddGroupDot = translate('OpenLP.Ui', 'Add group.')
self.Advanced = translate('OpenLP.Ui', 'Advanced')
self.AllFiles = translate('OpenLP.Ui', 'All Files')
self.Automatic = translate('OpenLP.Ui', 'Automatic')
self.BackgroundColor = translate('OpenLP.Ui', 'Background Color')
self.BackgroundColorColon = translate('OpenLP.Ui', 'Background color:')
self.BibleShortSearchTitle = translate('OpenLP.Ui', 'Search is Empty or too Short')
self.BibleShortSearch = translate('OpenLP.Ui', '<strong>The search you have entered is empty or shorter '
'than 3 characters long.</strong><br><br>Please try again with '
'a longer search.')
self.BibleNoBiblesTitle = translate('OpenLP.Ui', 'No Bibles Available')
self.BibleNoBibles = translate('OpenLP.Ui', '<strong>There are no Bibles currently installed.</strong><br><br>'
'Please use the Import Wizard to install one or more Bibles.')
self.Bottom = translate('OpenLP.Ui', 'Bottom')
self.Browse = translate('OpenLP.Ui', 'Browse...')
self.Cancel = translate('OpenLP.Ui', 'Cancel')
self.CCLINumberLabel = translate('OpenLP.Ui', 'CCLI number:')
self.CCLISongNumberLabel = translate('OpenLP.Ui', 'CCLI song number:')
self.CreateService = translate('OpenLP.Ui', 'Create a new service.')
self.ConfirmDelete = translate('OpenLP.Ui', 'Confirm Delete')
self.Continuous = translate('OpenLP.Ui', 'Continuous')
self.Default = translate('OpenLP.Ui', 'Default')
self.DefaultColor = translate('OpenLP.Ui', 'Default Color:')
self.DefaultServiceName = translate('OpenLP.Ui', 'Service %Y-%m-%d %H-%M',
'This may not contain any of the following characters: /\\?*|<>[]":+\n'
'See http://docs.python.org/library/datetime'
'.html#strftime-strptime-behavior for more information.')
self.Delete = translate('OpenLP.Ui', '&Delete')
self.DisplayStyle = translate('OpenLP.Ui', 'Display style:')
self.Duplicate = translate('OpenLP.Ui', 'Duplicate Error')
self.Edit = translate('OpenLP.Ui', '&Edit')
self.EmptyField = translate('OpenLP.Ui', 'Empty Field')
self.Error = translate('OpenLP.Ui', 'Error')
self.Export = translate('OpenLP.Ui', 'Export')
self.File = translate('OpenLP.Ui', 'File')
self.FontSizePtUnit = translate('OpenLP.Ui', 'pt', 'Abbreviated font pointsize unit')
self.Help = translate('OpenLP.Ui', 'Help')
self.Hours = translate('OpenLP.Ui', 'h', 'The abbreviated unit for hours')
self.IFdSs = translate('OpenLP.Ui', 'Invalid Folder Selected', 'Singular')
self.IFSs = translate('OpenLP.Ui', 'Invalid File Selected', 'Singular')
self.IFSp = translate('OpenLP.Ui', 'Invalid Files Selected', 'Plural')
self.Image = translate('OpenLP.Ui', 'Image')
self.Import = translate('OpenLP.Ui', 'Import')
self.LayoutStyle = translate('OpenLP.Ui', 'Layout style:')
self.Live = translate('OpenLP.Ui', 'Live')
self.LiveBGError = translate('OpenLP.Ui', 'Live Background Error')
self.LiveToolbar = translate('OpenLP.Ui', 'Live Toolbar')
self.Load = translate('OpenLP.Ui', 'Load')
self.Manufacturer = translate('OpenLP.Ui', 'Manufacturer', 'Singular')
self.Manufacturers = translate('OpenLP.Ui', 'Manufacturers', 'Plural')
self.Model = translate('OpenLP.Ui', 'Model', 'Singular')
self.Models = translate('OpenLP.Ui', 'Models', 'Plural')
self.Minutes = translate('OpenLP.Ui', 'm', 'The abbreviated unit for minutes')
self.Middle = translate('OpenLP.Ui', 'Middle')
self.New = translate('OpenLP.Ui', 'New')
self.NewService = translate('OpenLP.Ui', 'New Service')
self.NewTheme = translate('OpenLP.Ui', 'New Theme')
self.NextTrack = translate('OpenLP.Ui', 'Next Track')
self.NFdSs = translate('OpenLP.Ui', 'No Folder Selected', 'Singular')
self.NFSs = translate('OpenLP.Ui', 'No File Selected', 'Singular')
self.NFSp = translate('OpenLP.Ui', 'No Files Selected', 'Plural')
self.NISs = translate('OpenLP.Ui', 'No Item Selected', 'Singular')
self.NISp = translate('OpenLP.Ui', 'No Items Selected', 'Plural')
self.NoResults = translate('OpenLP.Ui', 'No Search Results')
self.OpenLP = translate('OpenLP.Ui', 'OpenLP')
self.OpenLPv2AndUp = translate('OpenLP.Ui', 'OpenLP 2.0 and up')
self.OpenLPStart = translate('OpenLP.Ui', 'OpenLP is already running. Do you wish to continue?')
self.OpenService = translate('OpenLP.Ui', 'Open service.')
self.OptionalShowInFooter = translate('OpenLP.Ui', 'Optional, this will be displayed in footer.')
self.OptionalHideInFooter = translate('OpenLP.Ui', 'Optional, this won\'t be displayed in footer.')
self.PlaySlidesInLoop = translate('OpenLP.Ui', 'Play Slides in Loop')
self.PlaySlidesToEnd = translate('OpenLP.Ui', 'Play Slides to End')
self.Preview = translate('OpenLP.Ui', 'Preview')
self.PreviewToolbar = translate('OpenLP.Ui', 'Preview Toolbar')
self.PrintService = translate('OpenLP.Ui', 'Print Service')
self.Projector = translate('OpenLP.Ui', 'Projector', 'Singular')
self.Projectors = translate('OpenLP.Ui', 'Projectors', 'Plural')
self.ReplaceBG = translate('OpenLP.Ui', 'Replace Background')
self.ReplaceLiveBG = translate('OpenLP.Ui', 'Replace live background.')
self.ReplaceLiveBGDisabled = translate('OpenLP.Ui', 'Replace live background is not available when the WebKit '
'player is disabled.')
self.ResetBG = translate('OpenLP.Ui', 'Reset Background')
self.ResetLiveBG = translate('OpenLP.Ui', 'Reset live background.')
self.RequiredShowInFooter = translate('OpenLP.Ui', 'Required, this will be displayed in footer.')
self.Seconds = translate('OpenLP.Ui', 's', 'The abbreviated unit for seconds')
self.SaveAndPreview = translate('OpenLP.Ui', 'Save && Preview')
self.Search = translate('OpenLP.Ui', 'Search')
self.SearchThemes = translate('OpenLP.Ui', 'Search Themes...', 'Search bar place holder text ')
self.SelectDelete = translate('OpenLP.Ui', 'You must select an item to delete.')
self.SelectEdit = translate('OpenLP.Ui', 'You must select an item to edit.')
self.Settings = translate('OpenLP.Ui', 'Settings')
self.SaveService = translate('OpenLP.Ui', 'Save Service')
self.Service = translate('OpenLP.Ui', 'Service')
self.ShortResults = translate('OpenLP.Ui', 'Please type more text to use \'Search As You Type\'')
self.Split = translate('OpenLP.Ui', 'Optional &Split')
self.SplitToolTip = translate('OpenLP.Ui',
'Split a slide into two only if it does not fit on the screen as one slide.')
self.StartingImport = translate('OpenLP.Ui', 'Starting import...')
self.StopPlaySlidesInLoop = translate('OpenLP.Ui', 'Stop Play Slides in Loop')
self.StopPlaySlidesToEnd = translate('OpenLP.Ui', 'Stop Play Slides to End')
self.Theme = translate('OpenLP.Ui', 'Theme', 'Singular')
self.Themes = translate('OpenLP.Ui', 'Themes', 'Plural')
self.Tools = translate('OpenLP.Ui', 'Tools')
self.Top = translate('OpenLP.Ui', 'Top')
self.UnsupportedFile = translate('OpenLP.Ui', 'Unsupported File')
self.VersePerSlide = translate('OpenLP.Ui', 'Verse Per Slide')
self.VersePerLine = translate('OpenLP.Ui', 'Verse Per Line')
self.Version = translate('OpenLP.Ui', 'Version')
self.View = translate('OpenLP.Ui', 'View')
self.ViewMode = translate('OpenLP.Ui', 'View Mode')
self.Video = translate('OpenLP.Ui', 'Video')
self.WebDownloadText = translate('OpenLP.Ui', 'Web Interface, Download and Install latest Version')
book_chapter = translate('OpenLP.Ui', 'Book Chapter')
chapter = translate('OpenLP.Ui', 'Chapter')
verse = translate('OpenLP.Ui', 'Verse')
gap = ' | '
psalm = translate('OpenLP.Ui', 'Psalm')
may_shorten = translate('OpenLP.Ui', 'Book names may be shortened from full names, for an example Ps 23 = '
'Psalm 23')
bible_scripture_items = \
[book_chapter, gap, psalm, ' 23<br>',
book_chapter, '%(range)s', chapter, gap, psalm, ' 23%(range)s24<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, gap, psalm, ' 23%(verse)s1%(range)s2<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, '%(list)s', verse, '%(range)s', verse, gap, psalm,
' 23%(verse)s1%(range)s2%(list)s5%(range)s6<br>',
book_chapter, '%(verse)s', verse, '%(range)s', verse, '%(list)s', chapter, '%(verse)s', verse, '%(range)s',
verse, gap, psalm, ' 23%(verse)s1%(range)s2%(list)s24%(verse)s1%(range)s3<br>',
book_chapter, '%(verse)s', verse, '%(range)s', chapter, '%(verse)s', verse, gap, psalm,
' 23%(verse)s1%(range)s24%(verse)s1<br><br>', may_shorten]
itertools.chain.from_iterable(itertools.repeat(strings, 1) if isinstance(strings, str)
else strings for strings in bible_scripture_items)
self.BibleScriptureError = ''.join(str(joined) for joined in bible_scripture_items)

View File

@ -29,9 +29,9 @@ import os
import re import re
import math import math
from PyQt5 import QtCore, QtGui, Qt, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.common.path import Path from openlp.core.common.path import Path
log = logging.getLogger(__name__ + '.__init__') log = logging.getLogger(__name__ + '.__init__')

View File

@ -29,17 +29,19 @@ import os
from copy import copy from copy import copy
from urllib.parse import quote_plus as urlquote from urllib.parse import quote_plus as urlquote
from sqlalchemy import Table, MetaData, Column, types, create_engine, UnicodeText from alembic.migration import MigrationContext
from alembic.operations import Operations
from sqlalchemy import Table, MetaData, Column, UnicodeText, types, create_engine
from sqlalchemy.engine.url import make_url from sqlalchemy.engine.url import make_url
from sqlalchemy.exc import SQLAlchemyError, InvalidRequestError, DBAPIError, OperationalError, ProgrammingError from sqlalchemy.exc import SQLAlchemyError, InvalidRequestError, DBAPIError, OperationalError, ProgrammingError
from sqlalchemy.orm import scoped_session, sessionmaker, mapper from sqlalchemy.orm import scoped_session, sessionmaker, mapper
from sqlalchemy.pool import NullPool from sqlalchemy.pool import NullPool
from alembic.migration import MigrationContext from openlp.core.common import delete_file
from alembic.operations import Operations from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import translate
from openlp.core.common import AppLocation, Settings, delete_file, translate
from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder
from openlp.core.common.settings import Settings
from openlp.core.lib.ui import critical_error_message_box from openlp.core.lib.ui import critical_error_message_box
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,8 +24,8 @@ Provide HTML Tag management and Formatting Tag access class
""" """
import json import json
from openlp.core.common import Settings from openlp.core.common.settings import Settings
from openlp.core.lib import translate from openlp.core.common.i18n import translate
class FormattingTags(object): class FormattingTags(object):

View File

@ -411,7 +411,7 @@ import logging
from string import Template from string import Template
from PyQt5 import QtWebKit from PyQt5 import QtWebKit
from openlp.core.common import Settings from openlp.core.common.settings import Settings
from openlp.core.lib.theme import BackgroundType, BackgroundGradientType, VerticalType, HorizontalType from openlp.core.lib.theme import BackgroundType, BackgroundGradientType, VerticalType, HorizontalType
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -31,7 +31,8 @@ import queue
from PyQt5 import QtCore from PyQt5 import QtCore
from openlp.core.common import Registry, Settings from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import ScreenList, resize_image, image_to_byte from openlp.core.lib import ScreenList, resize_image, image_to_byte
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -28,8 +28,10 @@ import re
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, RegistryProperties, Settings, UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.path import Path, path_to_str, str_to_path from openlp.core.common.path import Path, path_to_str, str_to_path
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ServiceItem, StringContent, ServiceItemContext from openlp.core.lib import ServiceItem, StringContent, ServiceItemContext
from openlp.core.lib.searchedit import SearchEdit from openlp.core.lib.searchedit import SearchEdit
from openlp.core.lib.ui import create_widget_action, critical_error_message_box from openlp.core.lib.ui import create_widget_action, critical_error_message_box

View File

@ -26,7 +26,9 @@ import logging
from PyQt5 import QtCore from PyQt5 import QtCore
from openlp.core.common import Registry, RegistryProperties, Settings, UiStrings from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.common.i18n import UiStrings
from openlp.core.version import get_version from openlp.core.version import get_version
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,8 +24,11 @@ Provide plugin management
""" """
import os import os
from openlp.core.common import extension_loader
from openlp.core.common.applocation import AppLocation
from openlp.core.common.registry import RegistryProperties
from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.lib import Plugin, PluginStatus from openlp.core.lib import Plugin, PluginStatus
from openlp.core.common import AppLocation, RegistryProperties, OpenLPMixin, RegistryMixin, extension_loader
class PluginManager(RegistryMixin, OpenLPMixin, RegistryProperties): class PluginManager(RegistryMixin, OpenLPMixin, RegistryProperties):

View File

@ -20,37 +20,15 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
:mod:`openlp.core.lib.projector.constants` module The :mod:`openlp.core.lib.projector.constants` module provides the constants used for projector errors/status/defaults
Provides the constants used for projector errors/status/defaults
""" """
import logging import logging
from openlp.core.common.i18n import translate
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
log.debug('projector_constants loaded') log.debug('projector_constants loaded')
from openlp.core.common import translate
__all__ = ['S_OK', 'E_GENERAL', 'E_NOT_CONNECTED', 'E_FAN', 'E_LAMP', 'E_TEMP',
'E_COVER', 'E_FILTER', 'E_AUTHENTICATION', 'E_NO_AUTHENTICATION',
'E_UNDEFINED', 'E_PARAMETER', 'E_UNAVAILABLE', 'E_PROJECTOR',
'E_INVALID_DATA', 'E_WARN', 'E_ERROR', 'E_CLASS', 'E_PREFIX',
'E_CONNECTION_REFUSED', 'E_REMOTE_HOST_CLOSED_CONNECTION', 'E_HOST_NOT_FOUND',
'E_SOCKET_ACCESS', 'E_SOCKET_RESOURCE', 'E_SOCKET_TIMEOUT', 'E_DATAGRAM_TOO_LARGE',
'E_NETWORK', 'E_ADDRESS_IN_USE', 'E_SOCKET_ADDRESS_NOT_AVAILABLE',
'E_UNSUPPORTED_SOCKET_OPERATION', 'E_PROXY_AUTHENTICATION_REQUIRED',
'E_SLS_HANDSHAKE_FAILED', 'E_UNFINISHED_SOCKET_OPERATION', 'E_PROXY_CONNECTION_REFUSED',
'E_PROXY_CONNECTION_CLOSED', 'E_PROXY_CONNECTION_TIMEOUT', 'E_PROXY_NOT_FOUND',
'E_PROXY_PROTOCOL', 'E_UNKNOWN_SOCKET_ERROR',
'S_NOT_CONNECTED', 'S_CONNECTING', 'S_CONNECTED',
'S_STATUS', 'S_OFF', 'S_INITIALIZE', 'S_STANDBY', 'S_WARMUP', 'S_ON', 'S_COOLDOWN',
'S_INFO', 'S_NETWORK_SENDING', 'S_NETWORK_RECEIVED',
'ERROR_STRING', 'CR', 'LF', 'PJLINK_ERST_DATA', 'PJLINK_ERST_STATUS', 'PJLINK_POWR_STATUS',
'PJLINK_PORT', 'PJLINK_MAX_PACKET', 'TIMEOUT', 'ERROR_MSG', 'PJLINK_ERRORS',
'STATUS_STRING', 'PJLINK_VALID_CMD', 'CONNECTION_ERRORS',
'PJLINK_DEFAULT_SOURCES', 'PJLINK_DEFAULT_CODES', 'PJLINK_DEFAULT_ITEMS']
# Set common constants. # Set common constants.
CR = chr(0x0D) # \r CR = chr(0x0D) # \r
LF = chr(0x0A) # \n LF = chr(0x0A) # \n

View File

@ -20,39 +20,40 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
:mod:`openlp.core.lib.projector.pjlink` module The :mod:`openlp.core.lib.projector.pjlink` module provides the necessary functions for connecting to a PJLink-capable
Provides the necessary functions for connecting to a PJLink-capable projector. projector.
PJLink Class 1 Specifications. PJLink Class 1 Specifications
http://pjlink.jbmia.or.jp/english/dl_class1.html ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Section 5-1 PJLink Specifications
Section 5-5 Guidelines for Input Terminals
PJLink Class 2 Specifications. Website: http://pjlink.jbmia.or.jp/english/dl_class1.html
http://pjlink.jbmia.or.jp/english/dl_class2.html
Section 5-1 PJLink Specifications
Section 5-5 Guidelines for Input Terminals
NOTE: - Section 5-1 PJLink Specifications
Function names follow the following syntax: - Section 5-5 Guidelines for Input Terminals
def process_CCCC(...):
WHERE: PJLink Class 2 Specifications
CCCC = PJLink command being processed. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Website: http://pjlink.jbmia.or.jp/english/dl_class2.html
- Section 5-1 PJLink Specifications
- Section 5-5 Guidelines for Input Terminals
.. note:
Function names follow the following syntax::
def process_CCCC(...):
where ``CCCC`` is the PJLink command being processed
""" """
import logging import logging
log = logging.getLogger(__name__)
log.debug('pjlink loaded')
__all__ = ['PJLink']
import re import re
from codecs import decode from codecs import decode
from PyQt5 import QtCore, QtNetwork from PyQt5 import QtCore, QtNetwork
from openlp.core.common import translate, qmd5_hash from openlp.core.common import qmd5_hash
from openlp.core.common.i18n import translate
from openlp.core.lib.projector.constants import CONNECTION_ERRORS, CR, ERROR_MSG, ERROR_STRING, \ from openlp.core.lib.projector.constants import CONNECTION_ERRORS, CR, ERROR_MSG, ERROR_STRING, \
E_AUTHENTICATION, E_CONNECTION_REFUSED, E_GENERAL, E_INVALID_DATA, E_NETWORK, E_NOT_CONNECTED, E_OK, \ E_AUTHENTICATION, E_CONNECTION_REFUSED, E_GENERAL, E_INVALID_DATA, E_NETWORK, E_NOT_CONNECTED, E_OK, \
E_PARAMETER, E_PROJECTOR, E_SOCKET_TIMEOUT, E_UNAVAILABLE, E_UNDEFINED, PJLINK_ERRORS, PJLINK_ERST_DATA, \ E_PARAMETER, E_PROJECTOR, E_SOCKET_TIMEOUT, E_UNAVAILABLE, E_UNDEFINED, PJLINK_ERRORS, PJLINK_ERST_DATA, \
@ -60,6 +61,11 @@ from openlp.core.lib.projector.constants import CONNECTION_ERRORS, CR, ERROR_MSG
STATUS_STRING, S_CONNECTED, S_CONNECTING, S_INFO, S_NETWORK_RECEIVED, S_NETWORK_SENDING, \ STATUS_STRING, S_CONNECTED, S_CONNECTING, S_INFO, S_NETWORK_RECEIVED, S_NETWORK_SENDING, \
S_NOT_CONNECTED, S_OFF, S_OK, S_ON, S_STATUS S_NOT_CONNECTED, S_OFF, S_OK, S_ON, S_STATUS
log = logging.getLogger(__name__)
log.debug('pjlink loaded')
__all__ = ['PJLink']
# Shortcuts # Shortcuts
SocketError = QtNetwork.QAbstractSocket.SocketError SocketError = QtNetwork.QAbstractSocket.SocketError
SocketSTate = QtNetwork.QAbstractSocket.SocketState SocketSTate = QtNetwork.QAbstractSocket.SocketState

View File

@ -25,8 +25,10 @@ import re
from string import Template from string import Template
from PyQt5 import QtGui, QtCore, QtWebKitWidgets from PyQt5 import QtGui, QtCore, QtWebKitWidgets
from openlp.core.common import Registry, RegistryProperties, OpenLPMixin, RegistryMixin, Settings from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.path import path_to_str from openlp.core.common.path import path_to_str
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import FormattingTags, ImageSource, ItemCapabilities, ScreenList, ServiceItem, expand_tags, \ from openlp.core.lib import FormattingTags, ImageSource, ItemCapabilities, ScreenList, ServiceItem, expand_tags, \
build_lyrics_format_css, build_lyrics_outline_css, build_chords_css build_lyrics_format_css, build_lyrics_outline_css, build_chords_css
from openlp.core.common import ThemeLevel from openlp.core.common import ThemeLevel

View File

@ -29,7 +29,9 @@ import copy
from PyQt5 import QtCore from PyQt5 import QtCore
from openlp.core.common import Registry, Settings, translate from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.common.i18n import translate
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,9 +24,9 @@ import logging
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common.settings import Settings
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_widget_action from openlp.core.lib.ui import create_widget_action
from openlp.core.common import Settings
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -23,7 +23,6 @@
The :mod:`serviceitem` provides the service item functionality including the The :mod:`serviceitem` provides the service item functionality including the
type and capability of an item. type and capability of an item.
""" """
import datetime import datetime
import html import html
import logging import logging
@ -33,8 +32,12 @@ import ntpath
from PyQt5 import QtGui from PyQt5 import QtGui
from openlp.core.common import RegistryProperties, Settings, translate, AppLocation, md5_hash from openlp.core.common import md5_hash
from openlp.core.lib import ImageSource, build_icon, clean_tags, expand_tags, expand_chords, create_thumb from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import translate
from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ImageSource, build_icon, clean_tags, expand_tags, expand_chords
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -23,12 +23,9 @@
The :mod:`~openlp.core.lib.settingstab` module contains the base SettingsTab class which plugins use for adding their The :mod:`~openlp.core.lib.settingstab` module contains the base SettingsTab class which plugins use for adding their
own tab to the settings dialog. own tab to the settings dialog.
""" """
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common.registry import RegistryProperties
from openlp.core.common import RegistryProperties
class SettingsTab(QtWidgets.QWidget, RegistryProperties): class SettingsTab(QtWidgets.QWidget, RegistryProperties):

View File

@ -26,10 +26,11 @@ import json
import logging import logging
from lxml import etree, objectify from lxml import etree, objectify
from openlp.core.common import AppLocation, de_hump
from openlp.core.common import de_hump
from openlp.core.common.applocation import AppLocation
from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder from openlp.core.common.json import OpenLPJsonDecoder, OpenLPJsonEncoder
from openlp.core.common.path import Path, str_to_path from openlp.core.lib import ScreenList, str_to_bool, get_text_file_string
from openlp.core.lib import str_to_bool, ScreenList, get_text_file_string
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -26,8 +26,10 @@ import logging
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, UiStrings, translate, is_macosx from openlp.core.common import is_macosx
from openlp.core.common.actions import ActionList from openlp.core.common.actions import ActionList
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry
from openlp.core.lib import build_icon from openlp.core.lib import build_icon

View File

@ -23,7 +23,7 @@ import datetime
from PyQt5 import QtGui, QtWidgets from PyQt5 import QtGui, QtWidgets
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button, create_button_box from openlp.core.lib.ui import create_button, create_button_box

View File

@ -27,7 +27,7 @@ import webbrowser
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.version import get_version from openlp.core.version import get_version
from openlp.core.lib import translate from openlp.core.common.i18n import translate
from .aboutdialog import UiAboutDialog from .aboutdialog import UiAboutDialog

View File

@ -27,9 +27,10 @@ from datetime import datetime, timedelta
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import AppLocation, Settings, SlideLimits, UiStrings, translate from openlp.core.common import SlideLimits
from openlp.core.common.languagemanager import format_time from openlp.core.common.applocation import AppLocation
from openlp.core.common.path import path_to_str from openlp.core.common.i18n import UiStrings, format_time, translate
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab, build_icon from openlp.core.lib import SettingsTab, build_icon
from openlp.core.ui.lib import PathEdit, PathType from openlp.core.ui.lib import PathEdit, PathType
from openlp.core.ui.style import HAS_DARK_STYLE from openlp.core.ui.style import HAS_DARK_STYLE

View File

@ -25,7 +25,8 @@ The GUI widgets of the exception dialog.
from PyQt5 import QtGui, QtWidgets from PyQt5 import QtGui, QtWidgets
from openlp.core.lib import translate, build_icon from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button, create_button_box from openlp.core.lib.ui import create_button, create_button_box

View File

@ -70,11 +70,14 @@ try:
except ImportError: except ImportError:
VLC_VERSION = '-' VLC_VERSION = '-'
from openlp.core.common import RegistryProperties, Settings, UiStrings, is_linux, translate from openlp.core.common import is_linux
from openlp.core.version import get_version from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.ui.exceptiondialog import Ui_ExceptionDialog
from openlp.core.ui.lib.filedialog import FileDialog from openlp.core.ui.lib.filedialog import FileDialog
from openlp.core.version import get_version
from .exceptiondialog import Ui_ExceptionDialog
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,7 +24,8 @@ The UI widgets for the rename dialog
""" """
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.lib import translate, build_icon from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -22,12 +22,11 @@
""" """
The file rename dialog. The file rename dialog.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from .filerenamedialog import Ui_FileRenameDialog from openlp.core.common.i18n import translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common import Registry, RegistryProperties, translate from openlp.core.ui.filerenamedialog import Ui_FileRenameDialog
class FileRenameForm(QtWidgets.QDialog, Ui_FileRenameDialog, RegistryProperties): class FileRenameForm(QtWidgets.QDialog, Ui_FileRenameDialog, RegistryProperties):

View File

@ -34,9 +34,12 @@ from tempfile import gettempdir
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, RegistryProperties, AppLocation, Settings, check_directory_exists, \ from openlp.core.common import clean_button_text, trace_error_handler
translate, clean_button_text, trace_error_handler from openlp.core.common.applocation import AppLocation
from openlp.core.common.path import Path from openlp.core.common.i18n import translate
from openlp.core.common.path import Path, create_paths
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import PluginStatus, build_icon from openlp.core.lib import PluginStatus, build_icon
from openlp.core.lib.ui import critical_error_message_box from openlp.core.lib.ui import critical_error_message_box
from openlp.core.common.httputils import get_web_page, get_url_file_size, url_get_file, CONNECTION_TIMEOUT from openlp.core.common.httputils import get_web_page, get_url_file_size, url_get_file, CONNECTION_TIMEOUT
@ -277,7 +280,7 @@ class FirstTimeForm(QtWidgets.QWizard, UiFirstTimeWizard, RegistryProperties):
self.no_internet_cancel_button.setVisible(False) self.no_internet_cancel_button.setVisible(False)
# Check if this is a re-run of the wizard. # Check if this is a re-run of the wizard.
self.has_run_wizard = Settings().value('core/has run wizard') self.has_run_wizard = Settings().value('core/has run wizard')
check_directory_exists(Path(gettempdir(), 'openlp')) create_paths(Path(gettempdir(), 'openlp'))
def update_screen_list_combo(self): def update_screen_list_combo(self):
""" """
@ -597,7 +600,7 @@ class FirstTimeForm(QtWidgets.QWizard, UiFirstTimeWizard, RegistryProperties):
'The following files were not able to be ' 'The following files were not able to be '
'downloaded:<br \\>{text}'.format(text=file_list))) 'downloaded:<br \\>{text}'.format(text=file_list)))
msg.setStandardButtons(msg.Ok) msg.setStandardButtons(msg.Ok)
ans = msg.exec() msg.exec()
return True return True
def _set_plugin_status(self, field, tag): def _set_plugin_status(self, field, tag):

View File

@ -24,7 +24,7 @@ The UI widgets of the language selection dialog.
""" """
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -24,8 +24,8 @@ The language selection dialog.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common.i18n import LanguageManager
from openlp.core.lib.ui import create_action from openlp.core.lib.ui import create_action
from openlp.core.common import LanguageManager
from .firsttimelanguagedialog import Ui_FirstTimeLanguageDialog from .firsttimelanguagedialog import Ui_FirstTimeLanguageDialog

View File

@ -24,8 +24,9 @@ The UI widgets for the first time wizard.
""" """
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common.uistrings import UiStrings from openlp.core.common import is_macosx, clean_button_text
from openlp.core.common import translate, is_macosx, clean_button_text, Settings from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.settings import Settings
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import add_welcome_page from openlp.core.lib.ui import add_welcome_page

View File

@ -24,9 +24,9 @@ The :mod:`formattingtagform` provides an Tag Edit facility. The Base set are pro
Custom tags can be defined and saved. The Custom Tag arrays are saved in a pickle so QSettings works on them. Base Tags Custom tags can be defined and saved. The Custom Tag arrays are saved in a pickle so QSettings works on them. Base Tags
cannot be changed. cannot be changed.
""" """
import re import re
from openlp.core.common import translate
from openlp.core.common.i18n import translate
from openlp.core.lib import FormattingTags from openlp.core.lib import FormattingTags

View File

@ -24,7 +24,7 @@ The UI widgets for the formatting tags window.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -24,10 +24,9 @@ The :mod:`formattingtagform` provides an Tag Edit facility. The Base set are pro
Custom tags can be defined and saved. The Custom Tag arrays are saved in a json string so QSettings works on them. Custom tags can be defined and saved. The Custom Tag arrays are saved in a json string so QSettings works on them.
Base Tags cannot be changed. Base Tags cannot be changed.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import FormattingTags from openlp.core.lib import FormattingTags
from openlp.core.ui.formattingtagdialog import Ui_FormattingTagDialog from openlp.core.ui.formattingtagdialog import Ui_FormattingTagDialog
from openlp.core.ui.formattingtagcontroller import FormattingTagController from openlp.core.ui.formattingtagcontroller import FormattingTagController

View File

@ -26,8 +26,11 @@ import logging
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, Settings, UiStrings, translate, get_images_filter from openlp.core.common import get_images_filter
from openlp.core.common.path import Path, path_to_str, str_to_path from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.path import Path
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab, ScreenList from openlp.core.lib import SettingsTab, ScreenList
from openlp.core.ui.lib import ColorButton, PathEdit from openlp.core.ui.lib import ColorButton, PathEdit

View File

@ -25,7 +25,7 @@ Provide a custom widget based on QPushButton for the selection of colors
""" """
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
class ColorButton(QtWidgets.QPushButton): class ColorButton(QtWidgets.QPushButton):

View File

@ -26,7 +26,8 @@ It is based on a QTableWidget but represents its contents in list form.
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import RegistryProperties, Settings from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ImageSource, ItemCapabilities, ServiceItem from openlp.core.lib import ImageSource, ItemCapabilities, ServiceItem

View File

@ -26,7 +26,8 @@ import os
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, UiStrings from openlp.core.common.i18n import UiStrings
from openlp.core.common.registry import Registry
class ListWidgetWithDnD(QtWidgets.QListWidget): class ListWidgetWithDnD(QtWidgets.QListWidget):

View File

@ -23,7 +23,7 @@ from enum import Enum
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.path import Path, path_to_str, str_to_path from openlp.core.common.path import Path, path_to_str, str_to_path
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.ui.lib.filedialog import FileDialog from openlp.core.ui.lib.filedialog import FileDialog

View File

@ -38,7 +38,8 @@ except ImportError:
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.lib import translate, FormattingTags from openlp.core.common.i18n import translate
from openlp.core.lib import FormattingTags
from openlp.core.lib.ui import create_action from openlp.core.lib.ui import create_action
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -26,7 +26,8 @@ import os
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, is_win from openlp.core.common import is_win
from openlp.core.common.registry import Registry
class TreeWidgetWithDnD(QtWidgets.QTreeWidget): class TreeWidgetWithDnD(QtWidgets.QTreeWidget):

View File

@ -23,11 +23,13 @@
The :mod:``wizard`` module provides generic wizard tools for OpenLP. The :mod:``wizard`` module provides generic wizard tools for OpenLP.
""" """
import logging import logging
import os
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, RegistryProperties, Settings, UiStrings, translate, is_macosx from openlp.core.common import is_macosx
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import add_welcome_page from openlp.core.lib.ui import add_welcome_page
from openlp.core.ui.lib.filedialog import FileDialog from openlp.core.ui.lib.filedialog import FileDialog

View File

@ -26,18 +26,20 @@ Some of the code for this form is based on the examples at:
* `http://www.steveheffernan.com/html5-video-player/demo-video-player.html`_ * `http://www.steveheffernan.com/html5-video-player/demo-video-player.html`_
* `http://html5demos.com/two-videos`_ * `http://html5demos.com/two-videos`_
""" """
import html import html
import logging import logging
import os import os
from PyQt5 import QtCore, QtWidgets, QtWebKit, QtWebKitWidgets, QtGui, QtMultimedia from PyQt5 import QtCore, QtWidgets, QtWebKit, QtWebKitWidgets, QtGui, QtMultimedia
from openlp.core.common import AppLocation, Registry, RegistryProperties, OpenLPMixin, Settings, translate,\ from openlp.core.common import is_macosx, is_win
is_macosx, is_win from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import translate
from openlp.core.common.mixins import OpenLPMixin
from openlp.core.common.path import path_to_str from openlp.core.common.path import path_to_str
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ServiceItem, ImageSource, ScreenList, build_html, expand_tags, image_to_byte from openlp.core.lib import ServiceItem, ImageSource, ScreenList, build_html, expand_tags, image_to_byte
from openlp.core.lib.theme import BackgroundType from openlp.core.lib.theme import BackgroundType
from openlp.core.ui import HideMode, AlertLocation, DisplayControllerType from openlp.core.ui import HideMode, AlertLocation, DisplayControllerType

View File

@ -36,10 +36,13 @@ from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.api import websockets from openlp.core.api import websockets
from openlp.core.api.http import server from openlp.core.api.http import server
from openlp.core.common import Registry, RegistryProperties, AppLocation, LanguageManager, Settings, UiStrings, \ from openlp.core.common import is_win, is_macosx, add_actions
check_directory_exists, translate, is_win, is_macosx, add_actions
from openlp.core.common.actions import ActionList, CategoryOrder from openlp.core.common.actions import ActionList, CategoryOrder
from openlp.core.common.path import Path, copyfile, path_to_str, str_to_path from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import LanguageManager, UiStrings, translate
from openlp.core.common.path import Path, copyfile, create_paths, path_to_str, str_to_path
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import Renderer, PluginManager, ImageManager, PluginStatus, ScreenList, build_icon from openlp.core.lib import Renderer, PluginManager, ImageManager, PluginStatus, ScreenList, build_icon
from openlp.core.lib.ui import create_action from openlp.core.lib.ui import create_action
from openlp.core.ui import AboutForm, SettingsForm, ServiceManager, ThemeManager, LiveController, PluginForm, \ from openlp.core.ui import AboutForm, SettingsForm, ServiceManager, ThemeManager, LiveController, PluginForm, \
@ -853,7 +856,7 @@ class MainWindow(QtWidgets.QMainWindow, Ui_MainWindow, RegistryProperties):
setting_sections.extend([plugin.name for plugin in self.plugin_manager.plugins]) setting_sections.extend([plugin.name for plugin in self.plugin_manager.plugins])
# Copy the settings file to the tmp dir, because we do not want to change the original one. # Copy the settings file to the tmp dir, because we do not want to change the original one.
temp_dir_path = Path(gettempdir(), 'openlp') temp_dir_path = Path(gettempdir(), 'openlp')
check_directory_exists(temp_dir_path) create_paths(temp_dir_path)
temp_config_path = temp_dir_path / import_file_path.name temp_config_path = temp_dir_path / import_file_path.name
copyfile(import_file_path, temp_config_path) copyfile(import_file_path, temp_config_path)
settings = Settings() settings = Settings()
@ -929,7 +932,14 @@ class MainWindow(QtWidgets.QMainWindow, Ui_MainWindow, RegistryProperties):
# Make sure it's a .conf file. # Make sure it's a .conf file.
export_file_path = export_file_path.with_suffix('.conf') export_file_path = export_file_path.with_suffix('.conf')
self.save_settings() self.save_settings()
Settings().export(export_file_path) try:
Settings().export(export_file_path)
except OSError as ose:
QtWidgets.QMessageBox.critical(self, translate('OpenLP.MainWindow', 'Export setting error'),
translate('OpenLP.MainWindow',
'An error occurred while exporting the settings: {err}'
).format(err=ose.strerror),
QtWidgets.QMessageBox.StandardButtons(QtWidgets.QMessageBox.Ok))
def on_mode_default_item_clicked(self): def on_mode_default_item_clicked(self):
""" """

View File

@ -26,7 +26,7 @@ import logging
from PyQt5 import QtCore from PyQt5 import QtCore
from openlp.core.common import Settings from openlp.core.common.settings import Settings
log = logging.getLogger(__name__ + '.__init__') log = logging.getLogger(__name__ + '.__init__')

View File

@ -19,15 +19,16 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 # # with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
"""
The :mod:`~openlp.core.api.endpoint` module contains various API endpoints
"""
import logging import logging
from openlp.core.api.http.endpoint import Endpoint from openlp.core.api.http.endpoint import Endpoint
from openlp.core.api.http import requires_auth from openlp.core.api.http import requires_auth
from openlp.core.common import Registry from openlp.core.common.registry import Registry
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
media_endpoint = Endpoint('media') media_endpoint = Endpoint('media')

View File

@ -29,8 +29,11 @@ import datetime
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.api.http import register_endpoint from openlp.core.api.http import register_endpoint
from openlp.core.common import OpenLPMixin, Registry, RegistryMixin, RegistryProperties, Settings, UiStrings, \ from openlp.core.common import extension_loader
extension_loader, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ItemCapabilities from openlp.core.lib import ItemCapabilities
from openlp.core.lib.ui import critical_error_message_box from openlp.core.lib.ui import critical_error_message_box
from openlp.core.ui import DisplayControllerType from openlp.core.ui import DisplayControllerType

View File

@ -22,7 +22,7 @@
""" """
The :mod:`~openlp.core.ui.media.mediaplayer` module contains the MediaPlayer class. The :mod:`~openlp.core.ui.media.mediaplayer` module contains the MediaPlayer class.
""" """
from openlp.core.common import RegistryProperties from openlp.core.common.registry import RegistryProperties
from openlp.core.ui.media import MediaState from openlp.core.ui.media import MediaState

View File

@ -25,7 +25,9 @@ The :mod:`~openlp.core.ui.media.playertab` module holds the configuration tab fo
import platform import platform
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, Settings, UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab from openlp.core.lib import SettingsTab
from openlp.core.lib.ui import create_button from openlp.core.lib.ui import create_button
from openlp.core.ui.media import get_media_players, set_media_players from openlp.core.ui.media import get_media_players, set_media_players

View File

@ -28,7 +28,7 @@ import mimetypes
from PyQt5 import QtCore, QtMultimedia, QtMultimediaWidgets from PyQt5 import QtCore, QtMultimedia, QtMultimediaWidgets
from openlp.core.lib import translate from openlp.core.common.i18n import translate
from openlp.core.ui.media import MediaState from openlp.core.ui.media import MediaState
from openlp.core.ui.media.mediaplayer import MediaPlayer from openlp.core.ui.media.mediaplayer import MediaPlayer

View File

@ -31,8 +31,9 @@ import sys
import ctypes import ctypes
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common import Settings, is_win, is_macosx, is_linux from openlp.core.common import is_win, is_macosx, is_linux
from openlp.core.lib import translate from openlp.core.common.i18n import translate
from openlp.core.common.settings import Settings
from openlp.core.ui.media import MediaState, MediaType from openlp.core.ui.media import MediaState, MediaType
from openlp.core.ui.media.mediaplayer import MediaPlayer from openlp.core.ui.media.mediaplayer import MediaPlayer

View File

@ -26,8 +26,8 @@ import logging
from PyQt5 import QtGui, QtWebKitWidgets from PyQt5 import QtGui, QtWebKitWidgets
from openlp.core.common import Settings from openlp.core.common.settings import Settings
from openlp.core.lib import translate from openlp.core.common.i18n import translate
from openlp.core.ui.media import MediaState from openlp.core.ui.media import MediaState
from openlp.core.ui.media.mediaplayer import MediaPlayer from openlp.core.ui.media.mediaplayer import MediaPlayer

View File

@ -24,7 +24,7 @@ The UI widgets of the plugin view dialog
#""" #"""
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -26,9 +26,10 @@ import logging
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import RegistryProperties, translate from openlp.core.common.i18n import translate
from openlp.core.common.registry import RegistryProperties
from openlp.core.lib import PluginStatus from openlp.core.lib import PluginStatus
from .plugindialog import Ui_PluginViewDialog from openlp.core.ui.plugindialog import Ui_PluginViewDialog
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,7 +24,7 @@ The UI widgets of the print service dialog.
""" """
from PyQt5 import QtCore, QtWidgets, QtPrintSupport from PyQt5 import QtCore, QtWidgets, QtPrintSupport
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.ui.lib import SpellTextEdit from openlp.core.ui.lib import SpellTextEdit

View File

@ -23,16 +23,17 @@
The actual print service dialog The actual print service dialog
""" """
import datetime import datetime
import os
import html import html
import lxml.html import lxml.html
from PyQt5 import QtCore, QtGui, QtWidgets, QtPrintSupport from PyQt5 import QtCore, QtGui, QtWidgets, QtPrintSupport
from openlp.core.common import Registry, RegistryProperties, Settings, UiStrings, translate from openlp.core.common.applocation import AppLocation
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import get_text_file_string from openlp.core.lib import get_text_file_string
from openlp.core.ui.printservicedialog import Ui_PrintServiceDialog, ZoomSize from openlp.core.ui.printservicedialog import Ui_PrintServiceDialog, ZoomSize
from openlp.core.common import AppLocation
DEFAULT_CSS = """/* DEFAULT_CSS = """/*
Edit this file to customize the service order print. Note, that not all CSS Edit this file to customize the service order print. Note, that not all CSS

View File

@ -20,22 +20,22 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
:mod: `openlp.core.ui.projector.editform` module The :mod: `openlp.core.ui.projector.editform` module provides the functions for adding/editing entries in the projector
database.
Provides the functions for adding/editing entries in the projector database.
""" """
import logging import logging
log = logging.getLogger(__name__)
log.debug('editform loaded')
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import translate, verify_ip_address from openlp.core.common import verify_ip_address
from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.projector.db import Projector from openlp.core.lib.projector.db import Projector
from openlp.core.lib.projector.constants import PJLINK_PORT from openlp.core.lib.projector.constants import PJLINK_PORT
log = logging.getLogger(__name__)
log.debug('editform loaded')
class Ui_ProjectorEditForm(object): class Ui_ProjectorEditForm(object):
""" """

View File

@ -29,9 +29,10 @@ import logging
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import RegistryProperties, Settings, OpenLPMixin, \ from openlp.core.common.i18n import translate
RegistryMixin, translate from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.ui.lib import OpenLPToolbar from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib.ui import create_widget_action from openlp.core.lib.ui import create_widget_action
from openlp.core.lib.projector import DialogSourceStyle from openlp.core.lib.projector import DialogSourceStyle
from openlp.core.lib.projector.constants import ERROR_MSG, ERROR_STRING, E_AUTHENTICATION, E_ERROR, \ from openlp.core.lib.projector.constants import ERROR_MSG, ERROR_STRING, E_AUTHENTICATION, E_ERROR, \
@ -39,6 +40,7 @@ from openlp.core.lib.projector.constants import ERROR_MSG, ERROR_STRING, E_AUTHE
S_INITIALIZE, S_NOT_CONNECTED, S_OFF, S_ON, S_STANDBY, S_WARMUP S_INITIALIZE, S_NOT_CONNECTED, S_OFF, S_ON, S_STANDBY, S_WARMUP
from openlp.core.lib.projector.db import ProjectorDB from openlp.core.lib.projector.db import ProjectorDB
from openlp.core.lib.projector.pjlink import PJLink, PJLinkUDP from openlp.core.lib.projector.pjlink import PJLink, PJLinkUDP
from openlp.core.ui.lib import OpenLPToolbar
from openlp.core.ui.projector.editform import ProjectorEditForm from openlp.core.ui.projector.editform import ProjectorEditForm
from openlp.core.ui.projector.sourceselectform import SourceSelectTabs, SourceSelectSingle from openlp.core.ui.projector.sourceselectform import SourceSelectTabs, SourceSelectSingle

View File

@ -28,7 +28,8 @@ import logging
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import translate, is_macosx from openlp.core.common import is_macosx
from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.projector.db import ProjectorSource from openlp.core.lib.projector.db import ProjectorSource
from openlp.core.lib.projector.constants import PJLINK_DEFAULT_SOURCES, PJLINK_DEFAULT_CODES from openlp.core.lib.projector.constants import PJLINK_DEFAULT_SOURCES, PJLINK_DEFAULT_CODES

View File

@ -20,21 +20,20 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
:mod:`openlp.core.ui.projector.tab` The :mod:`openlp.core.ui.projector.tab` module provides the settings tab in the settings dialog.
Provides the settings tab in the settings dialog.
""" """
import logging import logging
log = logging.getLogger(__name__)
log.debug('projectortab module loaded')
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common import Settings, UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab from openlp.core.lib import SettingsTab
from openlp.core.lib.projector import DialogSourceStyle from openlp.core.lib.projector import DialogSourceStyle
log = logging.getLogger(__name__)
log.debug('projectortab module loaded')
class ProjectorTab(SettingsTab): class ProjectorTab(SettingsTab):
""" """

View File

@ -24,7 +24,7 @@ The UI widgets for the service item edit dialog
""" """
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box, create_button from openlp.core.lib.ui import create_button_box, create_button

View File

@ -24,9 +24,8 @@ The service item edit dialog
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, RegistryProperties from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.ui.serviceitemeditdialog import Ui_ServiceItemEditDialog
from .serviceitemeditdialog import Ui_ServiceItemEditDialog
class ServiceItemEditForm(QtWidgets.QDialog, Ui_ServiceItemEditDialog, RegistryProperties): class ServiceItemEditForm(QtWidgets.QDialog, Ui_ServiceItemEditDialog, RegistryProperties):

View File

@ -32,11 +32,14 @@ from tempfile import mkstemp
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, RegistryProperties, AppLocation, Settings, ThemeLevel, OpenLPMixin, \ from openlp.core.common import ThemeLevel, split_filename, delete_file
RegistryMixin, check_directory_exists, UiStrings, translate, split_filename, delete_file
from openlp.core.common.actions import ActionList, CategoryOrder from openlp.core.common.actions import ActionList, CategoryOrder
from openlp.core.common.languagemanager import format_time from openlp.core.common.applocation import AppLocation
from openlp.core.common.path import Path, path_to_str, str_to_path from openlp.core.common.i18n import UiStrings, format_time, translate
from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.path import Path, create_paths, path_to_str, str_to_path
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ServiceItem, ItemCapabilities, PluginStatus, build_icon from openlp.core.lib import ServiceItem, ItemCapabilities, PluginStatus, build_icon
from openlp.core.lib.ui import critical_error_message_box, create_widget_action, find_and_set_in_combo_box from openlp.core.lib.ui import critical_error_message_box, create_widget_action, find_and_set_in_combo_box
from openlp.core.ui import ServiceNoteForm, ServiceItemEditForm, StartTimeForm from openlp.core.ui import ServiceNoteForm, ServiceItemEditForm, StartTimeForm
@ -592,7 +595,7 @@ class ServiceManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ServiceMa
audio_from = os.path.join(self.service_path, audio_from) audio_from = os.path.join(self.service_path, audio_from)
save_file = os.path.join(self.service_path, audio_to) save_file = os.path.join(self.service_path, audio_to)
save_path = os.path.split(save_file)[0] save_path = os.path.split(save_file)[0]
check_directory_exists(Path(save_path)) create_paths(Path(save_path))
if not os.path.exists(save_file): if not os.path.exists(save_file):
shutil.copy(audio_from, save_file) shutil.copy(audio_from, save_file)
zip_file.write(audio_from, audio_to) zip_file.write(audio_from, audio_to)

View File

@ -24,7 +24,8 @@ The :mod:`~openlp.core.ui.servicenoteform` module contains the `ServiceNoteForm`
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import Registry, RegistryProperties, translate from openlp.core.common.i18n import translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.ui.lib import SpellTextEdit from openlp.core.ui.lib import SpellTextEdit
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -24,7 +24,7 @@ The UI widgets of the settings dialog.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -27,12 +27,12 @@ import logging
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.api import ApiTab from openlp.core.api import ApiTab
from openlp.core.common import Registry, RegistryProperties from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.ui import AdvancedTab, GeneralTab, ThemesTab from openlp.core.ui import AdvancedTab, GeneralTab, ThemesTab
from openlp.core.ui.media import PlayerTab from openlp.core.ui.media import PlayerTab
from .settingsdialog import Ui_SettingsDialog
from openlp.core.ui.projector.tab import ProjectorTab from openlp.core.ui.projector.tab import ProjectorTab
from openlp.core.ui.settingsdialog import Ui_SettingsDialog
log = logging.getLogger(__name__) log = logging.getLogger(__name__)

View File

@ -24,7 +24,7 @@ The list of shortcuts within a dialog.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -20,15 +20,18 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Temple Place, Suite 330, Boston, MA 02111-1307 USA #
############################################################################### ###############################################################################
""" """
The :mod:`~openlp.core.ui.shortcutlistform` module contains the form class""" The :mod:`~openlp.core.ui.shortcutlistform` module contains the form class
"""
import logging import logging
import re import re
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import RegistryProperties, Settings, translate
from openlp.core.common.actions import ActionList from openlp.core.common.actions import ActionList
from .shortcutlistdialog import Ui_ShortcutListDialog from openlp.core.common.i18n import translate
from openlp.core.common.registry import RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.ui.shortcutlistdialog import Ui_ShortcutListDialog
REMOVE_AMPERSAND = re.compile(r'&{1}') REMOVE_AMPERSAND = re.compile(r'&{1}')

View File

@ -30,9 +30,12 @@ from threading import Lock
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, RegistryProperties, Settings, SlideLimits, UiStrings, translate, \ from openlp.core.common import SlideLimits
RegistryMixin, OpenLPMixin
from openlp.core.common.actions import ActionList, CategoryOrder from openlp.core.common.actions import ActionList, CategoryOrder
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ItemCapabilities, ServiceItem, ImageSource, ServiceItemAction, ScreenList, build_icon, \ from openlp.core.lib import ItemCapabilities, ServiceItem, ImageSource, ServiceItemAction, ScreenList, build_icon, \
build_html build_html
from openlp.core.lib.ui import create_action from openlp.core.lib.ui import create_action

View File

@ -24,7 +24,7 @@ The UI widgets for the time dialog
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from openlp.core.common import UiStrings, translate from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -24,10 +24,10 @@ The actual start time form.
""" """
from PyQt5 import QtCore, QtWidgets from PyQt5 import QtCore, QtWidgets
from .starttimedialog import Ui_StartTimeDialog from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common import Registry, RegistryProperties, UiStrings, translate
from openlp.core.lib.ui import critical_error_message_box from openlp.core.lib.ui import critical_error_message_box
from openlp.core.ui.starttimedialog import Ui_StartTimeDialog
class StartTimeForm(QtWidgets.QDialog, Ui_StartTimeDialog, RegistryProperties): class StartTimeForm(QtWidgets.QDialog, Ui_StartTimeDialog, RegistryProperties):

View File

@ -23,11 +23,12 @@
The Theme wizard The Theme wizard
""" """
import logging import logging
import os
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, RegistryProperties, UiStrings, translate, get_images_filter, is_not_image_file from openlp.core.common import get_images_filter, is_not_image_file
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.lib.theme import BackgroundType, BackgroundGradientType from openlp.core.lib.theme import BackgroundType, BackgroundGradientType
from openlp.core.lib.ui import critical_error_message_box from openlp.core.lib.ui import critical_error_message_box
from openlp.core.ui import ThemeLayoutForm from openlp.core.ui import ThemeLayoutForm

View File

@ -24,7 +24,7 @@ The layout of the theme
""" """
from PyQt5 import QtWidgets from PyQt5 import QtWidgets
from openlp.core.common import translate from openlp.core.common.i18n import translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.ui import create_button_box from openlp.core.lib.ui import create_button_box

View File

@ -28,10 +28,13 @@ from xml.etree.ElementTree import ElementTree, XML
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, RegistryProperties, AppLocation, Settings, OpenLPMixin, RegistryMixin, \ from openlp.core.common import delete_file
UiStrings, check_directory_exists, translate, delete_file from openlp.core.common.applocation import AppLocation
from openlp.core.common.languagemanager import get_locale_key from openlp.core.common.i18n import UiStrings, translate, get_locale_key
from openlp.core.common.path import Path, copyfile, path_to_str, rmtree from openlp.core.common.mixins import OpenLPMixin, RegistryMixin
from openlp.core.common.path import Path, copyfile, create_paths, path_to_str, rmtree
from openlp.core.common.registry import Registry, RegistryProperties
from openlp.core.common.settings import Settings
from openlp.core.lib import ImageSource, ValidationError, get_text_file_string, build_icon, \ from openlp.core.lib import ImageSource, ValidationError, get_text_file_string, build_icon, \
check_item_selected, create_thumb, validate_thumb check_item_selected, create_thumb, validate_thumb
from openlp.core.lib.theme import Theme, BackgroundType from openlp.core.lib.theme import Theme, BackgroundType
@ -176,9 +179,8 @@ class ThemeManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ThemeManage
:rtype: None :rtype: None
""" """
self.theme_path = AppLocation.get_section_data_path(self.settings_section) self.theme_path = AppLocation.get_section_data_path(self.settings_section)
check_directory_exists(self.theme_path)
self.thumb_path = self.theme_path / 'thumbnails' self.thumb_path = self.theme_path / 'thumbnails'
check_directory_exists(self.thumb_path) create_paths(self.theme_path, self.thumb_path)
def check_list_state(self, item, field=None): def check_list_state(self, item, field=None):
""" """
@ -594,7 +596,7 @@ class ThemeManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ThemeManage
# is directory or preview file # is directory or preview file
continue continue
full_name = directory_path / zipped_file_rel_path full_name = directory_path / zipped_file_rel_path
check_directory_exists(full_name.parent) create_paths(full_name.parent)
if zipped_file_rel_path.suffix.lower() == '.xml' or zipped_file_rel_path.suffix.lower() == '.json': if zipped_file_rel_path.suffix.lower() == '.xml' or zipped_file_rel_path.suffix.lower() == '.json':
file_xml = str(theme_zip.read(zipped_file), 'utf-8') file_xml = str(theme_zip.read(zipped_file), 'utf-8')
with full_name.open('w', encoding='utf-8') as out_file: with full_name.open('w', encoding='utf-8') as out_file:
@ -661,7 +663,7 @@ class ThemeManager(OpenLPMixin, RegistryMixin, QtWidgets.QWidget, Ui_ThemeManage
name = theme.theme_name name = theme.theme_name
theme_pretty = theme.export_theme(self.theme_path) theme_pretty = theme.export_theme(self.theme_path)
theme_dir = self.theme_path / name theme_dir = self.theme_path / name
check_directory_exists(theme_dir) create_paths(theme_dir)
theme_path = theme_dir / '{file_name}.json'.format(file_name=name) theme_path = theme_dir / '{file_name}.json'.format(file_name=name)
try: try:
theme_path.write_text(theme_pretty) theme_path.write_text(theme_pretty)

View File

@ -22,11 +22,12 @@
""" """
The Themes configuration tab The Themes configuration tab
""" """
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import Registry, Settings, ThemeLevel, UiStrings, translate from openlp.core.common import ThemeLevel
from openlp.core.common.i18n import UiStrings, translate
from openlp.core.common.registry import Registry
from openlp.core.common.settings import Settings
from openlp.core.lib import SettingsTab from openlp.core.lib import SettingsTab
from openlp.core.lib.ui import find_and_set_in_combo_box from openlp.core.lib.ui import find_and_set_in_combo_box

View File

@ -24,8 +24,8 @@ The Create/Edit theme wizard
""" """
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5 import QtCore, QtGui, QtWidgets
from openlp.core.common import UiStrings, translate, is_macosx from openlp.core.common import is_macosx
from openlp.core.common.path import Path from openlp.core.common.i18n import UiStrings, translate
from openlp.core.lib import build_icon from openlp.core.lib import build_icon
from openlp.core.lib.theme import HorizontalType, BackgroundType, BackgroundGradientType from openlp.core.lib.theme import HorizontalType, BackgroundType, BackgroundGradientType
from openlp.core.lib.ui import add_welcome_page, create_valign_selection_widgets from openlp.core.lib.ui import add_welcome_page, create_valign_selection_widgets

Some files were not shown because too many files have changed in this diff Show More