1
0
mirror of https://github.com/Pomax/BezierInfo-2.git synced 2025-10-01 10:36:43 +02:00

Explanation section (#260)

* rewritten
This commit is contained in:
Pomax
2020-08-08 14:18:23 -07:00
committed by GitHub
parent e784a5e33d
commit f2b7db8657
11 changed files with 133 additions and 89 deletions

View File

@@ -0,0 +1,65 @@
setup() {
this.step = 5;
}
draw() {
clear();
const dim = this.height,
w = dim,
h = dim,
w2 = w/2,
h2 = h/2,
w4 = w2/2,
h4 = h2/2;
setStroke(`black`);
line(0, h2, w, h2);
line(w2, 0, w2, h);
var offset = {x:w2, y:h2};
for(let t=0, p, mod; t<=this.step; t+=0.1) {
p = {
x: w2 + w4 * cos(t),
y: h2 + h4 * sin(t)
};
circle(p.x, p.y, 1);
mod = t % 1;
if(mod >= 0.9) {
text(`t = ${ round(t) }`,
w2 + 1.25 * w4 * cos(t) - 10,
h2 + 1.25 * h4 * sin(t) + 10
);
circle(p.x, p.y, 2);
}
}
}
onKeyDown() {
const key = this.keyboard.currentKey;
if (key === `ArrowUp`) { this.step++; }
if (key === `ArrowDown`) { this.step--; }
if (this.step < 1) this.step = 1;
redraw();
}
onMouseDown() {
this.mark = this.cursor.y;
}
onMouseUp() {
this.mark = false;
}
onMouseMove() {
if (this.mark) {
let diff = this.mark - this.cursor.y,
mapped = map(diff, -this.height/2, this.height/2, 1, 10, true);
this.step = mapped | 0;
redraw();
}
}

View File

@@ -41,7 +41,7 @@ There we go. <i>x</i>/<i>y</i> coordinates, linked through some mystery value <i
So, parametric curves don't define a <i>y</i> coordinate in terms of an <i>x</i> coordinate, like normal functions do, but they instead link the values to a "control" variable. If we vary the value of <i>t</i>, then with every change we get <strong>two</strong> values, which we can use as (<i>x</i>,<i>y</i>) coordinates in a graph. The above set of functions, for instance, generates points on a circle: We can range <i>t</i> from negative to positive infinity, and the resulting (<i>x</i>,<i>y</i>) coordinates will always lie on a circle with radius 1 around the origin (0,0). If we plot it for <i>t</i> from 0 to 5, we get this (use your up and down arrow keys to change the plot end value):
<Graphic title="A (partial) circle: x=sin(t), y=cos(t)" static={true} setup={this.setup} draw={this.draw} onKeyDown={this.props.onKeyDown}/>
<graphics-element title="A (partial) circle: x=sin(t), y=cos(t)" width="275" height="275" src="./circle.js"></graphics-element>
Bézier curves are just one out of the many classes of parametric functions, and are characterised by using the same base function for all of the output values. In the example we saw above, the <i>x</i> and <i>y</i> values were generated by different functions (one uses a sine, the other a cosine); but Bézier curves use the "binomial polynomial" for both the <i>x</i> and <i>y</i> outputs. So what are binomial polynomials?
@@ -97,7 +97,7 @@ It's basically just a sum of "every combination of <i>a</i> and <i>b</i>", progr
And that's the full description for Bézier curves. Σ in this function indicates that this is a series of additions (using the variable listed below the Σ, starting at ...=&lt;value&gt; and ending at the value listed on top of the Σ).
<div className="howtocode">
<div class="howtocode">
### How to implement the basis function

View File

@@ -39,7 +39,7 @@
というわけで、普通の関数では<i>y</i>座標を<i>x</i>座標によって定義しますが、パラメトリック曲線ではそうではなく、座標の値を「制御」変数と結びつけます。<i>t</i>の値を変化させるたびに<strong>2つ</strong>の値が変化するので、これをグラフ上の座標 (<i>x</i>,<i>y</i>)として使うことができます。例えば、先ほどの関数の組は円周上の点を生成します。負の無限大から正の無限大へと<i>t</i>を動かすと、得られる座標(<i>x</i>,<i>y</i>)は常に中心(0,0)・半径1の円の上に乗ります。<i>t</i>を0から5まで変化させてプロットした場合は、このようになります上下キーでプロットの上限を変更できます
<Graphic title="(部分)円 x=sin(t), y=cos(t)" static={true} setup={this.setup} draw={this.draw} onKeyDown={this.props.onKeyDown}/>
<graphics-element title="(部分)円 x=sin(t), y=cos(t)" width="275" height="275" src="./circle.js"></graphics-element>
ベジエ曲線はパラメトリック関数の一種であり、どの次元に対しても同じ基底関数を使うという点で特徴づけられます。先ほどの例では、<i>x</i>の値と<i>y</i>の値とで異なる関数(正弦関数と余弦関数)を使っていましたが、ベジエ曲線では<i>x</i><i>y</i>の両方で「二項係数多項式」を使います。では、二項係数多項式とは何でしょう?
@@ -95,7 +95,7 @@
そして、これがベジエ曲線の完全な表現です。この関数中のΣは、加算の繰り返し(Σの下にある変数を使って、...=<>から始めてΣの下にある値まで)を表します。
<div className="howtocode">
<div class="howtocode">
### 基底関数の実装方法

View File

@@ -39,7 +39,7 @@
所以,参数曲线不像一般函数那样,通过<i>x</i>坐标来定义<i>y</i>坐标,而是用一个“控制”变量将它们连接起来。如果改变<i>t</i>的值,每次变化时我们都能得到<strong>两个</strong>值,这可以作为图形中的(<i>x</i>,<i>y</i>)坐标。比如上面的方程组,生成位于一个圆上的点:我们可以使<i>t</i>在正负极值间变化,得到的输出(<i>x</i>,<i>y</i>)都会位于一个以原点(0,0)为中心且半径为1的圆上。如果我们画出<i>t</i>从0到5时的值将得到如下图像你可以用上下键来改变画的点和值
<Graphic title="(一部分的)圆: x=sin(t), y=cos(t)" static={true} setup={this.setup} draw={this.draw} onKeyDown={this.props.onKeyDown}/>
<graphics-element title="(一部分的)圆: x=sin(t), y=cos(t)" width="275" height="275" src="./circle.js"></graphics-element>
贝塞尔曲线是(一种)参数方程,并在它的多个维度上使用相同的基本方程。在上述的例子中<i>x</i>值和<i>y</i>值使用了不同的方程,与此不同的是,贝塞尔曲线的<i>x</i><i>y</i>都用了“二项多项式”。那什么是二项多项式呢?
@@ -95,7 +95,7 @@
这就是贝塞尔曲线完整的描述。在这个函数中的Σ表示了这是一系列的加法(用Σ下面的变量,从...=<>开始,直到Σ上面的数字结束)。
<div className="howtocode">
<div class="howtocode">
### 如何实现基本方程

View File

@@ -1,52 +0,0 @@
module.exports = {
statics: {
keyHandlingOptions: {
propName: "step",
values: {
"38": 0.1, // up arrow
"40": -0.1 // down arrow
},
controller: function(api) {
if (api.step < 0.1) {
api.step = 0.1;
}
}
}
},
setup: function(api) {
api.step = 5;
},
draw: function(api, curve) {
var dim = api.getPanelWidth(),
w = dim,
h = dim,
w2 = w/2,
h2 = h/2,
w4 = w2/2,
h4 = h2/2;
api.reset();
api.setColor("black");
api.drawLine({x:0,y:h2},{x:w,y:h2});
api.drawLine({x:w2,y:0},{x:w2,y:h});
var offset = {x:w2, y:h2};
for(var t=0, p; t<=api.step; t+=0.1) {
p = {
x: w4 * Math.cos(t),
y: h4 * Math.sin(t)
};
api.drawPoint(p, offset);
var modulo = t % 1;
if(modulo<0.05 || modulo> 0.95) {
api.text("t = " + Math.round(t), {
x: offset.x + 1.25 * w4 * Math.cos(t) - 10,
y: offset.y + 1.25 * h4 * Math.sin(t) + 5
});
api.drawCircle(p, 2, offset);
}
}
}
};

View File

@@ -1,4 +0,0 @@
var handler = require("./handler.js");
var generateBase = require("../../generate-base");
var keyHandling = require("../../decorators/keyhandling-decorator.jsx");
module.exports = keyHandling(generateBase("explanation", handler));

View File

@@ -636,13 +636,22 @@
<i>t</i> from 0 to 5, we get this (use your up and down arrow keys
to change the plot end value):
</p>
<Graphic
<graphics-element
title="A (partial) circle: x=sin(t), y=cos(t)"
static="{true}"
setup="{this.setup}"
draw="{this.draw}"
onKeyDown="{this.props.onKeyDown}"
width="275"
height="275"
src="./chapters/explanation/circle.js"
>
<fallback-image>
<img
width="275px"
height="275px"
src="./images/chapters/explanation/circle.png"
loading="lazy"
/>
Scripts are disabled. Showing fallback image.
</fallback-image></graphics-element
>
<p>
Bézier curves are just one out of the many classes of parametric
@@ -738,7 +747,7 @@
variable listed below the Σ, starting at ...=&lt;value&gt; and
ending at the value listed on top of the Σ).
</p>
<div className="howtocode">
<div class="howtocode">
<h3>How to implement the basis function</h3>
<p>
We could naively implement the basis function as a mathematical

