---
date: '2025-09-15'
description: linear map plus translation preserving lines, parallelism, and convex combinations through matrix operations and homogeneous coordinates.
id: affine transformation
modified: 2026-06-05 15:08:28 GMT-04:00
tags:
  - seed
title: affine transformation
created: '2025-09-15'
published: '2025-09-15'
pageLayout: default
slug: thoughts/affine-transformation
permalink: https://aarnphm.xyz/thoughts/affine-transformation.md
generator:
  quartz: v4.6.0
  hostedProvider: Cloudflare
  baseUrl: aarnphm.xyz
full: https://aarnphm.xyz/llms-full.txt
---
> \[!abstract\] What is an affine transformation?
>
> An affine transformation is a map of the form
> $\displaystyle f(x) = A\,x + b,$
> where $A\in\mathbb{R}^{m\times n}$ is a linear map and $b\in\mathbb{R}^m$ is a translation vector. Affine maps send lines to lines, preserve parallelism and ratios of lengths along a line, and preserve convex combinations. They generalize linear transformations by allowing translation.

Affines act on vectors in a vector space; see [[thoughts/Vector space]]. In $n$ dimensions, an affine map has $n^2+n$ degrees of freedom (entries of $A$ plus the $n$-vector $b$).

## standard form

- Definition: $f: \mathbb{R}^n\to\mathbb{R}^n$, $f(x)=A x + b$.
- Composition: for $f(x)=A_f x + b_f$ and $g(x)=A_g x + b_g$,
  $\displaystyle (f\circ g)(x) = A_f(A_g x + b_g) + b_f = (A_f A_g)\,x + (A_f b_g + b_f).$
- Invertibility: $f$ is invertible iff $A$ is invertible. The inverse is
  $\displaystyle f^{-1}(y) = A^{-1}(y - b).$
- Fixed point: a point $x_\star$ with $f(x_\star)=x_\star$ satisfies
  $\displaystyle (I - A) x_\star = b, \quad x_\star = (I-A)^{-1} b \;\text{ if }\; I-A \text{ is invertible}.$

## homogeneous coordinates

Affine maps become linear in one higher dimension using homogeneous coordinates. Define $\tilde{x} = \begin{bmatrix}x\\1\end{bmatrix}$ and
$\displaystyle \tilde{A} = \begin{bmatrix} A & b \\ 0 & 1 \end{bmatrix}. $
Then $\tilde{A}\,\tilde{x} = \begin{bmatrix} A x + b \\ 1 \end{bmatrix}$ encodes $f(x)=Ax+b$. Composition reduces to matrix multiplication of the $\tilde{A}$ blocks.

## geometric properties

- Linearity on barycentric combinations: for scalars $\{\lambda_i\}$ with $\sum_i \lambda_i = 1$,
  $\displaystyle f\Big(\sum_i \lambda_i x_i\Big) = \sum_i \lambda_i f(x_i).$
- Collinearity and parallelism are preserved; midpoints and centroids are preserved; general lengths and angles are not (unless $A$ is orthogonal and $\det A=\pm1$).
- Area/volume scale by $|\det A|$; orientation is preserved if $\det A>0$ and flipped if $\det A<0$.

## common 2d/3d examples

- Translation: $A=I$, $f(x)=x+b$.
- Uniform scaling by $s$: $A=s I$, $f(x)=s x$.
- Anisotropic scaling: $A=\operatorname{diag}(s_1,\dots,s_n)$.
- Rotation (2D):
  $\displaystyle A=\begin{bmatrix}\cos\theta & -\sin\theta\\ \sin\theta & \cos\theta\end{bmatrix},\quad f(x)=Ax.$
- Shear (2D, $x$-shear by $k$): $A=\begin{bmatrix}1 & k\\ 0 & 1\end{bmatrix}$.
- Reflection across a line/plane: $A$ is a Householder matrix $A=I-2uu^\top$ with $\|u\|=1$.

## algebraic structure

