Exemple #1
0
 def removetree(self):  # -> bool # utility
     return skfileio.removetree(self.path)
Exemple #2
0
def main():
    # Use UTF-8 encoding for Qt
    from PySide.QtCore import QTextCodec
    #sys_codec = QTextCodec.codecForLocale()
    u8codec = QTextCodec.codecForName("UTF-8")
    QTextCodec.setCodecForCStrings(u8codec)
    QTextCodec.setCodecForTr(u8codec)

    import config
    from sakurakit import skdebug
    #skdebug.DEBUG = config.APP_DEBUG or '--debug' in sys.argv
    skdebug.DEBUG = '--debug' in sys.argv
    print "browser: debug = %s" % skdebug.DEBUG

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

    if '--help' in sys.argv:
        print_help()
        dprint("leave: help")
        return

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

    from sakurakit import skos
    if skos.WIN:
        dprint("set app id")
        from sakurakit import skwin
        skwin.set_app_id("org.sakurakit.browser")

    import rc
    for it in (
            rc.DIR_CACHE_DATA,
            rc.DIR_CACHE_HISTORY,
            rc.DIR_CACHE_NETMAN,
            rc.DIR_CACHE_WEBKIT,
    ):
        if not os.path.exists(it):
            try:
                os.makedirs(it)
            except OSError:
                dwarn("warning: failed to create directory: %s" % it)

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

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

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

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

    dprint("load settings")
    import settings
    ss = settings.global_()
    ss.setParent(a)

    reader = settings.reader()
    #reader.setParent(a) # reader does NOT have a app parent

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

        if ss_version:
            from sakurakit import skfileio

            if ss_version <= 1417339268:
                for it in (
                        #rc.DIR_CACHE_DATA,
                        rc.DIR_CACHE_HISTORY,
                        rc.DIR_CACHE_NETMAN,
                        rc.DIR_CACHE_WEBKIT,
                ):
                    if os.path.exists(it):
                        skfileio.removetree(it)
                        try:
                            os.makedirs(it)
                        except OSError:
                            dwarn("warning: failed to create directory: %s" %
                                  it)

            if ss_version <= 1396371158:
                skfileio.removefile(rc.COOKIES_LOCATION)

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

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

    from sakurakit import skpaths
    skpaths.append_paths((
        #reader.localeEmulatorLocation(),
        reader.jbeijingLocation(),
        reader.ezTransLocation(),
        reader.atlasLocation(),
        os.path.join(reader.lecLocation(), r"Nova\JaEn")
        if reader.lecLocation() else "",
        os.path.join(reader.dreyeLocation(), r"DreyeMT\SDK\bin")
        if reader.dreyeLocation() else "",
    ))

    path = reader.fastaitLocation()
    if path:
        path = os.path.join(path, "GTS")
        if os.path.exists(path):
            from sakurakit import skfileio
            dllpaths = skfileio.listdirs(path)
            if dllpaths:
                skpaths.append_paths(dllpaths)

    dprint("set max thread count")
    from PySide.QtCore import QThreadPool
    if QThreadPool.globalInstance().maxThreadCount() < config.QT_THREAD_COUNT:
        QThreadPool.globalInstance().setMaxThreadCount(config.QT_THREAD_COUNT)

    dprint("load web settings")
    import webrc
    webrc.update_web_settings()

    if reader.isMainlandChina():
        dprint("set up proxy")
        from google import googletts
        googletts.setapi(config.PROXY_GOOGLE_TTS)
        import googleman
        googleman.setapi(config.PROXY_GOOGLE_TRANS)

    dprint("create main object")
    import main
    m = main.MainObject()
    m.run(a.arguments())

    dprint("exec")
    sys.exit(a.exec_())
Exemple #3
0
 def remove(self):  # override
     from sakurakit import skfileio
     return skfileio.removetree(os.path.dirname(self.path))
