Exemplo n.º 1
0
    def __init__(self, parent=None, style='default', paths=[]):
        from PySide.QtGui import QFontDatabase

        self._ui = parent  # parent UI
        self._style = style  # style to parse
        self._font_db = QFontDatabase()  # font database
        self._fonts = dict()  # dictionary of valid font types (ui, mono)

        self._config_paths = ()  # paths for cfg mods
        self._config_files = dict()  # cfg files

        self._qss_paths = ()  # qss file paths
        self._qss_files = dict()  # qss files
        self._initialized = False

        # debugging data
        self._data = dict()

        if not self._initialized:
            self.run(paths=paths)
    def findSizes(self,font):
        fontLogger.debug("font.key()=%s" % font.key())
        fontDatabase = QFontDatabase()

        self.sizeCombo.blockSignals(True)
        self.sizeCombo.clear()

        self.sizeComboFs.blockSignals(True)
        self.sizeComboFs.clear()

        styleStr = fontDatabase.styleString(font)
        if fontDatabase.isSmoothlyScalable(font.family(),styleStr):
            for size in QFontDatabase.standardSizes():
                self.sizeCombo.addItem(str(size))
                self.sizeComboFs.addItem(str(size))
        else:
            for size in fontDatabase.smoothSizes(font.family(),styleStr):
                self.sizeCombo.addItem(str(size))
                self.sizeComboFs.addItem(str(size))

        self.sizeCombo.blockSignals(False)
        self.sizeComboFs.blockSignals(False)

        currentSize = unicode(QSettings().value("worksheet/fontsize",
                                                QtReduceDefaults.FONTSIZE))
        sizeIndex = self.sizeCombo.findText(currentSize)
        self.sizeCombo.setCurrentIndex(sizeIndex)

        currentSize = unicode(QSettings().value("worksheet/fontsizefs",
                                                QtReduceDefaults.FONTSIZEFS))
        sizeIndex = self.sizeCombo.findText(currentSize)
        self.sizeComboFs.setCurrentIndex(sizeIndex)
Exemplo n.º 3
0
 def __nextGoodFontSize(self,font,size,step):
     info = QFontInfo(font)
     family = info.family()
     fontDatabase = QFontDatabase()
     styleStr = fontDatabase.styleString(font)
     fontLogger.debug("family=%s, style=%s" % (family,styleStr))
     if fontDatabase.isSmoothlyScalable(family,styleStr):
         sizes = QFontDatabase.standardSizes()
     else:
         sizes = fontDatabase.smoothSizes(family,styleStr)
     fontLogger.debug("looking for %s in %s step %d" % (size,sizes,step))
     nSize = size
     while nSize not in sizes and sizes[0] <= nSize and nSize <= sizes[-1]:
         nSize += step
     if nSize < sizes[0]:
         fontLogger.debug("out of range - returning %s" % sizes[0])
         return sizes[0]
     if sizes[-1] < nSize:
         fontLogger.debug("out of range - returning %s" % sizes[-1])
         return sizes[-1]
     fontLogger.debug("found %s" % nSize)
     return nSize
Exemplo n.º 4
0
    def setUpClass(cls):
        super(TestClockClient,cls).setUpClass()

        mainlog.setLevel(logging.WARNING) # logging.WARNING)
        cls.mem_logger = MemLogger()

        app = QApplication.instance()
        if app is None:
            app = QApplication(sys.argv)

        font_database = QFontDatabase()

        cls.app = app
        cls.window = MainWindow("TEST_CLOCK",cls.mem_logger,dao, font_database, call_mode=JsonCallWrapper.DIRECT_MODE) # IN_PROCESS_MODE
        cls.window.show()
    def __init__(self,parent=None):
        super(QtReduceFontComboBox,self).__init__()
        fdb = QFontDatabase()
        l = []
        self.fontDict = {}
        for fam in fdb.families(QFontDatabase.Latin):
            for sty in fdb.styles(fam):
                if not fam in l and fdb.isFixedPitch(fam,sty) \
                and not fdb.bold(fam,sty) and not fdb.italic(fam,sty) \
                and self.__osxHack(fam):
                    fontLogger.debug("family=%s, style=%s, isFixedPitch=%s" %
                                     (fam, sty, fdb.isFixedPitch(fam,sty)))
                    sizes = fdb.smoothSizes(fam,sty)
                    if sizes:
                        font = fdb.font(fam,sty,sizes[0])
                        if not font.exactMatch():
                            fontLogger.debug("no exactMatch for  %s %s %s" %
                                             (fam,sty,sizes[0]))

                        l += [fam]
                        self.fontDict.update({str(fam):font})
        l.sort
        self.addItems(l)
        self.currentIndexChanged.connect(self.currentIndexChangedHandler)
Exemplo n.º 6
0
    def __init__(self, parent=None, style='default', paths=[]):
        from PySide.QtGui import QFontDatabase

        self._ui            = parent                    # parent UI
        self._style         = style                     # style to parse
        self._font_db       = QFontDatabase()           # font database
        self._fonts         = dict()                    # dictionary of valid font types (ui, mono)

        self._config_paths  = ()                        # paths for cfg mods
        self._config_files  = dict()                    # cfg files

        self._qss_paths     = ()                        # qss file paths
        self._qss_files     = dict()                    # qss files
        self._initialized   = False

        # debugging data
        self._data          = dict()

        if not self._initialized:
            self.run(paths=paths)
