def _buildImg(deck, latex, fname, model): # add header/footer latex = (model.conf["latexPre"] + "\n" + latex + "\n" + model.conf["latexPost"]) # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texfile = file(namedtmp("tmp.tex"), "w") texfile.write(latex) texfile.close() # make sure we have a valid mediaDir mdir = deck.media.dir(create=True) oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate dvi os.chdir(tmpdir()) if call(latexCmd + ["tmp.tex"], stdout=log, stderr=log): return _errMsg("latex") # and png if call(latexDviPngCmd + ["tmp.dvi", "-o", "tmp.png"], stdout=log, stderr=log): return _errMsg("dvipng") # add to media shutil.copy2(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def _buildImg(col, latex, fname, model): # add header/footer & convert to utf8 latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) latex = latex.encode("utf8") # it's only really secure if run in a jail, but these are the most common for bad in ("write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): assert bad not in latex # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texfile = file(namedtmp("tmp.tex"), "w") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate dvi os.chdir(tmpdir()) if call(latexCmd + ["tmp.tex"], stdout=log, stderr=log): return _errMsg("latex") # and png if call(latexDviPngCmd + ["tmp.dvi", "-o", "tmp.png"], stdout=log, stderr=log): return _errMsg("dvipng") # add to media shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def _buildImg(col, latex, fname, model): # add header/footer & convert to utf8 latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) latex = latex.encode("utf8") # it's only really secure if run in a jail, but these are the most common for bad in ("write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): assert bad not in latex # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texfile = file(namedtmp("tmp.tex"), "w") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate dvi os.chdir(tmpdir()) if call(latexCmd + ["tmp.tex"], stdout=log, stderr=log): return _errMsg("latex") # and png if call(latexDviPngCmd + ["tmp.dvi", "-o", "tmp.png"], stdout=log, stderr=log): return _errMsg("dvipng") # add to media shutil.copy2(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def openFolder(path): if isWin: if isinstance(path, unicode): path = path.encode(sys.getfilesystemencoding()) call(["explorer", path], wait=False) else: QDesktopServices.openUrl(QUrl("file://" + path))
def _buildImg(col, latex, fname, model): # add header/footer & convert to utf8 latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) latex = latex.encode("utf8") # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ("write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): if bad in tmplatex: return _("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = file(texpath, "w") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate png os.chdir(tmpdir()) for latexCmd in latexCmds: if call(latexCmd, stdout=log, stderr=log): return _errMsg(latexCmd[0], texpath) # add to media shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def _buildImg(col, latex, fname, model): # add header/footer & convert to utf8 latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) latex = latex.encode("utf8") # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ("\\write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): # don't mind if the sequence is only part of a command bad_re = "\\" + bad + "[^a-zA-Z]" if re.search(bad_re, tmplatex): return _("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = file(texpath, "w") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate png os.chdir(tmpdir()) for latexCmd in latexCmds: if call(latexCmd, stdout=log, stderr=log): return _errMsg(latexCmd[0], texpath) # add to media shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def buildImg(deck, latex): log = open(os.path.join(tmpdir, "latex_log.txt"), "w+") texpath = os.path.join(tmpdir, "tmp.tex") texfile = file(texpath, "w") texfile.write(latex) texfile.close() # make sure we have a valid mediaDir mdir = deck.mediaDir(create=True) oldcwd = os.getcwd() if sys.platform == "win32": si = subprocess.STARTUPINFO() try: si.dwFlags |= subprocess.STARTF_USESHOWWINDOW except: si.dwFlags |= subprocess._subprocess.STARTF_USESHOWWINDOW else: si = None try: os.chdir(tmpdir) def errmsg(type): msg = _("Error executing %s.\n") % type try: log = open(os.path.join(tmpdir, "latex_log.txt")).read() msg += "<small><pre>" + cgi.escape(log) + "</pre></small>" except: msg += _("Have you installed latex and dvipng?") pass return msg if call(["latex", "-interaction=nonstopmode", "tmp.tex"], stdout=log, stderr=log, startupinfo=si): return (False, errmsg("latex")) if call(latexDviPngCmd + ["tmp.dvi", "-o", "tmp.png"], stdout=log, stderr=log, startupinfo=si): return (False, errmsg("dvipng")) # add to media target = latexImgFile(deck, latex) shutil.copy2(os.path.join(tmpdir, "tmp.png"), os.path.join(mdir, target)) return (True, target) finally: os.chdir(oldcwd)
def _save_latex_image( col: anki.collection.Collection, extracted: ExtractedLatex, header: str, footer: str, svg: bool, ) -> str | None: # add header/footer latex = f"{header}\n{extracted.latex_body}\n{footer}" # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ( "\\write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout", ): # don't mind if the sequence is only part of a command bad_re = f"\\{bad}[^a-zA-Z]" if re.search(bad_re, tmplatex): return col.tr.media_for_security_reasons_is_not(val=bad) # commands to use if svg: latex_cmds = svgCommands ext = "svg" else: latex_cmds = pngCommands ext = "png" # write into a temp file log = open(namedtmp("latex_log.txt"), "w", encoding="utf8") texpath = namedtmp("tmp.tex") texfile = open(texpath, "w", encoding="utf8") texfile.write(latex) texfile.close() oldcwd = os.getcwd() png_or_svg = namedtmp(f"tmp.{ext}") try: # generate png/svg os.chdir(tmpdir()) for latex_cmd in latex_cmds: if call(latex_cmd, stdout=log, stderr=log): return _err_msg(col, latex_cmd[0], texpath) # add to media with open(png_or_svg, "rb") as file: data = file.read() col.media.write_data(extracted.filename, data) os.unlink(png_or_svg) return None finally: os.chdir(oldcwd) log.close()
def export_audio(output_folder, field_names, model_ids, cards_per_batch, num_batches, num_loops, include_separator): "Save all audio files into one large audio file" audio_files = get_card_audio(cards_per_batch * num_batches, field_names, model_ids) # get files on machine audio_files = [ os.path.join(mw.col.media.dir(), field) for field in audio_files ] for batch_id in range(num_batches): audio_files_in_batch = audio_files[batch_id * cards_per_batch:(batch_id + 1) * cards_per_batch] output_file = os.path.join(output_folder, "batch%d.mp3" % batch_id) audio_list_tmp_file = namedtmp("studyahead_audio_list.txt") separator_audio = os.path.join(mw.pm.addonFolder(), 'Studyahead_Audio', 'file_separator.mp3') with codecs.open(audio_list_tmp_file, "w", "utf-8") as f: for i, audio_file in enumerate(audio_files_in_batch): for j in range(num_loops): f.write("file '%s'\n" % os.path.relpath( audio_file, os.path.dirname(audio_list_tmp_file)).replace( "\\", "/")) if i < len(audio_files_in_batch) and include_separator: f.write("file '%s'\n" % os.path.relpath( separator_audio, os.path.dirname(audio_list_tmp_file)).replace( "\\", "/")) output_command = [ "ffmpeg", "-y", "-f", "concat", "-safe", "0", "-i", audio_list_tmp_file.replace("\\", "/"), "-vcodec", "copy", output_file ] with open(namedtmp("studyahead_audio_log.txt"), "w") as log: call(output_command, wait=True, stdout=log, stderr=log)
def _buildSnd(col, abc, fname): '''Build the sound MP3 file itself and add it to the media dir''' abcfile = open(abcFile, "w") abcfile.write(abc) abcfile.close() log = open(abcFile+".log", "w") if call(abc2midiCmd, stdout=log, stderr=log): return _errMsg("abc2midi") if call(timidityCmd, stdout=log, stderr=log): return _errMsg("timidity") if call(lameCmd, stdout=log, stderr=log): return _errMsg("lame") # add to media try: shutil.move(mp3File, os.path.join(col.media.dir(), fname)) except: return _("Could not move MP3 file to media dir. No output?<br>")+_errMsg("move")
def _buildSnd(col, abc, fname): '''Build the sound MP3 file itself and add it to the media dir''' abcfile = open(abcFile, "w") abcfile.write(abc) abcfile.close() log = open(abcFile + ".log", "w") if call(abc2midiCmd, stdout=log, stderr=log): return _errMsg("abc2midi") if call(timidityCmd, stdout=log, stderr=log): return _errMsg("timidity") if call(lameCmd, stdout=log, stderr=log): return _errMsg("lame") # add to media try: shutil.move(mp3File, os.path.join(col.media.dir(), fname)) except: return _("Could not move MP3 file to media dir. No output?<br>" ) + _errMsg("move")
def _buildImg(col, latex, fname, model): # add header/footer & convert to utf8 latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) latex = latex.encode("utf8") # it's only really secure if run in a jail, but these are the most common for bad in ("write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): if bad in latex: return _("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = file(texpath, "w") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.png") try: # generate dvi os.chdir(tmpdir()) if call(latexCmd + ["tmp.tex"], stdout=log, stderr=log): return _errMsg("latex", texpath) # and png if call(latexDviPngCmd + ["tmp.dvi", "-o", "tmp.png"], stdout=log, stderr=log): return _errMsg("dvipng", texpath) # add to media shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd)
def _buildImg(col, ly, fname): '''Build the image PNG file itself and add it to the media dir.''' lyfile = open(lilypondFile, "w") lyfile.write(ly) lyfile.close() log = open(lilypondFile+".log", "w") if call(lilypondCmd, stdout=log, stderr=log): return _errMsg("lilypond") # add to media try: shutil.move(lilypondFile+".png", os.path.join(col.media.dir(), fname)) except: return _("Could not move LilyPond PNG file to media dir. No output?<br>")+_errMsg("lilypond")
def _buildImg(col, latex, fname, model): # add header/footer latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ("\\write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): # don't mind if the sequence is only part of a command bad_re = "\\" + bad + "[^a-zA-Z]" if re.search(bad_re, tmplatex): return _("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad # commands to use? if model.get("latexsvg", False): latexCmds = svgCommands ext = "svg" else: latexCmds = pngCommands ext = "png" # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = open(texpath, "w", encoding="utf8") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.%s" % ext) try: # generate png os.chdir(tmpdir()) for latexCmd in latexCmds: if call(latexCmd, stdout=log, stderr=log): return _errMsg(latexCmd[0], texpath) # add to media shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd) log.close()
def _buildImg(col, ly, fname): '''Build the image PNG file itself and add it to the media dir.''' lyfile = open(lilypondFile, "w") lyfile.write(ly) lyfile.close() log = open(lilypondFile + ".log", "w") if call(lilypondCmd, stdout=log, stderr=log): return _errMsg("lilypond") # add to media try: shutil.move(lilypondFile + ".png", os.path.join(col.media.dir(), fname)) except: return _( "Could not move LilyPond PNG file to media dir. No output?<br>" ) + _errMsg("lilypond")
def _build_img(ly, fname): """ Build the image file itself and add it to the media dir. :param ly: LilyPond code :param fname: Filename for rendered image :return: None if successful, else error message """ lyfile = open(TEMP_FILE, "w") lyfile.write(ly) lyfile.close() log = open(TEMP_FILE + ".log", "w") if call(LILYPOND_CMD, stdout=log, stderr=log): return _err_msg("lilypond") # add to media try: shutil.move(TEMP_FILE + OUTPUT_FILE_EXT, os.path.join(mw.col.media.dir(), fname)) except: return _( "Could not move LilyPond image file to media dir. No output?<br>" ) + _err_msg("lilypond")
def _buildImg(col, latex, fname, model): """Generate an image file from latex code latex's header and foot is added as in the model. The image is named fname and added to the media folder of this collection. The compiled file is in tmp.tex and its output (err and std) in latex_log.tex, replacing previous files of the same name. Both of those file are in the tmpdir as in utils.py Compiles to svg if latexsvg is set to true in the model, otherwise to png. The compilation commands are given above. In case of error, return an error message to be displayed instead of the LaTeX document. (Note that this image is not displayed in AnkiDroid. It is probably shown only in computer mode) Keyword arguments: col -- the current collection. It deals with media folder latex -- the code LaTeX to compile, as given in fields fname -- the name given to the generated png model -- the model in which is compiled the note. It deals with the header/footer, and the image file format """ # add header/footer latex = (model["latexPre"] + "\n" + latex + "\n" + model["latexPost"]) # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ("\\write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout"): # don't mind if the sequence is only part of a command bad_re = "\\" + bad + "[^a-zA-Z]" if re.search(bad_re, tmplatex): return _("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad # commands to use? if model.get("latexsvg", False): latexCmds = svgCommands ext = "svg" else: latexCmds = pngCommands ext = "png" # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = open(texpath, "w", encoding="utf8") texfile.write(latex) texfile.close() mdir = col.media.dir() oldcwd = os.getcwd() png = namedtmp("tmp.%s" % ext) try: # generate an image os.chdir(tmpdir()) for latexCmd in latexCmds: if call(latexCmd, stdout=log, stderr=log): return _errMsg(latexCmd[0], texpath) # add the image to the media folder shutil.copyfile(png, os.path.join(mdir, fname)) return finally: os.chdir(oldcwd) log.close()
def _save_latex_image( col: anki.collection.Collection, extracted: ExtractedLatex, header: str, footer: str, svg: bool, ) -> Optional[str]: # add header/footer latex = header + "\n" + extracted.latex_body + "\n" + footer # it's only really secure if run in a jail, but these are the most common tmplatex = latex.replace("\\includegraphics", "") for bad in ( "\\write18", "\\readline", "\\input", "\\include", "\\catcode", "\\openout", "\\write", "\\loop", "\\def", "\\shipout", ): # don't mind if the sequence is only part of a command bad_re = "\\" + bad + "[^a-zA-Z]" if re.search(bad_re, tmplatex): return (_("""\ For security reasons, '%s' is not allowed on cards. You can still use \ it by placing the command in a different package, and importing that \ package in the LaTeX header instead.""") % bad) # commands to use if svg: latexCmds = svgCommands ext = "svg" else: latexCmds = pngCommands ext = "png" # write into a temp file log = open(namedtmp("latex_log.txt"), "w") texpath = namedtmp("tmp.tex") texfile = open(texpath, "w", encoding="utf8") texfile.write(latex) texfile.close() oldcwd = os.getcwd() png_or_svg = namedtmp("tmp.%s" % ext) try: # generate png/svg os.chdir(tmpdir()) for latexCmd in latexCmds: if call(latexCmd, stdout=log, stderr=log): return _errMsg(latexCmd[0], texpath) # add to media with open(png_or_svg, "rb") as file: data = file.read() col.media.write_data(extracted.filename, data) os.unlink(png_or_svg) return None finally: os.chdir(oldcwd) log.close()