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 TikZ images for problems. #432

Merged
merged 2 commits into from
Dec 28, 2019
Merged

Conversation

drgrice1
Copy link
Member

@drgrice1 drgrice1 commented Sep 29, 2019

I am submitting this now so that others can take a look and at Michael Gage's request in issue #418. There is a matching pull request to the webwork2 code (openwebwork/webwork2#1030) that loads the module and sets the external convert program.

The general implementation is that a uniquely named working directory is created in the general webwork tmp location. Then a tex file is written and pdflatex run. Then convert is called to convert the pdf to a png, gif, or svg image. The image data is read, and then written to disk by the insertGraph method.

I also added a simple macro that basically does the same thing the PGgraphmacros.pl macro does for images generated with GD in terms of setting up the file name.

I changed the output directory of that method from the gif directory to the images directory (inside the course temporary html location). That part can be reverted if needed, but it seems silly to write what are almost always png images to a gif directory, and have a separate general image directory.

This builds on the work of Michael Gage and Peter Peluso (and others?)
in PG openwebwork#292.
Care is taken to ensure that the command line is not exposed.
I have updated the examples in pg/t/tikz_test for its usage as I have
implemented it.
@sean-fitzpatrick
Copy link

@drgrice1 are there any sample problems that use this code? I've moved an old WeBWorK server onto openwebwork:develop so I can test this out.
We're working this summer on getting a PreTeXt version of APEX Calculus ready for "prime time". The goal is to convert every exercise into a (ptx) WeBWorK problem -- but a lot of exercises have TikZ images, and not all of those images will translate well to pg graphs.

Slightly off-topic, but related: if this works out, how unrealistic is Asymptote as a next step? I'm not sure you'd want to be compiling asy diagrams in real time. But now that Asymptote supports WebGL as an output format, you could have some interactive 3D plots that are nicer than a lot of the existing examples. For example, here is an APEX exercise with an Asymptote figure rendered in WebGL.

@mgage
Copy link
Member

mgage commented May 27, 2020

@sean-fitzpatrick for elementary tikz unit tests look at https://github.com/openwebwork/pg/tree/develop/t/tikz_test notice this is in the develop version of pg.

existing 3d plots from Mathematica are at
https://demo.webwork.rochester.edu/webwork2/liveGraph_test/.

I notice that the labeling in Asymptote looks much nicer. Both use WebGL.

@sean-fitzpatrick
Copy link

Thanks. Mathematica is nice but we don't have a license. I think I'd have to save every penny of my professional expense account for three years to get a copy.

I'm still trying to learn Asymptote but it's free and open. Plus it's Canadian ;-) I even know the two lead developers. John Bowman has been very helpful in working with us to optimize Asymptote for PreTeXt HTML.

@sean-fitzpatrick
Copy link

I sort of have this working, except that the images aren't coming through:
Screenshot from 2020-05-29 14-43-11

Is the double slash before images correct: //images

@drgrice1
Copy link
Member Author

Did you make the changes to /etc/ImageMagick-6/policy.xml that are described on line 115 of /opt/webwork/webwork2/conf/site.conf.dist.

@drgrice1
Copy link
Member Author

The double slash doesn't matter. Linux ignores an extra slash in a path name.

@sean-fitzpatrick
Copy link

That did it, thanks. Forgot to update the conf files after moving to develop.

It's interesting that reloading the problem didn't get the image to load -- those image strings stay put. But if I delete the question from the set and then add it back in as a new problem, it loads fine.

@mgage for those Mathematica plots, do you just ship the html with the pg file? (I assume WeBWorK is not generating them on the fly.) I wonder if those demos could be adapted for asymptote-generated versions.

@mgage
Copy link
Member

mgage commented May 31, 2020

The images might have been cached by the browser? Did you do shift-reload?

I'm sure that Goeff's implementation of LiveJar can be improved to use other inputs:
https://webworkgoehle.blogspot.com/2015/05/livegraphics-and-javascript.html (he says so in the blog post.) The code is at https://github.com/openwebwork/pg/blob/master/macros/LiveGraphics3D.pl and points to the javaScript in webwork2/htdocs/js/LiveGraphics3D

@sean-fitzpatrick
Copy link

Thanks. Maybe someone will have time to look at the 3D code. (Not me, at least any time soon.)
One last possibly stupid question: the two TikZ demos run some fairly simple TikZ code. I see where there's room to add TikZ options, but there are limitations on what can go there.

How hard is it to set things up to load various TikZ libraries -- In particular, what if one wants to use pgfplots within a TikZ image? Experimenting suggests that the TikZ options can't contain preamble elements. Is there a place to put these?

