Surface NMR processing and inversion GUI
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

build_ui.py 4.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117
  1. # -*- coding: utf-8 -*-
  2. """
  3. Distutils extension for PyQt/PySide applications
  4. """
  5. import glob
  6. import os
  7. import subprocess
  8. import sys
  9. from setuptools import Command
  10. from .config import Config
  11. from .hooks import load_hooks
  12. from .utils import build_args, write_message
  13. class build_ui(Command):
  14. """
  15. Builds the Qt ui files as described in pyuic.json (or pyuic.cfg).
  16. """
  17. user_options = [
  18. ('force', None,
  19. 'Force flag, will force recompilation of every ui/qrc file'),
  20. ]
  21. def initialize_options(self):
  22. self.force = False
  23. self._hooks = load_hooks()
  24. def finalize_options(self):
  25. try:
  26. self.cfg = Config()
  27. self.cfg.load()
  28. except (IOError, OSError):
  29. write_message('cannot open pyuic.json (or pyuic.cfg)', 'red')
  30. self.cfg = None
  31. def is_outdated(self, src, dst, ui):
  32. if src.endswith('.qrc') or self.force:
  33. return True
  34. outdated = (not os.path.exists(dst) or
  35. (os.path.getmtime(src) > os.path.getmtime(dst)))
  36. if not outdated and not ui:
  37. # for qrc files, we need to check each individual resources.
  38. # If one of them is newer than the dst file, the qrc file must be
  39. # considered as outdated
  40. # file paths are relative to the qrc file path
  41. qrc_dirname = os.path.dirname(src)
  42. with open(src, 'r') as f:
  43. lines = f.read().splitlines()
  44. lines = [l for l in lines if '<file>' in l]
  45. cwd = os.getcwd()
  46. os.chdir(qrc_dirname)
  47. for line in lines:
  48. filename = line.replace('<file>', '').replace(
  49. '</file>', '').strip()
  50. filename = os.path.abspath(filename)
  51. if os.path.getmtime(filename) > os.path.getmtime(dst):
  52. outdated = True
  53. break
  54. os.chdir(cwd)
  55. return outdated
  56. def run(self):
  57. if not self.cfg:
  58. return
  59. for glob_exp, dest in self.cfg.files:
  60. for src in glob.glob(glob_exp):
  61. if not os.path.exists(src):
  62. write_message('skipping target %s, file not found' % src, 'yellow')
  63. continue
  64. src = os.path.join(os.getcwd(), src)
  65. dst = os.path.join(os.getcwd(), dest)
  66. ui = True
  67. if src.endswith('.ui'):
  68. ext = '_ui.py'
  69. cmd = self.cfg.uic_command()
  70. elif src.endswith('.qrc'):
  71. ui = False
  72. ext = '_rc.py'
  73. cmd = self.cfg.rcc_command()
  74. else:
  75. continue
  76. filename = os.path.split(src)[1]
  77. filename = os.path.splitext(filename)[0]
  78. dst = os.path.join(dst, filename + ext)
  79. try:
  80. os.makedirs(os.path.split(dst)[0])
  81. except OSError:
  82. pass
  83. if self.is_outdated(src, dst, ui):
  84. try:
  85. cmd = build_args(cmd, src, dst)
  86. subprocess.check_call(cmd)
  87. cmd = ' '.join(cmd)
  88. except subprocess.CalledProcessError as e:
  89. if e.output:
  90. write_message(cmd, 'yellow')
  91. write_message(e.output.decode(sys.stdout.encoding), 'red')
  92. else:
  93. write_message(cmd, 'red')
  94. except OSError as e:
  95. write_message(cmd, 'yellow')
  96. write_message(str(e), 'red')
  97. else:
  98. write_message(cmd, 'green')
  99. for hookname in self.cfg.hooks:
  100. try:
  101. hook = self._hooks[hookname]
  102. except KeyError:
  103. write_message('warning, unknonw hook: %r' % hookname, 'yellow')
  104. else:
  105. write_message('running hook %r' % hookname, 'blue')
  106. hook(dst)
  107. else:
  108. write_message('skipping %s, up to date' % src)