- The set of invertible affine transformations on $\mathbb{R}^n$ forms the affine group $\operatorname{GA}(n) \cong \operatorname{GL}(n) \ltimes \mathbb{R}^n$ (semidirect product of the general linear group with translations).
- Composition and inversion follow the block rules from the standard form. Determinants and traces refer to the linear part $A$.

## fitting an affine map

Given paired points $\{(x_i,y_i)\}_{i=1}^N$ with $x_i,y_i\in\mathbb{R}^n$, an affine map $y\approx Ax+b$ can be estimated via least squares by augmenting inputs $\hat{x}_i = [x_i^\top,\;1]^\top$ and solving
$\displaystyle \min_{\tilde{A}\in\mathbb{R}^{n\times(n+1)}}\; \sum_i \big\|y_i - \tilde{A} \, \hat{x}_i\big\|_2^2,$
where $\tilde{A}=[A\;\;b]$.

## invariants and non‑invariants

- Preserved: straightness of lines, parallelism, ratios of lengths along a common line, convexity, barycentric coordinates, centroid of point sets.
- Not preserved in general: angles, absolute lengths, circles/orthogonality (unless $A$ is a similarity/orthogonal transform), areas/volumes except up to factor $|\det A|$.

## notes

- When $A$ is orthogonal with $\det A=1$, $f$ is a rigid motion (rotation + translation) that preserves distances.
- When $A=s R$ with $R$ orthogonal and $s>0$, $f$ is a similarity (uniform scaling + rotation + translation) that preserves angles and scales lengths by $s$.

Affine shear + translation on a unit square ($A=\begin{bmatrix}1 & 0.6\\0 & 1\end{bmatrix}$, $b=\begin{bmatrix}1.2\\0.4\end{bmatrix}$):

