Moduł 02 · Podstawy

Podstawy matematyczne

SE(3), grupy Liego, FK/IK Pandy, jakobian, manipulowalność Yoshikawy, dynamika, singularności, topologia C-space.

TL;DR

Ten moduł ustala warsztat matematyczny dla całego kursu: jak reprezentować pozę robota, jak liczyć jak ona zależy od konfiguracji, gdzie kończą się sensowne reprezentacje (singularności, gimbal lock) i jaką topologię ma C-space dla redundantnego manipulatora. Wszystkie kolejne moduły (planowanie, optymalizacja, MPC) operują na obiektach zdefiniowanych tutaj.

Co już zakładamy: rachunek macierzowy, podstawy układów dynamicznych, intuicje z analizy. Czego nauczymy się tu w kontekście Pandy: SO(3) i SE(3) jako grupy Liego, jakobian J(q)R6×7J(q) \in \mathbb{R}^{6 \times 7}, wskaźnik Yoshikawy, singularności i topologia Q(S1)7\mathcal{Q} \subset (\mathbb{S}^1)^7 (ze stoperami, więc właściwie podzbiór ze ścianami).

Słownik podstawowych pojęć

Pięć terminów, które wracają w każdym kolejnym module. Jeśli już wiesz, czym jest manifold i SE(3)SE(3), możesz to pominąć.

Manifold (rozmaitość)
Przestrzeń, która lokalnie wygląda jak płaski Rn\mathbb{R}^n, ale globalnie może być zakrzywiona. Przykład: sfera S2\mathbb{S}^2 — w każdym punkcie da się narysować lokalną mapę (jak atlas geograficzny), ale całość nie jest płaszczyzną. Pojęcie kluczowe bo SO(3)SO(3)jest manifoldem (3D), a nie zwykłą przestrzenią R3\mathbb{R}^3 — to dlatego potrzebujemy specjalnych narzędzi do całkowania ruchu obrotowego.
SO(3)SO(3) — Special Orthogonal Group
Zbiór wszystkich rotacji 3D wokół stałego punktu. „Orthogonal" — macierz spełnia RR=IR^\top R = I (zachowuje długości i kąty). „Special" — detR=+1\det R = +1 (brak odbić; prawoskrętność zachowana). Wymiar: 3 (trzy niezależne parametry rotacji).
SE(3)SE(3) — Special Euclidean Group
Zbiór wszystkich sztywnych przemieszczeń w 3D — rotacja plus translacja. Każda poza (orientacja + pozycja) końcówki narzędzia robota to element SE(3)SE(3). Wymiar: 6 (3 rotacji + 3 translacji). Reprezentowane jako macierze jednorodne 4×4.
Lie group / algebra Liego
Lie group = grupa, która jest gładkim manifoldem (operacje grupowe są różniczkowalne). SO(3)SO(3) i SE(3)SE(3) to klasyczne przykłady.
Algebra Liego so(3)\mathfrak{so}(3), se(3)\mathfrak{se}(3) = przestrzeń styczna w identyczności = elementy „infinitezymalne" (prędkości kątowe, twisty). Połączenie: exp:so(3)SO(3)\exp: \mathfrak{so}(3) \to SO(3) (formuła Rodriguesa).
Tangent space (przestrzeń styczna)
Przestrzeń wektorowa „zaczepiona" w punkcie manifoldu — opisująca prędkości przejścia przez ten punkt. Dla SO(3)SO(3) w identyczności II tangent space to R3\mathbb{R}^3 (prędkości kątowe ω\omega). Dla manifolda Pandy w konfiguracji qq: tangent space to R7\mathbb{R}^7 (prędkości joints q˙\dot q).
Twist (se(3)\mathfrak{se}(3))
Element algebry Liego se(3)\mathfrak{se}(3) — para (ω,v)R6(\omega, v) \in \mathbb{R}^6opisująca jednoczesną prędkość kątową i liniową ciała sztywnego. Występuje wszędzie w robotyce: jakobian J(q):q˙twistJ(q): \dot q \mapsto \text{twist}, MPC operuje na twistach, CHOMP całkuje gradient w twistach.

