feat(geom9 ch1 wave3): §5 «Формулы площади» + §6 «Среднее геометрическое»
This commit is contained in:
@@ -1809,8 +1809,590 @@ function buildP4(){
|
||||
|
||||
wireReadBtn('p4');
|
||||
}
|
||||
function buildP5(){ _stubBuilder('p5', '§5', 'Формулы площади', 'p4', 'p6'); }
|
||||
function buildP6(){ _stubBuilder('p6', '§6', 'Среднее геометрическое', 'p5', 'final1'); }
|
||||
/* ===== §5 Формулы площади ===== */
|
||||
function buildP5(){
|
||||
const box = document.getElementById('p5-body');
|
||||
let html = '';
|
||||
|
||||
html += makeCard('theory', 'Площадь треугольника через две стороны и угол', '5.1', `
|
||||
<p>Площадь треугольника можно вычислить, зная <b>две стороны</b> и <b>угол между ними</b>:</p>
|
||||
<p style="text-align:center;font-size:1.15rem">$\\boxed{\\,S_\\triangle = \\dfrac{1}{2} a b \\sin C\\,}$</p>
|
||||
<p>Здесь $a$ и $b$ — две стороны треугольника, а $C$ — угол между ними (то есть угол при общей вершине этих сторон).</p>
|
||||
<details class="spoiler" open><summary>Откуда берётся $\\sin C$?</summary><div class="spoiler-body">
|
||||
<p>Опустим высоту $h$ из вершины $A$ на сторону $a = BC$. В прямоугольном треугольнике с гипотенузой $b$ и острым углом $C$ имеем:</p>
|
||||
<p style="text-align:center">$h = b \\sin C$.</p>
|
||||
<p>Тогда классическая формула $S = \\dfrac{1}{2} \\cdot a \\cdot h$ превращается в:</p>
|
||||
<p style="text-align:center">$S = \\dfrac{1}{2} a \\cdot b \\sin C = \\dfrac{1}{2} a b \\sin C$.</p>
|
||||
<p>Формула работает и для тупого угла $C$: тогда высота попадает на продолжение стороны, но $\\sin C$ всё равно положителен (из §4 знаем: $\\sin(180^\\circ - \\alpha) = \\sin \\alpha$).</p>
|
||||
</div></details>`);
|
||||
|
||||
html += makeCard('rule', 'Площадь параллелограмма', '5.2', `
|
||||
<p>Аналогичная формула — для параллелограмма:</p>
|
||||
<p style="text-align:center;font-size:1.15rem">$\\boxed{\\,S_{\\text{пар}} = a b \\sin \\alpha\\,}$</p>
|
||||
<p>Здесь $a, b$ — <b>смежные стороны</b> параллелограмма, $\\alpha$ — угол между ними.</p>
|
||||
<p><b>Почему такая формула?</b> Диагональ параллелограмма делит его на <b>два равных треугольника</b>. Площадь каждого по формуле §5.1 равна $\\dfrac{1}{2}ab\\sin\\alpha$, значит площадь всего параллелограмма — вдвое больше:</p>
|
||||
<p style="text-align:center">$S_{\\text{пар}} = 2 \\cdot \\dfrac{1}{2} ab \\sin \\alpha = ab \\sin \\alpha$.</p>
|
||||
<p><b>Частные случаи:</b></p>
|
||||
<ul style="padding-left:22px;line-height:1.85">
|
||||
<li>$\\alpha = 90^\\circ \\Rightarrow \\sin\\alpha = 1$, получаем <b>прямоугольник</b>: $S = ab$.</li>
|
||||
<li>Если $a = b$ — ромб со стороной $a$ и углом $\\alpha$: $S = a^2 \\sin \\alpha$.</li>
|
||||
</ul>`);
|
||||
|
||||
html += makeCard('example', 'Площадь четырёхугольника через диагонали', '5.3', `
|
||||
<p>Для любого выпуклого четырёхугольника есть «универсальная» формула — через диагонали и угол между ними:</p>
|
||||
<p style="text-align:center;font-size:1.15rem">$\\boxed{\\,S_{4} = \\dfrac{1}{2} d_1 d_2 \\sin \\varphi\\,}$</p>
|
||||
<p>где $d_1, d_2$ — диагонали, $\\varphi$ — угол между ними.</p>
|
||||
<p><b>Примеры применения:</b></p>
|
||||
<ul style="padding-left:22px;line-height:1.85">
|
||||
<li><b>Ромб</b> с диагоналями $6$ и $8$: диагонали ромба <b>перпендикулярны</b>, поэтому $\\varphi = 90^\\circ$ и $\\sin\\varphi = 1$:<br>
|
||||
$S = \\dfrac{1}{2} \\cdot 6 \\cdot 8 = 24$.</li>
|
||||
<li><b>Параллелограмм</b> со сторонами $5$ и $8$, углом $30^\\circ$ между ними:<br>
|
||||
$S = 5 \\cdot 8 \\cdot \\sin 30^\\circ = 40 \\cdot \\tfrac{1}{2} = 20$.</li>
|
||||
<li><b>Треугольник</b> со сторонами $4$ и $6$ и углом $90^\\circ$ между ними:<br>
|
||||
$S = \\dfrac{1}{2} \\cdot 4 \\cdot 6 \\cdot \\sin 90^\\circ = 12$ — то же, что катет × катет / 2.</li>
|
||||
</ul>
|
||||
<details class="spoiler"><summary>Подсказка по выбору формулы</summary><div class="spoiler-body">
|
||||
<ul style="padding-left:18px;line-height:1.85;margin:0">
|
||||
<li>Даны <b>две стороны + угол между ними</b> треугольника → $\\frac{1}{2}ab\\sin C$.</li>
|
||||
<li>Даны <b>две стороны + угол</b> параллелограмма → $ab\\sin\\alpha$.</li>
|
||||
<li>Даны <b>обе диагонали + угол между ними</b> → $\\frac{1}{2}d_1 d_2 \\sin\\varphi$ (для ромба $\\varphi = 90°$).</li>
|
||||
</ul>
|
||||
</div></details>`);
|
||||
|
||||
/* IV1 — SVG визуализатор «Площадь треугольника по углу» */
|
||||
html += `<div class="wg" id="p5-iv1">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 1</span><div class="wg-title">Площадь треугольника по углу</div></div>
|
||||
<div class="wg-help">Двигай ползунки сторон $a, b$ и угла $A$ — треугольник перестраивается, а площадь пересчитывается по формуле $S = \\tfrac{1}{2} a b \\sin A$.</div>
|
||||
<div class="sliders">
|
||||
<label>Сторона $a$<b id="p5-iv1-aval">6</b><input type="range" id="p5-iv1-a" min="3" max="9" step="1" value="6"></label>
|
||||
<label>Сторона $b$<b id="p5-iv1-bval">5</b><input type="range" id="p5-iv1-b" min="3" max="9" step="1" value="5"></label>
|
||||
<label>Угол $A$, °<b id="p5-iv1-Aval">60</b><input type="range" id="p5-iv1-A" min="20" max="160" step="5" value="60"></label>
|
||||
</div>
|
||||
<div style="background:var(--card);border-radius:10px;padding:10px;overflow-x:auto">
|
||||
<svg id="p5-iv1-svg" viewBox="0 0 400 320" style="width:100%;min-width:320px;height:auto;display:block"></svg>
|
||||
</div>
|
||||
<div id="p5-iv1-out" style="margin-top:10px;padding:12px 14px;background:var(--pri-soft);border-radius:9px;font-size:1rem;text-align:center;line-height:1.9"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV2 — Калькулятор параллелограмма */
|
||||
html += `<div class="wg" id="p5-iv2">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 2</span><div class="wg-title">Калькулятор площади параллелограмма</div></div>
|
||||
<div class="wg-help">Введи смежные стороны $a, b$ и угол $\\alpha$ между ними — найдём площадь по формуле $S = a b \\sin \\alpha$. При $\\alpha = 90^\\circ$ это просто прямоугольник.</div>
|
||||
<div style="display:flex;gap:10px;align-items:center;flex-wrap:wrap;justify-content:center;margin-bottom:10px">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$a$ =</span>
|
||||
<input type="number" id="p5-iv2-a" class="tinp" style="width:80px;text-align:center" value="6" min="0.1" step="0.1">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$b$ =</span>
|
||||
<input type="number" id="p5-iv2-b" class="tinp" style="width:80px;text-align:center" value="10" min="0.1" step="0.1">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$\\alpha$ =</span>
|
||||
<input type="number" id="p5-iv2-A" class="tinp" style="width:80px;text-align:center" value="30" min="1" max="179">
|
||||
<span style="font-family:'JetBrains Mono',monospace">°</span>
|
||||
<button class="btn primary" id="p5-iv2-go">Вычислить</button>
|
||||
</div>
|
||||
<div id="p5-iv2-out" style="padding:12px 14px;background:var(--card);border-radius:9px;text-align:center;font-size:1rem;min-height:50px"></div>
|
||||
<div class="feedback" id="p5-iv2-fb"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV3 — DnD сортер «Подбери формулу» */
|
||||
html += `<div class="wg" id="p5-iv3">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 3</span><div class="wg-title">Подбери формулу</div></div>
|
||||
<div class="wg-help">Распредели 6 фигур по трём «формульным ящикам». Тапни карточку, потом — нужный ящик (или перетащи).</div>
|
||||
<div class="dnd-hint"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M12 2v20"/><path d="M5 12h14"/></svg> 6 фигур — 3 формулы</div>
|
||||
<div id="p5-iv3-pool"></div>
|
||||
<div style="display:grid;grid-template-columns:repeat(auto-fit,minmax(200px,1fr));gap:10px;margin-top:8px">
|
||||
<div class="drop-box"><h5 data-cat="t">$S = \\tfrac{1}{2}ab\\sin C$</h5><div class="drop-items" data-cat="t"></div></div>
|
||||
<div class="drop-box"><h5 data-cat="p">$S = ab\\sin\\alpha$</h5><div class="drop-items" data-cat="p"></div></div>
|
||||
<div class="drop-box"><h5 data-cat="d">$S = \\tfrac{1}{2}d_1 d_2 \\sin\\varphi$</h5><div class="drop-items" data-cat="d"></div></div>
|
||||
</div>
|
||||
<div class="actions"><button class="btn primary" id="p5-iv3-check">Проверить</button><button class="btn" id="p5-iv3-reset">Сначала</button></div>
|
||||
<div class="feedback" id="p5-iv3-fb"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV4 — Тренажёр площади */
|
||||
html += `<div class="wg" id="p5-iv4">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 4</span><div class="wg-title">Тренажёр площади</div></div>
|
||||
<div class="wg-help">Реши задачу и введи число (целое или округлённое до целых).</div>
|
||||
<div class="score-display"><span>Задача <b id="p5-iv4-i">1</b> / 6</span><span>Очки: <b id="p5-iv4-s">0</b> / 6</span></div>
|
||||
<div id="p5-iv4-q" style="padding:14px;background:var(--pri-soft);border-radius:10px;font-size:1.05rem;margin-bottom:10px;text-align:center"></div>
|
||||
<div style="display:flex;gap:10px;align-items:center;flex-wrap:wrap;justify-content:center">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$S$ =</span>
|
||||
<input type="number" id="p5-iv4-ans" class="tinp" style="width:110px;text-align:center" step="0.1">
|
||||
<button class="btn primary" id="p5-iv4-go">Проверить</button>
|
||||
<button class="btn" id="p5-iv4-start">Заново</button>
|
||||
</div>
|
||||
<div class="feedback" id="p5-iv4-fb"></div>
|
||||
</div>`;
|
||||
|
||||
html += secNav('p4', 'p6');
|
||||
html += readButton('p5');
|
||||
|
||||
box.innerHTML = html;
|
||||
renderMath(box);
|
||||
|
||||
/* IV1 — SVG визуализатор */
|
||||
(function(){
|
||||
const slA = document.getElementById('p5-iv1-a');
|
||||
const slB = document.getElementById('p5-iv1-b');
|
||||
const slAng = document.getElementById('p5-iv1-A');
|
||||
const labA = document.getElementById('p5-iv1-aval');
|
||||
const labB = document.getElementById('p5-iv1-bval');
|
||||
const labAng = document.getElementById('p5-iv1-Aval');
|
||||
const svg = document.getElementById('p5-iv1-svg');
|
||||
const out = document.getElementById('p5-iv1-out');
|
||||
const seen = new Set();
|
||||
function draw(){
|
||||
const a = +slA.value, b = +slB.value, Adeg = +slAng.value;
|
||||
labA.textContent = a; labB.textContent = b; labAng.textContent = Adeg;
|
||||
const aRad = deg2rad(Adeg);
|
||||
// В пикселях: множитель 20 на единицу
|
||||
const k = 20;
|
||||
const aPx = a * k, bPx = b * k;
|
||||
// A в (80, 240), B справа по горизонтали, C — поворот на угол A вокруг A.
|
||||
const A = {x: 80, y: 240};
|
||||
const B = {x: 80 + aPx, y: 240};
|
||||
const C = {x: 80 + bPx * Math.cos(aRad), y: 240 - bPx * Math.sin(aRad)};
|
||||
// векторы в A: вдоль AB и вдоль AC
|
||||
const uAB = unitVec(A, B);
|
||||
const uAC = unitVec(A, C);
|
||||
let s = '';
|
||||
s += '<rect x="0" y="0" width="400" height="320" fill="none"/>';
|
||||
s += '<polygon points="'+A.x+','+A.y+' '+B.x+','+B.y+' '+C.x+','+C.y+'" fill="rgba(217,119,6,.1)" stroke="#b45309" stroke-width="2.2" stroke-linejoin="round"/>';
|
||||
// дуга угла A
|
||||
s += '<path d="'+angleArcAuto(A, uAB, uAC, 32)+'" fill="none" stroke="#dc2626" stroke-width="2.2"/>';
|
||||
// подпись угла A
|
||||
const halfRad = aRad / 2;
|
||||
const tx = A.x + 52*Math.cos(halfRad);
|
||||
const ty = A.y - 52*Math.sin(halfRad);
|
||||
s += '<text x="'+tx+'" y="'+ty+'" text-anchor="middle" dominant-baseline="middle" font-family="Inter,sans-serif" font-size="14" font-weight="700" fill="#dc2626">A='+Adeg+'°</text>';
|
||||
// вершины
|
||||
s += '<circle cx="'+A.x+'" cy="'+A.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<circle cx="'+B.x+'" cy="'+B.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<circle cx="'+C.x+'" cy="'+C.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<text x="'+(A.x-12)+'" y="'+(A.y+18)+'" text-anchor="end" font-family="Inter,sans-serif" font-size="16" font-weight="700" fill="#0f172a">A</text>';
|
||||
s += '<text x="'+(B.x+12)+'" y="'+(B.y+18)+'" text-anchor="start" font-family="Inter,sans-serif" font-size="16" font-weight="700" fill="#0f172a">B</text>';
|
||||
s += '<text x="'+(C.x + (C.x>=A.x?10:-10))+'" y="'+(C.y-8)+'" text-anchor="'+(C.x>=A.x?'start':'end')+'" font-family="Inter,sans-serif" font-size="16" font-weight="700" fill="#0f172a">C</text>';
|
||||
// подписи сторон
|
||||
s += '<text x="'+((A.x+B.x)/2)+'" y="'+(A.y+30)+'" text-anchor="middle" font-family="JetBrains Mono,monospace" font-size="12" fill="#b45309">a='+a+'</text>';
|
||||
const midAC = {x:(A.x+C.x)/2, y:(A.y+C.y)/2};
|
||||
// нормаль к AC, направленная "наружу" треугольника (от B)
|
||||
const nAC = {x:-(C.y-A.y), y:(C.x-A.x)};
|
||||
const nL = Math.sqrt(nAC.x*nAC.x+nAC.y*nAC.y)||1;
|
||||
// выбираем сторону, противоположную B
|
||||
const sign = ((B.x-A.x)*nAC.x + (B.y-A.y)*nAC.y) > 0 ? -1 : 1;
|
||||
const labP = {x: midAC.x + sign*14*nAC.x/nL, y: midAC.y + sign*14*nAC.y/nL};
|
||||
s += '<text x="'+labP.x+'" y="'+labP.y+'" text-anchor="middle" font-family="JetBrains Mono,monospace" font-size="12" fill="#b45309">b='+b+'</text>';
|
||||
svg.innerHTML = s;
|
||||
// расчёт площади
|
||||
const S = 0.5 * a * b * Math.sin(aRad);
|
||||
out.innerHTML = '$S = \\dfrac{1}{2} \\cdot a \\cdot b \\cdot \\sin A = \\dfrac{1}{2} \\cdot '+a+' \\cdot '+b+' \\cdot \\sin '+Adeg+'^\\circ \\approx '+S.toFixed(2)+'$';
|
||||
renderMath(out);
|
||||
seen.add(a+'_'+b+'_'+Adeg);
|
||||
if(seen.size >= 5 && !seen.has('done')){ addXp(10,'p5-iv1'); bumpProgress('p5', 15); seen.add('done'); }
|
||||
}
|
||||
[slA, slB, slAng].forEach(sl => sl.addEventListener('input', draw));
|
||||
draw();
|
||||
})();
|
||||
|
||||
/* IV2 — Калькулятор параллелограмма */
|
||||
(function(){
|
||||
const aI = document.getElementById('p5-iv2-a');
|
||||
const bI = document.getElementById('p5-iv2-b');
|
||||
const AI = document.getElementById('p5-iv2-A');
|
||||
const go = document.getElementById('p5-iv2-go');
|
||||
const out = document.getElementById('p5-iv2-out');
|
||||
const fb = document.getElementById('p5-iv2-fb');
|
||||
let solved = 0;
|
||||
function calc(){
|
||||
const a = parseFloat(aI.value), b = parseFloat(bI.value), Adeg = parseFloat(AI.value);
|
||||
if(isNaN(a) || isNaN(b) || isNaN(Adeg)){ feedback(fb, false, '✗ Введи все три числа.'); return; }
|
||||
if(a<=0 || b<=0){ feedback(fb, false, '✗ Стороны должны быть положительны.'); return; }
|
||||
if(Adeg<=0 || Adeg>=180){ feedback(fb, false, '✗ Угол должен быть в диапазоне (0°; 180°).'); return; }
|
||||
const r = deg2rad(Adeg);
|
||||
const S = a * b * Math.sin(r);
|
||||
let html = '$S = a \\cdot b \\cdot \\sin \\alpha = '+a+' \\cdot '+b+' \\cdot \\sin '+Adeg+'^\\circ \\approx '+S.toFixed(2)+'$';
|
||||
if(Math.abs(Adeg - 90) < 1e-9){
|
||||
html += '<br><span style="color:var(--ok);font-weight:700">Особый случай: $\\alpha = 90^\\circ$ — это прямоугольник, $S = a b = '+(a*b).toFixed(2)+'$.</span>';
|
||||
}
|
||||
out.innerHTML = html;
|
||||
renderMath(out);
|
||||
feedback(fb, true, '✓ Площадь найдена.');
|
||||
solved++;
|
||||
if(solved === 1){ addXp(10,'p5-iv2'); bumpProgress('p5', 15); }
|
||||
}
|
||||
go.addEventListener('click', calc);
|
||||
calc();
|
||||
})();
|
||||
|
||||
/* IV3 — DnD сортер */
|
||||
(function(){
|
||||
const items = [
|
||||
{ id:'f1', cat:'t', html:'треугольник со сторонами $a, b$ и углом $C$ между ними' },
|
||||
{ id:'f2', cat:'p', html:'параллелограмм со сторонами $a, b$ и углом $\\alpha$' },
|
||||
{ id:'f3', cat:'p', html:'прямоугольник со сторонами $a, b$ ($\\alpha=90^\\circ$)' },
|
||||
{ id:'f4', cat:'d', html:'ромб с диагоналями $d_1, d_2$' },
|
||||
{ id:'f5', cat:'d', html:'трапеция с диагоналями $d_1, d_2$ и углом $\\varphi$' },
|
||||
{ id:'f6', cat:'t', html:'равносторонний треугольник со стороной $a$ ($C = 60^\\circ$)' },
|
||||
];
|
||||
const sorter = setupSorter({
|
||||
poolId:'p5-iv3-pool',
|
||||
scopeSelector:'#p5-iv3',
|
||||
items: items,
|
||||
cats:['t','p','d'],
|
||||
columnLayout:true,
|
||||
});
|
||||
document.getElementById('p5-iv3-check').addEventListener('click', ()=>{
|
||||
const fb = document.getElementById('p5-iv3-fb');
|
||||
const placedCount = items.filter(it => sorter.placed[it.id]).length;
|
||||
const correct = items.filter(it => sorter.placed[it.id] === it.cat).length;
|
||||
if(placedCount < items.length){ feedback(fb, false, '✗ Размести все 6 фигур.'); return; }
|
||||
if(correct === items.length){ feedback(fb, true, '✓ Все 6 на месте! +15 XP'); addXp(15,'p5-iv3'); bumpProgress('p5', 25); }
|
||||
else feedback(fb, false, '✗ Правильно ' + correct + ' из 6. Попробуй ещё.');
|
||||
});
|
||||
document.getElementById('p5-iv3-reset').addEventListener('click', ()=>{ sorter.reset(); document.getElementById('p5-iv3-fb').style.display = 'none'; });
|
||||
})();
|
||||
|
||||
/* IV4 — Тренажёр */
|
||||
(function(){
|
||||
const Q = [
|
||||
{ q:'Треугольник: $a = 5$, $b = 8$, $C = 30^\\circ$. Найди $S$.', ans:10, tol:0.2, hint:'$S = \\tfrac{1}{2} \\cdot 5 \\cdot 8 \\cdot \\sin 30^\\circ = 20 \\cdot 0{,}5 = 10$' },
|
||||
{ q:'Параллелограмм: $a = 6$, $b = 10$, $\\alpha = 90^\\circ$. Найди $S$.', ans:60, tol:0.2, hint:'$\\sin 90^\\circ = 1$, $S = a b = 60$' },
|
||||
{ q:'Ромб с диагоналями $12$ и $16$. Найди $S$.', ans:96, tol:0.2, hint:'диагонали ромба перпендикулярны: $S = \\tfrac{1}{2} \\cdot 12 \\cdot 16 = 96$' },
|
||||
{ q:'Треугольник: $a = b = 4$, $C = 60^\\circ$. Найди $S$ (округли до целого).', ans:7, tol:0.5, hint:'$S = \\tfrac{1}{2} \\cdot 16 \\cdot \\sin 60^\\circ = 8 \\cdot \\tfrac{\\sqrt{3}}{2} = 4\\sqrt{3} \\approx 6{,}93 \\approx 7$' },
|
||||
{ q:'Прямоугольник со сторонами $7$ и $12$. Найди $S$.', ans:84, tol:0.2, hint:'$S = 7 \\cdot 12 = 84$' },
|
||||
{ q:'Треугольник: $a = 10$, $b = 10$, $C = 90^\\circ$. Найди $S$.', ans:50, tol:0.2, hint:'$S = \\tfrac{1}{2} \\cdot 100 \\cdot \\sin 90^\\circ = 50$' },
|
||||
];
|
||||
let i = 0, score = 0;
|
||||
function show(){
|
||||
if(i >= Q.length){
|
||||
document.getElementById('p5-iv4-q').innerHTML = '<b>Готово!</b> Результат: ' + score + ' / ' + Q.length;
|
||||
if(score === Q.length){ addXp(15,'p5-iv4'); bumpProgress('p5', 25); achievement('p5_done'); }
|
||||
else if(score >= 4){ addXp(8,'p5-iv4'); bumpProgress('p5', 15); }
|
||||
return;
|
||||
}
|
||||
document.getElementById('p5-iv4-i').textContent = (i+1);
|
||||
document.getElementById('p5-iv4-s').textContent = score;
|
||||
document.getElementById('p5-iv4-q').innerHTML = Q[i].q;
|
||||
document.getElementById('p5-iv4-ans').value = '';
|
||||
renderMath(document.getElementById('p5-iv4-q'));
|
||||
document.getElementById('p5-iv4-fb').style.display = 'none';
|
||||
}
|
||||
function go(){
|
||||
if(i >= Q.length) return;
|
||||
const fb = document.getElementById('p5-iv4-fb');
|
||||
const ans = parseFloat(document.getElementById('p5-iv4-ans').value);
|
||||
if(isNaN(ans)){ feedback(fb, false, '✗ Введи число.'); return; }
|
||||
if(Math.abs(ans - Q[i].ans) <= Q[i].tol){ score++; feedback(fb, true, '✓ Верно! '+Q[i].hint+'. Дальше ▶'); }
|
||||
else feedback(fb, false, '✗ Неверно. Ответ: '+Q[i].ans+' ('+Q[i].hint+'). Дальше ▶');
|
||||
document.getElementById('p5-iv4-s').textContent = score;
|
||||
i++;
|
||||
setTimeout(show, 1400);
|
||||
}
|
||||
document.getElementById('p5-iv4-go').addEventListener('click', go);
|
||||
document.getElementById('p5-iv4-ans').addEventListener('keydown', e=>{ if(e.key==='Enter') go(); });
|
||||
document.getElementById('p5-iv4-start').addEventListener('click', ()=>{ i=0; score=0; show(); });
|
||||
show();
|
||||
})();
|
||||
|
||||
wireReadBtn('p5');
|
||||
}
|
||||
|
||||
/* ===== §6 Среднее геометрическое в прямоугольном треугольнике ===== */
|
||||
function buildP6(){
|
||||
const box = document.getElementById('p6-body');
|
||||
let html = '';
|
||||
|
||||
html += makeCard('theory', 'Высота к гипотенузе и проекции катетов', '6.1', `
|
||||
<p>Рассмотрим прямоугольный треугольник $ABC$ с прямым углом $C$. Из вершины $C$ опустим <b>высоту</b> $h = CH$ на гипотенузу $c = AB$. Эта высота делит гипотенузу на два отрезка: $AH = b_1$ и $BH = a_1$, причём $a_1 + b_1 = c$.</p>
|
||||
<p>Тогда в треугольнике справедливы <b>три замечательных соотношения</b>:</p>
|
||||
<p style="text-align:center;font-size:1.1rem">$\\boxed{\\,h^2 = a_1 b_1,\\qquad a^2 = c \\cdot a_1,\\qquad b^2 = c \\cdot b_1\\,}$</p>
|
||||
<p>Здесь $a, b$ — катеты ($a = BC$ напротив $A$, $b = AC$ напротив $B$), $h$ — высота к гипотенузе, $a_1$ — проекция катета $a$ на гипотенузу (отрезок $BH$), $b_1$ — проекция катета $b$ на гипотенузу (отрезок $AH$).</p>
|
||||
<details class="spoiler"><summary>Откуда берутся эти соотношения?</summary><div class="spoiler-body">
|
||||
<p>Высота $CH$ разбивает $\\triangle ABC$ на два маленьких прямоугольных треугольника — $\\triangle ACH$ и $\\triangle CBH$. Все три треугольника <b>подобны друг другу</b> (имеют по два равных угла).</p>
|
||||
<p>Из подобия $\\triangle ACH \\sim \\triangle CBH$ получаем $\\dfrac{AH}{CH} = \\dfrac{CH}{BH}$, то есть $\\dfrac{b_1}{h} = \\dfrac{h}{a_1}$, откуда $h^2 = a_1 b_1$.</p>
|
||||
<p>Из подобия $\\triangle ABC \\sim \\triangle ACH$ получаем $\\dfrac{AB}{AC} = \\dfrac{AC}{AH}$, то есть $\\dfrac{c}{b} = \\dfrac{b}{b_1}$, откуда $b^2 = c b_1$. Аналогично — третье соотношение.</p>
|
||||
</div></details>`);
|
||||
|
||||
html += makeCard('rule', 'Среднее геометрическое', '6.2', `
|
||||
<p>Эти три формулы — это <b>среднее геометрическое</b> в действии. Среднее геометрическое чисел $x, y$ — это $\\sqrt{xy}$. Получаем:</p>
|
||||
<ul style="padding-left:22px;line-height:2">
|
||||
<li>$h = \\sqrt{a_1 b_1}$ — <b>высота</b> к гипотенузе есть среднее геометрическое проекций катетов.</li>
|
||||
<li>$a = \\sqrt{c \\cdot a_1}$ — катет $a$ есть среднее геометрическое гипотенузы и проекции этого катета.</li>
|
||||
<li>$b = \\sqrt{c \\cdot b_1}$ — катет $b$ есть среднее геометрическое гипотенузы и проекции этого катета.</li>
|
||||
</ul>
|
||||
<p>Эти три факта называют <b>метрическими соотношениями</b> в прямоугольном треугольнике, и они моментально решают задачи, в которых заданы какие-то «куски» гипотенузы.</p>
|
||||
<details class="spoiler"><summary>Почему «среднее геометрическое»?</summary><div class="spoiler-body">
|
||||
<p>Запись $h^2 = a_1 b_1$ означает, что $h$ — такое число, квадрат которого равен произведению $a_1$ и $b_1$. Это и есть классическое определение среднего геометрического двух положительных чисел: $h = \\sqrt{a_1 b_1}$.</p>
|
||||
</div></details>`);
|
||||
|
||||
html += makeCard('example', 'Примеры применения', '6.3', `
|
||||
<p><b>Пример 1.</b> $c = 10$, проекции $a_1 = 4$, $b_1 = 6$. Найти $h, a, b$.</p>
|
||||
<ul style="padding-left:22px;line-height:1.85">
|
||||
<li>$h = \\sqrt{a_1 b_1} = \\sqrt{4 \\cdot 6} = \\sqrt{24} = 2\\sqrt{6} \\approx 4{,}9$</li>
|
||||
<li>$a = \\sqrt{c \\cdot a_1} = \\sqrt{40} = 2\\sqrt{10}$</li>
|
||||
<li>$b = \\sqrt{c \\cdot b_1} = \\sqrt{60} = 2\\sqrt{15}$</li>
|
||||
</ul>
|
||||
<p><b>Пример 2.</b> Треугольник $6$–$8$–$10$ (3–4–5, умноженное на $2$). Найти $h, a_1, b_1$.</p>
|
||||
<ul style="padding-left:22px;line-height:1.85">
|
||||
<li>$a = 6$, $c = 10 \\Rightarrow a_1 = \\dfrac{a^2}{c} = \\dfrac{36}{10} = 3{,}6$</li>
|
||||
<li>$b = 8$, $c = 10 \\Rightarrow b_1 = \\dfrac{b^2}{c} = \\dfrac{64}{10} = 6{,}4$</li>
|
||||
<li>Проверка: $a_1 + b_1 = 3{,}6 + 6{,}4 = 10 = c$ ✓</li>
|
||||
<li>$h = \\sqrt{a_1 b_1} = \\sqrt{3{,}6 \\cdot 6{,}4} = \\sqrt{23{,}04} = 4{,}8$</li>
|
||||
</ul>
|
||||
<p><b>Сверка площадей:</b> $S = \\tfrac{1}{2} a b = \\tfrac{1}{2} \\cdot 6 \\cdot 8 = 24$ и $S = \\tfrac{1}{2} c h = \\tfrac{1}{2} \\cdot 10 \\cdot 4{,}8 = 24$. Совпало — соотношение работает.</p>`);
|
||||
|
||||
/* IV1 — SVG визуализатор */
|
||||
html += `<div class="wg" id="p6-iv1">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 1</span><div class="wg-title">Конструктор соотношений</div></div>
|
||||
<div class="wg-help">Меняй угол $A$ — точка $H$ перемещается по гипотенузе, проекции $a_1, b_1$ меняются, и три соотношения $h^2 = a_1 b_1$, $a^2 = c a_1$, $b^2 = c b_1$ всё время выполняются.</div>
|
||||
<div class="sliders">
|
||||
<label>Угол $A$, °<b id="p6-iv1-aval">40</b><input type="range" id="p6-iv1-a" min="30" max="60" step="1" value="40"></label>
|
||||
</div>
|
||||
<div style="background:var(--card);border-radius:10px;padding:10px;overflow-x:auto">
|
||||
<svg id="p6-iv1-svg" viewBox="0 0 480 320" style="width:100%;min-width:360px;height:auto;display:block"></svg>
|
||||
</div>
|
||||
<div id="p6-iv1-out" style="margin-top:10px;padding:12px 14px;background:var(--pri-soft);border-radius:9px;font-size:.98rem;line-height:1.95"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV2 — Калькулятор h */
|
||||
html += `<div class="wg" id="p6-iv2">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 2</span><div class="wg-title">Калькулятор $h$ и $c$</div></div>
|
||||
<div class="wg-help">Введи проекции катетов $a_1, b_1$ — найдём высоту $h$, гипотенузу $c$, катеты $a, b$ и площадь $S$.</div>
|
||||
<div style="display:flex;gap:10px;align-items:center;flex-wrap:wrap;justify-content:center;margin-bottom:10px">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$a_1$ =</span>
|
||||
<input type="number" id="p6-iv2-a1" class="tinp" style="width:90px;text-align:center" value="4" min="0.1" step="0.1">
|
||||
<span style="font-family:'JetBrains Mono',monospace">$b_1$ =</span>
|
||||
<input type="number" id="p6-iv2-b1" class="tinp" style="width:90px;text-align:center" value="9" min="0.1" step="0.1">
|
||||
<button class="btn primary" id="p6-iv2-go">Найти $h$ и $c$</button>
|
||||
</div>
|
||||
<div id="p6-iv2-out" style="padding:12px 14px;background:var(--card);border-radius:9px;font-size:1rem;line-height:1.85;min-height:50px"></div>
|
||||
<div class="feedback" id="p6-iv2-fb"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV3 — Какое соотношение? */
|
||||
html += `<div class="wg" id="p6-iv3">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 3</span><div class="wg-title">Какое соотношение применить?</div></div>
|
||||
<div class="wg-help">Даны какие-то элементы прямоугольного треугольника — выбери, какое из трёх соотношений поможет найти искомую величину.</div>
|
||||
<div class="score-display"><span>Задача <b id="p6-iv3-i">1</b> / 6</span><span>Очки: <b id="p6-iv3-s">0</b> / 6</span></div>
|
||||
<div id="p6-iv3-q" style="padding:14px;background:var(--pri-soft);border-radius:10px;font-size:1.05rem;text-align:center;margin-bottom:10px"></div>
|
||||
<div style="display:grid;grid-template-columns:repeat(auto-fit,minmax(150px,1fr));gap:8px">
|
||||
<button class="btn primary" data-ans="h" id="p6-iv3-h">$h^2 = a_1 b_1$</button>
|
||||
<button class="btn primary" data-ans="a" id="p6-iv3-a">$a^2 = c a_1$</button>
|
||||
<button class="btn primary" data-ans="b" id="p6-iv3-b">$b^2 = c b_1$</button>
|
||||
</div>
|
||||
<div class="feedback" id="p6-iv3-fb"></div>
|
||||
</div>`;
|
||||
|
||||
/* IV4 — Тренажёр */
|
||||
html += `<div class="wg" id="p6-iv4">
|
||||
<div class="wg-header"><span class="wg-badge">ИНТЕРАКТИВ 4</span><div class="wg-title">Тренажёр среднего геометрического</div></div>
|
||||
<div class="wg-help">Реши задачу и введи число (целое или округлённое до сотых).</div>
|
||||
<div class="score-display"><span>Задача <b id="p6-iv4-i">1</b> / 6</span><span>Очки: <b id="p6-iv4-s">0</b> / 6</span></div>
|
||||
<div id="p6-iv4-q" style="padding:14px;background:var(--pri-soft);border-radius:10px;font-size:1.05rem;margin-bottom:10px;text-align:center"></div>
|
||||
<div style="display:flex;gap:10px;align-items:center;flex-wrap:wrap;justify-content:center">
|
||||
<span style="font-family:'JetBrains Mono',monospace">ответ =</span>
|
||||
<input type="number" id="p6-iv4-ans" class="tinp" style="width:120px;text-align:center" step="0.01">
|
||||
<button class="btn primary" id="p6-iv4-go">Проверить</button>
|
||||
<button class="btn" id="p6-iv4-start">Заново</button>
|
||||
</div>
|
||||
<div class="feedback" id="p6-iv4-fb"></div>
|
||||
</div>`;
|
||||
|
||||
html += secNav('p5', 'final1');
|
||||
html += readButton('p6');
|
||||
|
||||
box.innerHTML = html;
|
||||
renderMath(box);
|
||||
|
||||
/* IV1 — SVG */
|
||||
(function(){
|
||||
const sl = document.getElementById('p6-iv1-a');
|
||||
const lab = document.getElementById('p6-iv1-aval');
|
||||
const svg = document.getElementById('p6-iv1-svg');
|
||||
const out = document.getElementById('p6-iv1-out');
|
||||
const seen = new Set();
|
||||
function draw(){
|
||||
const Adeg = +sl.value;
|
||||
lab.textContent = Adeg;
|
||||
const Arad = deg2rad(Adeg);
|
||||
// Гипотенуза AB длиной 300px по низу.
|
||||
const cPx = 300;
|
||||
const A = {x: 90, y: 260};
|
||||
const B = {x: 90 + cPx, y: 260};
|
||||
// Точка C — над гипотенузой, угол при A равен Adeg, угол при B равен 90 - Adeg.
|
||||
// AC = c * cos A, BC = c * sin A. Из A под углом Adeg вверх.
|
||||
const ACpx = cPx * Math.cos(Arad);
|
||||
// Координаты C: от A на расстояние AC под углом Adeg к AB (вверх)
|
||||
const C = {x: A.x + ACpx * Math.cos(Arad), y: A.y - ACpx * Math.sin(Arad)};
|
||||
// H — основание высоты из C на AB.
|
||||
const H = {x: C.x, y: A.y};
|
||||
// длины
|
||||
const a1 = Math.abs(H.x - B.x); // BH (проекция BC)
|
||||
const b1 = Math.abs(H.x - A.x); // AH (проекция AC)
|
||||
const hPx = Math.abs(C.y - H.y);
|
||||
const aPx = Math.sqrt((B.x-C.x)*(B.x-C.x) + (B.y-C.y)*(B.y-C.y));
|
||||
const bPx = Math.sqrt((A.x-C.x)*(A.x-C.x) + (A.y-C.y)*(A.y-C.y));
|
||||
// в "единичных" единицах (делим px на 30)
|
||||
const sc = 30;
|
||||
const a = aPx/sc, b = bPx/sc, c = cPx/sc, h = hPx/sc, _a1 = a1/sc, _b1 = b1/sc;
|
||||
let s = '';
|
||||
s += '<rect x="0" y="0" width="480" height="320" fill="none"/>';
|
||||
// подсветка маленьких треугольников
|
||||
s += '<polygon points="'+A.x+','+A.y+' '+H.x+','+H.y+' '+C.x+','+C.y+'" fill="rgba(14,165,233,.18)" stroke="none"/>';
|
||||
s += '<polygon points="'+B.x+','+B.y+' '+H.x+','+H.y+' '+C.x+','+C.y+'" fill="rgba(236,72,153,.18)" stroke="none"/>';
|
||||
// основной треугольник (контур)
|
||||
s += '<polygon points="'+A.x+','+A.y+' '+B.x+','+B.y+' '+C.x+','+C.y+'" fill="none" stroke="#b45309" stroke-width="2.4" stroke-linejoin="round"/>';
|
||||
// высота CH
|
||||
s += '<line x1="'+C.x+'" y1="'+C.y+'" x2="'+H.x+'" y2="'+H.y+'" stroke="#dc2626" stroke-width="2.2" stroke-dasharray="6 4"/>';
|
||||
// маркер прямого угла при C (катеты CA и CB)
|
||||
const uCA = unitVec(C, A);
|
||||
const uCB = unitVec(C, B);
|
||||
s += '<polyline points="'+rightAngleMark(C, uCA, uCB, 11)+'" fill="none" stroke="#0f172a" stroke-width="1.8"/>';
|
||||
// маркер прямого угла при H (CH и HB)
|
||||
const uHC = unitVec(H, C);
|
||||
const uHB = unitVec(H, B);
|
||||
s += '<polyline points="'+rightAngleMark(H, uHC, uHB, 9)+'" fill="none" stroke="#0f172a" stroke-width="1.6"/>';
|
||||
// вершины
|
||||
s += '<circle cx="'+A.x+'" cy="'+A.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<circle cx="'+B.x+'" cy="'+B.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<circle cx="'+C.x+'" cy="'+C.y+'" r="4" fill="#0f172a"/>';
|
||||
s += '<circle cx="'+H.x+'" cy="'+H.y+'" r="3.5" fill="#dc2626"/>';
|
||||
s += '<text x="'+(A.x-12)+'" y="'+(A.y+18)+'" text-anchor="end" font-family="Inter,sans-serif" font-size="15" font-weight="700">A</text>';
|
||||
s += '<text x="'+(B.x+12)+'" y="'+(B.y+18)+'" text-anchor="start" font-family="Inter,sans-serif" font-size="15" font-weight="700">B</text>';
|
||||
s += '<text x="'+C.x+'" y="'+(C.y-10)+'" text-anchor="middle" font-family="Inter,sans-serif" font-size="15" font-weight="700">C</text>';
|
||||
s += '<text x="'+H.x+'" y="'+(H.y+18)+'" text-anchor="middle" font-family="Inter,sans-serif" font-size="13" font-weight="700" fill="#dc2626">H</text>';
|
||||
// подписи отрезков
|
||||
s += '<text x="'+((A.x+H.x)/2)+'" y="'+(A.y+32)+'" text-anchor="middle" font-family="JetBrains Mono,monospace" font-size="11" fill="#0ea5e9">b₁='+b1.toFixed(0)+'</text>';
|
||||
s += '<text x="'+((H.x+B.x)/2)+'" y="'+(A.y+32)+'" text-anchor="middle" font-family="JetBrains Mono,monospace" font-size="11" fill="#ec4899">a₁='+a1.toFixed(0)+'</text>';
|
||||
s += '<text x="'+(H.x+10)+'" y="'+((C.y+H.y)/2)+'" text-anchor="start" font-family="JetBrains Mono,monospace" font-size="11" fill="#dc2626">h='+hPx.toFixed(0)+'</text>';
|
||||
s += '<text x="'+((A.x+C.x)/2 - 14)+'" y="'+((A.y+C.y)/2)+'" text-anchor="end" font-family="JetBrains Mono,monospace" font-size="11" fill="#b45309">b='+bPx.toFixed(0)+'</text>';
|
||||
s += '<text x="'+((B.x+C.x)/2 + 14)+'" y="'+((B.y+C.y)/2)+'" text-anchor="start" font-family="JetBrains Mono,monospace" font-size="11" fill="#b45309">a='+aPx.toFixed(0)+'</text>';
|
||||
svg.innerHTML = s;
|
||||
// соотношения (в пикселях — но проверка работает в любых единицах)
|
||||
out.innerHTML = '<b>Три соотношения (в пикселях):</b><br>'
|
||||
+ '$h^2 = '+hPx.toFixed(0)+'^2 \\approx '+(hPx*hPx).toFixed(0)+'$, $a_1 \\cdot b_1 = '+a1.toFixed(0)+' \\cdot '+b1.toFixed(0)+' \\approx '+(a1*b1).toFixed(0)+'$ ✓<br>'
|
||||
+ '$a^2 = '+aPx.toFixed(0)+'^2 \\approx '+(aPx*aPx).toFixed(0)+'$, $c \\cdot a_1 = '+cPx+' \\cdot '+a1.toFixed(0)+' \\approx '+(cPx*a1).toFixed(0)+'$ ✓<br>'
|
||||
+ '$b^2 = '+bPx.toFixed(0)+'^2 \\approx '+(bPx*bPx).toFixed(0)+'$, $c \\cdot b_1 = '+cPx+' \\cdot '+b1.toFixed(0)+' \\approx '+(cPx*b1).toFixed(0)+'$ ✓';
|
||||
renderMath(out);
|
||||
seen.add(Adeg);
|
||||
if(seen.size >= 5 && !seen.has('done')){ addXp(10,'p6-iv1'); bumpProgress('p6', 15); seen.add('done'); }
|
||||
}
|
||||
sl.addEventListener('input', draw);
|
||||
draw();
|
||||
})();
|
||||
|
||||
/* IV2 — Калькулятор */
|
||||
(function(){
|
||||
const aI = document.getElementById('p6-iv2-a1');
|
||||
const bI = document.getElementById('p6-iv2-b1');
|
||||
const go = document.getElementById('p6-iv2-go');
|
||||
const out = document.getElementById('p6-iv2-out');
|
||||
const fb = document.getElementById('p6-iv2-fb');
|
||||
let solved = 0;
|
||||
function calc(){
|
||||
const a1 = parseFloat(aI.value), b1 = parseFloat(bI.value);
|
||||
if(isNaN(a1) || isNaN(b1)){ feedback(fb, false, '✗ Введи оба числа.'); return; }
|
||||
if(a1<=0 || b1<=0){ feedback(fb, false, '✗ Проекции должны быть положительны.'); return; }
|
||||
const c = a1 + b1;
|
||||
const h = Math.sqrt(a1 * b1);
|
||||
const a = Math.sqrt(c * a1);
|
||||
const b = Math.sqrt(c * b1);
|
||||
const S = 0.5 * c * h;
|
||||
out.innerHTML = '<b>$c = a_1 + b_1 = '+a1+' + '+b1+' = '+c+'$</b><br>'
|
||||
+ '$h = \\sqrt{a_1 \\cdot b_1} = \\sqrt{'+a1+' \\cdot '+b1+'} = \\sqrt{'+(a1*b1)+'} \\approx '+h.toFixed(2)+'$<br>'
|
||||
+ '$a = \\sqrt{c \\cdot a_1} = \\sqrt{'+(c*a1)+'} \\approx '+a.toFixed(2)+'$<br>'
|
||||
+ '$b = \\sqrt{c \\cdot b_1} = \\sqrt{'+(c*b1)+'} \\approx '+b.toFixed(2)+'$<br>'
|
||||
+ '$S = \\dfrac{1}{2} c h \\approx '+S.toFixed(2)+'$ (сверка: $\\tfrac{1}{2}ab \\approx '+(0.5*a*b).toFixed(2)+'$)';
|
||||
renderMath(out);
|
||||
feedback(fb, true, '✓ Все элементы найдены.');
|
||||
solved++;
|
||||
if(solved === 1){ addXp(10,'p6-iv2'); bumpProgress('p6', 15); }
|
||||
}
|
||||
go.addEventListener('click', calc);
|
||||
calc();
|
||||
})();
|
||||
|
||||
/* IV3 — Какое соотношение? */
|
||||
(function(){
|
||||
const Q = [
|
||||
{ expr:'Известно $c = 10$, $a_1 = 4$. Найти катет $a$.', ans:'a', why:'$a^2 = c \\cdot a_1 = 40 \\Rightarrow a = \\sqrt{40}$' },
|
||||
{ expr:'Известно $a_1 = 9$, $b_1 = 16$. Найти высоту $h$.', ans:'h', why:'$h^2 = a_1 \\cdot b_1 = 144 \\Rightarrow h = 12$' },
|
||||
{ expr:'Известно $c = 25$, $b_1 = 9$. Найти катет $b$.', ans:'b', why:'$b^2 = c \\cdot b_1 = 225 \\Rightarrow b = 15$' },
|
||||
{ expr:'Известно $a = 6$, $c = 9$. Найти $a_1$.', ans:'a', why:'из $a^2 = c \\cdot a_1$: $a_1 = a^2/c = 36/9 = 4$' },
|
||||
{ expr:'Известно $h = 6$, $a_1 = 4$. Найти $b_1$.', ans:'h', why:'из $h^2 = a_1 b_1$: $b_1 = h^2/a_1 = 36/4 = 9$' },
|
||||
{ expr:'Известно $b = 8$, $c = 16$. Найти $b_1$.', ans:'b', why:'из $b^2 = c \\cdot b_1$: $b_1 = b^2/c = 64/16 = 4$' },
|
||||
];
|
||||
let i = 0, score = 0;
|
||||
function show(){
|
||||
if(i >= Q.length){
|
||||
document.getElementById('p6-iv3-q').innerHTML = '<b>Готово!</b> Результат: ' + score + ' / ' + Q.length;
|
||||
if(score === Q.length){ addXp(15,'p6-iv3'); bumpProgress('p6', 25); }
|
||||
else if(score >= Q.length - 1){ addXp(8,'p6-iv3'); bumpProgress('p6', 15); }
|
||||
return;
|
||||
}
|
||||
document.getElementById('p6-iv3-i').textContent = (i+1);
|
||||
document.getElementById('p6-iv3-s').textContent = score;
|
||||
document.getElementById('p6-iv3-q').innerHTML = Q[i].expr;
|
||||
renderMath(document.getElementById('p6-iv3-q'));
|
||||
document.getElementById('p6-iv3-fb').style.display = 'none';
|
||||
}
|
||||
function answer(a){
|
||||
if(i >= Q.length) return;
|
||||
const fb = document.getElementById('p6-iv3-fb');
|
||||
if(a === Q[i].ans){ score++; feedback(fb, true, '✓ Верно! '+Q[i].why+'. Дальше ▶'); }
|
||||
else feedback(fb, false, '✗ Нет. Нужно: '+Q[i].why+'. Дальше ▶');
|
||||
document.getElementById('p6-iv3-s').textContent = score;
|
||||
i++;
|
||||
setTimeout(show, 1200);
|
||||
}
|
||||
['h','a','b'].forEach(k=>{
|
||||
const btn = document.getElementById('p6-iv3-'+k); if(btn) btn.addEventListener('click', ()=>answer(k));
|
||||
});
|
||||
show();
|
||||
})();
|
||||
|
||||
/* IV4 — Тренажёр */
|
||||
(function(){
|
||||
const Q = [
|
||||
{ q:'$a_1 = 4$, $b_1 = 9$. Найти $h$.', ans:6, tol:0.05, hint:'$h = \\sqrt{4 \\cdot 9} = \\sqrt{36} = 6$' },
|
||||
{ q:'$c = 20$, $b_1 = 5$. Найти $b$.', ans:10, tol:0.05, hint:'$b = \\sqrt{c b_1} = \\sqrt{100} = 10$' },
|
||||
{ q:'$h = 12$, $a_1 = 9$. Найти $b_1$.', ans:16, tol:0.1, hint:'$b_1 = h^2/a_1 = 144/9 = 16$' },
|
||||
{ q:'$a = 6$, $c = 9$. Найти $a_1$.', ans:4, tol:0.05, hint:'$a_1 = a^2/c = 36/9 = 4$' },
|
||||
{ q:'Среднее геометрическое чисел $4$ и $25$.', ans:10, tol:0.05, hint:'$\\sqrt{4 \\cdot 25} = \\sqrt{100} = 10$' },
|
||||
{ q:'$c = 10$, $a_1 = 2$. Найти $a^2$.', ans:20, tol:0.1, hint:'$a^2 = c \\cdot a_1 = 10 \\cdot 2 = 20$' },
|
||||
];
|
||||
let i = 0, score = 0;
|
||||
function show(){
|
||||
if(i >= Q.length){
|
||||
document.getElementById('p6-iv4-q').innerHTML = '<b>Готово!</b> Результат: ' + score + ' / ' + Q.length;
|
||||
if(score === Q.length){ addXp(15,'p6-iv4'); bumpProgress('p6', 25); }
|
||||
else if(score >= 4){ addXp(8,'p6-iv4'); bumpProgress('p6', 15); }
|
||||
return;
|
||||
}
|
||||
document.getElementById('p6-iv4-i').textContent = (i+1);
|
||||
document.getElementById('p6-iv4-s').textContent = score;
|
||||
document.getElementById('p6-iv4-q').innerHTML = Q[i].q;
|
||||
document.getElementById('p6-iv4-ans').value = '';
|
||||
renderMath(document.getElementById('p6-iv4-q'));
|
||||
document.getElementById('p6-iv4-fb').style.display = 'none';
|
||||
}
|
||||
function go(){
|
||||
if(i >= Q.length) return;
|
||||
const fb = document.getElementById('p6-iv4-fb');
|
||||
const ans = parseFloat(document.getElementById('p6-iv4-ans').value);
|
||||
if(isNaN(ans)){ feedback(fb, false, '✗ Введи число.'); return; }
|
||||
if(Math.abs(ans - Q[i].ans) <= Q[i].tol){ score++; feedback(fb, true, '✓ Верно! '+Q[i].hint+'. Дальше ▶'); }
|
||||
else feedback(fb, false, '✗ Неверно. Ответ: '+Q[i].ans+' ('+Q[i].hint+'). Дальше ▶');
|
||||
document.getElementById('p6-iv4-s').textContent = score;
|
||||
i++;
|
||||
setTimeout(show, 1400);
|
||||
}
|
||||
document.getElementById('p6-iv4-go').addEventListener('click', go);
|
||||
document.getElementById('p6-iv4-ans').addEventListener('keydown', e=>{ if(e.key==='Enter') go(); });
|
||||
document.getElementById('p6-iv4-start').addEventListener('click', ()=>{ i=0; score=0; show(); });
|
||||
show();
|
||||
})();
|
||||
|
||||
wireReadBtn('p6');
|
||||
}
|
||||
|
||||
function buildFinal1(){
|
||||
const body = document.getElementById('final1-body');
|
||||
|
||||
Reference in New Issue
Block a user