summaryrefslogtreecommitdiff
path: root/graphics/epix/samples/lighting.flx
blob: 80997bebeb707a23d35a98a9e762345d2344a2ec (plain)
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
/* -*-flix-*- */
// compile with flix -I. [-DAXES] lighting.flx
// in a directory containing lighting.h
#include "epix.h"
#include "lighting.h"
using namespace ePiX;

// mesh intervals for torus
int N1(36), N2(12);

// torus
P F(double x, double y)
{
  double R(5-2*Sin(M_PI*y/N2));
  return P(R*Cos(2*M_PI*x/N1), R*Sin(2*M_PI*x/N1), 2*Cos(M_PI*y/N2));
}

int main(int argc, char* argv[])
{
  if (argc == 3)
    {
      char* arg;
      double temp1, temp2;
      temp1=strtod(argv[1], &arg);
      temp2=strtod(argv[2], &arg);

      tix()=temp1/temp2;
    }
  picture(P(-10,-10),P(10,10), "4x4in");

  begin();
  set_crop();

  backing(Black());

  domain R(P(0,N2), P(N1,2*N2), mesh(N1,N2), mesh(2*N1,2*N2));

  // manual layering below may require adjustment if the camera is moved
  camera.at(P(4,6,4));
  camera.range(16);

#ifdef AXES
  yellow();
  label(P(8,0,0), P(-2,-2), "$\\mathbf{x}$", bl);
  label(P(0,8,0), P( 2,-2), "$\\mathbf{y}$", br);
  label(P(0,0,8), P( 0, 4), "$\\mathbf{z}$", t);
#endif

  // draw grid only
  pen(Green(), 0.15);
  plot(F, R);

  // axes (with solid arrowheads) and shaded surface
#ifdef AXES
  arrow(P(0,0,0), P(8,0,0));
  arrow(P(0,0,0), P(0,8,0));
  arrow(P(0,0,0), P(0,0,8));
#endif

  rgb(0.8, 0.4, 0);
  fill();
  Color chip_color(White());     // true color of torus
  Color ambient(RGB(1,0.75,0));  // ambient light

  Fog fog(White(), 0.0125);

  // spot light location
  P spot_at(sph(10, M_PI_4, 2*M_PI*tix())); // traverses a longitude

  // P spot_b=P(5,0,0)+cyl(10, 2*M_PI*tix(), 5); // or latitude
  // P spot_b(5,-5,10);                        // or stays put
  Spot spot(Blue(), spot_at);

  std::vector<Chip> surf_mesh;
  // torus, surface reflectivity .75
  for (int i=0; i<N1; ++i)
    for (int j=0; j<N2; ++j)
      surf_mesh.push_back(Chip(F(i,j), F(i+1,j), F(i+1,j+1), F(i,j+1),
			       0.75, chip_color));

  sort(surf_mesh.begin(), surf_mesh.end(), chip_distance());

#ifdef SHOW_SPOT
  // mark spot light's location
  if (spot_at.x2() <= 0)
    {
      blue();
      box(spot.m_loc);
    }
#endif

  // draw shaded surface mesh
  for (unsigned int i=0; i<surf_mesh.size(); ++i)
    surf_mesh.at(i).draw(fog, spot, ambient);

#ifdef SHOW_SPOT
  if (spot_at.x2() > 0)
    {
      blue();
      box(spot.m_loc);
    }
#endif

#ifdef AXES
  // re-draw hidden portions
  green();
  line(P(3,0,0), P(8,0,0));
  line(P(0,3,0), P(0,8,0));
  line(P(0,0,0), P(0,0,8));
#endif

  fill(false);
  // redraw front portion of mesh partially covered by solid surface
  pen(Green(), 0.15);
  plot(F, R.resize1(0, 0.25*N1));

  // labels
  base(White(), 1);
  line(P(3,0,6), F(0,0.25*N2));
  line(P(6,0,4), F(0,-0.25*N2));

  label_border(Green(0.6), "0.5pt");
  label_color(Black());
  label_mask(RGB(1,0.8,0.2));

  font_size("footnotesize");
  masklabel(P(3,0,6), P(0,0), "Total curvature $-\\pi$", t);
  masklabel(P(6,0,4), P(0,0), "Total curvature $\\pi$", t);

  pst_format();
  end();
}