Reprezentacje rotacji w SO(3)SO(3)

Cztery równoważne sposoby zapisu jednej rotacji. Każdy ma inny zestaw zalet i pułapek. Praktycznie: kwaterniony do reprezentacji wewnętrznej (interpolacja SLERP, brak singularności), macierze do mnożenia transformacji, axis-angle do interpretacji geometrycznej i wykładni exp:so(3)SO(3)\exp: \mathfrak{so}(3) \to SO(3), kąty Eulera tylko do UI (gdy potrzebny intuicyjny opis dla człowieka — z ostrzeżeniem o gimbal lock).

Cztery reprezentacje tej samej rotacji

X obróconyY obróconyZ obróconyoś rotacji kświat (linie przerywane)mysz obraca widok
Oś rotacji (wektor)
x0.00
y1.00
z0.00
Kąt rotacji θ
60°
Presety
Macierz 3×3 (SO(3))
[0.500, 0.000, 0.866]
[0.000, 1.000, 0.000]
[-0.866, 0.000, 0.500]
99 liczb, detR=+1\det R = +1, RR=IR^\top R = I
Kwaternion (Hamilton)
w = 0.8660
x = 0.0000
y = 0.5000
z = 0.0000
44 liczby, q=1\|q\| = 1, antypoda ±q\pm q = ta sama rotacja
Axis-angle (Rodrigues)
k = [0.000, 1.000, 0.000]
θ = 1.0472 rad
= 60.0°
3+13 + 1 liczb (oś + kąt), wektor obrotu θkR3\theta \mathbf{k} \in \mathbb{R}^3
Kąty Eulera XYZ
α (x) = 0.0°
β (y) = 60.0°
γ (z) = 0.0°
33 liczby; R=Rx(α)Ry(β)Rz(γ)R = R_x(\alpha) R_y(\beta) R_z(\gamma)
Co zauważyć: wszystkie cztery zapisy opisują tę samą rotację — różnią się liczbą parametrów (9 / 4 / 4 / 3) i odpornością na osobliwości. Kwaternion ma 4 parametry + jedno ograniczenie q=1\|q\|=1, więc 2 stopnie swobody więcej niż minimum (3) — to dodatkowy kontekst eliminujący gimbal lock. Włącz preset „gimbal: β=90°" by zobaczyć, jak kąty Eulera dezenformują (α + γ nierozróżnialne).
Krok 1

SO(3) jako manifold

SO(3)SO(3) to grupa rotacji 3D — formalnie zbiór macierzy 3×3 spełniających dwa warunki:

SO(3)={RR3×3:RR=I,  detR=+1}SO(3) = \{R \in \mathbb{R}^{3\times 3} \,:\, R^\top R = I,\; \det R = +1\}

Wymiar manifoldu: 3 (9 elementów - 6 niezależnych więzów ortogonalności). Tangent space w identyczności: so(3)\mathfrak{so}(3) = macierze skośnie-symetryczne 3×3, izomorficzne z R3\mathbb{R}^3 przez mapę „hat" ω[ω]×\omega \mapsto [\omega]_\times. To podstawa do liczenia prędkości kątowych i całkowania ruchu.

Krok 2

exp / log map

Rodrigues: R=I+sinθ[k^]+(1cosθ)[k^]2R = I + \sin\theta \,[\hat k] + (1-\cos\theta)\,[\hat k]^2, gdzie θ\theta kąt, k^\hat k jednostkowa oś rotacji. To exp map z so(3)\mathfrak{so}(3) do SO(3)SO(3). W kursie wykorzystamy ją w CHOMP/TrajOpt (moduł 07) — tam całkujemy ruch w tangent space.

Krok 3

Gimbal lock kątów Eulera

Włącz preset gimbal: β=90° we widgecie powyżej. Przy β=±π/2\beta = \pm \pi/2 pierwsza i trzecia oś rotacji nakładają się — tracimy jeden stopień swobody. Skutki: pochodne R/α\partial R/\partial \alpha i R/γ\partial R/\partial \gamma stają się liniowo zależne. Dlatego sterowanie i planowanie operuje na kwaternionach lub axis-angle, nigdy na czystych kątach Eulera.

