1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
|
%% $Id: pst-node-doc.tex 304 2010-04-22 08:23:39Z herbert $
\documentclass[11pt,english,BCOR10mm,DIV12,bibliography=totoc,parskip=false,smallheadings
headexclude,footexclude,oneside]{pst-doc}
\listfiles
\usepackage[utf8]{inputenc}
\usepackage{pst-plot}
\usepackage{pst-node}
\let\pstFV\fileversion
\let\belowcaptionskip\abovecaptionskip
%
\newcommand\xstrut{\vphantom{\tabular{c}Üg\\Üg\endtabular}}
\newcommand\psBox[3][white]{\rput(#2){\rnode{#2}{%
\psframebox[fillcolor=#1]{\xstrut\makebox[3.2cm]{\tabular{c}#3\endtabular}}}}}
\def\bgImage{%
\psscalebox{0.85}{%
\begin{pspicture}(-1,-1)(21,7)
\psset{framearc=0.2,shadow=true,fillstyle=solid,shadowcolor=black!55}
\psBox[blue!30]{7,6}{politische\\Kommunikation}
\psBox[red!30]{3,4}{interpersonale\\Kommunikation}
\psBox[red!30]{13,4}{massenmediale\\Kommunikation}
\psBox[green!30]{1,2}{starke\\Beziehung}
\psBox[green!30]{5,2}{schwache\\Beziehung}
\psBox[green!30]{9,2}{Fernsehen}
\psBox[green!30]{17,2}{Zeitungen}
\psBox[cyan!30]{7,0}{öffentlich-rechtl.\\Fernsehen}
\psBox[cyan!30]{11,0}{privates\\Fernsehen}
\psBox[cyan!30]{15,0}{Boulevard-\\Zeitungen}
\psBox[cyan!30]{19,0}{Abonnement-\\Zeitungen}
\end{pspicture}
\psset{shadow=false,angleA=-90,angleB=90,linewidth=2pt}
\ncangles{7,6}{3,4}\ncangles{7,6}{13,4}
\ncangles{3,4}{1,2}\ncangles{3,4}{5,2}
\ncangles{13,4}{9,2}\ncangles{13,4}{17,2}
\ncangles{9,2}{7,0}\ncangles{9,2}{11,0}
\ncangles{17,2}{15,0}\ncangles{17,2}{19,0}}
}
\lstset{explpreset={pos=l,width=-99pt,overhang=0pt,hsep=\columnsep,vsep=\bigskipamount,rframe={}}}
\begin{document}
\title{\texttt{pst-node}\\Nodes and node connections%
\\\small v.\pstFV}
%\docauthor{Michael Sharpe\\Herbert Vo\ss}
\author{Timothy Van Zandt\\Michael Sharpe\\Herbert Vo\ss}
\date{\today}
\maketitle
\begin{abstract}
This version of \LPack{pst-node} uses the extended keyval handling
of pst-xkey and has a lot of the macros which were recently in
the package \LPack{pstricks-add}. This documentation describes in the first part
the basic node commands and connection from the old PSTricks documentation.
The second part describes only the
new and changed stuff. .
\vfill
\noindent
Thanks to: Denis Girou; Rolf Niepraschk; Sebastian Rahtz;
\end{abstract}
\clearpage
\tableofcontents
\clearpage
\part{Basic commands, connections and labels}
The following pages are from the original documentation of
\PST. This documentation file \LFile{pst-docfull} should be part of any
\TeX\ distribution and was inserted here with the following command:
\verb+\includepdf[pages=6-32]{pst-docfull}+
\clearpage
\setcounter{page}{33}
\part{New commands}
%--------------------------------------------------------------------------------------
\section{Relative nodes with \nxLcs{psGetNodeCenter}}
%--------------------------------------------------------------------------------------
\begin{BDef}
\Lcs{psGetNodeCenter}\Largb{node name}\\
%\Lcs{psGetNodeEdgeA}\Largb{node type}\Largb{node name}
\end{BDef}
This command makes sense only at
the PostScript level. It defines the two variables \Larg{node.x}
and \Larg{node.y} which can be used to define relative nodes. The
following example defines the node \verb+MyNode+ and a second one
relative to the first one, with 4 units left and 4 units up.
\Larg{node} must be an existing node name.
\begin{LTXexample}[width=5cm]
\begin{pspicture}[showgrid=true,arrowscale=2](5,5)
\pnode(4.5,0.5){MyNode}
\psdot(MyNode)
\pnode(! \psGetNodeCenter{MyNode}
MyNode.x 4 sub MyNode.y 4 add){MySecondNode}
\psdot(MySecondNode)
\ncline[linecolor=red]{<->}{MyNode}{MySecondNode}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=5cm]
\begin{pspicture}[showgrid=true](5,5)
\rput(1.5,0.5){\trinode{CN}{NodeA}}
\rput(3.5,2.5){\trinode{EN}{NodeB}}
\pnode(! \psGetNodeCenter{CN}
CN.x 2 add CN.y 1 add ){MyCNode}
\ncline[linecolor=red]{<->}{MyCNode}{EN}
\ncline[linecolor=blue]{<->}{CN}{EN}
\end{pspicture}
\end{LTXexample}
%--------------------------------------------------------------------------------------
\section{\nxLcs{ncdiag} and \nxLcs{pcdiag}}
%--------------------------------------------------------------------------------------
With the new option \Lkeyword{lineAngle} the lines drawn by the \Lcs{ncdiag} macro
can now have a specified gradient. Without this option one has to define the two
arms (which maybe zero) and PSTricks draws the connection between them. Now there
is only a static \Lkeyword{armA}, the second one \Lkeyword{armB} is calculated when an angle
\Lkeyword{lineAngle} is defined. This angle is the gradient of the intermediate line
between the two arms. The syntax of \Lcs{ncdiag} is
\begin{BDef}
\Lcs{ncdiag}\OptArgs\Largb{node A}\Largb{node B}\\
\Lcs{pcdiag}\OptArgs\Largs{node A}\Largs{node B}
\end{BDef}
\begin{tabularx}{\linewidth}{l|X}
name & meaning\\\hline
\Lkeyword{lineAngle} & angle of the intermediate line segment. Default is 0, which is the same
than using \Lcs{ncdiag} without the \Lkeyword{lineAngle} option.\tabularnewline
\end{tabularx}
\begin{LTXexample}[width=5.5cm]
\begin{pspicture}(5,6)
\circlenode{A}{A}\quad\circlenode{C}{C}%
\quad\circlenode{E}{E}
\rput(0,4){\circlenode{B}{B}}
\rput(1,5){\circlenode{D}{D}}
\rput(2,6){\circlenode{F}{F}}
\psset{arrowscale=2,linearc=0.2,%
linecolor=red,armA=0.5, angleA=90,angleB=-90}
\ncdiag[lineAngle=20]{->}{A}{B}
\ncput*[nrot=:U]{line I}
\ncdiag[lineAngle=20]{->}{C}{D}
\ncput*[nrot=:U]{line II}
\ncdiag[lineAngle=20]{->}{E}{F}
\ncput*[nrot=:U]{line III}
\end{pspicture}
\end{LTXexample}
The \Lcs{ncdiag} macro sets the \Lkeyword{armB} dynamically to the calculated value. Any
user setting of \Lkeyword{armB} is overwritten by the macro. The \Lkeyword{armA} could be set to
a zero length:
\begin{LTXexample}[width=4.5cm]
\begin{pspicture}(4,3)
\rput(0.5,0.5){\circlenode{A}{A}}
\rput(3.5,3){\circlenode{B}{B}}
{\psset{linecolor=red,arrows=<-,arrowscale=2}
\ncdiag[lineAngle=60,%
armA=0,angleA=0,angleB=180]{A}{B}
\ncdiag[lineAngle=60,%
armA=0,angleA=90,angleB=180]{A}{B}}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=4.5cm]
\begin{pspicture}(4,3)
\rput(1,0.5){\circlenode{A}{A}}
\rput(4,3){\circlenode{B}{B}}
{\psset{linecolor=red,arrows=<-,arrowscale=2}
\ncdiag[lineAngle=60,
armA=0.5,angleA=0,angleB=180]{A}{B}
\ncdiag[lineAngle=60,
armA=0,angleA=70,angleB=180]{A}{B}
\ncdiag[lineAngle=60,
armA=0.5,angleA=180,angleB=180]{A}{B}}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=4.5cm]
\begin{pspicture}(4,5.5)
\cnode*(0,0){2pt}{A} \cnode*(0.25,0){2pt}{C}
\cnode*(0.5,0){2pt}{E}\cnode*(0.75,0){2pt}{G}
\cnode*(2,4){2pt}{B} \cnode*(2.5,4.5){2pt}{D}
\cnode*(3,5){2pt}{F} \cnode*(3.5,5.5){2pt}{H}
{\psset{arrowscale=2,linearc=0.2,
linecolor=red,armA=0.5, angleA=90,angleB=-90}
\pcdiag[lineAngle=20]{->}(A)(B)
\pcdiag[lineAngle=20]{->}(C)(D)
\pcdiag[lineAngle=20]{->}(E)(F)
\pcdiag[lineAngle=20]{->}(G)(H)}
\end{pspicture}
\end{LTXexample}
%--------------------------------------------------------------------------------------
\section{\nxLcs{ncdiagg} and \nxLcs{pcdiagg}}
%--------------------------------------------------------------------------------------
This is nearly the same as \Lcs{ncdiag} except that
\Lkeyword{armB}=0 and the \Lkeyword{angleB} value is computed by the
macro, so that the line ends at the node with an angle like a
\Lcs{pcdiagg} line. The syntax of \Lcs{ncdiagg}/\Lcs{pcdiagg}
is
\begin{BDef}
\Lcs{ncdiag}\OptArgs\Largb{node A}\Largb{node B}\\
\Lcs{pcdiag}\OptArgs\Largs{node A}\Largs{node B}
\end{BDef}
\begin{LTXexample}[width=5cm]
\begin{pspicture}(4,6)
\psset{linecolor=black}
\circlenode{A}{A}\quad\circlenode{C}{C}\quad%
\circlenode{E}{E}
\rput(0,4){\circlenode{B}{B}}
\rput(1,5){\circlenode{D}{D}}
\rput(2,6){\circlenode{F}{F}}
{\psset{arrowscale=2,linearc=0.2,
linecolor=red,armA=0.5, angleA=90}
\ncdiagg[lineAngle=-160]{->}{A}{B}
\ncput*[nrot=:U]{line I}
\ncdiagg[lineAngle=-160]{->}{C}{D}
\ncput*[nrot=:U]{line II}
\ncdiagg[lineAngle=-160]{->}{E}{F}
\ncput*[nrot=:U]{line III}}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=5cm]
\begin{pspicture}(4,6)
\psset{linecolor=black}
\cnode*(0,0){2pt}{A} \cnode*(0.25,0){2pt}{C}
\cnode*(0.5,0){2pt}{E}\cnode*(0.75,0){2pt}{G}
\cnode*(2,4){2pt}{B} \cnode*(2.5,4.5){2pt}{D}
\cnode*(3,5){2pt}{F} \cnode*(3.5,5.5){2pt}{H}
{\psset{arrowscale=2,linearc=0.2,
linecolor=red,armA=0.5, angleA=90}
\pcdiagg[lineAngle=20]{->}(A)(B)
\pcdiagg[lineAngle=20]{->}(C)(D)
\pcdiagg[lineAngle=20]{->}(E)(F)
\pcdiagg[lineAngle=20]{->}(G)(H)}
\end{pspicture}
\end{LTXexample}
The only catch for \Lcs{ncdiagg} is that you need the right
value for \Lkeyword{lineAngle}. If the node connection is on the wrong
side of the second node, then choose the corresponding angle,
e.\,g.: if $20$ is wrong then take $-160$, which differs by $180$.
\begin{LTXexample}[width=4cm]
\begin{pspicture}(4,1.5)
\circlenode{a}{A}
\rput[l](3,1){\rnode{b}{H}}
\ncdiagg[lineAngle=60,angleA=180,armA=.5,nodesepA=3pt,linecolor=blue]{b}{a}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=4cm]
\begin{pspicture}(4,1.5)
\circlenode{a}{A}
\rput[l](3,1){\rnode{b}{H}}
\ncdiagg[lineAngle=60,armA=.5,nodesepB=3pt,linecolor=blue]{a}{b}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=4cm]
\begin{pspicture}(4,1.5)
\circlenode{a}{A}
\rput[l](3,1){\rnode{b}{H}}
\ncdiagg[lineAngle=-120,armA=.5,nodesepB=3pt,linecolor=blue]{a}{b}
\end{pspicture}
\end{LTXexample}
%--------------------------------------------------------------------------------------
\section{\nxLcs{ncbarr}}
%--------------------------------------------------------------------------------------
This has the same behaviour as \Lcs{ncbar}, but has 5 segments
and all are horizontal ones. This is the reason why \Lkeyword{angleA}
must be $0$ or alternatively $180$. All other values are set to
$0$ by the macro. The intermediate horizontal line is symmetrical
to the distance of the two nodes.
\begin{BDef}
\Lcs{ncbarr}\OptArgs\Largb{node A}\Largb{node B}\\
\end{BDef}
\begin{LTXexample}[width=3.5cm]
\psset{arrowscale=2}%
\circlenode{X}{X}\\[1cm]
\circlenode{Y}{Y}
\ncbarr[angleA=0,arrows=->,arrowscale=2]{X}{Y}
\end{LTXexample}
\begin{LTXexample}[width=3.5cm]
\psset{arrowscale=2}%
\ovalnode{X}{Xxxxx}\\[1cm]
\circlenode{Y}{Yyyy}
\ncbarr[angleA=180,arrows=->,arrowscale=2,linecolor=red]{X}{Y}
\end{LTXexample}
\begin{LTXexample}[width=3.5cm]
\psset{arrowscale=2}%
\ovalnode{X}{Xxxxx}\\[1cm]
\circlenode{Y}{Yyyy}
\ncbarr[angleA=20,arm=1cm,arrows=->,arrowscale=2]{X}{Y}
\end{LTXexample}
%--------------------------------------------------------------------------------------
\section{\nxLcs{psLNode} and \nxLcs{psLCNode}}
%--------------------------------------------------------------------------------------
\Lcs{psLNode} interpolates the Line $\overline{AB}$ by the given value and sets a node at this
point. The syntax is
%
\begin{BDef}
\Lcs{psLNode}\Largs{P1}\Largs{P2}\Largb{value}\Largb{node name}\\
\Lcs{psLCNode}\Largs{P1}\Largb{value 1}\Largs{P2}\Largb{value 2}\Largb{node name}
\end{BDef}
\begin{LTXexample}[width=5cm]
\begin{pspicture}(5,5)
\psgrid[subgriddiv=0,griddots=10]
\psset{linecolor=red}
\psline{o-o}(1,1)(5,5)
\psLNode(1,1)(5,5){0.75}{PI}
\qdisk(PI){4pt}
\psset{linecolor=blue}
\psline{o-o}(4,3)(2,5)
\psLNode(4,3)(2,5){-0.5}{PII}
\qdisk(PII){4pt}
\end{pspicture}
\end{LTXexample}
\bigskip
The \Lcs{psLCNode} macro builds the linear combination of the two given
vectors and stores the end of
the new vector as a node. All vectors start at $(0,0)$, so a \Lcs{rput} maybe
appropriate. The syntax is
\begin{LTXexample}[width=5cm]
\begin{pspicture}[showgrid=true](5,3)
\psset{linecolor=black}
\psline[linestyle=dashed]{->}(3,1.5)
\psline[linestyle=dashed]{->}(0.375,1.5)
\psset{linecolor=red}
\psline{->}(2,1)\psline{->}(0.5,2)
\psLCNode(2,1){1.5}(0.5,2){0.75}{PI}
\psline[linewidth=2pt]{->}(PI)
\psset{linecolor=black}
\psline[linestyle=dashed](3,1.5)(PI)
\psline[linestyle=dashed](0.375,1.5)(PI)
\end{pspicture}
\end{LTXexample}
%--------------------------------------------------------------------------------------
\section{\nxLcs{nlput} and \nxLcs{psLDNode}}
%--------------------------------------------------------------------------------------
\Lcs{ncput} allows you to set a label relative to the first node
of the last node connection. With \Lcs{nlput} this can be done
absolute to a given node. The syntax is different to the other
node connection macros. It uses internally the macro
\Lcs{psLDNode} which places a node absolute to two given points,
starting from the first one.
\begin{BDef}
\Lcs{nlput}\OptArgs\Largs{A}\Largs{B}\Largb{distance}\Largb{text}\\
\Lcs{psLDNode}\OptArgs\Largs{A}\Largs{B}\Largb{distance}\Largb{node name}
\end{BDef}
\begin{LTXexample}[width=5cm]
\begin{pspicture}(5,2)
\pnode(0,0){A}
\pnode(5,2){B}
\ncline{A}{B}
\psLDNode(A)(B){1.5cm}{KN}\qdisk(KN){2pt}
\nlput[nrot=:U](A)(B){1cm}{Test}
\nlput[nrot=:D](A)(B){2cm}{Test}
\nlput[nrot=:U](A)(B){3cm}{Test}
\nlput(A)(B){4cm}{Test}
\end{pspicture}
\end{LTXexample}
\section{Extensions}
\subsection{Quick overview}
All macros in this section are connected in one way or other with the
construction or deployment of
one or more nodes of type \Lcs{pnode}, which is to say in effect,
named points. For the remainder of this section, node always means \Lcs{pnode}.
Nodes are one of
the most powerful features of pstricks---the ``trickiest tricks'' in the words of
its originator. If used without appropriate caution, they can produce PostScript errors
that can be difficult to track down. For example, suppose you have defined a node \texttt{A}
by \verb|\pnode(1,1){A}|, and then, a little later, you want to move the node a bit to the
right, and you write \verb|\pnode([nodesep=.5cm]A){A}|. On processing the file you will
see an error message from ghostscript: \Lps{stackunderflow}\verb| in --exch--|.
The lesson is: you may not assign a node name if a node by that name is involved
explicitly in its definition. To reassign a node name safely, you have to write instead something like
\begin{verbatim}
\pnode([nodesep=.5cm]A){Atemp}
\pnode(Atemp){A}
\end{verbatim}
This problem afflicts a number of other node-forming macros based on a \Lcs{pnode} construction, as most are.
Nodes are more complicated than they appear. Each node is stored not only with a recipe
for finding its coordinates, but also with the coordinate system in effect when it was
defined. Part of the retrieval process involves modifying the coordinates if necessary
so that they represent the same point on the page even if the coordinate system has
changed. This is important, but has some unexpected consequences. Normally, the simplest
way to translate an object is with \Lcs{rput}.
\begin{verbatim}
\pnode(1,1){P}% define P as (1,1)
\rput(2,3){\psdot{P}}% places dot at original P=(1,1)
\end{verbatim}
is different from
\begin{verbatim}
\rput(2,3){\pnode(1,1){P}\psdot{P}}
% places dot at (1,1)+(2,3)
\end{verbatim}
Effectively, \Lcs{rput} and \Lcs{uput} are not useful for translating previously
defined nodes, but they are useful for defining new nodes relative to fixed positions.
The new macros in this section
are of several kinds: (i) utility macros, some used
internally by the package and some of general use; (ii) macros that manipulate one or
more nodes to produce other nodes; (iii) constructions intended to be used with nodes and
node sequences. By a node sequence is meant one or more nodes having a common root name
followed by an index---eg, P0 P1 P2 ... P5 is a node sequence with root name P. It is
easy to define such node sequences using the \Lcs{multido} macro, or using one of a
number of macros in this section.
\subsection{Node expressions}
A number of macros in the package (eg, \Lcs{psxline}) permit the use of node expressions,
by which is meant an expression like
\begin{verbatim}
.25(1,3)+.333(2;90)-1.2([nodesep=.5cm]Q)
\end{verbatim}
which specifies a linear combination of points (the items enclosed in parentheses)
specified in any manner acceptable to \Lcs{SpecialCoor}.
%The items themselves cannot
%themselves be node expressions, as they are not acceptable to \Lcs{SpecialCoor}.
Node expressions are handled by \Lcs{nodexn}, which calls the macros \Lcs{hasparen} and
\Lcs{parsenodexn} to do the real work. If you write code that needs to be able to handle node expressions, you use
\begin{BDef}
\Lcs{nodexn}\Largb{expr}\Largb{nodename}
\end{BDef}
which returns a node \verb|<nodename>| once \verb|<expr>| has been fully parsed. It is safe to
reuse a node name, as in
\begin{verbatim}
\nodexn{(P)+.5(1,2)}{P}
\end{verbatim}
The following macros amount to special cases of node expressions.
\begin{BDef}
\Lcs{AtoB}\Largr{A}\Largr{B}\Largb{C}
\end{BDef}
defines a node by name C essentially as B-A, as vectors. It is safe to use
\Lcs{AtoB}\verb|(Q)(P){P}| and \Lcs{AtoB}\verb|(Q)(P){Q}|.
\begin{BDef}
\Lcs{AplusB}\Largr{A}\Largr{B}\Largb{C}
\end{BDef}
defines node by name C essentially as A+B, as vectors. It is safe to use
\Lcs{AplusB}\verb|(Q)(P){P}| and \Lcs{AplusB}\verb|(Q)(P){Q}|.
\begin{BDef}
\Lcs{midAB}\Largr{A}\Largr{B}\Largb{C}
\end{BDef}
defines node by name C essentially as $(A+B)/2$, as vectors. It is safe to use \Lcs{midAB}\verb|(Q)(P){P}|
and \Lcs{midAB}\verb|(Q)(P){Q}|.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,2.5)
\psset{arrows=->,arrowscale=1.5}
\pnode(2,1){P}\pnode(.5,1){Q}
\AtoB(Q)(P){QP}
\AplusB(Q)(P){R}
\psline(0,0)(P)\uput[-45](P){P}
\psline(0,0)(Q)\uput[135](Q){Q}
\psline(0,0)(QP)\uput[-70](QP){QP}
\psline(0,0)(R)\uput[160](R){R}
\psline[linestyle=dashed](Q)(P)
\psline[linestyle=dashed](Q)(R)
\psline[linestyle=dashed](P)(R)
\end{pspicture}
\end{LTXexample}
\subsection{The main macros}
\begin{BDef}
\Lcs{normalvec}\Largr{coords}\Largb{nodename}
\end{BDef}
For example,
\begin{verbatim}
\normalvec(P){P}\normalvec(2;30){Q}
\end{verbatim}
first redefines the node {\tt P} as a node whose vector interpretation is of the same
length as the original {\tt P}, but rotated 90 degrees. The second instance has the
same effect as \Lcs{pnode}\verb|(2;120){Q}|.
\begin{BDef}
\Lcs{curvepnode}\Largb{tval}\Largb{expression in t}\Largb{nodename}
\end{BDef}
For example,
\begin{verbatim}
\curvepnode{1}{cos(t) | sin(t)}{P}
\end{verbatim}
sets a node named {\tt P} at \verb|(cos(1), sin(1))| and a node named {\tt Ptang}
which represents a unit vector in the tangent direction to the curve at {\tt P}.
The expression in {\tt t} in this case is algebraic, which is detected automatically by the macro.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,2)
\def\exn{cos(t) | sin(t)}
\psparametricplot[algebraic]{0}{2}{\exn}
\curvepnode{1}{\exn}{P}
\psdot(P)\uput[45](P){P}
\end{pspicture}
\end{LTXexample}
\vspace{2pc}
\begin{BDef}
\Lcs{psparnode}\Largb{t}\Largb{expression in t}\Largb{<nodename>}
\end{BDef}
is called by the command \Lcs{curvename} if the expression is PostScript, not algebraic.
\begin{BDef}
\Lcs{algparnode}\Largb{t}\Largb{expression in t}\Largb{nodename}
\end{BDef}
is called by the command \Lcs{curvename} if the expression is algebraic, not PostScript.
\begin{BDef}
\Lcs{curvepnodes}\Largb{tmin}\Largb{tmax}\Largb{expr. in t}\Largb{nodeRoot}
\end{BDef}
Uses current setting of plotpoints (default 50) to define a node sequence of points along the curve. Eg,
\begin{verbatim}
\curvepnodes[plotpoints=100]{0}{1}{t+t^2 | Ex(-t)}{P}
\end{verbatim}
sets nodes {\tt P0 .. P99} at equally spaced {\tt t} values along the curve,
and assigns the macro \Lcs{Pnodecount} to 99, the highest index. The expression in {\tt t}
may be either algebraic or PostScript, and is handled automatically. The values
\verb|<tmin>, <tmax>| may be expressed using PostScript---eg, \verb|{Pi neg}{PiDiv2}|.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,3)
\def\exn{t+t^2 | 2*Ex(-t)}
\psset{plotpoints=100}
\psparametricplot[algebraic]{0}{1}{\exn}
\curvepnodes{0}{1}{\exn}{P}
\psdot(P50)\uput[75](P50){P50}
\psdot(P99)\uput[75](P99){P99}
\end{pspicture}
\end{LTXexample}
\begin{BDef}
\Lcs{fnpnode}\Largb{xval}\Largb{expression in x}\Largb{nodename}
\end{BDef}
sets a single node on the graph. Eg,
\begin{verbatim}
\fnpnode{.5}{x x 1 add mul 2 div}{P}
\end{verbatim}
declares the node P at the point x=0.5 on the graph. It has the same effect as
\begin{verbatim}
\pnode(!/x 0.5 def x x x 1 add mul 2 div}){P}
\end{verbatim}
If your expression in {\tt t} is algebraic, you must specify the keyword {\tt algebraic}, as in
\Lcs{fnpnode}\verb|[algebraic]{0.5}{x*(x+1)/2}{P}|.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,3)
\def\exn{x x 1 add mul 2 div}
\psplot{0}{2}{\exn}
\fnpnode{0.5}{\exn}{Q}
\psdot(Q)\uput[-45](Q){Q}
\end{pspicture}
\end{LTXexample}
\vspace{2pc}
\begin{BDef}
\Lcs{fnpnodes}\Largb{xmin}\Largb{xmax}\Largb{expression in x}\Largb{nodeRoot}
\end{BDef}
Is similar to \Lcs{curvenodes}, but for the graph of a function. The keyword \Lkeyword{algebraic}
must be specified if your expression is indeed algebraic.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,3)
\def\exn{x x 1 add mul 2 div}
\psplot{0}{2}{\exn}
\fnpnodes[plotpoints=10]{0}{2}{\exn}{A}
\psdot(A4)\uput[-45](A4){A4}
\end{pspicture}
\end{LTXexample}
\vspace{2pc}
\begin{BDef}
\Lcs{shownode}\Largr{P}
\end{BDef}
is a debugging tool, which displays in the console window the coordinates of node P.
This will not appear until the final stage of processing the PostScript file. You will
get a PostScript error if the node you specify is undefined.
\begin{BDef}
\Lcs{getnodelist}\Largb{node root name}\Largb{next command}
\end{BDef}
is useful in writing pstricks macros, where there is a list of parenthesized coordinates
to be read and turned into a node sequence, following which \verb|<next command>| is followed.
\begin{BDef}
\Lcs{pnodes}\Largb{P}\Largr{1,2}\Largr{2;3}\ldots
\end{BDef}
is effectively \Lcs{getnodelist}\Largb{P}\Largb{}\verb|(1,2)(2;3)...|, just a quick way to
turn a list of coordinates into a node sequence P0 P1 ...
\begin{BDef}
\Lcs{psnline}\OptArgs\Largb{arrows}\Largr{coors}\Largb{name}
\end{BDef}
for example, expects that there are nodes named P3..P8, and gives the same result as
\begin{verbatim}
\psline[linewidth=1pt]{->}(P3)(P4)(P5)(P6)(P7)(P8)
\end{verbatim}
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(2.5,2)
\pnodes{P}(.1,.1)(1;10)(*2 {x^2/4})(0,1.4)
%defines P0..P3--now join them
\psnline[arrowscale=2]{-D>}(0,3){P}
\end{pspicture}
\end{LTXexample}
\vspace{2pc}
\begin{BDef}
\Lcs{psLCNodeVar}\Largr{node A}\Largr{node B}\Largr{factorA,factorB}\Largb{node name}
\end{BDef}
is similar to \Lcs{psLCNode},
and provides a means of forming a linear combination of two nodes, thought of as vectors. Where
\begin{verbatim}
\psLCNode(A){a}(B){b}{C}
\end{verbatim}
effectively makes \verb|C=aA+bB|,
\begin{verbatim}
\psLCNodeVar(A)(B)(a,b){C}
\end{verbatim}
does the same, but the third argument \verb|(a,b)| may be specified in any form acceptable
to \Lcs{SpecialCoor}. (With \Lcs{psLCNode}, each coefficient may be specified in PostScript code.)
One other difference is that \Lcs{psLCNodeVar} allows the reuse of a node name in place. For example,
it is possible to write
\begin{verbatim}
\psLCNodeVar(A)(B)(2,3){A}% symbol A reassigned
\end{verbatim}
where the equivalent in \Lcs{psLCNode} will lead to a PostScript error. Since \Lcs{AtoB} and \Lcs{AplusB}
are defined using \Lcs{psLCNodeVar}, they also allow node name reuse: \Lcs{AtoB}\verb|(Q)(P){P}| is legal.
\begin{BDef}
\Lcs{psRelNodeVar}\Largr{node A}\Largr{node B}\Largr{radius;angle}\Largb{node name}
\end{BDef}
is similar to \Lcs{psRelNode}, and provides a means of scaling and rotating a line segment AB about A. The effect of
\begin{verbatim}
\psRelNodeVar(A)(B)(2;30){C}
\end{verbatim}
is the same as
\begin{verbatim}
\psRelNode[angle=30](A)(B){2}{C}
\end{verbatim}
but the third argument (2;30) may be specified in any form acceptable to \Lcs{SpecialCoor},
while specifying the angle argument in \Lcs{psRelNode} using PostScript is not possible.
Note that \Lcs{psRelNodeVar}\verb|(0,0)(A)(B){C}| may be interpreted as defining {\tt C} to
be the complex product of {\tt A} and {\tt B}.
\begin{LTXexample}[width=5cm]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\pnode(0,.5){P}\pnode(1.5,.75){Q}
\psRelNodeVar(P)(Q)(2;20){R}
\psline(Q)(P)\uput[-45](P){P}
\uput[-70](Q){Q}
\psline(P)(R)\uput[-70](R){R}
\end{pspicture}
\end{LTXexample}
\begin{BDef}
\Lcs{psRelLineVar}\Largr{node A}\Largr{node B}\Largr{radius;angle}\Largb{node name}
\end{BDef}
stands to \Lcs{psRelLine} as \Lcs{psRelNodeVar} stands relative to \Lcs{psRelNode}.
\Lcs{psRelLine}\verb|Var(A)(B)(a;b){C}| defines the node {\tt C}, and, in addition, draws the line segment {\tt AC}.
\begin{BDef}
\Lcs{rhombus}\Largb{edge length}\Largr{A}\Largb{B}\Largb{C}\Largb{D}
\end{BDef}
computes the two remaining vertices C, D given two opposing vertices A, B
of a rhombus with specified edge length. It does not draw the rhombus, which
could be handled easily by \Lcs{psline}. Internally, \Lcs{rhombus} uses
\Lcs{psRelNodeVar}.
\begin{BDef}
\Lcs{psrline}\Largr{P}\Largr{Q}\ldots
\end{BDef}
is like \Lcs{psline}, but drawing a line starting at (P), with successive
increments (Q)... It has the same options as\Lcs{psline}.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\pnode(0,.5){P}\pnode(1,1){Q}
\psrline{->}(P)(Q)(2;20)
\uput[-45](P){P}
\end{pspicture}
\end{LTXexample}
\begin{BDef}
\Lcs{psxline}\Largr{basept}\Largb{nodexpr1}\Largb{nodexpr2}
\end{BDef}
The {\tt x} here stands for expression. The idea is that one builds a
line from \verb|<basept>+<nodexpr1>| to \verb|<basept>+<nodexpr2>|.
\begin{LTXexample}[width=.35\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,4)
\def\pfn{t | t^2/4}
\psparametricplot[algebraic]{0}{3.5}{\pfn}
\curvepnode{2}{\pfn}{P}% sets P, Ptang
\normalvec(Ptang){Q}\uput[-45](P){P}
\psxline[linecolor=red]{<->}(P){-(Ptang)}{1.5(Ptang)}
\psxline[linecolor=blue]{->}(P){}{.5(Q)}%can use {} for {(0,0)}
\end{pspicture}
\end{LTXexample}
\vspace{2pc}
\begin{BDef}
\Lcs{polyIntersections}\Largb{Name1}\Largb{Name2}\Largr{A}\Largr{B}\Largb{P}\ldots\\
\Lcs{polyIntersections}\Largb{Name1}\Largb{Name2}\Largr{A}\Largr{B}\Largb{P}\Largb{n}\\
\end{BDef}
is the most complicated macro in the collection. It has two forms.
\begin{verbatim}
\polyIntersections{<Name1>}{<Name2>}(A)(B)(1,2)(3;30)(6,5)...
\end{verbatim}
defines the polyline \verb|L=(1,2)(3;30)(6,5)...|, and computes the two points of
intersection closest to {\tt A} in each direction with the directed line starting at
A heading toward B. The first intersection point in the positive direction is named
\verb|<Name1>|, and the first intersection point in the opposite direction (from A)
is named \verb|<Name2>|. If one or other of these intersections is empty, the nodes are
set to remote points on the line {\tt AB}. The effect of the line joining the constructed
nodes depends on the location of {\tt A} and {\tt B} relative to {\tt L}, with two cases worth noting.
\begin{itemize}
\item if {\tt L} is closed and if {\tt A, B} are interior to one of its components, the
resulting line extends across that component of {\tt L}, and contains {\tt AB}.
\item If {\tt L} is simple and closed, one of {\tt A, B} is inside and the other outside,
the resulting line segment will contain {\tt A} but not {\tt B}.
\end{itemize}
\begin{verbatim}
\polyIntersections{<Name1>}{<Name2>}(A)(B){P}{n}
\end{verbatim}
has exactly the same effect as
\begin{verbatim}
\polyIntersections{<Name1>}{<Name2>}(A)(B)(P0)(P1)...(Pn)
\end{verbatim}
assuming \verb|P0...Pn| to be previously defined nodes.
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\pnodes{P}(0,.5)(3,.5)(2.5,2)(.5,2.5)(0,.5)
\pnode(1,1.1){A}\pnode(2,1.5){B}
\polyIntersections{N1}{N2}(A)(B){P}{4}
\psnline(0,4){P}
\psdots(A)(B)\psline(N1)(N2)
\uput[-60](A){A}\uput[-60](B){B}
\uput[0](N1){N1}\uput[-180](N2){N2}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\pnodes{P}(0,.5)(3,.5)(2.5,2)(.5,2.5)(0,.5)
\pnode(1,1.1){A}\pnode(2,3){B}
\polyIntersections{N1}{N2}(A)(B){P}{4}
\psnline(0,4){P}
\psdots(A)(B)\psline(N1)(N2)
\uput[-60](A){A}\uput[-60](B){B}
\uput[90](N1){N1}\uput[-90](N2){N2}
\end{pspicture}
\end{LTXexample}
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\def\fn{1.5+sin(t)+.4*sin(2*t)%
| 1+cos(t)+.2*cos(2*t)+.2*sin(4*t)}%
\pnode(1,1.1){A}\pnode(2,1.2){B}
\psset{plotpoints=100}
\psparametricplot[algebraic]{0}{6.283}{\fn}
\curvepnodes{0}{6.283}{\fn}{Z}
\polyIntersections{N1}{N2}(A)(B){Z}{99}
\psdots(A)(B)\psline(N1)(N2)
\uput[-60](A){A}\uput[-60](B){B}
\uput[0](N1){N1}\uput[220](N2){N2}
\end{pspicture}
\end{LTXexample}
\vspace{1pc}
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\def\fn{1.5+sin(t)+.4*sin(2*t)%
| 1+cos(t)+.2*cos(2*t)+.2*sin(4*t)}%
\pnode(.8,.6){A}\pnode(2.5,-.5){B}
\psset{plotpoints=100}
\psparametricplot[algebraic]{0}{6.283}{\fn}
\curvepnodes{0}{6.283}{\fn}{Z}
\polyIntersections{N1}{N2}(A)(B){Z}{99}
\psdots(A)(B)\psline(N1)(N2)
\uput[90](A){A}\uput[-60](B){B}
\uput[70](N1){N1}\uput[180](N2){N2}
\end{pspicture}
\end{LTXexample}
\vspace{1pc}
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\pnodes{P}(0,.5)(3,.5)(2.5,2)(.5,2.5)(0,.5)
\pnode(1,1.1){A}\pnode(2,1.5){B}
\polyIntersections{N1}{N2}(A)(B){P}{3}
\psnline(0,3){P}
\psdots(A)(B)
\psclip{\psframe[linestyle=none](-.5,-.5)(3.5,2.5)}
\psline(N1)(N2)\endpsclip
\uput[-60](A){A}\uput[-60](B){B}
\uput[0](N1){N1}\uput[-180](N2){N2}
\end{pspicture}
\end{LTXexample}
\vspace{1pc}
\begin{LTXexample}[width=.375\textwidth]
\begin{pspicture}[showgrid=true](-.5,-.5)(3.5,3)
\def\fn{x+sin(2*x)}
\psplot[algebraic]{0}{3.14}{\fn}
\fnpnodes[algebraic]{0}{3.14}{\fn}{P}
\pnode(.6,.8){A}\pnode(1.5,1.1){B}
\polyIntersections{N1}{N2}(A)(B){P}{49}
\psdots(A)(B)
\uput[-90](A){A}\uput[-90](B){B}
\psline(N1)(N2)
\psset{linestyle=dashed}
\psline(N1)(N1 | 0,0)
\psline(N2)(N2 | 0,0)
\uput[70](N1){N1}\uput[170](N2){N2}
\end{pspicture}
\end{LTXexample}
\vspace{1pc}
\begin{BDef}
\Lcs{ArrowNotch}\Largb{<NodeName>}\Largb{<nodeindex>}\Largb{<direction>}\Largb{<Notch>}
\end{BDef}
takes as inputs the root name of the node sequence, the index at which the arrow
tip is to be drawn, and the direction (one of \verb+>,<+) of the arrow. It then
constructs the notch as a node with name \verb|<Notch>|. The arrowhead may then be
drawn with a command like \Lcs{psline}\verb|{->}(N)(P3)|, assuming the tip was to be {\tt P3}
and the notch was {\tt N}. Keep in mind that the macro takes its settings for linewidth,
arrowscale, etc from the current values, so it is generally preferable to include them
in a \Lcs{psset} before drawing the curve and calling \Lcs{ArrowNotch}.
(Alternatively, they may be included as optional settings in \Lcs{ArrowNotch}.)
The first example below shows a case where the native arrow direction is not
good. The second shows how to make a version using \Lcs{ArrowNotch}. Notice that the minimum and maximum
parameter values in the second example had to be modified to keep the curve
from protruding near the end arrowheads.
\Lcs{ArrowNotch} is a computationally expensive macro (quadratic in {\tt plotpoints}) designed to
improve the placement of arrows on curves in those cases (high curvature, large values of
linewidth, arrowscale, etc) where the native arrow direction is not optimal. The macro
depends on the construction of a node sequence, say {\tt P0..Pn}, of samples of the curve
(eg, with \Lcs{curvepnodes}) from which it computes the position of the notch of the arrow
so that, when drawn, the arrow notch will be located on the curve in all cases. It operates
with only two particular arrow shapes---those arrows specified with either
\verb|->| or \verb|-D>|, or their reverses.
\begin{LTXexample}[width=.375\textwidth]
\def\fn{1.5+1.5*cos(t) | 1+sin(t)}
\psset{linewidth=2pt,arrowscale=3}
\begin{pspicture}(0,0)(3.5,3)
\psparametricplot[algebraic,arrows=<->]{PiDiv2 neg}{Pi}{\fn}
\end{pspicture}
\end{LTXexample}
\vspace{1pc}
\begin{LTXexample}[width=.375\textwidth]
\def\fn{1.5+1.5*cos(t) | 1+sin(t)}
\psset{linewidth=2pt,arrowscale=3}
\begin{pspicture}(0,0)(3.5,3)
\curvepnodes{PiDiv2 neg}{Pi}\fn{P}%create P0..P49
\ArrowNotch{P}{0}{<}{Q}
\ArrowNotch{P}{49}{>}{R}
\ArrowNotch[arrowscale=1.5]{P}{27}{>}{S}
\psparametricplot[algebraic]{-1.47}{2.95}{\fn}
\psline{->}(Q)(P0)
\psline{->}(R)(P49)
\psline[arrowscale=1.5]{->}(S)(P27)
\end{pspicture}
\end{LTXexample}
\clearpage
\section{List of all optional arguments for \texttt{pst-node}}
\xkvview{family=pst-node,columns={key,type,default}}
\nocite{*}
\bgroup
\RaggedRight
\bibliographystyle{plain}
\bibliography{pst-node-doc}
\egroup
\printindex
\end{document}
|