-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathfunctions.html
More file actions
198 lines (182 loc) · 8.49 KB
/
Copy pathfunctions.html
File metadata and controls
198 lines (182 loc) · 8.49 KB
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
<!DOCTYPE html>
<html>
<head>
<title>Function Plotter</title></title>
<link rel="stylesheet" href="//code.jquery.com/ui/1.10.4/themes/smoothness/jquery-ui.css">
<link rel="stylesheet" href="https://stackedit.io/res-min/themes/base.css" />
<script src="//code.jquery.com/jquery-1.10.2.js"></script>
<script src="//code.jquery.com/ui/1.10.4/jquery-ui.js"></script>
<script type = "text/javascript" src = "Common/webgl-utils.js"></script>
<script type = "text/javascript" src = "Common/initShaders2.js"></script>
<script type = "text/javascript" src = "Common/MV.js"></script>
<style type="text/css">
.editor {
position: relative !important;
border: 2px solid lightgrey;
margin: auto;
height: 100px;
width: 100%;
}
</style>
</head>
<body>
<a href="https://github.com/stharding/function-plotter/"><img style="position: absolute; top: 0; right: 0; border: 0;" src="https://camo.githubusercontent.com/a6677b08c955af8400f44c6298f40e7d19cc5b2d/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f6769746875622f726962626f6e732f666f726b6d655f72696768745f677261795f3664366436642e706e67" alt="Fork me on GitHub" data-canonical-src="https://s3.amazonaws.com/github/ribbons/forkme_right_gray_6d6d6d.png"></a>
<div style="width: 100%; float: left;">
<div id="left-canvas" style="width: 50%; float: left; padding-left:0.5cm; padding-top:0.3cm">
<canvas id = "gl-canvas" class = "canv" style="background-color:#eee">
Oops ... your browser doesn't support the HTML5 canvas element
</canvas>
<div style="padding-left:0.7cm;">
To the right are three code editing areas which are pre-filled with some
default code. All of the code is <code>GLSL</code> and is subject to its
restrictions. Of particular note, in most cases, there is no automatic
conversion between integers and floats. For example, the expression
<code>1 + 2.0</code> will not compile: since the literal <code>1</code> is an
integer and the literal <code>2.0</code> is a float. <p></p>
The function plotter has two distinct modes of operation: 2d mode and 3d
mode. <p></p>
In 2d mode, the user specified function of x and y will be plotted. The
output value of the function is output as a 'heat map'. Specifically, the
(user modifiable) <code>getcolor()</code> function determines the color for a
z-value. The user can use the mouse wheel to 'zoom' in and out and click
and drag to pan and zoom (this is nothing more than specifying the dom
in
of the function). Additionally, the arrow keys will pan and the up and
down arrow keys will also zoom if the shift key is pressed.<p></p>
Once the user has set the function to be plotted and is satisfied with the
bounds and the coloring the function can be plotted in 3d. The actual z
value of the function is computed for each pixel. Vertices correspondin
to each pixel in the canvas are generated and the image that was rendered
in 2d mode is used as a texture to shade the vertices. <p></p>
In 3d mode, there are a couple more options to be aware of: render mode,
and normalize mode. There are two render modes. The first is triangle-
strip mode which will render function as a solid surface. The second is
point-mode where each vertex is simply rendered as a point. This often
gives the impression of a mesh. <p></p>
3d mouse interaction is as follows: Clicking and dragging will rotate the
plot in the direction of the drag (along the x and y axis). The plot can
be moved up and down by holding the shift key and dragging the mouse up
and down. The plot can be rotated on the z-axis by holding the shift key
while clicking and dragging left or right. <p></p>
This plotter is extremely versatile and can plot absolutely any function
of x and y. In fact the only limitation is inherent in the name
'function'. That is to say that this plotter can only plot functions in
the mathematical sense that a function can have only one output for a
given input. This means that you cannot plot spheres or cubes etc. To
demonstrate the versatility of this plotter, the following code is
provided to plot the mandelbrot set and the julia set. Just copy and paste
the <code>getcolor()</code> function into the color function area and the <code>
mandelbrot()</code> or <code>julia()</code> into the helper function area. Then
put <code>mandelbrot(x,y)</code> into the expression area.
<p></p>
<pre class="editor" id="example">
vec4 getcolor(float z)
{
if (z == max - 1.0) return vec4(0,0,0,1);
z/=max;
float r = z + z > 1.0 ? 1.0 / (z + z) : z + z;
float g = z > 1.0 ? 1.0 / (z * z) : z;
float b = z > 1.0 ? 1.0 / z : z * z;
return vec4(r, g, b, 1.0);
}
const float max = 100.0;
float mandelbrot(float fx, float fy) {
float iteration = 0.0;
float x = 0.0;
float y = 0.0;
float xtemp = 0.0;
for ( float i = 0.0; i < max; ++i )
{
if ( sqrt(x * x + y * y) <= 4.0 ) {
xtemp = x * x - y * y + fx;
y = 2.0 * x * y + fy;
x = xtemp;
iteration = i;
}
else{ break; }
}
return iteration;
}
const float max = 100.0;
float julia( float x, float y ) {
float cRe = -0.7;
float cIm = 0.27015;
float z = 0.0;
float xtemp;
for(float i = 0.0; i < max; i++)
{
xtemp = x * x - y * y + cRe;
y = 2.0 * x * y + cIm;
x = xtemp;
if((x * x + y * y) > 4.0) break;
z = i;
}
return z;
}
</pre>
</div>
</div>
<div id="instructions" style="width: 40%; float: right; padding-right:1.3cm;">
<h2>Function Plotter</h2>
<h4>Works best in Chrome! (there are known issues with Firefox)</h4>
<h4>Please review the <a href="index.html">README</a> for detailed documentation</h4>
Feel Free to modify the <code>getcolor()</code>
function (just don't change it's name)
<pre class="editor" id="clr_input" style="height: 200px">
vec4 getcolor(float z)
{
float r = z + z > 1.0 ? 1.0 / (z + z) : z + z;
float g = z > 1.0 ? 1.0 / (z * z) : z;
float b = z > 1.0 ? 1.0 / z : z * z;
return vec4(r, g, b, 1.0);
}</pre>
<p></p>
Helper function(s) ( <span class="comment label label-warning">optional</span> -- just remember to use glsl syntax ...):
<br><pre class = "editor" id="helper_input" rows="4" cols="80" style="font-family: monospace;">
//
// Write any custom functions here ...
//
</pre><br>
<span class="comment label label-danger">Required:</span> Input an expression in terms of
<code>x</code> and <code>y</code> e.g.: <code>sin( x*x + y*y )</code>
<br><pre class="editor" id="function_input">
// enter an expression to plot here (or use this example)
sin( x*x + y*y )
</pre><br>
<button onclick="set_function();" > Render2D </button>
<button onclick="go3D();" > Render3D </button>
<!-- <button onclick="saveImage(true);" > Save Image </button>--><br>
Current Render mode: <code><span id="points_mode">Triangle Strip</span></code>
<span id="point_size_group" hidden="true">Point Size:
<input type="range" id="point_size_slider" min="100" max="1000" value="1" oninput="setPointSize(value)">
<output id="point_size_output">1.0</output></span><br>
Current Normalize mode: <code><span id="normalize_mode">Normalized</span></code><br>
<button onclick="togglePoints();" > Toggle Points/Trinagle Strip </button>
<button onclick="toggleNormalize();" > Toggle Normalization </button><br><br>
Set bounds: <br>
Min X: <label id="minX"></label><br>
<input id = "set_min_x"
type = "text" style="width: 100%"><br><br>
Max X: <label id = "maxX"></label><br>
<input id = "set_max_x"
type = "text" style="width: 100%"><br><br>
Min Y: <label id = "minY"></label><br>
<input id = "set_min_y"
type = "text" style="width: 100%"><br><br>
Max Y: <label id = "maxY"></label><br>
<input id = "set_max_y"
type = "text" style="width: 100%"><br><br>
<button onclick="set_range()">Set</button>
<p></p>
</div>
</div>
<!--
<div id="dialog" title="Save Image">
<img id="save_img" height="300px" width="300px"></img>
<p>Right click on the image and select 'save as'. Click the 'X' to close this dialog.</p>
</div>
-->
<script src="Common/ace-builds/src-noconflict/ace.js" type="text/javascript" charset="utf-8"></script>
<script type = "text/javascript" src = "functions.js"></script>
</body>
</html>