@mgage
Copy link
Member

mgage commented Jun 4, 2020

If you can point us to several "real" TikZ problems that use libraries and preambles we can figure out how to add them to the current implementation. The 'examples' available at the moment were kludged together to test the proof-of-concept implementation that we've started with. What we need now is exactly what you are providing -- people who want to use TikZ for educational problems -- so that we can see what else needs to be done to make those problems run.

@drgrice1
Copy link
Member Author

drgrice1 commented Jun 4, 2020

I suspected that this question would come up. It wouldn't be hard to add options to the TikZImage.pm file for adding additional latex packages like pgfplots (pgfplots is not a tikz library, it is a latex package). Note that additional tikz libraries can already be added. Add them as in the following example:

$image = createTikzImage();
$image->tikzLibraries("calc,arrows.meta");

@sean-fitzpatrick
Copy link

So, here is the use case for us: we have a work in progress conversion of APEX Calculus from LaTeX into PreTeXt. Greg has a lot of exercises that have TikZ images (including pgfplots).

@Alex-Jordan has done a lot of work to get all the exercises coded as PreTeXt WeBWorK in the earlier chapters. Frequency of TikZ images increases in later chapters (esp. applications of integration).

So we have problems in the book that are currently in some intermediate state, like this one:

<exercise>
        <!-- <webwork>
            <pg-code>
              $x0 = Compute("-1");
              $x1 = Compute("1");
              $f = Formula("-3x^3+2x+2");
              $g = Formula("x^2+x-1");
              $F = Formula("-x^4/3+3x^2/2+2x");
              $G = Formula("x^3/3+x^2/2-x");
              $D = Formula("$F-$G");
              $area = $D->eval(x=>$x1) - $D->eval(x=>$x0);
            </pg-code> -->
            <statement>
              <p>
                Find the area of the shaded region in the graph below.
              </p>
              <sidebyside width="47%">
            <!-- START figures/fig_07_01_ex_05.tex -->
                <image xml:id="img_07_01_ex_05">
                  <description></description>
                  <latex-image>

                  \begin{tikzpicture}

                  \begin{axis}[
                  axis on top,
                  xtick={-1,1},
                  ytick={-1,1,2,3},
                  ymin=-1.5,ymax=3.5,
                  xmin=-1.1,xmax=1.1
                  ]

                  \addplot [name path=A,firstcurvestyle,-,domain=-1.05:1.05] {x^2+x-1} node [shift={(-35pt,-60pt)},black] {\scriptsize $y=x^2+x-1$};
                  \addplot [name path=B,firstcurvestyle,-,domain=-1.05:1.05,samples=60] {-3*x^3+3*x+2} node [shift={(-120pt,25pt)},black] {\scriptsize $y=-3x^3+3x+2$};

                  \addplot [firstcurvestyle,areastyle] fill between [of=A and B,soft clip={domain=-1:1}];

                  \end{axis}

                  \end{tikzpicture}

                  </latex-image>
                </image>
            <!-- figures/fig_07_01_ex_05.tex END -->
              </sidebyside>
              <!-- <p>
                <var name="$area" width="10"/>
              </p> -->
  <!-- 10/3 -->
            </statement>
            <answer>
              <p>
                <m>10/3</m>
              </p>
            </answer>
        <!-- </webwork> -->
      </exercise>

The webwork parts of the exercise are commented out so we can keep the TikZ image. (In this case we probably could replace it by a WeBWorK graph, but keeping TikZ would be nicer.)

What you can't see in the above is the latex preamble that gets added in by an image processing script. This is where things like \usepackage{pgfplots} gets loaded, along with a lot of styling options on things like curve style and axis format.

So if TikZ support goes live in 2.16, we'd need to figure out how PreTeXt should communicate the different pieces to the WeBWorK server to build the pg file.

Here's the image preamble that gets loaded at the top of every tikz_image.tex file that gets extracted from PreTeXt source. I guess if we had a dedicated WeBWorK server for handling APEX PreTeXt, we would need to put all this in the TikZImage.pm file.