Exemplo n.º 7
0
 def findSizes(self, font):
     fontDatabase = QFontDatabase()
     currentSize = self.sizeComboBox.currentText()
     with Lib.BlockSignals(self.sizeComboBox):
         self.sizeComboBox.clear()
         if fontDatabase.isSmoothlyScalable(font.family(),
                                            fontDatabase.styleString(font)):
             for size in QFontDatabase.standardSizes():
                 self.sizeComboBox.addItem(str(size))
         else:
             for size in fontDatabase.smoothSizes(
                     font.family(), fontDatabase.styleString(font)):
                 self.sizeComboBox.addItem(str(size))
         self.sizeComboBox.setEditable(False)
     sizeIndex = self.sizeComboBox.findText(currentSize)
     if sizeIndex == -1:
         self.sizeComboBox.setCurrentIndex(
             max(0,
                 self.sizeComboBox.count() / 3))
     else:
         self.sizeComboBox.setCurrentIndex(sizeIndex)
Exemplo n.º 8
0
 def __nextGoodFontSize(self, font, size, step):
     info = QFontInfo(font)
     family = info.family()
     fontDatabase = QFontDatabase()
     styleStr = fontDatabase.styleString(font)
     fontLogger.debug("family=%s, style=%s" % (family, styleStr))
     if fontDatabase.isSmoothlyScalable(family, styleStr):
         sizes = QFontDatabase.standardSizes()
     else:
         sizes = fontDatabase.smoothSizes(family, styleStr)
     fontLogger.debug("looking for %s in %s step %d" % (size, sizes, step))
     nSize = size
     while nSize not in sizes and sizes[0] <= nSize and nSize <= sizes[-1]:
         nSize += step
     if nSize < sizes[0]:
         fontLogger.debug("out of range - returning %s" % sizes[0])
         return sizes[0]
     if sizes[-1] < nSize:
         fontLogger.debug("out of range - returning %s" % sizes[-1])
         return sizes[-1]
     fontLogger.debug("found %s" % nSize)
     return nSize