<figure class="tikz" data-remark-tikz style=""><span class="tikz-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><annotation encoding="application/x-tex">"\\usepackage{tikz}\n\\begin{document}\n\\begin{tikzpicture}[scale=1]\n  % axes and grid\n  \\draw[step=1cm,gray!30,very thin] (-0.5,-0.5) grid (4.0,3.5);\n  \\draw[->] (-0.5,0) -- (4.0,0) node[below right] {$x$};\n  \\draw[->] (0,-0.5) -- (0,3.5) node[above left] {$y$};\n  % original unit square S\n  \\filldraw[fill=blue!10,draw=blue,thick] (0,0) -- (1,0) -- (1,1) -- (0,1) -- cycle;\n  \\node[blue] at (0.5,1.2) {$S$};\n  % transformed square: cm = [[a,b],[c,d]] with translation (e,f)\n  \\begin{scope}[cm={1,0.6,0,1,(1.2,0.4)}]\n    \\filldraw[fill=red!10,draw=red,thick] (0,0) -- (1,0) -- (1,1) -- (0,1) -- cycle;\n    \\node[red] at (0.5,1.2) {$f(S)$};\n  \\end{scope}\n  % annotate A and b\n  \\node at (3.1,3.1) {$A=\\begin{bmatrix}1 &#x26; 0.6\\\\0 &#x26; 1\\end{bmatrix}$};\n  \\node at (3.1,2.5) {$b=\\begin{bmatrix}1.2\\\\0.4\\end{bmatrix}$};\n\\end{tikzpicture}\n\\end{document}"</annotation></semantics></math></span><img src="data:image/svg+xml;base64,PHN2ZyB2ZXJzaW9uPSIxLjEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiIHdpZHRoPSIxNDAuODE4NTZwdCIgaGVpZ2h0PSIxMjcuMTI2ODhwdCIgdmlld0JveD0iLTcyIC03MiAxNDAuODE4NTYgMTI3LjEyNjg4Ij48ZyBzdHJva2UtbWl0ZXJsaW1pdD0iMTAiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC01Ny44NDM2NDMxODg0NzY1NSw0MC40MzA1MTE0NzQ2MDkzNykgc2NhbGUoMSwtMSkiPjxnIHN0cm9rZT0iIzAwMCIgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZS13aWR0aD0iMC40Ij4gPGcgc3Ryb2tlPSIjZDlkOWQ5IiBmaWxsPSIjZDlkOWQ5Ij4gPGcgc3Ryb2tlLXdpZHRoPSIwLjIiPiA8cGF0aCBkPSIgTSAtMTQuMjI2MzYgLTE0LjIyNjM2IE0gLTE0LjIyNjM2IDAuMCBMIDExMy44MTA5NyAwLjAgTSAtMTQuMjI2MzYgMjguNDUyNzQgTCAxMTMuODEwOTcgMjguNDUyNzQgTSAtMTQuMjI2MzYgNTYuOTA1NDkgTCAxMTMuODEwOTcgNTYuOTA1NDkgTSAtMTQuMjI2MzYgODUuMzU4MjMgTCAxMTMuODEwOTcgODUuMzU4MjMgTSAwLjAgLTE0LjIyNjM2IEwgMC4wIDk5LjU4NDYgTSAyOC40NTI3NCAtMTQuMjI2MzYgTCAyOC40NTI3NCA5OS41ODQ2IE0gNTYuOTA1NDkgLTE0LjIyNjM2IEwgNTYuOTA1NDkgOTkuNTg0NiBNIDg1LjM1ODIzIC0xNC4yMjYzNiBMIDg1LjM1ODIzIDk5LjU4NDYgTSAxMTMuODAwOTggLTE0LjIyNjM2IEwgMTEzLjgwMDk4IDk5LjU4NDYgTSAxMTMuODEwOTcgOTkuNTg0NiAgIiBmaWxsPSJub25lIj48L3BhdGg+IDwvZz4gPC9nPiA8cGF0aCBkPSIgTSAtMTQuMjI2MzYgMC4wIEwgMTEzLjQxMDk4IDAuMCAgIiBmaWxsPSJub25lIj48L3BhdGg+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKDExMy42MTA5OCwwLjApIj4gPGcgc3Ryb2tlLWRhc2hhcnJheT0ibm9uZSIgc3Ryb2tlLWRhc2hvZmZzZXQ9IjAuMCI+IDxnIHN0cm9rZS1saW5lY2FwPSJyb3VuZCI+IDxnIHN0cm9rZS1saW5lam9pbj0icm91bmQiPiA8cGF0aCBkPSIgTSAtMi4wNzk5OSAyLjM5OTk4IEMgLTEuNjk5OTggMC45NTk5OCAtMC44NTMxOCAwLjI4IDAuMCAwLjAgQyAtMC44NTMxOCAtMC4yOCAtMS42OTk5OCAtMC45NTk5OCAtMi4wNzk5OSAtMi4zOTk5OCAgIiBmaWxsPSJub25lIj48L3BhdGg+IDwvZz4gPC9nPiA8L2c+ICA8L2c+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKDExNy4zNDM5NSwtNy44Mzg1MikiPiA8ZyBzdHJva2U9IiMwMDAiIGZpbGw9IiMwMDAiPiA8ZyBzdHJva2U9Im5vbmUiIHRyYW5zZm9ybT0ic2NhbGUoLTEsMSkgdHJhbnNsYXRlKC01Ny44NDM2NDMxODg0NzY1NSw0MC40MzA1MTE0NzQ2MDkzNykgc2NhbGUoLTEsLTEpIj48ZyBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIj4gPHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iNDAuNDMwNTExNDc0NjA5MzciIHg9Ii01Ny44NDM2NDMxODg0NzY1NSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayIgZm9udC1zdHlsZT0iaXRhbGljIj54PC90ZXh0PjwvZz4gPC9nPiA8L2c+PC9nPiA8L2c+IDxwYXRoIGQ9IiBNIDAuMCAtMTQuMjI2MzYgTCAwLjAgOTkuMTg0NiAgIiBmaWxsPSJub25lIj48L3BhdGg+IDxnIHRyYW5zZm9ybT0ibWF0cml4KDAuMCwxLjAsLTEuMCwwLjAsMC4wLDk5LjM4NDYpIj4gPGcgc3Ryb2tlLWRhc2hhcnJheT0ibm9uZSIgc3Ryb2tlLWRhc2hvZmZzZXQ9IjAuMCI+IDxnIHN0cm9rZS1saW5lY2FwPSJyb3VuZCI+IDxnIHN0cm9rZS1saW5lam9pbj0icm91bmQiPiA8cGF0aCBkPSIgTSAtMi4wNzk5OSAyLjM5OTk4IEMgLTEuNjk5OTggMC45NTk5OCAtMC44NTMxOCAwLjI4IDAuMCAwLjAgQyAtMC44NTMxOCAtMC4yOCAtMS42OTk5OCAtMC45NTk5OCAtMi4wNzk5OSAtMi4zOTk5OCAgIiBmaWxsPSJub25lIj48L3BhdGg+IDwvZz4gPC9nPiA8L2c+ICA8L2c+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKC04Ljc5NDU3LDEwNS4wNjIpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsNDAuNDMwNTExNDc0NjA5MzcpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQwLjQzMDUxMTQ3NDYwOTM3IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siIGZvbnQtc3R5bGU9Iml0YWxpYyI+eTwvdGV4dD48L2c+IDwvZz4gPC9nPjwvZz4gPC9nPiA8ZyBmaWxsPSIjZTZlNmZmIj4gPGcgc3Ryb2tlPSIjMDBmIj4gPGcgc3Ryb2tlLXdpZHRoPSIwLjgiPiA8cGF0aCBkPSIgTSAwLjAgMC4wIEwgMjguNDUyNzQgMC4wIEwgMjguNDUyNzQgMjguNDUyNzQgTCAwLjAgMjguNDUyNzQgWiAgIj48L3BhdGg+IDwvZz4gPC9nPiA8L2c+IDxnIHN0cm9rZT0iIzAwZiIgZmlsbD0iIzAwZiI+IDxnIHN0cm9rZT0iIzAwZiIgZmlsbD0iIzAwZiI+IDwvZz4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoMTAuODcyMjEsMzAuNzI2NTUpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsNDAuNDMwNTExNDc0NjA5MzcpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwZiI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQwLjQzMDUxMTQ3NDYwOTM3IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iIzAwMDBmZiIgZm9udC1zdHlsZT0iaXRhbGljIj5TPC90ZXh0PjwvZz4gPC9nPiA8L2c+PC9nPiA8L2c+IDwvZz4gPGcgZmlsbD0iI2ZmZTZlNiI+IDxnIHN0cm9rZT0iI2YwMCI+IDxnIHN0cm9rZS13aWR0aD0iMC44Ij4gPHBhdGggZD0iIE0gMzQuMTQzMiAxMS4zODA5MiBMIDYyLjU5NTk1IDI4LjQ1MjczIEwgNjIuNTk1OTUgNTYuOTA1NDcgTCAzNC4xNDMyIDM5LjgzMzY2IFogICI+PC9wYXRoPiA8L2c+IDwvZz4gPC9nPiA8ZyBzdHJva2U9IiNmMDAiIGZpbGw9IiNmMDAiPiA8ZyBzdHJva2U9IiNmMDAiIGZpbGw9IiNmMDAiPiA8L2c+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKDM4LjE0MDM4LDUxLjU2MDAzKSI+IDxnIHN0cm9rZT0iIzAwMCIgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZT0ibm9uZSIgdHJhbnNmb3JtPSJzY2FsZSgtMSwxKSB0cmFuc2xhdGUoLTU3Ljg0MzY0MzE4ODQ3NjU1LDQwLjQzMDUxMTQ3NDYwOTM3KSBzY2FsZSgtMSwtMSkiPjxnIGZpbGw9IiNmMDAiPiA8ZyBzdHJva2U9Im5vbmUiPiA8dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSI0MC40MzA1MTE0NzQ2MDkzNyIgeD0iLTU3Ljg0MzY0MzE4ODQ3NjU1IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9IiNmZjAwMDAiIGZvbnQtc3R5bGU9Iml0YWxpYyI+ZjwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSI0MC40MzA1MTE0NzQ2MDkzNyIgeD0iLTUxLjg3MTM4MzY2Njk5MjE3IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9IiNmZjAwMDAiPig8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iNDAuNDMwNTExNDc0NjA5MzciIHg9Ii00Ny45ODI0ODEwMDI4MDc2MSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSIjZmYwMDAwIiBmb250LXN0eWxlPSJpdGFsaWMiPlM8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iNDAuNDMwNTExNDc0NjA5MzciIHg9Ii00MS4yNzQxNTY1NzA0MzQ1NiIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSIjZmYwMDAwIj4pPC90ZXh0PjwvZz4gPC9nPiA8L2c+PC9nPiA8L2c+IDwvZz4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoNTguNjIwMzUsODUuNzAzNjkpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsNDAuNDMwNTExNDc0NjA5MzcpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQwLjQzMDUxMTQ3NDYwOTM3IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siIGZvbnQtc3R5bGU9Iml0YWxpYyI+QTwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSI0MC40MzA1MTE0NzQ2MDkzNyIgeD0iLTQ3LjU2NTkxNDE1NDA1MjczIiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9ImJsYWNrIj49PC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjMzMDM4MzMwMDc4MTI0MyIgeD0iLTM3LjAxMDM5ODg2NDc0NjA5IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9ImJsYWNrIj7iiJk8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iMzQuMzMwNDc0ODUzNTE1NjIiIHg9Ii0zMS43MzI1OTczNTEwNzQyMSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+MTwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIzNC4zMzA0NzQ4NTM1MTU2MiIgeD0iLTE2LjczMjU4MjA5MjI4NTE1MyIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+MDwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIzNC4zMzA0NzQ4NTM1MTU2MiIgeD0iLTExLjczMjU2MzAxODc5ODgyNiIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayIgZm9udC1zdHlsZT0iaXRhbGljIj46PC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjM0LjMzMDQ3NDg1MzUxNTYyIiB4PSItOC45NTQ3NzY3NjM5MTYwMTQiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siPjY8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iNDYuMzMwNDc0ODUzNTE1NjIiIHg9Ii0zMS43MzI1OTczNTEwNzQyMSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+MDwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSI0Ni4zMzA0NzQ4NTM1MTU2MiIgeD0iLTEyLjg0MzY4MTMzNTQ0OTIxNSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+MTwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIyNi4zMzAzODMzMDA3ODEyNDMiIHg9Ii0zLjk1NDc2NTMxOTgyNDIxOCIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+wrg8L3RleHQ+PC9nPiA8L2c+IDwvZz48L2c+IDwvZz4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoNjcuNzI0NTMsNjguNjMxODcpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsNDAuNDMwNTExNDc0NjA5MzcpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQwLjQzMDUxMTQ3NDYwOTM3IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siIGZvbnQtc3R5bGU9Iml0YWxpYyI+YjwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSI0MC40MzA1MTE0NzQ2MDkzNyIgeD0iLTUwLjc3NDI2NTI4OTMwNjYyNiIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+PTwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIyNi4zMzAzODMzMDA3ODEyNDMiIHg9Ii00MC4yMTg3NDk5OTk5OTk5OSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+4oiZPC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjM0LjMzMDQ3NDg1MzUxNTYyIiB4PSItMzQuOTQwOTQ4NDg2MzI4MTIiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siPjE8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iMzQuMzMwNDc0ODUzNTE1NjIiIHg9Ii0yOS45NDA5Mjk0MTI4NDE3OSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayIgZm9udC1zdHlsZT0iaXRhbGljIj46PC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjM0LjMzMDQ3NDg1MzUxNTYyIiB4PSItMjcuMTYzMTQzMTU3OTU4OTc3IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9ImJsYWNrIj4yPC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQ2LjMzMDQ3NDg1MzUxNTYyIiB4PSItMzQuOTQwOTQ4NDg2MzI4MTIiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siPjA8L3RleHQ+PHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iNDYuMzMwNDc0ODUzNTE1NjIiIHg9Ii0yOS45NDA5Mjk0MTI4NDE3OSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayIgZm9udC1zdHlsZT0iaXRhbGljIj46PC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjQ2LjMzMDQ3NDg1MzUxNTYyIiB4PSItMjcuMTYzMTQzMTU3OTU4OTc3IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9ImJsYWNrIj40PC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjMzMDM4MzMwMDc4MTI0MyIgeD0iLTIyLjE2MzEzMTcxMzg2NzE4NCIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayI+wrg8L3RleHQ+PC9nPiA8L2c+IDwvZz48L2c+IDwvZz4gPC9nPiA8L2c+IDwvZz48L3N2Zz4=" alt="tikz diagram" loading="lazy" decoding="async"><figcaption><em>source code</em><button class="source-code-button" aria-label="copy source code for this tikz graph" title="copy source code for this tikz graph"><svg class="source-icon" xmlns="http://www.w3.org/2000/svg" width="12" height="16" viewBox="0 -4 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><use href="#code-icon"></use></svg><svg class="check-icon" xmlns="http://www.w3.org/2000/svg" width="12" height="16" viewBox="0 -4 16 16" fill="currentColor" stroke="none" stroke-width="0" stroke-linecap="round" stroke-linejoin="round"><use href="#github-check"></use></svg></button></figcaption></figure>

Rotation + translation on a triangle ($A=R_\theta$, $\theta=25^\circ$, $b=(1.0,0.6)$):

<figure class="tikz" data-remark-tikz style=""><span class="tikz-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><annotation encoding="application/x-tex">"\\usepackage{tikz}\n\\begin{document}\n\\begin{tikzpicture}[scale=1]\n  % axes\n  \\draw[->] (-0.5,0) -- (3.5,0) node[below right] {$x$};\n  \\draw[->] (0,-0.5) -- (0,3.0) node[above left] {$y$};\n  % original triangle T\n  \\filldraw[fill=green!12,draw=green!60!black,thick]\n    (0,0) -- (1.2,0.2) -- (0.3,1.1) -- cycle;\n  \\node[green!50!black] at (0.7,0.8) {$T$};\n  % rotated + translated triangle via cm = R_theta and shift b\n  % cm = [cos theta, -sin theta; sin theta, cos theta]\n  \\begin{scope}[cm={0.9063,-0.4226,0.4226,0.9063,(1.0,0.6)}]\n    \\filldraw[fill=orange!15,draw=orange!70!black,thick]\n      (0,0) -- (1.2,0.2) -- (0.3,1.1) -- cycle;\n    \\node[orange!70!black] at (0.7,0.8) {$f(T)$};\n  \\end{scope}\n\\end{tikzpicture}\n\\end{document}"</annotation></semantics></math></span><img src="data:image/svg+xml;base64,PHN2ZyB2ZXJzaW9uPSIxLjEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiIHdpZHRoPSIxMjYuNTkyMThwdCIgaGVpZ2h0PSIxMTIuOTAwNTFwdCIgdmlld0JveD0iLTcyIC03MiAxMjYuNTkyMTggMTEyLjkwMDUxIj48ZyBzdHJva2UtbWl0ZXJsaW1pdD0iMTAiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC01Ny44NDM2NDMxODg0NzY1NSwyNi4yMDQxNDczMzg4NjcxOCkgc2NhbGUoMSwtMSkiPjxnIHN0cm9rZT0iIzAwMCIgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZS13aWR0aD0iMC40Ij4gPHBhdGggZD0iIE0gLTE0LjIyNjM2IDAuMCBMIDk5LjE4NDYgMC4wICAiIGZpbGw9Im5vbmUiPjwvcGF0aD4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoOTkuMzg0NiwwLjApIj4gPGcgc3Ryb2tlLWRhc2hhcnJheT0ibm9uZSIgc3Ryb2tlLWRhc2hvZmZzZXQ9IjAuMCI+IDxnIHN0cm9rZS1saW5lY2FwPSJyb3VuZCI+IDxnIHN0cm9rZS1saW5lam9pbj0icm91bmQiPiA8cGF0aCBkPSIgTSAtMi4wNzk5OSAyLjM5OTk4IEMgLTEuNjk5OTggMC45NTk5OCAtMC44NTMxOCAwLjI4IDAuMCAwLjAgQyAtMC44NTMxOCAtMC4yOCAtMS42OTk5OCAtMC45NTk5OCAtMi4wNzk5OSAtMi4zOTk5OCAgIiBmaWxsPSJub25lIj48L3BhdGg+IDwvZz4gPC9nPiA8L2c+ICA8L2c+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKDEwMy4xMTc1NywtNy44Mzg1MikiPiA8ZyBzdHJva2U9IiMwMDAiIGZpbGw9IiMwMDAiPiA8ZyBzdHJva2U9Im5vbmUiIHRyYW5zZm9ybT0ic2NhbGUoLTEsMSkgdHJhbnNsYXRlKC01Ny44NDM2NDMxODg0NzY1NSwyNi4yMDQxNDczMzg4NjcxOCkgc2NhbGUoLTEsLTEpIj48ZyBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIj4gPHRleHQgYWxpZ25tZW50LWJhc2VsaW5lPSJiYXNlbGluZSIgeT0iMjYuMjA0MTQ3MzM4ODY3MTgiIHg9Ii01Ny44NDM2NDMxODg0NzY1NSIgZm9udC1mYW1pbHk9InNlcmlmIiBmb250LXNpemU9IjEwIiBmaWxsPSJibGFjayIgZm9udC1zdHlsZT0iaXRhbGljIj54PC90ZXh0PjwvZz4gPC9nPiA8L2c+PC9nPiA8L2c+IDxwYXRoIGQ9IiBNIDAuMCAtMTQuMjI2MzYgTCAwLjAgODQuOTU4MjQgICIgZmlsbD0ibm9uZSI+PC9wYXRoPiA8ZyB0cmFuc2Zvcm09Im1hdHJpeCgwLjAsMS4wLC0xLjAsMC4wLDAuMCw4NS4xNTgyMykiPiA8ZyBzdHJva2UtZGFzaGFycmF5PSJub25lIiBzdHJva2UtZGFzaG9mZnNldD0iMC4wIj4gPGcgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIj4gPGcgc3Ryb2tlLWxpbmVqb2luPSJyb3VuZCI+IDxwYXRoIGQ9IiBNIC0yLjA3OTk5IDIuMzk5OTggQyAtMS42OTk5OCAwLjk1OTk4IC0wLjg1MzE4IDAuMjggMC4wIDAuMCBDIC0wLjg1MzE4IC0wLjI4IC0xLjY5OTk4IC0wLjk1OTk4IC0yLjA3OTk5IC0yLjM5OTk4ICAiIGZpbGw9Im5vbmUiPjwvcGF0aD4gPC9nPiA8L2c+IDwvZz4gIDwvZz4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTguNzk0NTcsOTAuODM1NjMpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsMjYuMjA0MTQ3MzM4ODY3MTgpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjIwNDE0NzMzODg2NzE4IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iYmxhY2siIGZvbnQtc3R5bGU9Iml0YWxpYyI+eTwvdGV4dD48L2c+IDwvZz4gPC9nPjwvZz4gPC9nPiA8ZyBmaWxsPSIjZTFmZmUxIj4gPGcgc3Ryb2tlPSIjMDkwIj4gPGcgc3Ryb2tlLXdpZHRoPSIwLjgiPiA8cGF0aCBkPSIgTSAwLjAgMC4wIEwgMzQuMTQzMiA1LjY5MDQ2IEwgOC41MzU5IDMxLjI5ODE5IFogICI+PC9wYXRoPiA8L2c+IDwvZz4gPC9nPiA8ZyBzdHJva2U9IiMwMDgwMDAiIGZpbGw9IiMwMDgwMDAiPiA8ZyBzdHJva2U9IiMwMDgwMDAiIGZpbGw9IiMwMDgwMDAiPiA8L2c+IDxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKDE2LjMwMDUsMTkuMzQ1NjEpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsMjYuMjA0MTQ3MzM4ODY3MTgpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iIzAwODAwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjIwNDE0NzMzODg2NzE4IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iIzAwODAwMCIgZm9udC1zdHlsZT0iaXRhbGljIj5UPC90ZXh0PjwvZz4gPC9nPiA8L2c+PC9nPiA8L2c+IDwvZz4gPGcgZmlsbD0iI2ZmZWNkOSI+IDxnIHN0cm9rZT0iI2IzNTkwMCI+IDxnIHN0cm9rZS13aWR0aD0iMC44Ij4gPHBhdGggZD0iIE0gMjguNDUyNzQgMTcuMDcxODEgTCA2MS44MDEzOSA3Ljc5OTg3IEwgNDkuNDE1NjMgNDEuODI5ODggWiAgIj48L3BhdGg+IDwvZz4gPC9nPiA8L2c+IDxnIHN0cm9rZT0iI2IzNTkwMCIgZmlsbD0iI2IzNTkwMCI+IDxnIHN0cm9rZT0iI2IzNTkwMCIgZmlsbD0iI2IzNTkwMCI+IDwvZz4gPGcgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoNDUuNjMxNDEsMjYuNzg0MTUpIj4gPGcgc3Ryb2tlPSIjMDAwIiBmaWxsPSIjMDAwIj4gPGcgc3Ryb2tlPSJub25lIiB0cmFuc2Zvcm09InNjYWxlKC0xLDEpIHRyYW5zbGF0ZSgtNTcuODQzNjQzMTg4NDc2NTUsMjYuMjA0MTQ3MzM4ODY3MTgpIHNjYWxlKC0xLC0xKSI+PGcgZmlsbD0iI2IzNTkwMCI+IDxnIHN0cm9rZT0ibm9uZSI+IDx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjIwNDE0NzMzODg2NzE4IiB4PSItNTcuODQzNjQzMTg4NDc2NTUiIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iI2IzNTkwMCIgZm9udC1zdHlsZT0iaXRhbGljIj5mPC90ZXh0Pjx0ZXh0IGFsaWdubWVudC1iYXNlbGluZT0iYmFzZWxpbmUiIHk9IjI2LjIwNDE0NzMzODg2NzE4IiB4PSItNTEuODcxMzgzNjY2OTkyMTciIGZvbnQtZmFtaWx5PSJzZXJpZiIgZm9udC1zaXplPSIxMCIgZmlsbD0iI2IzNTkwMCI+KDwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIyNi4yMDQxNDczMzg4NjcxOCIgeD0iLTQ3Ljk4MjQ4MTAwMjgwNzYxIiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9IiNiMzU5MDAiIGZvbnQtc3R5bGU9Iml0YWxpYyI+VDwvdGV4dD48dGV4dCBhbGlnbm1lbnQtYmFzZWxpbmU9ImJhc2VsaW5lIiB5PSIyNi4yMDQxNDczMzg4NjcxOCIgeD0iLTQwLjc0OTgxNjg5NDUzMTI0IiBmb250LWZhbWlseT0ic2VyaWYiIGZvbnQtc2l6ZT0iMTAiIGZpbGw9IiNiMzU5MDAiPik8L3RleHQ+PC9nPiA8L2c+IDwvZz48L2c+IDwvZz4gPC9nPiA8L2c+IDwvZz4gPC9nPjwvc3ZnPg==" alt="tikz diagram" loading="lazy" decoding="async"><figcaption><em>source code</em><button class="source-code-button" aria-label="copy source code for this tikz graph" title="copy source code for this tikz graph"><svg class="source-icon" xmlns="http://www.w3.org/2000/svg" width="12" height="16" viewBox="0 -4 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><use href="#code-icon"></use></svg><svg class="check-icon" xmlns="http://www.w3.org/2000/svg" width="12" height="16" viewBox="0 -4 16 16" fill="currentColor" stroke="none" stroke-width="0" stroke-linecap="round" stroke-linejoin="round"><use href="#github-check"></use></svg></button></figcaption></figure>