Interpolacja orientacji: SLERP

Naiwne interpolowanie kwaternionów liniowo (LERP) i normalizacja daje punkt na 3-sferze, ale nie po geodezyjnej — prędkość kątowa nie jest stała. SLERP (Shoemake 1985) interpoluje po łuku największego koła, dając stałą prędkość kątową. Krytyczne dla animacji i trajektorii TCP w robotyce.

SLERP vs LERP — interpolacja orientacji 3D (Shoemake 1985)

θ(t) = ∠(q_0, q(t)) — kąt od pozycji startowej
075150t = 01θ [°]LERPSLERP
dθ/dt — prędkość kątowa (SLERP = constant)
087.9175.8t = 01dθ/dt [°/jednostka t]LERPSLERP
Co pokazuje demo: (1) Włącz LERP przy Ω150°\Omega \approx 150° — zauważ że prędkość kątowa nie jest stała: zwalnia przy końcach, szybsza w środku. Wykres dθ/dtd\theta/dt ma kształt parabolicznego garbu. (2) Włącz SLERPdθ/dt=Ωd\theta/dt = \Omega constant. To geodezyjny ruch na 3-sferze kwaternionów jednostkowych. (3) Dla bardzo małego Ω\Omega(< 30°) różnica jest praktycznie niewidoczna — stąd LERP+normalize (NLERP) wystarcza dla animacji 60 fps z drobnymi krokami.

Formuła SLERP

qslerp(t)=sin ⁣((1t)Ω)sinΩq0+sin(tΩ)sinΩq1,Ω=arccos(q0q1)q_{\text{slerp}}(t) = \frac{\sin\!\big((1-t)\Omega\big)}{\sin\Omega}\, q_0 + \frac{\sin(t\,\Omega)}{\sin\Omega}\, q_1,\quad \Omega = \arccos(q_0 \cdot q_1)

Geometrycznie: q0,q1q_0, q_1 to dwa punkty na 3-sferze S3R4S^3 \subset \mathbb{R}^4. SLERP daje geodezyjną ścieżkę między nimi — najkrótszy łuk po sferze. LERP zaś interpoluje liniowo w R4\mathbb{R}^4 a po renormalizacji rzutuje na sferę — daje punkt sferze, ale po cięciwie akordu, nie po łuku.

SE(3)SE(3): pełna poza w przestrzeni

Poza robota (lub jego końcówki) to element SE(3)=SO(3)R3SE(3) = SO(3) \ltimes \mathbb{R}^3 — pół-bezpośredni iloczyn rotacji i translacji. Macierzowa reprezentacja jednorodna (4×4):

g=[Rp01]R4×4,RSO(3),  pR3g = \begin{bmatrix} R & p \\ \mathbf{0} & 1 \end{bmatrix} \in \mathbb{R}^{4\times 4}, \quad R \in SO(3), \; p \in \mathbb{R}^3

Tangent space (twist) se(3)R6\mathfrak{se}(3) \cong \mathbb{R}^6: para (ω,v)(\omega, v) — prędkość kątowa i liniowa. Jakobian J(q)R6×nJ(q) \in \mathbb{R}^{6 \times n} mapuje q˙(v,ω)\dot q \to (v, \omega):

[vω]=J(q)q˙\begin{bmatrix} v \\ \omega \end{bmatrix} = J(q) \,\dot q

Dla Pandy n=7n = 7, więc JR6×7J \in \mathbb{R}^{6 \times 7} redundancja. JJ ma więcej kolumn niż wierszy → nieskończenie wiele rozwiązań dla zadanego (v,ω)(v, \omega). Wykorzystanie tej redundancji to temat modułu 11.

Parametry DH — od ramienia do macierzy

Denavit-Hartenberg (1955) — uniwersalna konwencja zapisu kinematyki manipulatora seryjnego (łańcucha kinematycznego bez gałęzi). Idea: każde ogniwo opisujemy czterema liczbami zamiast pełną macierzą 4×4. Z 7 ogniw Pandy: 28 liczb, nie 7×16=112.

Cztery parametry DH

