1656
Комментарий:
|
3961
|
Удаления помечены так. | Добавления помечены так. |
Строка 3: | Строка 3: |
При работе с растровой графикой очень частая операция — масштабирование объектов. Суть операции в том, чтобы точку ''X,,0,,'' в диапазоне от ''A,,0,,'' до ''B,,0,,'' превратить в точку ''X,,1,,'' в диапазоне от ''A,,1,,'' до ''B,,1,,'' с соблюдением пропорций: | == Масштабирование == При работе с растровой графикой очень частая операция — масштабирование объектов. Суть операции в том, чтобы число ''X,,0,,'' в диапазоне от ''A,,0,,'' до ''B,,0,,'' превратить в число ''X,,1,,'' в диапазоне от ''A,,1,,'' до ''B,,1,,'' с соблюдением пропорций: |
Строка 10: | Строка 11: |
{{{!python | {{{#!python |
Строка 12: | Строка 13: |
return float(X0-A0)/(B0-A0)*(B1-A1)+A1 | return float(X0-A0)/(B0-A0)*(B1-A1)+A1 |
Строка 18: | Строка 19: |
up() goto(A,y) down() stamp() goto(x,y) stamp() goto(B,y) stamp() up() |
up() goto(A,y) down() stamp() goto(x,y) stamp() goto(B,y) stamp() up() |
Строка 35: | Строка 36: |
== Поворот == Более подробно см [[RW:Поворот]] в Википедии. Вспомним¸ что sin угла и cos угла — это длины противолежащего и прилежащего катетов в прямоугольном треугольнике с единичной гипотенузой: {{attachemnt:sincos.png}} Обратим внимание, что картинка также иллюстрирует поворот на угол ''A'' против часовой стрелки точки пересечения положительной полуоси абсцисс и единичной окружности с центром в начале координат. Сравнительно несложно (поворотом этой картинки на произвольный угол) доказать, что поворот ''любой'' точки на единичной окружности аналогичен, и получить следующую функцию поворота точки ''M'' на угол ''A'' относительно точки `(0,0)`: {{{#!python def rotate(M,A): X=M[0]*cos(A)-M[1]*sin(A) Y=M[1]*cos(A)+M[0]*sin(A) return X,Y }}} Проверим. Зададим функцию рисования ломаной по точкам: {{{#!python def draw(line): up() goto(*line[0]) down() for x,y in line[1:]: goto(x,y) up() }}} Убедимся, что поворот на угол, близкий к `pi` относительно (0,0) переносит фигуру из первого в третий квадрант (при повороте ровно на `pi` будет наблюдаться центральная симметрия): {{{#!python l = [(100,200),(200,50),(50,100),(150,50)] ll = [rotate(m,2.75) for m in l] draw(l) draw(ll) }}} == Перенос + масштабирование + поворот == Осталось решить, какая точка в операции «перенос + масштабирование + поворот» будет служить началом координат. '''TODO''' |
Перенос, масштабирование и вращение
Масштабирование
При работе с растровой графикой очень частая операция — масштабирование объектов. Суть операции в том, чтобы число X0 в диапазоне от A0 до B0 превратить в число X1 в диапазоне от A1 до B1 с соблюдением пропорций:
Значение X0 сначала надо нормализовать: перевести из диапазона A0…B0 в диапазон 0…1. Для чего из X0 надо вычесть нижнюю границу диапазона A0 и поделить результат на длину диапазона B0-A0: X=(X0-A0)/(B0-A0)
Затем перевести в новый диапазон A1…B1 теми же операциями в обратном порядке. Получаем функцию переноса с масштабированием scale():
Проверим, как это выглядит с помощью Черепашки:
Поворот
Более подробно см Поворот в Википедии.
Вспомним¸ что sin угла и cos угла — это длины противолежащего и прилежащего катетов в прямоугольном треугольнике с единичной гипотенузой:
Обратим внимание, что картинка также иллюстрирует поворот на угол A против часовой стрелки точки пересечения положительной полуоси абсцисс и единичной окружности с центром в начале координат.
Сравнительно несложно (поворотом этой картинки на произвольный угол) доказать, что поворот любой точки на единичной окружности аналогичен, и получить следующую функцию поворота точки M на угол A относительно точки (0,0):
Проверим. Зададим функцию рисования ломаной по точкам:
Убедимся, что поворот на угол, близкий к pi относительно (0,0) переносит фигуру из первого в третий квадрант (при повороте ровно на pi будет наблюдаться центральная симметрия):
Перенос + масштабирование + поворот
Осталось решить, какая точка в операции «перенос + масштабирование + поворот» будет служить началом координат.
TODO