Exemple #4
0
def migrate(ss_version):  # long ->
    import os
    from glob import glob
    from sakurakit import skfileio
    from sakurakit.skdebug import dprint, dwarn
    import config, rc, settings

    dprint("enter")

    ss = settings.global_()

    try:  # this try is in case I forgot certain rc directories for update
        if ss_version <= 1440815402:  # This is not really needed though
            for it in (  # delete all existing references
                    rc.DIR_CACHE_AWS,
                    rc.DIR_CACHE_DMM,
                    rc.DIR_CACHE_GETCHU,
                    rc.DIR_CACHE_GYUTTO,
                    rc.DIR_CACHE_DIGIKET,
                    rc.DIR_CACHE_DLSITE,
                    rc.DIR_CACHE_HOLYSEAL,
                    rc.DIR_CACHE_TRAILERS,
                    rc.DIR_CACHE_SCAPE,
            ):
                if os.path.exists(it):
                    skfileio.removetree(it)
                    skfileio.makedirs(it)
        else:
            return

        if ss_version <= 1436681107:  # reset embed name option
            ss.remove('EmbeddedNameText')
            ss.remove('EmbeddedNameVisible')
            ss.remove('EmbeddedNameTranslation')
            ss.remove('EmbeddedNameTranscoding')
            ss.remove('EmbeddedScenarioTranscoding')
            ss.remove('EmbeddedOtherTranscoding')
        else:
            return
        if ss_version <= 1435945343:
            ss.remove('EmbeddedScenarioText')  # reset scenario text visibility
            ss.remove('WindowTranscoding')  # disable transcoding by default
            ss.remove(
                'EmbeddedOtherText')  # enable charset detection by default
        else:
            return
        if ss_version <= 1434217165:
            dst = rc.xml_path('terms')
            if dst and not os.path.exists(dst):
                src = rc.DIR_USER_XML + '/terms.xml'
                if os.path.exists(src):
                    try:
                        os.rename(src, dst)
                    except Exception, e:
                        dwarn(e)

        if ss_version <= 1432306894:
            ss.remove('GameAgentConvertsKanji')  # use default settings
        else:
            return

        if ss_version <= 1432219874:
            ss.remove('KoreanFont')  # use default korean font
        else:
            return

        if ss_version <= 1430531862:
            s = ss.value('BlockedLanguages')
            if isinstance(s, set):
                ss.setValue('BlockedLanguages', ','.join(s))
            elif not isinstance(s, basestring):
                ss.setValue('BlockedLanguages', '')
        else:
            return

        if ss_version > 1428623451 and ss_version <= 1429000689:  # re-align EDICT with UniDic
            path = rc.MECAB_EDICT_PATH
            if os.path.exists(path):
                skfileio.removefile(path)
                if os.path.exists(rc.EDICT_PATH) and os.path.exists(
                        rc.DIR_UNIDIC):
                    from scripts import edict
                    edict.align()
                else:
                    ss.setValue('EdictEnabled', False)
        else:
            return

        if ss_version and ss_version <= 1428623451:  # reset edict
            ss.setValue('EdictEnabled', False)
            path = rc.EDICT_PATH
            if os.path.exists(path):
                skfileio.removefile(path)
        else:
            return

        if ss_version <= 1428015070:  # clear old terms by default
            xmlfile = rc.xml_path('terms')
            if xmlfile and os.path.exists(xmlfile):
                skfileio.removefile(xmlfile)
        else:
            return

        if ss_version <= 1423687966:  # reset retranslator
            ss.setValue('Retranslator', '')
        else:
            return

        if ss_version <= 1422396934:
            ss.setValue('RubyText', True)
        else:
            return

        if ss_version <= 1419101101:
            xmlfile = rc.xml_path('terms')
            skfileio.removefile(xmlfile)
        else:
            return

        if ss_version <= 1418719123:
            path = rc.DIR_XML_COMMENT
            try:
                for it in glob(os.path.join(rc.DIR_CACHE_SUB, '*.xml')):
                    os.rename(
                        it,
                        os.path.join(rc.DIR_XML_COMMENT, os.path.basename(it)))
            except Exception, e:
                dwarn(e)
Exemple #5
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()
Exemple #6
0
            ss.setValue('SubtitleVoice', False)  # disable subtitle by default
            ss.setValue('SpeakGameText', True)  # enable auto TTS by default
            ss.setValue('VoiceCharacter',
                        True)  # enable voice character by default
        else:
            return

        if ss_version <= 1412717706:
            ss.setValue('TTSEngine', 'baidu')
        else:
            return

        if ss_version <= 1410806479:
            path = rc.DIR_CACHE_AVATAR
            if os.path.exists(path):
                skfileio.removetree(path)
                skfileio.makedirs(path)
        else:
            return

        if ss_version <= 1409368561:  # reset float illegal value
            ss.setValue('DictionaryPopupWidth',
                        config.SETTINGS_DICT_POPUP_WIDTH)
        else:
            return

        if ss_version <= 1406156022:
            # http://sakuradite.com/topic/337
            # Disable UniDicMJL
            if ss.value('MeCabDictionary') == 'unidic-mlj':
                ss.setValue('MeCabDictionary', '')