Ticket #12299: trac_12299_plot_3D_static_img.patch

File trac_12299_plot_3D_static_img.patch, 9.5 KB (added by gutow, 9 years ago)

update to remove duplicate patches

  • new file sage/interfaces/jmoldata.py

    # HG changeset patch
    # User Jonathan Gutow <gutow@uwosh.edu>
    # Date 1338133362 18000
    # Node ID 0bb75312f38635ee2ef3197e6468b58bddcf87e5
    # Parent  52fab674604c69f1a39963a3e951fb28d6387329
    Trac 12299: static 3-D Jmol generated images
    
    diff --git a/sage/interfaces/jmoldata.py b/sage/interfaces/jmoldata.py
    new file mode 100644
    - +  
     1r"""
     2Interface for extracting data and generating images from Jmol readable files.
     3
     4JmolData is a no GUI version of Jmol useful for extracting data from files Jmol
     5reads and for generating image files.
     6
     7AUTHORS:
     8Jonathan Gutow (2012-03-21): initial version
     9
     10#*******************************************************************************
     11#       Copyright (C) 2012 Jonathan Gutow (gutow@uwosh.edu)
     12#
     13#  Distributed under the terms of the GNU General Public License (GPL)
     14#  as published by the Free Software Foundation; either version 2 of
     15#  the License, or (at your option) any later version.
     16#                  http://www.gnu.org/licenses/
     17#*******************************************************************************
     18"""
     19from sage.structure.sage_object import SageObject
     20
     21from sage.misc.misc import tmp_filename
     22from sage.misc.misc import SAGE_LOCAL
     23
     24import subprocess
     25import os
     26
     27class JmolDataError(Exception):
     28    def __init__(self, value):
     29        self.value = value
     30    def __str__(self):
     31        return repr(self.value)
     32
     33class JmolData(SageObject):
     34    r"""
     35    .. TODO::
     36        DONE 1) create an image file (user choosable JPG, PNG, GIF)
     37        DONE 1.5) function to check if jvm is available
     38        DONE 1.75) raise exception if export_image is called without JVM being available.
     39        2) create an animated image file if spin is on (GIF)
     40        3) Put data extracted from a file into a variable/string/structure to return
     41    """
     42    def __init__(self):
     43        pass
     44
     45    def is_jvm_available(self):
     46        #scratch file for  Jmol errors and status
     47        jmolscratch = os.path.expanduser("~/.sage/sage_notebook.sagenb/jmol_scratch")
     48        if not os.path.exists(jmolscratch):
     49            os.mkdir(jmolscratch)
     50        scratchout = os.path.join(jmolscratch,"jmolout.txt")
     51        jout=open(scratchout,'w')
     52        testjavapath = os.path.join(SAGE_LOCAL, "share/jmol/testjava.sh")
     53        result = subprocess.call([testjavapath],stdout=jout)
     54        jout.close()
     55        if (result == 0):
     56            return (True)
     57        else:
     58            return (False)
     59           
     60    def export_image(self,
     61        targetfile,
     62        datafile, #name (path) of data file Jmol can read or script file telling it what to read or load
     63        datafile_cmd='script', #"script" or "load"
     64        image_type ='PNG', #PNG, JPG, GIF
     65        figsize=5,
     66        **kwds):
     67        """
     68        This executes JmolData.jar to make an image file.
     69       
     70        INPUT:
     71            targetfile -- the full path to the file where the image should be written.
     72            datafile   -- full path to the data file Jmol can read or text of a script
     73                telling Jmol what to read or load.
     74            datafile_cmd -- "script" or "load" defaults to "script", should be load for a data file.
     75            image_type -- "PNG" "JPG" or "GIF" defaults to "PNG"
     76            figsize -- number = (pixels/side)/100 defaults to 5.
     77           
     78        OUTPUT:
     79            image file , .png, .gif or .jpg (default .png)
     80           
     81        .. NOTE::
     82            Examples will generate an error message if a functional Java Virtual Machine (JVM) is not installed
     83            on the machine the Sage instance is running on.
     84           
     85        .. WARNING::
     86            Programmers using this module should check that the JVM is available before making calls to
     87            avoid the user getting error messages.  Check for the JVM using the function
     88            is_jvm_available(), which returns True if a JVM is available.
     89           
     90        EXAMPLES::
     91       
     92        Use Jmol to load a pdb file containing some DNA from a web data base and make an image of the DNA.
     93        If you execute this in the notebook, the image will appear in the output cell.
     94        ::
     95            sage: from sage.interfaces.jmoldata import JmolData
     96            sage: JData = JmolData()
     97            sage: script = "load =1lcd;display DNA;moveto 0.0 { -473 -713 -518 59.94} 100.0 0.0 0.0 {21.17 26.72 27.295} 27.544636 {0.0 0.0 0.0} -25.287832 64.8414 0.0;"
     98            sage: testfile = "DNA.png"
     99            sage: JData.export_image(targetfile=testfile,datafile=script,image_type="PNG")
     100            sage: print os.path.exists(testfile)
     101            True
     102       
     103        Use Jmol to save an image of a 3-D object created in Sage.  This method is used internally
     104        by plot3d to generate static images.  This example doesn't have correct scaling.
     105        ::
     106       
     107            sage: from sage.interfaces.jmoldata import JmolData
     108            sage: JData = JmolData()
     109            sage: D=dodecahedron()
     110            sage: from sage.misc.misc import SAGE_TMP
     111            sage: archive_name=os.path.join(SAGE_TMP, "archive.jmol.zip")
     112            sage: D.export_jmol(archive_name)  #not scaled properly...need some more steps.
     113            sage: testfile = os.path.join(SAGE_TMP, "testimage.png")
     114            sage: script = 'set defaultdirectory "'+archive_name+'"\n script SCRIPT\n'
     115            sage: JData.export_image(targetfile =testfile,datafile = script, image_type="PNG")
     116            sage: print os.path.exists(testfile)
     117            True
     118
     119         """
     120        if (self.is_jvm_available()):
     121            # Set up paths, file names and scripts
     122            jmolpath = os.path.join(SAGE_LOCAL, "share/jmol/JmolData.jar")
     123            launchscript = ""
     124            if (datafile_cmd!='script'):
     125                launchscript = "load "
     126            launchscript = launchscript + datafile
     127            #print launchscript
     128            imagescript = "write "+ image_type +" "+targetfile+"\n"
     129            #print imagescript
     130           
     131            sizeStr = "%sx%s" %(figsize*100,figsize*100)
     132            #scratch file for  Jmol errors and status
     133            jmolscratch = os.path.expanduser("~/.sage/sage_notebook.sagenb/jmol_scratch")
     134            if not os.path.exists(jmolscratch):
     135                os.mkdir(jmolscratch)
     136            scratchout = os.path.join(jmolscratch,"jmolout.txt")
     137            jout=open(scratchout,'w')
     138            #now call the java application and write the file.
     139            result = subprocess.call(["java","-jar",jmolpath,"-iox","-g",sizeStr,"-J",launchscript,"-j",imagescript],stdout=jout)
     140            jout.close()
     141        else:
     142            errStr = "Java Virtual Machine not available.\n"
     143            errStr +="This should be checked before calling JmolData().export_image().\n"
     144            errStr +="Use JmolData().is_jvm_available() to check.\n"
     145            errStr +="Administrator should install JVM."
     146            raise JmolDataError(errStr)
  • sage/plot/plot3d/base.pyx

    diff --git a/sage/plot/plot3d/base.pyx b/sage/plot/plot3d/base.pyx
    a b  
    11291129
    11301130            # We need a script to load the file
    11311131            f = open(filename + '.'+ext, 'w')
     1132            import sagenb
    11321133            if EMBEDDED_MODE:
    1133                 import sagenb
    11341134                path = "cells/%s/%s" %(sagenb.notebook.interact.SAGE_CELL_ID, archive_name)
    11351135            else:
    11361136                path = archive_name
     
    11381138            f.write('script SCRIPT\n')
    11391139            f.close()
    11401140
     1141            # If the server has a Java installation we can make better static images with Jmol
     1142            # Test for Java then make image with Jmol or Tachyon if no JavaVM
     1143            if EMBEDDED_MODE:
     1144                #name image file
     1145                head,tail = os.path.split(archive_name)
     1146                png_path = os.path.join(head,'.jmol_images')
     1147                if  not os.path.exists(png_path):
     1148                    os.mkdir(png_path)
     1149                png_name = os.path.join(png_path,filename)
     1150                #test for JavaVM
     1151                from sage.interfaces.jmoldata import JmolData
     1152                jdata = JmolData()
     1153                if (jdata.is_jvm_available()):
     1154                    # make the image with Jmol
     1155                    # hack...need absolute paths since jvm running outside of sage environment
     1156                    cellhead, celltail =os.path.split(os.path.realpath(os.path.join(os.path.curdir,"data")))
     1157                    celldir = os.path.join(cellhead,"cells",str(sagenb.notebook.interact.SAGE_CELL_ID))
     1158                    png_name = png_name+".jmol.png"
     1159                    png_fullpath = os.path.join(celldir,png_name)
     1160                    archive_fullpath = os.path.join(celldir,archive_name)
     1161                    #print png_fullpath
     1162                    script = 'set defaultdirectory \"'+archive_fullpath+'\"\n script SCRIPT\n'
     1163                    #print script
     1164                    jdata.export_image(targetfile = png_fullpath,datafile=script,image_type="PNG", figsize = fg)
     1165                else:
     1166                    #make the image with tachyon
     1167                    T = self._prepare_for_tachyon(frame, axes, frame_aspect_ratio, aspect_ratio, zoom)
     1168                    tachyon_rt(T.tachyon(), png_name+".jmol.png", verbosity, True, opts)
     1169
     1170                       
    11411171        if viewer == 'canvas3d':
    11421172            T = self._prepare_for_tachyon(frame, axes, frame_aspect_ratio, aspect_ratio, zoom)
    11431173            data = flatten_list(T.json_repr(T.default_render_params()))