Dla każdego przegubu ii:

  • ai1a_{i-1} — długość ogniwa poprzedniego, czyli długość wspólnej normalnej między osiami zi1z_{i-1} i ziz_i. Mierzymy wzdłuż osi xi1x_{i-1}.
  • αi1\alpha_{i-1} — kąt skręcenia osi zz między ogniwami; obrót wokół xi1x_{i-1}.
  • did_i — offset wzdłuż osi ziz_i, gdzie ogniwo łączy się z poprzednim.
  • θi\theta_i — kąt przegubu; dla przegubu rewolutnego ten parametr jest zmienną konfiguracyjną qiq_i.

Konwencja (Modified DH, Craig): osie ziz_i układa się wzdłuż osi obrotu i-tego przegubu (dla rewolutnych) lub osi przesuwu (dla pryzmatycznych). Osie xix_i wzdłuż wspólnej normalnej z zi1z_{i-1} (lub dowolne jeśli osie są równoległe).

Macierz pojedynczego przejścia Tii1T_i^{i-1}

Złożenie 4 elementarnych transformacji w ścisłym porządku:

Tii1=Rx(αi1)skręcˊ xTx(ai1)idzˊ wzdłuz˙ xRz(θi)obroˊt przegubuTz(di)przesunˊ wzdłuz˙ zT_i^{i-1} = \underbrace{R_x(\alpha_{i-1})}_{\text{skręć x}} \cdot \underbrace{T_x(a_{i-1})}_{\text{idź wzdłuż x}} \cdot \underbrace{R_z(\theta_i)}_{\text{obrót przegubu}} \cdot \underbrace{T_z(d_i)}_{\text{przesuń wzdłuż z}}

Po rozwinięciu mamy konkretną macierz 4×4:

Tii1=[cθisθi0ai1sθicαi1cθicαi1sαi1disαi1sθisαi1cθisαi1cαi1dicαi10001]T_i^{i-1} = \begin{bmatrix} c_{\theta_i} & -s_{\theta_i} & 0 & a_{i-1} \\ s_{\theta_i} c_{\alpha_{i-1}} & c_{\theta_i} c_{\alpha_{i-1}} & -s_{\alpha_{i-1}} & -d_i s_{\alpha_{i-1}} \\ s_{\theta_i} s_{\alpha_{i-1}} & c_{\theta_i} s_{\alpha_{i-1}} & c_{\alpha_{i-1}} & d_i c_{\alpha_{i-1}} \\ 0 & 0 & 0 & 1 \end{bmatrix}

gdzie cx=cosxc_x = \cos x, sx=sinxs_x = \sin x. Implementacja w src/lib/panda/fk.ts (dhTransform) — 16 obliczanych pól, 8 wywołań sin/cos.

Tabela DH Pandy (Modified DH, Franka FCI)

Przegub ia_{i-1} [m]α_{i-1} [rad]d_i [m]θ_iCo opisuje
1000.333q₁Bark (shoulder yaw) — pionowa kolumna 33.3 cm
20−π/20q₂Shoulder pitch — skręć oś o −90°, oś rotacji teraz pozioma
30π/20.316q₃Upper arm — długość ramienia 31.6 cm
40.0825π/20q₄Elbow — offset 8.25 cm wzdłuż x (charakterystyczny dla Pandy)
5−0.0825−π/20.384q₅Forearm — długość 38.4 cm; ujemne a kompensuje offset z 4
60π/20q₆Wrist pitch (przed twist)
70.088π/20q₇Gripper twist — ostatni przegub przed flange
flange000.1070Statyczne (bez przegubu): 10.7 cm offsetu do TCP

Suma długości: 0.333 + 0.316 + 0.384 + 0.107 + offsety (0.0825 + 0.088) ≈ 1.19 m. To maksymalny reach Pandy. Workspace (osiągalna pozycja TCP) to kula o promieniu ~0.85 m wokół bazy (z wycięciami przy krawędziach z powodu joint limits).

Wizualizacja DH frames — gdzie żyje każdy układ

DH frames na Pandzie — gdzie żyje każdy układ

