Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement viewer for import tomograms #3

Merged
merged 7 commits into from May 7, 2019
Merged
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
3 changes: 2 additions & 1 deletion tomo/viewers/__init__.py
Expand Up @@ -25,4 +25,5 @@
# **************************************************************************

from .viewers_data import TomoDataViewer
from .viewer_imod import ImodViewer, ImodObjectView
from .viewer_imod import ImodViewer, ImodObjectView
from .viewer_tomograms import ViewerProtImportTomograms
153 changes: 153 additions & 0 deletions tomo/viewers/viewer_tomograms.py
@@ -0,0 +1,153 @@
# **************************************************************************
# *
# * Authors: Adrian Quintana (adrian@eyeseetea.com) [1]
# *
# * [1] EyeSeeTea Ltd, London, UK
# *
# * 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'
# *
# **************************************************************************


"""
This module implements visualization program
for input tomograms.
"""

import os
from distutils.spawn import find_executable
from tkMessageBox import showerror

import pyworkflow.protocol.params as params
from pyworkflow.em.convert import ImageHandler
from pyworkflow.viewer import DESKTOP_TKINTER, WEB_DJANGO, ProtocolViewer, MessageView, MSG_ERROR
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please check line length of max 80, as stated in PEP8

import pyworkflow.em.viewers as viewers

from tomo.protocols import protocol_import_tomograms
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Still here you are referring to "internal" implementation file 'protocol_import_tomograms'. This is not a good practice since this file can change, or merged...the class definition should be available from tomo.protocols (defined in its init.py file), so it should be something like this:
from tomo.protocols import ProtImportTomograms # so you don't really need to know where the class is implemented


TOMOGRAM_SLICES = 1
TOMOGRAM_CHIMERA = 0


class ViewerProtImportTomograms(ProtocolViewer):
""" Wrapper to visualize different type of objects
with the Xmipp program xmipp_showj. """

_label = 'viewer input tomogram'
_targets = [protocol_import_tomograms.ProtImportTomograms]
_environments = [DESKTOP_TKINTER, WEB_DJANGO]

def _defineParams(self, form):
form.addSection(label='Visualization of input tomograms')
form.addParam('displayTomo', params.EnumParam,
choices=['chimera', 'slices'],
default=TOMOGRAM_CHIMERA,
display=params.EnumParam.DISPLAY_HLIST,
label='Display tomogram with',
help='*chimera*: display tomograms as surface with '
'Chimera.\n *slices*: display tomograms as 2D slices '
'along z axis.\n If number of tomograms == 1, '
'a system of coordinates is shown'
)

def _getVisualizeDict(self):
return {
'displayTomo': self._showTomograms,
}

def _validate(self):
if (self.displayTomo == TOMOGRAM_CHIMERA
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is a plugin specific to Chimera, have you checked if some of this functionality is already there?

and find_executable(viewers.viewer_chimera.Chimera.getProgram()) is None):
return ["chimera is not available. "
"Either install it or choose option 'slices'. "]
return []

# =========================================================================
# ShowTomograms
# =========================================================================

def _showTomograms(self, paramName=None):
if self.displayTomo == TOMOGRAM_CHIMERA:
return self._showTomogramsChimera()

elif self.displayTomo == TOMOGRAM_SLICES:
return self._showTomogramsSlices()

def _createSetOfTomograms(self):
try:
setOfTomograms = self.protocol.outputTomograms
sampling = self.protocol.outputTomograms.getSamplingRate()
except:
setOfTomograms = self.protocol._createSetOfTomograms()
setOfTomograms.append(self.protocol.outputTomogram)
sampling = self.protocol.outputTomogram.getSamplingRate()

return sampling, setOfTomograms

def _showTomogramsChimera(self):
""" Create a chimera script to visualize selected tomograms. """
tmpFileNameCMD = self.protocol._getTmpPath("chimera.cmd")
f = open(tmpFileNameCMD, "w")
sampling, _setOfTomograms = self._createSetOfTomograms()
count = 0 # first model in chimera is a tomogram

if len(_setOfTomograms) == 1:
count = 1 # first model in chimera is the bild file
# if we have a single tomogram then create axis
# as bild file. Chimera must read the bild file first
# otherwise system of coordinates will not
# be in the center of the window

dim = self.protocol.outputTomogram.getDim()[0]
tmpFileNameBILD = os.path.abspath(self.protocol._getTmpPath(
"axis.bild"))
viewers.viewer_chimera.Chimera.createCoordinateAxisFile(dim,
bildFileName=tmpFileNameBILD,
sampling=sampling)
f.write("open %s\n" % tmpFileNameBILD)
f.write("cofr 0,0,0\n") # set center of coordinates
count = 1 # skip first model because is not a 3D map

for tomo in _setOfTomograms:
localTomo = os.path.abspath(ImageHandler.removeFileType(
tomo.getFileName()))
if localTomo.endswith("stk"):
self.showError("Extension .stk is not supported")
f.write("open %s\n" % localTomo)
f.write("volume#%d style surface voxelSize %f\n" %
(count, sampling))
count += 1

if len(_setOfTomograms) > 1:
f.write('tile\n')
else:
x, y, z = tomo.getShiftsFromOrigin()
f.write("volume#1 origin %0.2f,%0.2f,%0.2f\n" % (x, y, z))
f.close()
return [viewers.viewer_chimera.ChimeraView(tmpFileNameCMD)]

def _showTomogramsSlices(self):
# Write an sqlite with all tomograms selected for visualization.
sampling, setOfTomograms = self._createSetOfTomograms()

if len(setOfTomograms) == 1:
return [self.objectView(self.protocol.outputTomogram)]

return [self.objectView(setOfTomograms)]