<latex-image-preamble>
      \usepackage{pgfplots}
      \usepackage{tikz-cd}
      \usetikzlibrary{positioning,matrix,arrows,arrows.meta}

      \usetikzlibrary{shapes,decorations,shadows,fadings}
      \usepgfplotslibrary{fillbetween,decorations.softclip,polar}

      \setlength{\marginparwidth}{215pt}

      \usepackage{tkz-euclide}
      %\usetkzobj{all}

      \usepackage{ifthen}

      \newboolean{colorprint}
      \setboolean{colorprint}{true}

      \colorlet{firstcolor}{blue}
      \colorlet{secondcolor}{red}
      \colorlet{thirdcolor}{magenta}
      \pgfplotsset{firstcurvestyle/.style={color=firstcolor,mark=none,thick,{Kite}-{Kite},solid,fill=firstcolor!50,fill=none}}
      \pgfplotsset{secondcurvestyle/.style={color=secondcolor,mark=none,thick,{Kite}-{Kite},dashdotted,fill=secondcolor!50,fill=none}}
      \pgfplotsset{thirdcurvestyle/.style={color=thirdcolor,mark=none,thick,{Kite}-{Kite},dashdotdotted,fill=thirdcolor!50,fill=none}}
      \pgfplotsset{areastyle/.style={fill,opacity=0.5,draw=none}}\pgfplotsset{tangentline/.style={color=black,mark=none,thick,{Kite}-{Kite},solid}}
      \pgfplotsset{tangentline/.style={color=black,mark=none,thick,{Kite}-{Kite},solid}}
      \pgfplotsset{tangentlineseg/.style={color=black,mark=none,thick,-,solid}}
      \pgfplotsset{lineseg/.style={color=black,mark=none,solid}}
      \pgfplotsset{normalline/.style={color=black,mark=none,thick,{Kite}-{Kite},dashed}}
      \pgfplotsset{normallineseg/.style={color=black,mark=none,thick,-,dashed}}
      \pgfplotsset{secantline/.style={color=black,mark=none,thin,{Kite}-{Kite},dashed}}
      \pgfplotsset{secantlineseg/.style={color=black,mark=none,thin,-,dashed}}
      \pgfplotsset{asymptote/.style={color=black,mark=none,thick,{Kite}-{Kite},dashed}}
      \pgfplotsset{guideline/.style={color=black,mark=none,-}}
      \pgfplotsset{symmetryline/.style={color=black,mark=none,-,dashed}}
      \pgfplotsset{openinterval/.style={color=black,mark=none,ultra thick,{Parenthesis}-{Parenthesis}}}
      \pgfplotsset{closedinterval/.style={color=black,mark=none,ultra thick,{Bracket}-{Bracket}}}

      \pgfplotscreateplotcyclelist{curvestylelist}{%
        firstcurvestyle\\%
        secondcurvestyle\\%
        thirdcurvestyle\\%
      }

      %To disable arrows, edit these and the above lines accordingly
      \pgfplotsset{leftarrow/.style={{Kite}-}}
      \pgfplotsset{rightarrow/.style={-{Kite}}}

      % Redefine these to be empty to turn off axis discontinuities
      \pgfplotsset{xdiscontinuity/.style={axis x discontinuity=parallel}}
      \pgfplotsset{ydiscontinuity/.style={axis y discontinuity=crunch}}

      \pgfplotsset{hollowdot/.style={color=firstcolor,fill=white,only marks,mark=*}}
      \pgfplotsset{soliddot/.style={color=firstcolor,fill=firstcolor,only marks,mark=*}}

      \pgfplotsset{every axis/.append style = {
        cycle list name = curvestylelist,
        %tick label style = {font = \scriptsize},
        axis x line = middle,
        axis y line = middle,
        xlabel = {$x$},
        ylabel = {$y$},
        %x label style = {font = \scriptsize},
        %y label style = {font = \scriptsize},
        minor x tick num = 1,
        minor y tick num = 1,
        %width = {ifthenelse(.9\linewidth>240pt,240pt,.9\linewidth)},
        name=myplot,
      }}

      \pgfplotsset{numberline/.style = {
        xmin=-10,xmax=10,
        minor xtick={-11,-10,...,11},
        xtick={-10,-5,...,10},
        axis y line=none,
        every axis x label/.style={at={(current axis.right of origin)},anchor=west},
        y=15pt,
        axis lines=middle,
        enlarge x limits,
        xlabel={},
        grid=none,
        clip=false,
        axis background/.style={},
      }}
    </latex-image-preamble>

@Alex-Jordan
Copy link
Contributor

Does the current implementation of this allow for dynamic images? For example, can I set $m = random(1,3,1); and then make a plot of y=$m x?

If not, then I think we (PreTeXt) do not need this right now. The right approach would just be for PTX to build image files from tikz in the PTX source, and those image files should be automatically packaged alongside the .pg files that PTX makes.

We are interested in being able to make randomized versions of images too, so that we can code the PG problems to be randomizable. If that is part of this project, I'll think harder.

@drgrice1
Copy link
Member Author

drgrice1 commented Jun 4, 2020

Yes, this does allow for dynamic images. You can make a plot involving random parameters.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants