def multisave(filename, pattern="all", state=-1, append=0, format='', quiet=1, _self=cmd): ''' DESCRIPTION "multisave" will save a multi-entry PDB file. Every object in the given selection (pattern) will have a HEADER and a CRYST (if symmetry is defined) record, and is terminated with END. Loading such a multi-entry PDB file into PyMOL will load each entry as a separate object. This behavior is different to the "save" command, where a multi-object selection is written "flat" to a PDB file, without HEADER or CRYST records. ARGUMENTS filename = string: file path to be written pattern = str: atom selection (before 1.8.4: object name pattern) state = int: object state (-1=current, 0=all) {default: -1} append = 0/1: append to existing file {default: 0} format = str: file format {default: guess from extension, or 'pdb'} ''' from pymol.importing import filename_to_format _, _, format_guessed, zipped = filename_to_format(filename) if zipped: raise pymol.CmdException(zipped + ' not supported with multisave') if not format: format = format_guessed or 'pdb' if format == 'pmo': raise pymol.CmdException('pmo format not supported anymore') if format not in ('pdb', 'cif'): raise pymol.CmdException(format + ' format not supported with multisave') s = get_str(format, pattern, state, '', -1, 1, quiet, _self) if s is None: if _self._raising(): raise QuietException return DEFAULT_ERROR filename = _self.exp_path(filename) with open(filename, 'a' if int(append) else 'w') as handle: handle.write(s) return DEFAULT_SUCCESS
def ext_get_primary(ext): r''' If `ext` is an alias for another extension, return the other, otherwise return `ext` ''' try: from pymol import importing except ImportError: print('import pymol failed') return ext return importing.filename_to_format('.' + ext)[2]
def save(filename, selection='(all)', state=-1, format='', ref='', ref_state=-1, quiet=1, partial=0, *, _self=cmd): ''' DESCRIPTION "save" writes content to a file. USAGE save filename [, selection [, state [, format ]]] ARGUMENTS filename = string: file path to be written selection = string: atoms to save {default: (all)} state = integer: state to save {default: -1 (current state)} PYMOL API cmd.save(string file, string selection, int state, string format) NOTES The file format is automatically chosen if the extesion is one of the supported output formats: pdb, pqr, mol, sdf, pkl, pkla, mmd, out, dat, mmod, cif, pov, png, pse, psw, aln, fasta, obj, mtl, wrl, dae, idtf, or mol2. If the file format is not recognized, then a PDB file is written by default. For molecular files and where applicable and supported: * if state = -1 (default), then only the current state is written. * if state = 0, then a multi-state output file is written. SEE ALSO load, get_model ''' quiet = int(quiet) # preprocess selection selection = selector.process(selection) # r = DEFAULT_ERROR # analyze filename from pymol.importing import filename_to_format, _eval_func _, _, format_guessed, zipped = filename_to_format(filename) filename = _self.exp_path(filename) # file format if not format: if not format_guessed: raise pymol.CmdException('Unrecognized file format') format = format_guessed # PyMOL session if format in ( 'pse', 'psw', ): _self.set( "session_file", # always use unix-like path separators filename.replace("\\", "/"), quiet=1) if not quiet: print(" Save: Please wait -- writing session file...") func_type4 = { 'mmod': io.mmd.toFile, 'pkl': io.pkl.toFile, # binary pickle 'pkla': lambda model, filename: io.pkl.toFile( model, filename, bin=0), # ascii pickle } contents = None if format in savefunctions: # generic forwarding to format specific save functions func = savefunctions[format] func = _eval_func(func) kw_all = { 'filename': filename, 'selection': selection, 'name': selection, # alt (get_ccp4str) 'state': state, 'format': format, 'ref': ref, 'ref_state': ref_state, 'quiet': quiet, 'partial': partial, '_self': _self, } import inspect sig = inspect.signature(func, follow_wrapped=False) kw = {} for n, param in sig.parameters.items(): if param.kind == inspect.Parameter.VAR_KEYWORD: kw = kw_all break if param.kind == inspect.Parameter.VAR_POSITIONAL: print('FIXME: savefunctions[%s]: *args' % (format)) elif param.kind == inspect.Parameter.POSITIONAL_ONLY: raise Exception('positional-only arguments not supported') elif n in kw_all: kw[n] = kw_all[n] contents = func(**kw) if 'filename' in sig.parameters: # assume function wrote directly to file and returned a status return contents elif format in func_type4: func_type4[format](_self.get_model(selection, state, ref, ref_state), filename) r = DEFAULT_SUCCESS else: raise pymol.CmdException('File format not supported for export') # function returned sequence of strings or bytes if isinstance(contents, (tuple, list)) and contents: contents = contents[0][:0].join(contents) if cmd.is_string(contents): if not isinstance(contents, bytes): contents = contents.encode() if zipped == 'gz': import gzip fopen = gzip.open else: fopen = open if zipped == 'bz2': import bz2 contents = bz2.compress(contents) with fopen(filename, 'wb') as handle: handle.write(contents) r = DEFAULT_SUCCESS if _self._raising(r): raise QuietException if not quiet: if r == DEFAULT_SUCCESS: print(' Save: wrote "' + filename + '".') else: print(' Save-Error: no file written') return r
def save(filename, selection='(all)', state=-1, format='', ref='', ref_state=-1, quiet=1, partial=0,_self=cmd): ''' DESCRIPTION "save" writes content to a file. USAGE save filename [, selection [, state [, format ]]] ARGUMENTS filename = string: file path to be written selection = string: atoms to save {default: (all)} state = integer: state to save {default: -1 (current state)} PYMOL API cmd.save(string file, string selection, int state, string format) NOTES The file format is automatically chosen if the extesion is one of the supported output formats: pdb, pqr, mol, sdf, pkl, pkla, mmd, out, dat, mmod, cif, pov, png, pse, psw, aln, fasta, obj, mtl, wrl, dae, idtf, or mol2. If the file format is not recognized, then a PDB file is written by default. For molecular files and where applicable and supported: * if state = -1 (default), then only the current state is written. * if state = 0, then a multi-state output file is written. SEE ALSO load, get_model ''' quiet = int(quiet) # preprocess selection selection = selector.process(selection) # r = DEFAULT_ERROR # analyze filename from pymol.importing import filename_to_format, _eval_func _, _, format_guessed, zipped = filename_to_format(filename) filename = _self.exp_path(filename) # file format if not format: if not format_guessed: raise pymol.CmdException('Unrecognized file format') format = format_guessed # PyMOL session if format in ('pse', 'psw',): _self.set("session_file", # always use unix-like path separators filename.replace("\\", "/"), quiet=1) if not quiet: print(" Save: Please wait -- writing session file...") func_type4 = { 'mmod': io.mmd.toFile, 'pkl': io.pkl.toFile, # binary pickle 'pkla': lambda model, filename: io.pkl.toFile(model, filename, bin=0), # ascii pickle } contents = None if format in savefunctions: # generic forwarding to format specific save functions func = savefunctions[format] func = _eval_func(func) kw = { 'filename': filename, 'selection': selection, 'name': selection, # alt (get_ccp4str) 'state': state, 'format': format, 'ref': ref, 'ref_state': ref_state, 'quiet': quiet, 'partial': partial, '_self': _self, } import inspect spec = inspect.getargspec(func) if spec.varargs: print('FIXME: savefunctions[%s]: *args' % (format)) if not spec.keywords: kw = dict((n, kw[n]) for n in spec.args if n in kw) contents = func(**kw) if 'filename' in spec.args: # assume function wrote directly to file and returned a status return contents elif format in func_type4: func_type4[format](_self.get_model(selection, state, ref, ref_state), filename) r = DEFAULT_SUCCESS else: raise pymol.CmdException('File format not supported for export') # function returned sequence of strings or bytes if isinstance(contents, (tuple, list)) and contents: contents = contents[0][:0].join(contents) if cmd.is_string(contents): if not isinstance(contents, bytes): contents = contents.encode() if zipped == 'gz': import gzip fopen = gzip.open else: fopen = open if zipped == 'bz2': import bz2 contents = bz2.compress(contents) with fopen(filename, 'wb') as handle: handle.write(contents) r = DEFAULT_SUCCESS if _self._raising(r,_self): raise QuietException if not quiet: if r == DEFAULT_SUCCESS: print(' Save: wrote "' + filename + '".') else: print(' Save-Error: no file written') return r