fix(geom8 ch4): §3 — маркеры прямого угла НА ВНУТРЕННЕЙ стороне касательной (к O)
Маркер прямого угла в точке касания T должен быть на той стороне, где геометрически находится угол 90° — внутри треугольника OTA, т.е. между направлениями T→O и T→A. Раньше использовалось +u_radius (от центра наружу) → маркер оказывался ВНЕ круга на дальней от A стороне. Изменено на -u_radius (внутрь, к центру). Теперь маркер показывает угол 90° между OT и tangent правильно. Затронуты: - §3 Card 3.1 (статичная) - §3 Интерактив 1 (slider OA) - §3 Интерактив 2 (пошаговое доказательство) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1259,10 +1259,13 @@ function buildP3(){
|
||||
<!-- OA bisector -->
|
||||
<line x1="95" y1="100" x2="220" y2="92" stroke="#64748b" stroke-width="1.5" stroke-dasharray="5,3"/>
|
||||
<circle cx="220" cy="92" r="4" fill="#0369a1"/>
|
||||
<!-- right-angle at T₂=(115,53): u_r=(20/50,-47/50)=(0.4,-0.94) u_t=(0.94,0.4) s=8 -->
|
||||
<polyline points="118.2,45.5 125.7,48.7 122.5,56.2" fill="none" stroke="#0369a1" stroke-width="1.6"/>
|
||||
<!-- right-angle at T₁=(112,146): u_r=(0.34,0.92) u_t=+CW_perp=(0.92,-0.34) toward A s=8 -->
|
||||
<polyline points="114.7,153.4 122.1,150.7 119.4,143.3" fill="none" stroke="#0369a1" stroke-width="1.6"/>
|
||||
<!-- right-angle at T₂=(115,53): arms point INWARD (toward O) and toward A -->
|
||||
<!-- u_r=(0.4,-0.94) from O to T₂; toO=-u_r=(-0.4,0.94); u_t toward A=(0.938,0.348); s=8 -->
|
||||
<!-- p1=T₂+8·toO=(111.8,60.5) corner=p1+8·u_t=(119.3,63.3) p2=T₂+8·u_t=(122.5,55.8) -->
|
||||
<polyline points="111.8,60.5 119.3,63.3 122.5,55.8" fill="none" stroke="#0369a1" stroke-width="1.8"/>
|
||||
<!-- right-angle at T₁=(112,146): u_r=(0.34,0.92) from O to T₁; toO=(-0.34,-0.92); u_t toward A=(0.895,-0.447); s=8 -->
|
||||
<!-- p1=T₁+8·toO=(109.3,138.6) corner=p1+8·u_t=(116.5,135.0) p2=T₁+8·u_t=(119.2,142.4) -->
|
||||
<polyline points="109.3,138.6 116.5,135.0 119.2,142.4" fill="none" stroke="#0369a1" stroke-width="1.8"/>
|
||||
<!-- labels: O left of center, A right of point -->
|
||||
<text x="79" y="104" font-size="11" font-weight="700" fill="#0369a1">O</text>
|
||||
<text x="224" y="96" font-size="11" font-weight="700" fill="#0369a1">A</text>
|
||||
@@ -1391,16 +1394,15 @@ function buildP3(){
|
||||
const sinA=R/OA, cosA=AT/OA;
|
||||
const T1x=cx+R*sinA, T1y=cy-R*cosA;
|
||||
const T2x=cx+R*sinA, T2y=cy+R*cosA;
|
||||
// right angle markers — ut must point TOWARD A from each tangent point
|
||||
const ur1x=(T1x-cx)/R, ur1y=(T1y-cy)/R; // T1 is upper; radius points upper-right
|
||||
// CCW perp of upper-right radius = lower-right = toward A ✓
|
||||
const ut1x=-(ur1y), ut1y=ur1x;
|
||||
// right angle markers — arms must point INWARD (toward O) and toward A
|
||||
const ur1x=(T1x-cx)/R, ur1y=(T1y-cy)/R; // outward radial unit
|
||||
const ut1x=-(ur1y), ut1y=ur1x; // CCW perp = toward A for upper T1
|
||||
const s=8;
|
||||
const rm1=`${(T1x+ur1x*s).toFixed(1)},${(T1y+ur1y*s).toFixed(1)} ${(T1x+ur1x*s+ut1x*s).toFixed(1)},${(T1y+ur1y*s+ut1y*s).toFixed(1)} ${(T1x+ut1x*s).toFixed(1)},${(T1y+ut1y*s).toFixed(1)}`;
|
||||
const ur2x=(T2x-cx)/R, ur2y=(T2y-cy)/R; // T2 is lower; radius points lower-right
|
||||
// CW perp of lower-right radius = upper-right = toward A ✓
|
||||
const ut2x=ur2y, ut2y=-ur2x;
|
||||
const rm2=`${(T2x+ur2x*s).toFixed(1)},${(T2y+ur2y*s).toFixed(1)} ${(T2x+ur2x*s+ut2x*s).toFixed(1)},${(T2y+ur2y*s+ut2y*s).toFixed(1)} ${(T2x+ut2x*s).toFixed(1)},${(T2y+ut2y*s).toFixed(1)}`;
|
||||
// marker: T+s·(-u_r), T+s·(-u_r)+s·u_t, T+s·u_t — uses INWARD direction (-u_r)
|
||||
const rm1=`${(T1x-ur1x*s).toFixed(1)},${(T1y-ur1y*s).toFixed(1)} ${(T1x-ur1x*s+ut1x*s).toFixed(1)},${(T1y-ur1y*s+ut1y*s).toFixed(1)} ${(T1x+ut1x*s).toFixed(1)},${(T1y+ut1y*s).toFixed(1)}`;
|
||||
const ur2x=(T2x-cx)/R, ur2y=(T2y-cy)/R;
|
||||
const ut2x=ur2y, ut2y=-ur2x; // CW perp = toward A for lower T2
|
||||
const rm2=`${(T2x-ur2x*s).toFixed(1)},${(T2y-ur2y*s).toFixed(1)} ${(T2x-ur2x*s+ut2x*s).toFixed(1)},${(T2y-ur2y*s+ut2y*s).toFixed(1)} ${(T2x+ut2x*s).toFixed(1)},${(T2y+ut2y*s).toFixed(1)}`;
|
||||
/* Position T₁ label OUTSIDE circle, above-left of T₁ (away from upper tangent) */
|
||||
const T1lx=(T1x-cx)/R, T1ly=(T1y-cy)/R; /* outward unit */
|
||||
const T1labelX=T1x+T1lx*14-6, T1labelY=T1y+T1ly*14+3;
|
||||
@@ -1475,12 +1477,13 @@ function buildP3(){
|
||||
tri1=`<polygon points="${cx},${cy} ${T1x.toFixed(1)},${T1y.toFixed(1)} ${Ax},${Ay}" fill="rgba(6,182,212,.12)" stroke="#06b6d4" stroke-width="1.3"/>`;
|
||||
tri2=`<polygon points="${cx},${cy} ${T2x.toFixed(1)},${T2y.toFixed(1)} ${Ax},${Ay}" fill="rgba(2,132,199,.10)" stroke="#0284c7" stroke-width="1.3"/>`;
|
||||
const s=7;
|
||||
const ur1x=(T1x-cx)/R, ur1y=(T1y-cy)/R; // T1 upper
|
||||
const ut1x=-(ur1y), ut1y=ur1x; // CCW perp → toward A ✓
|
||||
const rm1=`${(T1x+ur1x*s).toFixed(1)},${(T1y+ur1y*s).toFixed(1)} ${(T1x+ur1x*s+ut1x*s).toFixed(1)},${(T1y+ur1y*s+ut1y*s).toFixed(1)} ${(T1x+ut1x*s).toFixed(1)},${(T1y+ut1y*s).toFixed(1)}`;
|
||||
const ur2x=(T2x-cx)/R, ur2y=(T2y-cy)/R; // T2 lower
|
||||
const ut2x=ur2y, ut2y=-ur2x; // CW perp → toward A ✓
|
||||
const rm2=`${(T2x+ur2x*s).toFixed(1)},${(T2y+ur2y*s).toFixed(1)} ${(T2x+ur2x*s+ut2x*s).toFixed(1)},${(T2y+ur2y*s+ut2y*s).toFixed(1)} ${(T2x+ut2x*s).toFixed(1)},${(T2y+ut2y*s).toFixed(1)}`;
|
||||
const ur1x=(T1x-cx)/R, ur1y=(T1y-cy)/R; // outward
|
||||
const ut1x=-(ur1y), ut1y=ur1x; // CCW perp → toward A for upper T1
|
||||
// marker INWARD: T+s·(-u_r) and T+s·u_t
|
||||
const rm1=`${(T1x-ur1x*s).toFixed(1)},${(T1y-ur1y*s).toFixed(1)} ${(T1x-ur1x*s+ut1x*s).toFixed(1)},${(T1y-ur1y*s+ut1y*s).toFixed(1)} ${(T1x+ut1x*s).toFixed(1)},${(T1y+ut1y*s).toFixed(1)}`;
|
||||
const ur2x=(T2x-cx)/R, ur2y=(T2y-cy)/R;
|
||||
const ut2x=ur2y, ut2y=-ur2x; // CW perp → toward A for lower T2
|
||||
const rm2=`${(T2x-ur2x*s).toFixed(1)},${(T2y-ur2y*s).toFixed(1)} ${(T2x-ur2x*s+ut2x*s).toFixed(1)},${(T2y-ur2y*s+ut2y*s).toFixed(1)} ${(T2x+ut2x*s).toFixed(1)},${(T2y+ut2y*s).toFixed(1)}`;
|
||||
equal=`<polyline points="${rm1}" fill="none" stroke="#0369a1" stroke-width="1.8"/><polyline points="${rm2}" fill="none" stroke="#0369a1" stroke-width="1.8"/>`;
|
||||
}
|
||||
if(ph==='done'||ph==='equal'){
|
||||
|
||||
Reference in New Issue
Block a user