Exemplo n.º 9
0
class StylesheetManager(object):
    """
    The StylesheetManager reads and parses stylesheet data, plus does some basic sass 
    substitution via external config files.

    :param QtGui.QWidget parent: parent UI.
    :param str style: default style name.
    :param list paths: additional search paths.
    """
    def __init__(self, parent=None, style='default', paths=[]):
        from PySide.QtGui import QFontDatabase

        self._ui = parent  # parent UI
        self._style = style  # style to parse
        self._font_db = QFontDatabase()  # font database
        self._fonts = dict()  # dictionary of valid font types (ui, mono)

        self._config_paths = ()  # paths for cfg mods
        self._config_files = dict()  # cfg files

        self._qss_paths = ()  # qss file paths
        self._qss_files = dict()  # qss files
        self._initialized = False

        # debugging data
        self._data = dict()

        if not self._initialized:
            self.run(paths=paths)

    def run(self, paths=[]):
        """
        Read all of the currently defined config files/stylesheets.

        :param str style: style name to parse.
        :param list paths: additional search paths.
        """
        self._fonts = self.initializeFontsList()

        self._config_paths = self._get_config_paths(paths=paths)
        self._config_files = self._get_config_files(self._config_paths)
        self._qss_paths = self._get_qss_paths(paths=paths)
        self._qss_files = self._get_qss_files(self._qss_paths)

        # set parent defaults if not already set
        defaults = self.font_defaults()
        for default in defaults.keys():
            if hasattr(self._ui, default):
                if getattr(self._ui, default) is None:
                    value = defaults.get(default)
                    #print '# DEBUG: setting UI default; "%s", "%s"' % (default, value)
                    setattr(self._ui, default, value)

        self._initialized = True

    @property
    def style(self):
        return self._style

    def style_data(self, **kwargs):
        """
        Return the stylesheet data.

        :returns: parsed stylesheet data.
        :rtype: str
        """
        stylesheet_name = kwargs.pop('stylesheet_name', 'default')
        palette_style = kwargs.pop('palette_style', 'default')
        font_style = kwargs.pop('font_style', 'default')

        self._data = dict()
        parser = StyleParser(self,
                             style=stylesheet_name,
                             palette_style=palette_style,
                             font_style=font_style)
        parser.run(style=stylesheet_name,
                   palette_style=palette_style,
                   font_style=font_style)
        data = parser.data(**kwargs)

        # grab data here for debugging
        self._data = parser._data
        return data

    @property
    def config_names(self):
        """
        Returns a list of config file names.

        :returns: list of config names.
        :rtype: list
        """
        return self._config_files.keys()

    def config_files(self, style='default'):
        """
        Returns a dictionary of config files for the given style.

        :param str style: style name to return.

        :returns: font/palette config files.
        :rtype: dict
        """
        return self._config_files.get(style, {})

    @property
    def qss_names(self):
        """
        Returns a list of stylesheet file names.

        :returns: list of stylesheet names.
        :rtype: list
        """
        return self._qss_files.keys()

    @property
    def palette_styles(self):
        """
        Returns a list of palette style names.

        :returns: list of palette names.
        :rtype: list
        """
        styles = []
        for style_name, files in self._config_files.iteritems():
            if 'palette' in files:
                value = files.get('palette', None)
                if value is not None:
                    if os.path.exists(value):
                        styles.append(style_name)
        return styles

    @property
    def font_styles(self):
        """
        Returns a list of font style names.

        :returns: list of font style names.
        :rtype: list
        """
        styles = []
        for style_name, files in self._config_files.iteritems():
            if 'fonts' in files:
                value = files.get('fonts', None)
                if value is not None:
                    if os.path.exists(value):
                        styles.append(style_name)
        return styles

    @property
    def qss_files(self):
        return self._qss_files.values()

    def _get_config_paths(self, paths=[]):
        """
        Read configs from config paths.

        :param list paths: list of paths to add to the scan.

        :returns: array of search paths.
        :rtype: tuple
        """
        if paths and type(paths) in [str, unicode]:
            paths = [
                paths,
            ]

        cfg_paths = ()
        cfg_paths = cfg_paths + (options.SCENEGRAPH_CONFIG_PATH, )

        # read external paths
        if 'SCENEGRAPH_CONFIG_PATH' in os.environ:
            spaths = os.getenv('SCENEGRAPH_CONFIG_PATH').split(':')
            if paths:
                for p in paths:
                    if p not in spaths:
                        spaths.append(p)

            for path in spaths:
                if path not in cfg_paths:
                    if not os.path.exists(path):
                        log.warning(
                            'config path "%s" does not exist, skipping.' %
                            path)
                        continue
                    log.debug('reading config external path: "%s".' % path)
                    cfg_paths = cfg_paths + (path, )

        return cfg_paths

    def _get_qss_paths(self, paths=[]):
        """
        Read stylesheets from config paths.

        :param list paths: list of paths to add to the scan.

        :returns: array of search paths.
        :rtype: tuple
        """
        if paths and type(paths) in [str, unicode]:
            paths = [
                paths,
            ]

        qss_paths = ()
        qss_paths = qss_paths + (options.SCENEGRAPH_STYLESHEET_PATH, )

        # read external paths
        if 'SCENEGRAPH_STYLESHEET_PATH' in os.environ:
            qpaths = os.getenv('SCENEGRAPH_STYLESHEET_PATH').split(':')
            if paths:
                for p in paths:
                    if p not in qpaths:
                        qpaths.append(p)

            for path in qpaths:
                if path not in qss_paths:
                    if not os.path.exists(path):
                        log.warning(
                            'stylesheet path "%s" does not exist, skipping.' %
                            path)
                        continue
                    log.debug('reading external stylesheet path: "%s".' % path)
                    qss_paths = qss_paths + (path, )

        return qss_paths

    def _get_config_files(self, paths=[]):
        """
        Get config files.

        :param list path: ist of paths to add to the scan.

        :returns: dictionary of config names/filenames.
        :rtype: dict
        """
        cfg_files = dict()
        if not paths:
            return []

        for path in paths:
            for fn in os.listdir(path):
                bn, fext = os.path.splitext(fn)
                if fext.lower() in ['.ini', '.cfg']:
                    cfg_file = os.path.join(path, fn)

                    names = bn.split('-')
                    if len(names) < 2:
                        log.warning('improperly named config file: "%s"' %
                                    cfg_file)
                        continue

                    style_name, cfg_type = names
                    if style_name not in cfg_files:
                        cfg_files[style_name] = dict(fonts=None, palette=None)

                    log.debug('adding %s config "%s" from "%s".' %
                              (cfg_type, style_name, cfg_file))
                    cfg_files[style_name][cfg_type] = cfg_file
        return cfg_files

    def _get_qss_files(self, paths=[]):
        """
        Get qss files.

        :param list path: ist of paths to add to the scan.

        :returns: dictionary of stylesheet names/filenames.
        :rtype: dict
        """
        qss_files = dict()
        if not paths:
            return []

        for path in paths:
            for fn in os.listdir(path):
                bn, fext = os.path.splitext(fn)
                if fext.lower() in ['.qss', '.css']:
                    qss_file = os.path.join(path, fn)
                    if qss_file not in qss_files.values():
                        style_name = self._parse_stylesheet_name(qss_file)
                        if style_name is None:
                            log.warning('cannot parse style name from "%s".' %
                                        qss_file)
                            style_name = 'no-style'

                        log.debug('adding stylesheet "%s" from "%s".' %
                                  (style_name, qss_file))

                        if style_name not in qss_files:
                            qss_files[style_name] = qss_file
        return qss_files

    def _parse_stylesheet_name(self, filename):
        """
        Parse the stylesheet name from a file.

        :param str: filename to read.

        :returns: style name.
        :rtype: str
        """
        style_name = None
        if os.path.exists(filename):
            for line in open(filename, 'r'):
                line = line.rstrip('\n')
                rline = line.lstrip(' ')
                rline = rline.rstrip()
                smatch = re.search(regex.get('style_name'), rline)
                if smatch:
                    style_name = smatch.group('style')
                    break
        return style_name

    def add_config(self, filename, name=None):
        """
        Add a config to the config files attribute.

        :param str filename: filename to read.
        :param str name: name of the config.
        """
        if filename in self._config_files.values():
            for cfg_name, cfg_file in self._config_files.iteritems():
                if cfg_file == filename:
                    if name != cfg_name:
                        self._config_files.pop(cfg_name)
        self._config_files[name] = filename

    #- Fonts -----
    def initializeFontsList(self, valid=[]):
        """
        Builds the manager fonts list.

        :param list valid: list of valid font names.

        :returns: dictionary of fonts.
        :rtype: dict
        """
        if not valid:
            valid = [
                x for fontlist in options.SCENEGRAPH_VALID_FONTS.values()
                for x in fontlist
            ]

        result = dict(ui=[], mono=[])
        for font_name in self._font_db.families():
            if font_name in valid:
                if not self._font_db.isFixedPitch(font_name):
                    result['ui'].append(font_name)
                else:
                    result['mono'].append(font_name)
        return result

    def buildUIFontList(self, valid=[]):
        """
        Returns a list of monospace fonts.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('ui')

        families = []
        for font_name in self._fonts.get('ui'):
            if font_name in valid:
                families.append(font_name)
        return families

    def buildMonospaceFontList(self, valid=[]):
        """
        Returns a list of monospace fonts.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('mono')

        families = []
        for font_name in self._fonts.get('mono'):
            if font_name in valid:
                families.append(font_name)
        return families

    def buildNodesFontList(self, valid=[]):
        """
        Returns a list of fonts for node display.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('nodes')

        families = []
        all_fonts = [x for fontlist in self._fonts.values() for x in fontlist]
        for font_name in all_fonts:
            if font_name in valid:
                families.append(font_name)
        return families

    def font_defaults(self, platform=None, style='default'):
        """
        Builds a dictionary of font & size defaults by platform.

        :param str platform: os type

        :returns: font and font size defaults dictionary.
        :rtype: dict
        """
        if platform is None:
            platform = options.PLATFORM

        defaults = dict()

        def_font_config = self.config_files(style).get('fonts', None)
        if not os.path.exists(def_font_config):
            log.error('config "%s" does not exist.' % def_font_config)
            return defaults

        parser = StyleParser(self)
        data = parser._parse_configs(def_font_config)
        data = parser._parse_platform_data(data)

        # substitute attribute names
        for attr, val in data.iteritems():
            attr = re.sub('-', '_', attr)
            defaults[attr] = val
        return defaults
Exemplo n.º 10
0
from PySide.QtCore import Qt, QCoreApplication
from PySide.QtGui import QPixmap, QFont, QFontDatabase, QApplication, QSplashScreen

#create application and set properties

if __name__ == '__main__':
    #QCoreApplication.setAttribute(Qt.AA_ShareOpenGLContexts)
    #QCoreApplication.setAttribute(Qt.AA_EnableHighDpiScaling)

    app = QApplication(sys.argv)
    app.setOrganizationName('Bioinformatics and Integrative Genomics')
    app.setOrganizationDomain('http://big.cdu.edu.cn')
    app.setApplicationName('Krait')

    #set font family
    QFontDatabase.addApplicationFont(":/fonts/roboto.ttf")

    #support windows 7, 10 taskbar icon
    import ctypes
    if os.name == 'nt':
        myappid = 'BIG.Krait.ssr.1.0'
        ctypes.windll.shell32.SetCurrentProcessExplicitAppUserModelID(myappid)

    splash_img = QPixmap(":/icons/splash.png")
    splash = QSplashScreen(splash_img)
    splash.setWindowFlags(Qt.WindowStaysOnTopHint | Qt.SplashScreen
                          | Qt.FramelessWindowHint)
    splash.setStyleSheet("font-family:roboto; font-size: 14px;")
    splash.setEnabled(False)
    splash.show()
Exemplo n.º 11
0
#*   as published by the Free Software Foundation; either version 2 of     *
#*   the License, or (at your option) any later version.                   *
#*   for detail see the LICENCE text file.                                 *
#*                                                                         *
#*   FreeCAD 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 Lesser General Public License for more details.                   *
#*                                                                         *
#*   You should have received a copy of the GNU General Public License     *
#*   along with Dimensioning FreeCAD Workbench.                            *
#*   If not, see <https://www.gnu.org/licenses/>                           *
#*                                                                         *
#***************************************************************************/


import FreeCADGui, FreeCAD
import Dimensioning_rc #create resources
import Page
import Orthographic
import Annotation
import Image
import Test

from PySide.QtGui import QFontDatabase

# load default font
QFontDatabase.addApplicationFont(":/fonts/ISO_3098.ttf")
QFontDatabase.addApplicationFont(":/fonts/ISO_3098Italic.ttf")

Exemplo n.º 12
0
class StylesheetManager(object):
    """
    The StylesheetManager reads and parses stylesheet data, plus does some basic sass 
    substitution via external config files.

    :param QtGui.QWidget parent: parent UI.
    :param str style: default style name.
    :param list paths: additional search paths.
    """
    def __init__(self, parent=None, style='default', paths=[]):
        from PySide.QtGui import QFontDatabase

        self._ui            = parent                    # parent UI
        self._style         = style                     # style to parse
        self._font_db       = QFontDatabase()           # font database
        self._fonts         = dict()                    # dictionary of valid font types (ui, mono)

        self._config_paths  = ()                        # paths for cfg mods
        self._config_files  = dict()                    # cfg files

        self._qss_paths     = ()                        # qss file paths
        self._qss_files     = dict()                    # qss files
        self._initialized   = False

        # debugging data
        self._data          = dict()

        if not self._initialized:
            self.run(paths=paths)

    def run(self, paths=[]):
        """
        Read all of the currently defined config files/stylesheets.

        :param str style: style name to parse.
        :param list paths: additional search paths.
        """
        self._fonts = self.initializeFontsList()

        self._config_paths = self._get_config_paths(paths=paths)
        self._config_files = self._get_config_files(self._config_paths)
        self._qss_paths = self._get_qss_paths(paths=paths)
        self._qss_files = self._get_qss_files(self._qss_paths)

        # set parent defaults if not already set
        defaults = self.font_defaults()
        for default in defaults.keys():
            if hasattr(self._ui, default):
                if getattr(self._ui, default) is None:
                    value = defaults.get(default)
                    #print '# DEBUG: setting UI default; "%s", "%s"' % (default, value)
                    setattr(self._ui, default, value)

        self._initialized = True

    @property
    def style(self):
        return self._style

    def style_data(self, **kwargs):
        """
        Return the stylesheet data.

        :returns: parsed stylesheet data.
        :rtype: str
        """
        stylesheet_name = kwargs.pop('stylesheet_name', 'default')
        palette_style = kwargs.pop('palette_style', 'default')
        font_style = kwargs.pop('font_style', 'default')
        
        self._data = dict()
        parser = StyleParser(self, style=stylesheet_name, palette_style=palette_style, font_style=font_style)
        parser.run(style=stylesheet_name, palette_style=palette_style, font_style=font_style)
        data = parser.data(**kwargs)

        # grab data here for debugging
        self._data = parser._data
        return data

    @property
    def config_names(self):
        """
        Returns a list of config file names.

        :returns: list of config names.
        :rtype: list
        """
        return self._config_files.keys()    

    def config_files(self, style='default'):
        """
        Returns a dictionary of config files for the given style.

        :param str style: style name to return.

        :returns: font/palette config files.
        :rtype: dict
        """
        return self._config_files.get(style, {})

    @property
    def qss_names(self):
        """
        Returns a list of stylesheet file names.

        :returns: list of stylesheet names.
        :rtype: list
        """
        return self._qss_files.keys()    

    @property
    def palette_styles(self):
        """
        Returns a list of palette style names.

        :returns: list of palette names.
        :rtype: list
        """
        styles = []
        for style_name, files in self._config_files.iteritems():
            if 'palette' in files:
                value = files.get('palette', None)
                if value is not None:
                    if os.path.exists(value):
                        styles.append(style_name)
        return styles

    @property
    def font_styles(self):
        """
        Returns a list of font style names.

        :returns: list of font style names.
        :rtype: list
        """
        styles = []
        for style_name, files in self._config_files.iteritems():
            if 'fonts' in files:
                value = files.get('fonts', None)
                if value is not None:
                    if os.path.exists(value):
                        styles.append(style_name)
        return styles

    @property
    def qss_files(self):
        return self._qss_files.values() 

    def _get_config_paths(self, paths=[]):
        """
        Read configs from config paths.

        :param list paths: list of paths to add to the scan.

        :returns: array of search paths.
        :rtype: tuple
        """
        if paths and type(paths) in [str, unicode]:
            paths = [paths,]

        cfg_paths = ()
        cfg_paths = cfg_paths + (options.SCENEGRAPH_CONFIG_PATH,)

        # read external paths
        if 'SCENEGRAPH_CONFIG_PATH' in os.environ:
            spaths = os.getenv('SCENEGRAPH_CONFIG_PATH').split(':')
            if paths:
                for p in paths:
                    if p not in spaths:
                        spaths.append(p)

            for path in spaths:
                if path not in cfg_paths:
                    if not os.path.exists(path):
                        log.warning('config path "%s" does not exist, skipping.' % path)
                        continue
                    log.debug('reading config external path: "%s".' % path)
                    cfg_paths = cfg_paths + (path,)

        return cfg_paths

    def _get_qss_paths(self, paths=[]):
        """
        Read stylesheets from config paths.

        :param list paths: list of paths to add to the scan.

        :returns: array of search paths.
        :rtype: tuple
        """
        if paths and type(paths) in [str, unicode]:
            paths = [paths,]

        qss_paths = ()
        qss_paths = qss_paths + (options.SCENEGRAPH_STYLESHEET_PATH,)

        # read external paths
        if 'SCENEGRAPH_STYLESHEET_PATH' in os.environ:
            qpaths = os.getenv('SCENEGRAPH_STYLESHEET_PATH').split(':')
            if paths:
                for p in paths:
                    if p not in qpaths:
                        qpaths.append(p)

            for path in qpaths:
                if path not in qss_paths:
                    if not os.path.exists(path):
                        log.warning('stylesheet path "%s" does not exist, skipping.' % path)
                        continue
                    log.debug('reading external stylesheet path: "%s".' % path)
                    qss_paths = qss_paths + (path,)

        return qss_paths

    def _get_config_files(self, paths=[]):
        """
        Get config files.

        :param list path: ist of paths to add to the scan.

        :returns: dictionary of config names/filenames.
        :rtype: dict
        """
        cfg_files = dict()
        if not paths:
            return []

        for path in paths:
            for fn in os.listdir(path):
                bn, fext = os.path.splitext(fn)
                if fext.lower() in ['.ini', '.cfg']:
                    cfg_file = os.path.join(path, fn)

                    names = bn.split('-')
                    if len(names) < 2:
                        log.warning('improperly named config file: "%s"' % cfg_file)
                        continue

                    style_name, cfg_type = names
                    if style_name not in cfg_files:
                        cfg_files[style_name] = dict(fonts=None, palette=None)

                    log.debug('adding %s config "%s" from "%s".' % (cfg_type, style_name, cfg_file))
                    cfg_files[style_name][cfg_type] = cfg_file
        return cfg_files

    def _get_qss_files(self, paths=[]):
        """
        Get qss files.

        :param list path: ist of paths to add to the scan.

        :returns: dictionary of stylesheet names/filenames.
        :rtype: dict
        """
        qss_files = dict()
        if not paths:
            return []

        for path in paths:
            for fn in os.listdir(path):
                bn, fext = os.path.splitext(fn)
                if fext.lower() in ['.qss', '.css']:
                    qss_file = os.path.join(path, fn)
                    if qss_file not in qss_files.values():
                        style_name = self._parse_stylesheet_name(qss_file)
                        if style_name is None:
                            log.warning('cannot parse style name from "%s".' % qss_file)
                            style_name = 'no-style'

                        log.debug('adding stylesheet "%s" from "%s".' % (style_name, qss_file))

                        if style_name not in qss_files:
                            qss_files[style_name] = qss_file
        return qss_files

    def _parse_stylesheet_name(self, filename):
        """
        Parse the stylesheet name from a file.

        :param str: filename to read.

        :returns: style name.
        :rtype: str
        """
        style_name = None
        if os.path.exists(filename):
            for line in open(filename,'r'):
                line = line.rstrip('\n')
                rline = line.lstrip(' ')
                rline = rline.rstrip()
                smatch = re.search(regex.get('style_name'), rline)
                if smatch:
                    style_name = smatch.group('style')
                    break
        return style_name

    def add_config(self, filename, name=None):
        """
        Add a config to the config files attribute.

        :param str filename: filename to read.
        :param str name: name of the config.
        """
        if filename in self._config_files.values():
            for cfg_name, cfg_file in self._config_files.iteritems():
                if cfg_file == filename:
                    if name != cfg_name:
                        self._config_files.pop(cfg_name)
        self._config_files[name] = filename

    #- Fonts -----
    def initializeFontsList(self, valid=[]):
        """
        Builds the manager fonts list.

        :param list valid: list of valid font names.

        :returns: dictionary of fonts.
        :rtype: dict
        """
        if not valid:
            valid = [x for fontlist in options.SCENEGRAPH_VALID_FONTS.values() for x in fontlist]

        result = dict(ui=[], mono=[])
        for font_name in self._font_db.families():
            if font_name in valid:
                if not self._font_db.isFixedPitch(font_name):                
                    result['ui'].append(font_name)
                else:
                    result['mono'].append(font_name)
        return result

    def buildUIFontList(self, valid=[]):
        """
        Returns a list of monospace fonts.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('ui')

        families = []
        for font_name in self._fonts.get('ui'):
            if font_name in valid:
                families.append(font_name)
        return families

    def buildMonospaceFontList(self, valid=[]):
        """
        Returns a list of monospace fonts.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('mono')

        families = []
        for font_name in self._fonts.get('mono'):
            if font_name in valid:
                families.append(font_name)
        return families

    def buildNodesFontList(self, valid=[]):
        """
        Returns a list of fonts for node display.
        """
        if not valid:
            valid = options.SCENEGRAPH_VALID_FONTS.get('nodes')

        families = []
        all_fonts = [x for fontlist in self._fonts.values() for x in fontlist]
        for font_name in all_fonts:
            if font_name in valid:
                families.append(font_name)
        return families

    def font_defaults(self, platform=None, style='default'):
        """
        Builds a dictionary of font & size defaults by platform.

        :param str platform: os type

        :returns: font and font size defaults dictionary.
        :rtype: dict
        """
        if platform is None:
            platform = options.PLATFORM

        defaults = dict()

        def_font_config = self.config_files(style).get('fonts', None)
        if not os.path.exists(def_font_config):
            log.error('config "%s" does not exist.' % def_font_config)
            return defaults

        parser = StyleParser(self)
        data = parser._parse_configs(def_font_config)
        data = parser._parse_platform_data(data)

        # substitute attribute names
        for attr, val in data.iteritems():
            attr = re.sub('-', '_', attr)
            defaults[attr] = val
        return defaults
Exemplo n.º 13
0
def main():
    """
  @return  int
  """
    import os, sys
    from PySide.QtCore import QTextCodec
    # Use UTF-8 encoding for Qt
    #sys_codec = QTextCodec.codecForLocale()
    u8codec = QTextCodec.codecForName("UTF-8")
    QTextCodec.setCodecForCStrings(u8codec)
    QTextCodec.setCodecForTr(u8codec)

    debug = '--debug' in sys.argv  # bool
    print >> sys.stderr, "reader: debug = %s" % debug

    from sakurakit import skdebug
    #skdebug.DEBUG = config.APP_DEBUG or '--debug' in sys.argv
    skdebug.DEBUG = debug

    import config
    config.APP_DEBUG = debug

    from sakurakit.skdebug import dprint, dwarn
    dprint("enter")

    if '--help' in sys.argv:
        print_help()
        dprint("exit: help")
        #sys.exit(os.EX_USAGE)
        return 0

    # Singleton
    # - Through mutex
    #   See: http://code.activestate.com/recipes/474070-creating-a-single-instance-application/
    #   See: http://code.google.com/p/python-windows-tiler/source/browse/singleinstance.py
    # - Through file
    #   See: http://stackoverflow.com/questions/380870/python-single-instance-of-program
    dprint("check single instance")

    from lockfile import lockfile

    app_mutex = lockfile.SingleProcessMutex()
    single_app = app_mutex.tryLock()
    if not single_app:
        dprint("multiple instances are running")

    dprint("python = %s" % sys.executable)
    #dprint("rootdir = %s" % rootdir)
    #dprint("mecabrc = %s" % mecabrc_path)

    from sakurakit import skos
    # Must be set before any GUI is showing up
    # http://stackoverflow.com/questions/1551605/how-to-set-applications-taskbar-icon-in-windows-7
    if skos.WIN:
        dprint("set app id")
        from sakurakit import skwin
        skwin.set_app_id("org.sakurakit.reader")

    # Detect user language
    import settings

    ss = settings.global_()

    uilang = ss.uiLanguage()
    if not uilang:
        uilang = guess_language()
        ss.setValue('Language', uilang)

    lang = ss.userLanguage()
    if not lang:
        lang = guess_language()
        ss.setValue('UserLanguage', lang)

    dprint("user language = %s" % lang)

    # Warm-up shiboken dlls
    #if os.name == 'nt':
    #  dprint("load shiboken plugins")
    #  import pytexscript
    #  import pytexthook

    #Switch to OpenGL engine
    #from Qt5.QtWidgets import QApplication
    #QApplication.setGraphicsSystem("opengl")

    #dprint("elevate process priviledges")
    #from sakurakit import skos
    #if skos.WIN:
    #  from sakurakit import skwin
    #  skwin.enable_drop_event()

    dprint("init dic locations")
    from opencc import opencc
    opencc.setdicpaths(config.OPENCC_DICS)

    from hanviet import hanviet
    hanviet.setdicpaths(config.HANVIET_DICS)

    from hanjaconv import hanjaconv
    hanjaconv.setdicdir(config.HANJA_DIC_PATH)

    from pinyinconv import pinyinconv
    pinyinconv.setdicpath(config.PINYIN_DIC_PATH)

    dprint("create app")
    import app
    a = app.Application(sys.argv)

    #dprint("os default font:", a.font())
    #a.setFont(config.FONT_DEFAULT)
    #dprint("current default font:", a.font())

    # Fix the encoding issue for the current directory
    #from PySide.QtCore import QDir
    #QDir.setCurrent(a.applicationDirPath())

    if not single_app:
        from rpcman import RpcClient
        dprint("send metacall")
        r = RpcClient()
        r.start()
        if r.waitForConnected():
            r.activate()
            a.processEvents()
        else:
            dprint("warning: cannot connect to the server")
        dwarn("leave: multiple instance")
        #sys.exit(os.EX_UNAVAILABLE)
        return 0

    # Must come after QApplication is created
    dprint("load fonts")
    from PySide.QtGui import QFontDatabase
    for path in config.FONT_LOCATIONS.itervalues():
        if os.path.exists(path):
            for root, dirs, files in os.walk(path):
                FONT_EXTS = frozenset(('.otf', '.ttf', '.ttc'))
                for f in files:
                    if os.path.splitext(f.lower())[1] in FONT_EXTS:
                        p = os.path.join(root, f)
                        index = QFontDatabase.addApplicationFont(p)
                        if index >= 0:
                            dprint(
                                QFontDatabase.applicationFontFamilies(index))
                        else:
                            dwarn("failed to load font %s" % f)

    ff = config.ui_font(ss.uiLanguage())
    if ff:
        a.setFontFamily(ff)

    #ff = ss.applicationFontFamily()
    #if ff:
    #  dprint("font family = %s" % ff)
    #  a.setFontFamily(ff)
    #ss.applicationFontFamilyChanged.connect(a.setFontFamily)

    dprint("load translation")
    a.loadTranslations()

    dprint("autosync settings")
    ss.autoSync()  # Load before qapplication is created

    opt_splash = '--nosplash' not in sys.argv

    if opt_splash:
        dprint("show splash")
        from splashscreen import StartupSplashScreen
        splash = StartupSplashScreen()
        splash.show()

    a.processEvents()  # process event to make it show

    #dprint("cache fonts")
    #import fonts
    #fonts.test()

    # Take the ownership of sakurakit translation
    dprint("take the ownership of translations")
    from sakurakit import sktr
    sktr.manager().setParent(a)

    import mytr
    mytr.manager().setParent(a)
    mytr.my.setParent(a)

    # There should be at least one existing window (rootWindow), or sth is wrong
    #a.setQuitOnLastWindowClosed(False)

    #dprint("check unicode codec")
    #from sakurakit.skunicode import qunicode
    #ustr = qunicode("あのね", 'utf8')
    #assert ustr, "failed to load text code plugin from qt.conf"

    #dprint('init directories')
    #from PySide.QtCore import QDir

    import rc
    from sakurakit import skfileio
    dprint("remove broken caches")
    for it in rc.DIR_APP_TMP, :
        if os.path.exists(it):
            skfileio.removetree(it)

    map(
        skfileio.makedirs,
        (
            rc.DIR_YAML_SUB,
            rc.DIR_XML_COMMENT,
            rc.DIR_XML_VOICE,
            rc.DIR_XML_REF,
            #rc.DIR_DICT_MECAB, # not used
            rc.DIR_CACHE_AVATAR,
            rc.DIR_CACHE_AWS,
            rc.DIR_CACHE_DATA,
            rc.DIR_CACHE_IMAGE,
            rc.DIR_CACHE_DMM,
            rc.DIR_CACHE_TOKUTEN,
            rc.DIR_CACHE_FREEM,
            rc.DIR_CACHE_STEAM,
            rc.DIR_CACHE_MELON,
            rc.DIR_CACHE_GETCHU,
            rc.DIR_CACHE_GYUTTO,
            rc.DIR_CACHE_DIGIKET,
            rc.DIR_CACHE_DLSITE,
            rc.DIR_CACHE_HOLYSEAL,
            rc.DIR_CACHE_SCAPE,
            rc.DIR_CACHE_TRAILERS,
            rc.DIR_CACHE_WEB,
            rc.DIR_CACHE_SYNC,
            rc.DIR_TMP_OCR,
            rc.DIR_TMP_TERM,  # not needed, though
            rc.DIR_TMP_TTS,
        ))

    if skos.WIN:
        from sakurakit import skwin
        for it in rc.DIR_APP_LIBRARY, rc.DIR_APP_CACHE:
            if os.path.exists(it):
                skwin.set_file_readonly(it)

    dprint("load settings")
    ss.setParent(a)

    dprint("append library path")

    from sakurakit import skpaths
    skpaths.append_paths((
        # TransCAT must be initialized BEFORE JBeijing, or the translation will fail
        ss.transcatLocation(),
        ss.jbeijingLocation(),
        ss.ezTransLocation(),
        ss.atlasLocation(),
        ss.zunkoLocation(),
        ss.localeEmulatorLocation(),
        ss.ntleasLocation(),
        os.path.join(ss.dreyeLocation(), r"DreyeMT\SDK\bin")
        if ss.dreyeLocation() else "",
    ))

    path = ss.lecLocation()
    if path:
        skpaths.append_paths((
            os.path.join(path, r"Nova\JaEn"),
            os.path.join(path, r"PARS\EnRU"),
        ))

    path = ss.fastaitLocation()
    if path:
        path = os.path.join(path, 'GTS')
        if os.path.exists(path):
            dllpaths = skfileio.listdirs(path)
            if dllpaths:
                skpaths.append_paths(dllpaths)

    if sys.getrecursionlimit() < config.PY_RECURSION_LIMIT:
        dprint("increase recursion limit")
        sys.setrecursionlimit(config.PY_RECURSION_LIMIT)

    dprint("reduce socket timeout")
    import socket
    socket.setdefaulttimeout(config.PY_SOCKET_TIMEOUT)

    #import threading
    #if threading.stack_size() < config.PY_STACK_SIZE:
    #  dprint("increase stack size")
    #  threading.stack_size(config.PY_STACK_SIZE)

    # On unix:
    # stackoverflow.com/questions/5061582/setting-stacksize-in-a-python-script
    #import resource
    #resource.setrlimit(resource.RLIMIT_STACK, (2**29,-1))

    dprint("config python site-packages")

    # Disable requests SSL certificate warning
    # https://github.com/kennethreitz/requests/issues/2214
    import requests
    requests.packages.urllib3.disable_warnings()

    # Disable HTTP request session
    # See: http://docs.python-requests.org/en/latest/user/advanced/#keep-alive
    # See: http://stackoverflow.com/questions/10115126/python-requests-close-http-connection
    #import requests
    #s = requests.session()
    #s.config['keep_alive'] = False

    import numpy
    numpy.seterr(all='ignore')  # ignore overflow warning

    dprint("update settings")

    ss_version = ss.version()
    if ss_version != config.VERSION_TIMESTAMP:
        dprint("app update detected, migrate settings")
        if ss_version:
            migrate(ss_version)

        from sakurakit import skdatetime
        ss.setUpdateTime(skdatetime.current_unixtime())

        ss.setVersion(config.VERSION_TIMESTAMP)
        ss.sync()

    if not ss.userName() or not ss.userId():
        dprint("set user credential to guest")
        # Must be consistent with dataman.GUEST
        ss.setValue('UserId', 4)
        ss.setValue('UserName', 'guest')
        ss.setValue('UserPassword', 'guest')
        ss.setValue('UserGender', '')
        ss.setValue('UserAvatar', '')
        ss.setValue('UserColor', '')

    if ss.isCursorThemeEnabled():
        dprint("load cursor theme")
        import curtheme
        curtheme.load()

    # Disable RBMT if CaboCha or UniDic is disabled
    #if ss.isTranslationSyntaxEnabled() and not (
    #    ss.isCaboChaEnabled() and ss.meCabDictionary() == 'unidic'):
    #  ss.setTranslationSyntaxEnabled(False)

    #dprint("set max thread count")
    from PySide.QtCore import QThreadPool
    currentThreadCount = QThreadPool.globalInstance().maxThreadCount()
    if currentThreadCount < config.QT_THREAD_COUNT:
        dprint("increase thread pool capacity: %s -> %s" %
               (currentThreadCount, config.QT_THREAD_COUNT))
        QThreadPool.globalInstance().setMaxThreadCount(config.QT_THREAD_COUNT)

    dprint("register qml plugins")
    import qmlplugin

    dprint("query system metrics")
    import sysinfo

    dprint("create main object")

    import main
    m = main.MainObject(a)
    m.init()

    if opt_splash:
        dprint("schedule to finish splash")
        splash.finishLater(1500)  # hide after 1.5 seconds

    from functools import partial
    from sakurakit import skevents
    skevents.runlater(partial(m.run, a.arguments()), 50)
    #m.run(a.arguments())

    #import netman
    #netman.manager().queryComments(gameId=183)

    #import hashutil
    #print hashutil.md5sum('/Users/jichi/tmp/t.cpp')

    dprint("exec")
    returnCode = a.exec_()

    # FIXME: Cannot normally exit
    # Shiboken 1.2 hang on exit!
    # All destructors are Invoked!

    dprint("unlock the mutex")
    app_mutex.unlock()

    import defs
    if returnCode == defs.EXIT_RESTART:
        skos.restart_my_process(['-B'])  # -B: force disabling *.pyc and *.pyo
    else:
        #sys.exit(returnCode)
        #if skos.WIN: # prevent hanging on windows/mac
        skos.kill_my_process()