View File

@@ -488,13 +488,22 @@
というわけで、普通の関数では<i>y</i>座標を<i>x</i>座標によって定義しますが、パラメトリック曲線ではそうではなく、座標の値を「制御」変数と結びつけます。<i>t</i>の値を変化させるたびに<strong>2つ</strong>の値が変化するので、これをグラフ上の座標
(<i>x</i>,<i>y</i>)として使うことができます。例えば、先ほどの関数の組は円周上の点を生成します。負の無限大から正の無限大へと<i>t</i>を動かすと、得られる座標(<i>x</i>,<i>y</i>)は常に中心(0,0)・半径1の円の上に乗ります。<i>t</i>を0から5まで変化させてプロットした場合は、このようになります上下キーでプロットの上限を変更できます
</p>
<Graphic
<graphics-element
title="(部分)円 x=sin(t), y=cos(t)"
static="{true}"
setup="{this.setup}"
draw="{this.draw}"
onKeyDown="{this.props.onKeyDown}"
width="275"
height="275"
src="./chapters/explanation/circle.js"
>
<fallback-image>
<img
width="275px"
height="275px"
src="./images/chapters/explanation/circle.png"
loading="lazy"
/>
Scripts are disabled. Showing fallback image.
</fallback-image></graphics-element
>
<p>
ベジエ曲線はパラメトリック関数の一種であり、どの次元に対しても同じ基底関数を使うという点で特徴づけられます。先ほどの例では、<i>x</i>の値と<i>y</i>の値とで異なる関数(正弦関数と余弦関数)を使っていましたが、ベジエ曲線では<i>x</i><i>y</i>の両方で「二項係数多項式」を使います。では、二項係数多項式とは何でしょう?
@@ -556,7 +565,7 @@
<p>
そして、これがベジエ曲線の完全な表現です。この関数中のΣは、加算の繰り返し(Σの下にある変数を使って、...=&lt;&gt;から始めてΣの下にある値まで)を表します。
</p>
<div className="howtocode">
<div class="howtocode">
<h3>基底関数の実装方法</h3>
<p>
上で説明した関数を使えば、数学的な組み立て方で、基底関数をナイーブに実装することもできます。

