Source code for xmipp3.protocols.protocol_multiple_fscs

# **************************************************************************
# *
# * Authors:     Carlos Oscar S. Sorzano (coss@cnb.csic.es)
# *
# * Unidad de  Bioinformatica of Centro Nacional de Biotecnologia , CSIC
# *
# * This program is free software; you can redistribute it and/or modify
# * it under the terms of the GNU General Public License as published by
# * the Free Software Foundation; either version 2 of the License, or
# * (at your option) any later version.
# *
# * This program is distributed in the hope that it will be useful,
# * but WITHOUT ANY WARRANTY; without even the implied warranty of
# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# * GNU General Public License for more details.
# *
# * You should have received a copy of the GNU General Public License
# * along with this program; if not, write to the Free Software
# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
# * 02111-1307  USA
# *
# *  All comments concerning this program package may be sent to the
# *  e-mail address 'scipion@cnb.csic.es'
# *
# **************************************************************************
from pwem.emlib.image import ImageHandler
from pwem.objects import FSC
from pwem.protocols import ProtAnalysis3D
from pyworkflow import VERSION_1_1
from pyworkflow.protocol.constants import STEPS_PARALLEL
import pyworkflow.protocol.params as params
import pwem.emlib.metadata as md

from xmipp3.convert import locationToXmipp


[docs]class XmippProtMultipleFSCs(ProtAnalysis3D): """ Compute the FSCs between a reference volume and a set of input volumes. A mask can be provided and the volumes are aligned by default. """ _label = 'multiple fscs' _lastUpdateVersion = VERSION_1_1 def __init__(self, **args): ProtAnalysis3D.__init__(self, **args) self.stepsExecutionMode = STEPS_PARALLEL def _defineParams(self, form): form.addSection(label='Input') form.addParam('referenceVolume', params.PointerParam, pointerClass='Volume', label="Reference volume", help='The rest of volumes will be compared to this one') form.addParam('inputVolumes', params.MultiPointerParam, pointerClass='Volume', label="Volumes to compare", help='Set of volumes to compare to the reference volume') form.addParam('mask', params.PointerParam, pointerClass='VolumeMask', allowsNull=True, label="Mask", help='A mask may be provided and it is applied before ' 'comparing the different volumes') form.addParam('doAlign', params.BooleanParam, default=True, label="Align volumes?", help="Align volumes to reference before comparing. A local " "alignment is performed so the initial orientation " "of the volumes should be relatively similar") form.addParallelSection(threads=8, mpi=1) #--------------------------- INSERT steps functions -------------------------------------------- def _insertAllSteps(self): stepId = self._insertFunctionStep('prepareReferenceStep', self.referenceVolume.get().getObjId()) allVols = [] for i, vol in enumerate(self.inputVolumes): volId = self._insertFunctionStep('compareVolumeStep', vol.get().getLocation(), i+1, prerequisites=[stepId]) allVols.append(volId) self._insertFunctionStep('createOutputStep', prerequisites=allVols) def _resizeVolume(self, volFn): """ Resize input volume if not of the same size of referenceVol """ refDim = self.referenceVolume.get().getXDim() volDim = ImageHandler().getDimensions(volFn) if refDim != volDim: self.runJob('xmipp_image_resize', "-i %s --dim %d" % (volFn, refDim)) def _maskVolume(self, volFn): """ Mask input volume multiplying by mask.vol. """ self.runJob("xmipp_image_operate", "-i %s --mult %s" % (volFn, self._getExtraPath("mask.vol")))
[docs] def prepareReferenceStep(self,volId): inputMask = self.mask.get() ih = ImageHandler() fnRef = self._getExtraPath("reference.vol") ih.convert(self.referenceVolume.get(), fnRef) if inputMask is not None: fnMask = self._getExtraPath("mask.vol") ih.convert(self.mask.get(), fnMask) self._resizeVolume(fnMask) self._maskVolume(fnRef)
[docs] def compareVolumeStep(self, volLoc, i): fnRef = self._getExtraPath("reference.vol") sampling = self.referenceVolume.get().getSamplingRate() fnRoot = self._getExtraPath("volume_%02d" % i) fnVol = fnRoot + ".vol" self.runJob("xmipp_image_convert","-i %s -o %s -t vol"%(locationToXmipp(volLoc[0],volLoc[1]),fnVol)) # Resize if the volume has different size than the reference self._resizeVolume(fnVol) if self.doAlign: # Align against the reference if selected self.runJob('xmipp_volume_align', "--i1 %s --i2 %s --apply --local" % (fnRef, fnVol)) if self.mask.hasValue(): # Mask volume if input mask self._maskVolume(fnVol) # Finally compute the FSC args = "--ref %s -i %s -o %s_fsc.xmd --sampling_rate %f" % (fnRef, fnVol, fnRoot, sampling) self.runJob("xmipp_resolution_fsc", args)
[docs] def createOutputStep(self): fscSet = self._createSetOfFSCs() for i, vol in enumerate(self.inputVolumes): index = i + 1 fnFsc = self._getExtraPath("volume_%02d_fsc.xmd" % index) mdFsc = md.MetaData(fnFsc) fscLabel = vol.get().getObjLabel() or 'FSC %d' % index fsc = FSC(objLabel=fscLabel) fsc.loadFromMd(mdFsc, md.MDL_RESOLUTION_FREQ, md.MDL_RESOLUTION_FRC) fscSet.append(fsc) self._defineOutputs(outputFSCs=fscSet) self._defineSourceRelation(self.referenceVolume, fscSet) for i, vol in enumerate(self.inputVolumes): self._defineSourceRelation(vol, fscSet)