Co zobaczyć: każdy niebieski wektor Z to oś, wokół której obraca się dany joint (Panda ma 7 jointów rewolutnych, więc 7 osi Z są osiami obrotu). Czerwony X to wspólna normalna z poprzednią osią Z — zgodnie z konwencją DH każda nowa oś X jest prostopadła do X poprzedniego. Frame 0 = baza (w world origin), frame 8 = flange (= TCP po dodaniu 107 mm offsetu wzdłuż Z_7). Najedź na wpis w liście po prawej żeby podświetlić frame. Suwakami ruszaj jointami i obserwuj jak osie Z każdego frame'u obracają się zgodnie z θi=qi\theta_i = q_i.

Forward kinematics — composition łańcucha

FK to złożenie 7 macierzy DH plus statyczna transformacja flange:

g(q)=T10(q1)T21(q2)T32(q3)T43(q4)T54(q5)T65(q6)T76(q7)Tflange7g(q) = T_1^0(q_1) \cdot T_2^1(q_2) \cdot T_3^2(q_3) \cdot T_4^3(q_4) \cdot T_5^4(q_5) \cdot T_6^5(q_6) \cdot T_7^6(q_7) \cdot T_{\text{flange}}^7

Implementacja w TS — kanoniczna pętla src/lib/panda/fk.ts:

let T = I4;
for (let i = 0; i < 7; i++) {
  T = mat4mul(T, dhTransform(PANDA_DH[i], q[i]));
  frames.push(T);  // zapamiętaj dla jakobianu / wizualizacji
}
T = mat4mul(T, flangeOffset);  // statyczne 10.7 cm

Wynik dla q_home: g(qhome).p(0.307,0,0.487)g(q_{\text{home}}).p \approx (0.307, 0, 0.487) m. Smoke test w lib/panda/__smoke.ts sprawdza to per build.

Złożoność: O(n) mnożeń macierzy, czyli ~7×16 float operations = ~112 mnożeń + sin/cos w każdym kroku. Czas wykonania w przeglądarce: ~5 μs per ewaluacja FK. Pandy 1 kHz control loop < 0.5% budżetu czasowego.

Inverse kinematics — metody numeryczne

Dla zadanego pose gdSE(3)g_d \in SE(3) znajdź qq takie, że g(q)=gdg(q) = g_d. Pandzie 7-DOF brak postaci zamkniętej (nie spełnia warunku Piepera — ostatnie 3 osie nie przecinają się w jednym punkcie). Dla takich robotów używamy numeryki.

Newton-Raphson na pose error

Niech e(q)=log(gd1g(q))se(3)e(q) = \log(g_d^{-1} g(q)) \in \mathfrak{se}(3) = 6-wektor błędu (twist od bieżącej do docelowej pozy). Linearyzacja: e(q+Δq)e(q)+J(q)Δqe(q + \Delta q) \approx e(q) + J(q) \Delta q. Krok Newtona:

Δq=J+(q)e(q),q(k+1)=q(k)+Δq\Delta q = -J^+(q) \cdot e(q), \quad q^{(k+1)} = q^{(k)} + \Delta q

Iteruj aż e<ϵ\|e\| < \epsilon. Konwergencja kwadratowa w pobliżu rozwiązania, ale wrażliwa na singularności i lokalne minima.

Damped Least Squares (DLS)

W pobliżu singularności J+J^+ wybucha. Fix: Jλ+=J(JJ+λ2I)1J^+_\lambda = J^\top (JJ^\top + \lambda^2 I)^{-1} z λ[0.001,0.05]\lambda \in [0.001, 0.05]. Patrz moduł 11 dla szczegółów.

TRAC-IK (Beeson & Ames 2015)

Hybryda: dwie metody równolegle: SQP (KDL standard) + twist-aware DLS. Bierze pierwsze udane. Threshold: 95% success rate na typowych zadaniach Pandy, vs 70% klasycznego KDL.

IKFast (Diankov 2010)

Generowanie analitycznej IK przez Gröbner basis dla konkretnego robota. Dla 6-DOF: zamknięta postać do 16 rozwiązań. Dla 7-DOF wymaga ustalenia 1 parametru redundancji (np. zawsze q7=0q_7 = 0, lub elbow angle = const).