View File

@@ -191,8 +191,8 @@ class GraphicsAPI extends BaseAPI {
*/
line(x1, y1, x2, y2) {
this.ctx.beginPath();
this.ctx.moveTo(x1 + 0.5, y1 + 0.5);
this.ctx.lineTo(x2 + 0.5, y2 + 0.5);
this.ctx.moveTo(x1, y1);
this.ctx.lineTo(x2, y2);
this.ctx.stroke();
}
@@ -201,7 +201,7 @@ class GraphicsAPI extends BaseAPI {
*/
circle(x, y, r) {
this.ctx.beginPath();
this.ctx.arc(x + 0.5, y + 0.5, r, 0, this.TAU);
this.ctx.arc(x, y, r, 0, this.TAU);
this.ctx.fill();
this.ctx.stroke();
}
@@ -214,15 +214,15 @@ class GraphicsAPI extends BaseAPI {
y = x.y;
x = x.x;
}
this.ctx.fillText(str, x + 0.5, y + 0.5);
this.ctx.fillText(str, x, y);
}
/**
* Draw a rectangle start with {p} in the upper left
*/
rect(x, y, w, h) {
this.ctx.fillRect(x + 0.5, y + 0.5, w, h);
this.ctx.strokeRect(x + 0.5, y + 0.5, w, h);
this.ctx.fillRect(x, y, w, h);
this.ctx.strokeRect(x, y, w, h);
}
/**

View File

@@ -50,6 +50,14 @@ div.print:after {
left: -2em;
}
div.howtocode {
position: relative;
border: 1px solid black;
background: rgb(246, 255, 255);
margin: 1em;
padding: 1em 1em 0 1em;
}
div.note {
position: relative;
border: 1px solid black;

View File

@@ -473,13 +473,22 @@
<p>
所以,参数曲线不像一般函数那样,通过<i>x</i>坐标来定义<i>y</i>坐标,而是用一个“控制”变量将它们连接起来。如果改变<i>t</i>的值,每次变化时我们都能得到<strong>两个</strong>值,这可以作为图形中的(<i>x</i>,<i>y</i>)坐标。比如上面的方程组,生成位于一个圆上的点:我们可以使<i>t</i>在正负极值间变化,得到的输出(<i>x</i>,<i>y</i>)都会位于一个以原点(0,0)为中心且半径为1的圆上。如果我们画出<i>t</i>从0到5时的值将得到如下图像你可以用上下键来改变画的点和值
</p>
<Graphic
<graphics-element
title="(一部分的)圆: x=sin(t), y=cos(t)"
static="{true}"
setup="{this.setup}"
draw="{this.draw}"
onKeyDown="{this.props.onKeyDown}"
width="275"
height="275"
src="./chapters/explanation/circle.js"
>
<fallback-image>
<img
width="275px"
height="275px"
src="./images/chapters/explanation/circle.png"
loading="lazy"
/>
Scripts are disabled. Showing fallback image.
</fallback-image></graphics-element
>
<p>
贝塞尔曲线是(一种)参数方程,并在它的多个维度上使用相同的基本方程。在上述的例子中<i>x</i>值和<i>y</i>值使用了不同的方程,与此不同的是,贝塞尔曲线的<i>x</i><i>y</i>都用了“二项多项式”。那什么是二项多项式呢?
@@ -541,7 +550,7 @@
<p>
这就是贝塞尔曲线完整的描述。在这个函数中的Σ表示了这是一系列的加法(用Σ下面的变量,从...=&lt;&gt;开始,直到Σ上面的数字结束)。
</p>
<div className="howtocode">
<div class="howtocode">
<h3>如何实现基本方程</h3>
<p>
我们可以用之前说过的方程,来简单地实现基本方程作为数学构造,如下: