1 #!/usr/bin/env python 2 3 """ 4 Theming common functionality. 5 6 Copyright (C) 2018, 2019 Paul Boddie <paul@boddie.org.uk> 7 8 This program is free software; you can redistribute it and/or modify it under 9 the terms of the GNU General Public License as published by the Free Software 10 Foundation; either version 3 of the License, or (at your option) any later 11 version. 12 13 This program is distributed in the hope that it will be useful, but WITHOUT 14 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 15 FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 16 details. 17 18 You should have received a copy of the GNU General Public License along with 19 this program. If not, see <http://www.gnu.org/licenses/>. 20 """ 21 22 from os import listdir, makedirs 23 from os.path import exists, isfile, join, split 24 from shutil import copy 25 import codecs 26 27 class Theme: 28 29 "A common theme abstraction." 30 31 default_encoding = "utf-8" 32 33 def __init__(self, metadata): 34 35 "Initialise the theme with the given 'metadata'." 36 37 self.metadata = metadata 38 39 # Obtain essential metadata. 40 41 self.linker = metadata.get_linker() 42 self.output = metadata.get_output() 43 44 def apply(self, text): 45 46 "Apply this theme to the given 'text', returning a themed version." 47 48 return text 49 50 def get_resource_base(self): 51 52 "Return the filesystem base of resources for instances of this class." 53 54 return split(self.__class__.origin)[0] 55 56 def get_resource(self, filename): 57 58 "Return the complete path for the resource with the given 'filename'." 59 60 base = self.get_resource_base() 61 return join(base, filename) 62 63 def install_resource(self, filename, target=None): 64 65 """ 66 Install the resource with the given 'filename' into a location having 67 the given 'target' name (or 'filename' if 'target' is omitted). 68 """ 69 70 if not self.output.can_write(): 71 return 72 73 pathname = self.get_resource(filename) 74 outpath = self.output.get_filename(target or filename) 75 76 self.copy(pathname, outpath) 77 78 def copy(self, pathname, outpath): 79 80 "Copy 'pathname' to 'outpath'." 81 82 if isfile(pathname): 83 outdir = split(outpath)[0] 84 if outdir and not exists(outdir): 85 makedirs(outdir) 86 copy(pathname, outpath) 87 else: 88 if not exists(outpath): 89 makedirs(outpath) 90 for filename in listdir(pathname): 91 self.copy(join(pathname, filename), join(outpath, filename)) 92 93 def load_resource(self, filename): 94 95 "Return the textual content of the resource with the given 'filename'." 96 97 f = codecs.open(self.get_resource(filename), encoding=self.default_encoding) 98 try: 99 return f.read() 100 finally: 101 f.close() 102 103 # vim: tabstop=4 expandtab shiftwidth=4