Pełne wyprowadzenie analityczne IK (Puma560, 6-DOF, warunek Piepera) w siostrzanym projekcie ik-platform — środek nadgarstka, q₁ z geometrii, q₂q₃ z prawa kosinusów, q₄q₅q₆ z macierzy rotacji, 8 rodzin rozwiązań.

Jakobian i wskaźnik manipulowalności (Yoshikawy)

Jakobian geometryczny J(q)R6×7J(q) \in \mathbb{R}^{6 \times 7} opisuje wzajemność prędkości joints i prędkości TCP (linear + kątowej). Manipulowalność mówi jak dobrze robot jest „przygotowany" w danej konfiguracji — czyli jak duże prędkości TCP może osiągać dla jednostkowych prędkości joints.

w(q)=det(J(q)J(q))=i=16σi(J)w(q) = \sqrt{\det(J(q) J(q)^\top)} = \prod_{i=1}^{6} \sigma_i(J)

Druga równość: σi\sigma_i to wartości szczególne JJ, więc ww = iloczyn długości półosi elipsoidy manipulowalności. Mała ww oznacza, że jedna z osi jest prawie zerowa — niemal-singularność. w=0w = 0 dokładnie wtedy, gdy JJ traci rank.

W demo poniżej widzisz elipsoidę manipulowalności (część liniowa, 3×3) w pozycji TCP. Suwakami joints obserwuj jak zmienia się jej kształt — przy konfiguracjach „rozprostowanego ramienia" elipsoida się spłaszcza.

Trzy warianty Jakobianu — spatial, body, hybrid

W papersachi bibliotekach robotyki spotkasz różne definicje „jakobianu". Najczęstsze nieporozumienie w  implementacji: liczę spatialJacobian, a wzór wymaga body. Trzy warianty, wszystkie 6×n:

1. Spatial Jacobian Js(q)J_s(q)

Definiowany tak, że dla twistu w world frame:

Vs=Js(q)q˙,Vs=(ωs,vs)se(3)V_s = J_s(q) \, \dot q, \quad V_s = (\omega_s, v_s) \in \mathfrak{se}(3)

gdzie vsv_s = prędkość liniowa frame'u końcówki wyrażona w world ALE z punktem zaczepienia w origin world (interpretacja „extended twist"). Kolumna i-ta JsJ_s: Adgiw(zi)\text{Ad}_{g_i^{w}}(z_i) gdzie ziz_i = oś joint i, giwg_i^w = pose frame'u i w world. To jakobian używany w klasycznych pochodnych algebra Liego (Murray-Li-Sastry).

2. Body Jacobian Jb(q)J_b(q)

