[Tex/LaTex] Pgfplot – Cross section of a 3D line plot (Poincare Sections)

pgfplotstikz-pgf

I have plotted a 3D line using this following data:

p p1t p2t
-65.79  -210.81 137.73
-124.76 -182.7  189.67
-170.78 -141.97 233.17
-206.39 -96.42  257.48
-226.99 -40.212 268.45
-231.57 20.337  255.59
-226.75 78.518  223.62
-210.81 137.73  175.85
-182.7  189.67  113.02
-141.97 233.17  46.467
-96.42  257.48  -21.029
-40.212 268.45  -88.289
20.337  255.59  -145.29
78.518  223.62  -187.76
137.73  175.85  -219.49
189.67  113.02  -236.46
233.17  46.467  -239.94
257.48  -21.029 -232.83
268.45  -88.289 -215.23
255.59  -145.29 -188.55
223.62  -187.76 -150.57
175.85  -219.49 -105.58
113.02  -236.46 -53.317
46.467  -239.94 8.5742
-21.029 -232.83 69.439
-88.289 -215.23 133.3
-145.29 -188.55 189.99
-187.76 -150.57 237.67
-219.49 -105.58 270.35
-236.46 -53.317 280.53
-239.94 8.5742  273.67
-232.83 69.439  242.25
-215.23 133.3   192.67
-188.55 189.99  124.54
-150.57 237.67  54.914
-105.58 270.35  -17.003
-53.317 280.53  -84.499
8.5742  273.67  -144.65
69.439  242.25  -186.34
133.3   192.67  -215.7
189.99  124.54  -232.52
237.67  54.914  -232.44
270.35  -17.003 -224.46
280.53  -84.499 -207.1
273.67  -144.65 -179.78
242.25  -186.34 -143
192.67  -215.7  -100.92
124.54  -232.52 -51.028
54.914  -232.44 5.9691
-17.003 -224.46 64.545
-84.499 -207.1  124.38
-144.65 -179.78 178.78
-186.34 -143    225.43
-215.7  -100.92 259.53
-232.52 -51.028 273.98
-232.44 5.9691  271.22
-224.46 64.545  241.22
-207.1  124.38  191.33
-179.78 178.78  128.33
-143    225.43  57.519
-100.92 259.53  -12.74
-51.028 273.98  -82.841
5.9691  271.22  -138.81
64.545  241.22  -184.6
124.38  191.33  -216.97
178.78  128.33  -231.49
225.43  57.519  -232.67

The plot will look like this.
enter image description here
Now,

  1. I would like to plot a cross-section of this 3D plot (i.e a 2D plot – a plane that for instance passes through p1=0)

  2. I want a dotted rectangle in the 3D plot to represent which cross-section I'm plotting.

  3. How do I make the x, y, and z labels parallel to their respective axes?

Here is a MWE:

\documentclass{standalone}
\usepackage{pgfplots}
\usepackage{pgfplotstable}
\usepackage{graphicx}
\usepackage{tikz}
\usepackage{pgf}
\usepackage{mathtools}
\pgfplotsset{compat=newest}
\begin{document}
\begin{tikzpicture}
\begin{axis}[xlabel=p1, ylabel=p1t, zlabel=p2t, tick style={draw=none}]

\addplot3[smooth, mark=none, color=black] table [x=p, y=p1t, z=p2t]{dummy.txt};

\end{axis}
\end{tikzpicture}
\end{document}

Progress Update: Although there is a method to do this for surface plots, the same doesn't work for line plots.

Best Answer

I would use a split approach, really -- I am posting this here because I am sure that someone with Lua skills will integrate it in a standalone LaTeX source. It happens I know python... and I will learn from the other answer :-)

So I created this quick and dirty python script to find the intercepts, by linear interpolation:

#! /usr/bin/env python3
#
# use as ./process.py filename x-coordinate-to-cut
# 
import sys
xcut = float(sys.argv[2])
with open(sys.argv[1]) as f:
    i=-1
    for line in f:
        i += 1
        if i==0:
            print ("p1t p2t")
            continue # skip first line
        data = [float(f) for f in line.split()]
        if i==1:
            old_data = data 
            continue
        if (old_data[0] <= xcut and data[0] > xcut) or (old_data[0] >= xcut and data[0] < xcut):
            # crossing the plane
            y = old_data[1] + (data[1]-old_data[1])/(data[0]-old_data[0])*(xcut - old_data[0])
            z = old_data[2] + (data[2]-old_data[2])/(data[0]-old_data[0])*(xcut - old_data[0])
            print("%g %g" % (y,z))
        old_data = data

And use it to create data points for the cut at p=0:

./process.py dummy.txt 0.0 > cross0.txt
./process.py dummy.txt 100.0 > cross100.txt
./process.py dummy.txt 200.0 > cross200.txt

and now with the source:

\documentclass[border=10pt]{standalone}
\usepackage{pgfplots}\pgfplotsset{compat=1.13}
\usepackage{pgfplotstable}
\usepackage{graphicx}
\usepackage{tikz}
\usepackage{pgf}
\usepackage{mathtools}
\pgfplotsset{compat=newest}
\begin{document}
\begin{tikzpicture}
\begin{axis}[xlabel=p1, ylabel=p1t, zlabel=p2t, tick style={draw=none},
    xmin=-300, xmax=300, ymin=-300, ymax=300, zmin=-300, zmax=300]
    \addplot3[smooth, mark=none, color=black] table [x=p, y=p1t, z=p2t]{dummy.txt};
    \draw [dashed, red] (0,-300,-300) -- (0,300,-300) -- (0,300,300) -- (0,-300,300) -- cycle; 
    \draw [dashed, blue] (100,-300,-300) -- (100,300,-300) -- (100,300,300) -- (100,-300,300) -- cycle; 
    \draw [dashed, green] (200,-300,-300) -- (200,300,-300) -- (200,300,300) -- (200,-300,300) -- cycle; 
\end{axis}
\end{tikzpicture}
\begin{tikzpicture}
    \begin{axis}[xlabel=p1t, ylabel=p2t, tick style={draw=none},
        xmin=-300, xmax=300, ymin=-300, ymax=300]
        \addplot [red, only marks] table [x=p1t, y=p2t]{cross0.txt};
        \addplot [blue, only marks] table [x=p1t, y=p2t]{cross100.txt};
        \addplot [green, only marks] table [x=p1t, y=p2t]{cross200.txt};
        \legend{$p=0$, $p=100$, $p=200$}
    \end{axis}
\end{tikzpicture}

\end{document}

I have the result:

Ok, now it's the correct one

which obviously needs a bit of love to massage a bit, but I think it's more or less what the OP wanted.