The Key points under the graph are not read from the formula. Each curve is walked: nine hundred samples across whatever width of x-axis is currently on screen, looking for three things, and every one found is marked on the graph as well as listed.
If the value is negative at one sample and positive at the next, the curve crossed zero between them, so the crossing is squeezed down by repeated halving — sixty times, which is far past the precision a double can hold — until the interval is a point. That is bisection, and it is the oldest root-finder there is. It is slow and it cannot fail to converge, which is the trade every numerical method makes in one direction or the other.
Two things make a sign change a lie. A vertical asymptote flips sign without any root: 1/x is deeply negative just left of zero and deeply positive just right of it. So the value found is checked — at a real root it has fallen below both neighbours, at an asymptote it has grown past them, and the asymptote is discarded. And a sample landing exactly on zero is neither negative nor positive, so a strict comparison steps over it; sin(x) lost its root at the origin that way while finding all six of its neighbours. An exact zero now counts, but only on its own: floor(x) is zero all the way from 0 to 1, and every sample in that run used to be listed as a separate root.
The slope between consecutive samples is a crude derivative, and where it changes sign the curve may have turned round. May: at every asymptote of tan(x) the curve leaves the top of the screen and comes back at the bottom, and the sampled slope flips there too — which used to report eight maxima and minima that tan(x) does not have. So each candidate is checked against the derivative itself, which must really be positive on one side and negative on the other, and is then pinned down by bisecting the derivative. The coordinate is exact to many more places than the sample spacing, and it no longer moves as you zoom.
For every pair of curves on screen, the same search runs on f(x) − g(x). A change of sign is a crossing. The Compare & intersect preset is the instructive case: x^2 − 2 and 2x − 3 differ by (x − 1)^2, which is never negative, so the line never crosses the parabola at all. It touches it, at (1, −1), and is its tangent there.
Anything narrower than one sample. Across a window 20 units wide the samples are about 0.022 apart, so sin(200x) has roots far closer together than that and the panel will find a haphazard subset of them. Zooming in fixes it, because the window shrinks and the sampling density with it — but the honest summary is that this panel finds what is visible at the scale you are looking at, which is the same thing your eye is doing.
A root that touches zero without crossing never changes sign, so no sign-change method can see it. The curve of x^2 has one at the origin. It is found the other way round: as a turning point whose value is zero, to nine significant figures of the curve's height on screen, and listed as a root that touches. The same goes for two curves that touch. What it cannot tell apart is a turning point that comes within a billionth of zero without reaching it; that is listed as touching too.
Everything is found within the visible window only. Pan, and the list changes. That is deliberate: a root off the side of the screen is not a root of what you are looking at.
A recursive-descent evaluator (no eval), so 2x, 2*x and x*2 mean the same, and unsupported input is rejected rather than silently misread.
One point per horizontal pixel, joined into a curve. Breaks at undefined values or jumps larger than the visible range: a real discontinuity, not a drawing error.
x and y always share one scale, so sqrt(9−x^2) is a true semicircle at every zoom, never a squashed ellipse.
Each in its own colour, hideable or deletable: compare a function with its derivative, or see where two curves intersect (marked with diamonds).
The domain is every x the function accepts; the range is every y it can produce. sqrt(x) has domain x ≥ 0: try it and watch the curve simply not exist for negative x.
A line a curve approaches but never touches. 1/x approaches both axes; tan(x) shoots to ±∞ at every odd multiple of 90°, so its curve breaks into separate arcs. Plotting 1/x shows two separate branches meeting nowhere near x = 0: a vertical line at the asymptote is not part of the graph, because the function is undefined there.
Where a curve crosses the x-axis, f(x) = 0. Where two curves meet they share the same (x, y). The “Compare & intersect” preset is worth a look: the line does not cross the parabola, it touches it at (1, −1) as its tangent.
+, −, *, /, ^ and parentheses; sin, cos, tan, asin, acos, atan, sqrt, cbrt, abs, ln, log, log2, exp, floor, ceil, round, sign; the constants pi and e. Implicit multiplication works: 2x, 2sin(x) and (x+1)(x−1) are understood without a *.
The curve is evaluated at intervals across the range, so anything narrower than the gap between samples (a very fast oscillation, a spike, a removable hole, a root squeezed between two points) can be missed entirely. If a shape looks suspiciously smooth, zoom in and check. The near-vertical line sometimes drawn through an asymptote is an artefact of joining samples.
Standard notation: +, -, *, /, ^ for powers, and parentheses. sin, cos, tan, asin, acos, atan, sqrt, cbrt, abs, ln, log, log2, exp, floor, ceil, round and sign all work, along with the constants pi and e. Implicit multiplication works too — 2x, 2sin(x) and (x+1)(x-1) are all understood without a * sign.
A vertical line at an asymptote like x=0 for 1/x isn't actually part of the function's graph — the function is undefined there, not infinite in a way that draws a line. This tool detects the jump and breaks the curve into separate pieces, the same way a correct hand-drawn sketch would.
Yes — the x and y axes always share the same scale (the same number of pixels per unit), so a function like sqrt(9-x^2) traces a genuine semicircle rather than a squashed ellipse, at every zoom level.
Up to eight, each in its own colour, any of which can be hidden or deleted independently — useful for comparing a function against its derivative, or seeing where two curves intersect.
Real-valued functions of a single variable x. The curve is sampled across the width of the plot, so any feature narrower than the spacing between samples — a very fast oscillation, a narrow spike — can be missed entirely; if a shape looks suspiciously smooth, zoom in and check. Breaks at asymptotes are detected by a jump test rather than by solving for them, inputs with no real result simply leave a gap, and implicit relations such as x² + y² = 1 cannot be entered because the parser expects y as a function of x.
Releases in which this page changed, newest last. Derived from the archived copy of every release, not from notes written afterwards — so it reflects what actually shipped. Site-wide passes are left out; they are in the full changelog.