Twist wyrażony w body frame (frame'ie końcówki):

Vb=Jb(q)q˙,Vb=(ωb,vb)V_b = J_b(q) \, \dot q, \quad V_b = (\omega_b, v_b)

vbv_b = prędkość liniowa w reprezentacji body. Naturalne dla zadań w przestrzeni narzędzia (force-feedback, peg-in-hole — chcemy prędkość „przy końcówce"). Związek z spatial: Jb=Adg1JsJ_b = \text{Ad}_{g^{-1}} J_s.

3. Geometric / hybrid Jacobian Jg(q)J_g(q)

Najczęściej w praktyce. Prędkość liniowa końcówki w world, prędkość kątowa w world. NIE jest „prawdziwym" twistem (mieszamy reprezentacje), ale jest najwygodniejszy obliczeniowo:

[vewωew]=Jg(q)q˙\begin{bmatrix} v_e^w \\ \omega_e^w \end{bmatrix} = J_g(q) \, \dot q

Kolumna i-ta dla przegubu rewolutnego:

Jg,i=[ziw×(pewpiw)ziw]J_{g,i} = \begin{bmatrix} z_i^w \times (p_e^w - p_i^w) \\ z_i^w \end{bmatrix}

To jest jakobian, który implementuję w lib/panda/jacobian.ts— używany w CHOMP, TrajOpt, MPC, redundancji. Wszystkie wartości w world frame, łatwo wizualizować i komponować z target velocity.

Konwersje między wariantami

Mając JgJ_g (najprostszy do obliczenia), pozostałe wyznaczamy przez transformację adjoint:

Adg=[R[p]×R0R]R6×6\text{Ad}_g = \begin{bmatrix} R & [p]_\times R \\ 0 & R \end{bmatrix} \in \mathbb{R}^{6 \times 6}

gdzie g=(R,p)g = (R, p), [p]×[p]_\times = macierz skośnie-symetryczna z pp. Adjoint mapuje twisty między frame'ami.

Praktyczna reguła wyboru

  • Sterowanie w przestrzeni zadania (OSC, CBF, tracking pose) — geometric JgJ_g: chcę „idź w +x w world".
  • Force feedback / contact tasks — body JbJ_b: siła mierzona przy końcówce.
  • Lie-theoretic analysis (CHOMP geodesics, exp coords) — spatial JsJ_s: kompozycja z exp/log naturalna.
  • MoveIt2, Pinocchio — domyślnie geometric, ale z funkcjami konwersji.

Pułapka — manipulability i numeric stability

Wskaźnik manipulowalności w(q)=det(JJ)w(q) = \sqrt{\det(JJ^\top)} zależy od wyboru wariantu jakobianu. Na singularności wszystkie są równoważnie 0, ale w pobliżu wartości się różnią (kierunki głównych osi elipsoidy w  różnych frame'ach). Implementacje typowo używają geometric, ale warto być świadomym przy porównaniu z literaturą.

Singularności

Singularność = konfiguracja qq^* taka, że rank(J(q))<6\text{rank}(J(q^*)) < 6. W tej konfiguracji jakobian nie jest pełnego rzędu: istnieje kierunek w przestrzeni prędkości TCP, którego nie da się osiągnąć żadną prędkością joints (a fakt że Panda jest 7-DOF nie pomaga, bo redundancja jest w joints, nie w task space).

Klasyfikacja: brzegowe (TCP na granicy osiągalności — ramię całkowicie rozprostowane) i wewnętrzne (specjalne wewnętrzne konfiguracje, jak wyrównane osie sąsiednich joints).

Pokażemy mechanizm na klasycznym 2-link arm (RR planarny), gdzie singularność wyraża się jednym wzorem:

detJ(q1,q2)=L1L2sinq2\det J(q_1, q_2) = L_1 L_2 \sin q_2

Singularne: q2=0q_2 = 0 (ramię rozprostowane) i q2=±πq_2 = \pm \pi (złożone). Suwakami zobacz jak detJ\det J przechodzi przez 0.

2-link arm — singularności (det J → 0)

baseq₁=0.79TCP
det J = L₁·L₂·sin q₂ jako funkcja q₂
−π0π
Singularności (czerwone linie): q2{0,±π}q_2 \in \{0, \pm\pi\}.
Bieżący detJ\det J = 0.8000
q₁45°
q₂90°

Topologia przestrzeni konfiguracyjnej

Q\mathcal{Q} nie jest zwykłym Rn\mathbb{R}^n — kąty obrotowe są cyrkulane (02π0 \equiv 2\pi), więc każdy joint to S1\mathbb{S}^1, nie odcinek. Skutki praktyczne:

  • Metryka w C-space nie jest euklidesowa — odległość między qa=350°q_a = 350° a qb=10°q_b = 10° to 20°20°, nie 340°340°. To wpływa na każdy planer (A*, RRT, CHOMP) — używa się angle wrap lub pracuje na cosinusach.
  • Topologia drasycznie inna od euklidesa. Np. RRT* na torusie zachowuje się inaczej niż na płaszczyźnie (ścieżki mogą „okrążać" świat).
  • Dla Pandy z limitami joints (np. q1[2.897,2.897]q_1 \in [-2.897, 2.897] rad, nie pełne [π,π][-\pi, \pi]) niektóre joints są quasi-cyrkulane — okrąg ze „ścianami". Topologicznie bliżej do odcinka.

C-space 2-link = torus 𝕊¹ × 𝕊¹

kwadrat [−π, π]² z identyfikacją krawędzi
π−πq₁ →q₂ ↑
Niebieskie krawędzie (góra ≡ dół) i fioletowe (lewa ≡ prawa) są sklejone.
Wynik: S1×S1=T2\mathbb{S}^1 \times \mathbb{S}^1 = \mathbb{T}^2.
ten sam punkt na torusie 3D
q₁q₂
q₁ — pozycja wokół osi torusa.
q₂ — pozycja wokół przekroju.
q₁45°
q₂90°

Dla pełnej Pandy z 7 joints C-space to S1×R6\mathbb{S}^1 \times \mathbb{R}^6 (przy nieograniczonym joint 1) z limit-walls — niewizualizowalne bezpośrednio, ale intuicja torusa (sklejenie krawędzi) uogólnia się.

Dynamika — szybkie podsumowanie

Równanie ruchu manipulatora w postaci Lagrange'a:

M(q)q¨+C(q,q˙)q˙+g(q)=τ+J(q)FextM(q)\,\ddot q + C(q,\dot q)\,\dot q + g(q) = \tau + J^\top(q)\,F_{\text{ext}}

gdzie MM macierz mas, Cq˙C \dot q człony Coriolisa i odśrodkowe, gg grawitacja, τ\tau momenty napędowe, FextF_{\text{ext}} zewnętrzne siły.

Algorytm rekursywny RNEA (Recursive Newton-Euler) liczy τ\tau z (q,q˙,q¨)(q, \dot q, \ddot q) w czasie liniowym względem liczby joints. Implementacja: Pinocchio.

Pełna pochodna i implementacja w ik-platform/modules/9-dynamics — tu, w module planowania, dynamika pojawi się dopiero w modułach 10 (MPC dynamiczne) i 13 (kontakt). Do tego momentu pracujemy kinematycznie.

Ściąga

Reprezentacje rotacji — kiedy czego użyć

  • Macierz 3×3: do mnożenia transformacji (efektywna numerycznie). Pamięć: 9 floats.
  • Kwaternion: do interpolacji (SLERP), nie ma gimbal lock, stabilność numeryczna. Pamięć: 4 floats z więzem q=1\|q\| = 1.
  • Axis-angle / wektor obrotu θk\theta \mathbf{k}: do so(3)\mathfrak{so}(3) (planowanie w tangent space). 3 floats.
  • Euler XYZ: nigdy wewnętrznie. Wyłącznie do UI gdy potrzebny intuicyjny zapis dla człowieka.

Jakobian i singularności

p˙=J(q)q˙,w(q)=det(JJ)\dot p = J(q)\,\dot q, \quad w(q) = \sqrt{\det(J J^\top)}

Pandy JR6×7J \in \mathbb{R}^{6\times 7}, redundancja = 1. Singularność ⇔ rank JJ < 6 ⇔ w=0w = 0.

SE(3)

g=[Rp01],se(3)(ω,v)g = \begin{bmatrix} R & p \\ 0 & 1 \end{bmatrix},\quad \mathfrak{se}(3) \ni (\omega, v)

Dynamika

M(q)q¨+C(q,q˙)q˙+g(q)=τM(q)\ddot q + C(q,\dot q)\dot q + g(q) = \tau

Referencje do dalszej lektury

  • Lynch & Park, Modern Robotics: Mechanics, Planning, and Control (Cambridge 2017) — kanoniczny podręcznik z Lie groups jako centralnym narzędziem. Rozdziały 2 (configuration space), 3 (SE(3)), 5 (kinematyka), 8 (dynamika). wykłady + ćwiczenia online.
  • Murray, Li & Sastry, A Mathematical Introduction to Robotic Manipulation (CRC 1994) — głębsza analiza Lie groups w robotyce. Dostępna online bezpłatnie.
  • Yoshikawa, „Manipulability of Robotic Mechanisms" (IJRR 1985) — pierwotny paper definiujący wskaźnik w(q)w(q).
  • Diebel, „Representing attitude: Euler angles, unit quaternions, and rotation vectors" (Stanford 2006) — pełen przegląd konwersji ze wzorami numerycznie stabilnymi.
  • Pinocchio — biblioteka C++/Python do FK, IK, dynamiki, jakobianów, manifoldów Lie groups dla manipulatorów i floating-base. stack-of-tasks/pinocchio.
  • Franka Robotics docs — parametry DH, limity: control_parameters.