Андрей Смирнов
Время чтения: ~17 мин.
Просмотров: 0

Прямоугольная система координат

Перспективная проекция

Если вы когда-либо наблюдали за реальным миром, то наверняка заметили, что объекты, расположенные дальше, выглядят намного меньше. Этот странный эффект мы называем перспективой. Перспектива особенно заметна, когда смотришь в конец бесконечной автомагистрали или железной дороги, как это видно на следующем изображении:

Как вы видите, из-за перспективы кажется что линии сходятся тем больше, чем дальше они находятся. Это как раз тот эффект, который перспективная проекция пытается имитировать, и достигается он посредством матрицы перспективной проекции. Матрица проекции отображает заданный диапазон усеченной пирамиды в пространство отсечения, и при этом манипулирует w-компонентой каждой вершины таким образом, что чем дальше от наблюдателя находится вершина, тем больше становится это w-значение. После преобразования координат в пространство отсечения, все они попадают в диапазон от -w до w (вершины, находящиеся вне этого диапазона, отсекаются). OpenGL требует, чтобы конечным выводом вершинного шейдера были координаты, находящиеся между значениями -1,0 и 1,0. Таким образом, когда координаты находятся в пространстве отсечения, к ним применяется перспективное деление:

Каждый компонент координаты вершины делится на свою w-компоненту, что уменьшает значения координат пропорционально удалению от зрителя

Это еще одна причина важности w-компонента, поскольку он помогает нам с перспективной проекцией. Полученные после этого координаты находятся в нормализованном пространстве устройства

Если вам интересно разобраться, как рассчитываются ортогональные и перспективные матрицы проекции (и вы не слишком боитесь математики), то могу порекомендовать эту отличную статью Songho.

Матрицу перспективной проекции в библиотеке GLM можно создать следующим образом:

glm::perspective создает усеченную пирамиду, которая определяет видимое пространство, а все, что находится за его пределами и не попадет в объем пространства отсечения будет обрезано. Перспективная усеченная пирамида может быть представлена как коробка трапециевидной формы, каждая координата внутри которой будет отображена в точку в пространстве отсечения. Изображение перспективной усеченной пирамиды показано ниже:

Первый параметр устанавливает значение fov (field of view), что обозначает «поле обзора«, и определяет, насколько велика видимая область. Для реалистичного представления этот параметр обычно устанавливается равным 45.0f, но для получения подобия doom-стилю вы можете задавать и большие значения. Второй параметр задает соотношение сторон, которое рассчитывается путем деления ширины области просмотра на её высоту. Третий и четвертый параметры задают ближнюю и дальнюю плоскости усеченной пирамиды. Обычно мы устанавливаем ближайшее расстояние равным 0.1f, а дальнее 100.0f. Все вершины расположенные между ближней и дальней плоскостью и попадающие в объем усеченной пирамиды будут визуализированы.

При использовании ортогональной проекции каждая координата вершины непосредственно отображается в пространство отсечения без какого-либо мнимого перспективного деления (перспективное деление производится, но w-компонент на результат никак не влияет (он остается равен 1) и, следовательно, не имеет никакого эффекта). Поскольку ортографическая проекция не учитывает перспективу, то объекты, расположенные дальше, не кажутся меньше, что создает странное визуальное впечатление. По этой причине ортографическая проекция в основном используется для 2D-рендеринга и различных архитектурных или инженерных приложений, где мы бы предпочли отсутствие искажений, обусловленных перспективой. В таких приложениях, как Blender, предназначенных для 3D-моделирования, ортографическая проекция иногда используется во время моделирования, потому что она более точно отображает измерения и пропорции каждого объекта. Ниже приведено сравнение обоих проекционных методов в Blender:

Вы можете видеть, что при перспективной проекции удаленные вершины оказываются намного дальше, в то время как в ортографической проекции скорость удаления вершин одинаковая и не зависит от расстояния до наблюдателя.

Переходим к 3D

Теперь, когда мы знаем, как преобразовать 3D-координаты в 2D-координаты, мы можем начать отображать наши объекты в виде реальных 3D-объектов, а не ущербных 2D-плоскостей, которые мы показывали до сих пор.

Для начала рисования в 3D мы первым делом создадим матрицу модели. Матрица модели состоит из сдвигов, масштабирования и/или поворотов, которые мы бы хотели применить, чтобы преобразовать все вершины объекта в глобальное мировое пространство. Давайте немного изменим нашу плоскость, повернув ее по оси X, чтобы она выглядела так, будто лежит на полу. Матрица модели будет выглядеть следующим образом:

Умножив координаты вершин на эту матрицу модели мы преобразуем их в мировые координаты. Наша плоскость лежащая на полу, представляет собой таким образом плоскость в мировом пространстве.

Затем нам нужно создать матрицу вида. Чтобы объект стал видимым нам нужно немного сдвинуться в сцене назад (потому что точка зрения наблюдателя в мировом пространстве находится в начале координат (0,0,0)). Для перемещения по сцене, подумайте о следующем:

Это именно то, что делает матрица вида: мы перемещаем всю сцену в сторону противоположную той, в которую бы мы хотели сдвинуть камеру. Так как нам нужно двигаться назад, и поскольку OpenGL использует правую систему координат, то мы должны перемещаться в положительном направлении оси z. Мы осуществляем это, сдвигая всю сцену в отрицательную сторону оси z. Это создает впечатление, что мы движемся назад.

Мы обсудим перемещение по сцене более подробно в следующем уроке. На данный момент матрица вида выглядит так:

Последнее, что нам нужно определить — это матрица проекции. Для нашей сцены мы будем использовать перспективную проекцию, поэтому объявим матрицу следующим образом:

Теперь, когда мы создали матрицы преобразования, мы должны передать их нашим шейдерам. Сначала давайте объявим в вершинном шейдере матрицы преобразования как uniform и умножим их на координаты вершин:

Мы также должны отправить матрицы в шейдер (обычно это делается для каждой итерации, так как матрицы преобразования имеют тенденцию часто меняться):

Теперь, когда наши координаты вершин преобразуются матрицами модели, вида и матрицей проекции, конечный объект должен:

  • Отклонен назад до самого пола.
  • Немного от нас удалён.
  • Быть отображенным с учетом перспективы (его размеры должна становиться меньше с увеличением расстояния до зрителя).

Давайте проверим, действительно ли результат соответствует этим требованиям:

Это и правда похоже на 3D-плоскость, которая покоится на каком-то воображаемом полу. Если вы не получили такого же результата, проверьте полный исходный код, вершинный шейдер и фрагментный шейдер.

Собираем все вместе.

Теперь, когда мы знаем все основополагающие принципы координат, давайте пройдемся по примерам различных задач. Мы используем деталь, после ручной обработки, чтобы определить внешнюю форму. Теперь используем станок с ЧПУ, чтобы просверлить несколько точных отверстий.

Задача 1.

Сначала нам нужно обезопасить и установить наши оси и исходную точку:

• Деталь зажимается в тисках, которые крепятся болтами к нашему столу станка и распределяются по осям станка.

• Это сохраняет ось X в WCS выровненной с осью X станка.

• Левая часть детали находится напротив тисков. Это устанавливает воспроизводимое начало оси X.

• Поскольку одна часть тисков зафиксирована, мы можем использовать эту часть для определения повторяемого начала оси Y, находя это местоположение с помощью зонда или другим методом.

С нашей WCS станок теперь понимает положение запаса относительно его собственных внутренних координат. Процесс обработки начинается с обработки и сверления на лицевой стороне детали.

Задача 2.

Теперь деталь должна быть перевернута, чтобы работать на другой стороне. Поскольку мы просто перевернули деталь на 180 градусов, внешний контур был симметричным, а предыдущие смещения X и Y были повторяемыми, WCS не изменится. Мы также используем тот же инструмент, поэтому можно использовать то же Z-смещение.

Здесь следует помнить одну важную переменную силу зажима вашего тиска. Если вы еще не видели его, операторы обычно отмечают закрытое положение тисков черным маркером или используют динамометрический ключ. Почему они это делают? Для создания постоянного зажимного давления при перемещении или вращении деталей. Изменения давления зажима могут привести к различиям в позиционировании детали или другим сбоям, таким как деформация детали или изгиб, в зависимости от геометрии детали. Предполагая, что наше усилие зажима более или менее одинаково, теперь можно обрабатывать.

Задача 3.

Теперь нам нужно просверлить последние несколько отверстий, для чего необходимо поставить деталь на ее конец. Это вращение не меняет XY-происхождение WCS. Однако теперь у нас есть меньшее расстояние перемещения между нашим инструментом и деталью.

Это требует использования нового смещения, которое сместит исходную точку в верхний угол детали. Мы также удалили параллели, чтобы увеличить поверхность захвата, и опустили тиски, чтобы они соединялись с поверхностью детали, а не с нижним карманом.

Мы все еще можем использовать две наши исходные плоскости отсчета для выполнения задачи 3.

Итак, дорогие читатели, вы прошли курс молодого бойца и готовы к обработке на ЧПУ станке.

Географическая система координат

Замкнутая поверхность внешнего контура Земли представлена сфероидной геометрической формой. За основные направления ориентирования на ней можно принять дуги на поверхности шара. На упрощенно представленном уменьшенном макете нашей планеты в виде глобуса (фигура земли) можно зрительно увидеть принятые линии отсчета в виде Гринвичского меридиана и экваториальной линии.

В этом примере выражена общепринятая во всем мире именно пространственная система географических координат. В ней введены понятия долготы и широты. Имея градусные единицы измерения, они представляют угловую величину. Многим знакомы их определения. Следует напомнить, что географическая долгота конкретной точки представляет угол между двумя плоскостями, проходящими через нулевой (Гринвичский) меридиан и меридиан в определяемой точке расположения. Под географической широтой точки принят угол, образующийся между отвесной линией (или нормалью) к ней и плоскостью экватора. 

Моменты

Построение фрезера с ЧПУ может быть как достаточно простым, так и трудоемким. Часть людей сначала подробно все изучают и рассчитывают, а некоторые сразу собирают его, корректируют всплывшие недочеты и наблюдают за его работой. На самом деле, лучший подход – это сочетание двух методов.

Вышеприведенный рисунок показывает наглядный пример оси, который показан в двух измерениях. Изучив вид спереди, можно обнаружить, что узел движется вправо, пока идет движение по направляющим Y.

Погружной рычаг находится на расстоянии Zmax и режет материал при перемещении вправо. Это действие создает режущее усилие, которое приводит к перемещению узла Z.

Усилие резки постоянно изменяется, и зависит от таких факторов, как:

  1. Частота вращения шпинделя.
  2. Количество канавок на фрезе ЧПУ.
  3. Скорость подачи.
  4. Обрабатываемый материал.

На данном этапе также нужно понять, что присутствует и величина, направленная противоположно движению оси Z.

Усилие резания образует величину, которая изображена на рисунке выше как “А”. Момент – это сила, приложенная на расстоянии.

«A» = D6 x Режущее усилие.

Этот момент проворачивает рычаг крепления шпинделя против направления обработки, вращающего весь узел оси.

Br> Данный момент способствует возникновению сил, прикладываемых к линейным опорным направляющим и самим линейным подшипникам. (Обозначено желтыми стрелками)

Z-буфер

OpenGL хранит всю информацию о глубине в Z-буфере, также известном как буфер глубины. GLFW создает это буфер автоматически (он так же имеет буфер кадра, который хранит цвета выходного изображения). Глубина хранится для каждого фрагмента (в качестве z-значения) и всякий раз, когда фрагмент выводит свой цвет, OpenGL сравнивает его значение глубины со значениями из Z-буфера, и если текущий фрагмент находится позади другого фрагмента он отбрасывается, а в противном случае перезаписывается. Этот процесс называется проверка глубины и осуществляется OpenGL автоматически.

Тем не менее, если мы хотим быть уверены в том, что OpenGL действительно выполняет проверку глубины, то сначала нам нужно её включить, потому что по-умолчанию она выключена. Включение проверки глубины осуществляется с помощью функции glEnable. Функции glEnable и glDisable позволяют включить/отключить определенные возможности OpenGL. Опции OpenGL включаются/выключаются, пока не будет сделан другой вызов функции для их отключения/включения. На данный момент мы хотим разрешить проверку глубины, включая параметр GL_DEPTH_TEST:

Так как мы используем буфер глубины, то нам нужно его очищать перед каждой итерацией визуализации (в противном случае в буфере останется информация о глубине предыдущих кадров). Мы можем очистить буфер глубины таким же образом как и буфера цвета, указав в функции glClear бит GL_DEPTH_BUFFER_BIT:

Давайте повторно запустим нашу программу и посмотрим, выполняет ли теперь OpenGL проверку глубины:

Your browser does not support HTML5 video.

Вот и всё! Наш куб полностью текстурирован, с правильной проверкой глубины, еще и вращается. Здесь исходный код для проверки.

Понятия астрономической и геодезической системы координат и их различия

Географическая система условно объединяет астрономическую и геодезическую системы

Для того чтобы было понятно какие все-таки существуют различия обратите внимание на определения геодезических и астрономических координат (долготы, широты, высоты). В астрономической системе широта рассматривается как угол между экваториальной плоскостью и отвесной линией в точке определения

А сама форма Земли в ней рассматривается как условный геоид, математически приближенно приравненный к сфере. В геодезической системе широта образовывается нормалью к поверхности земного эллипсоида в конкретной точке и плоскостью экватора. Третьи координаты в этих системах дают окончательное представление в их различиях. Астрономическая (ортометрическая) высота представляет собой превышение по отвесной линии между фактической и точкой на поверхности уровенного геоида. Геодезической высотой считается расстояние по нормали от поверхности эллипсоида до точки вычисления. 

Прямоугольная система координат на плоскости

Прямоугольная система координат на плоскости образуется двумя взаимно перпендикулярными осями координат X′X{\displaystyle X’X} и Y′Y{\displaystyle Y’Y}. Оси координат пересекаются в точке O{\displaystyle O}, которая называется началом координат, на каждой оси выбрано положительное направление.

Рис. 1

Положение точки A{\displaystyle A} на плоскости определяется двумя координатами x{\displaystyle x} и y{\displaystyle y}. Координата x{\displaystyle x} равна длине отрезка OB{\displaystyle OB}, координата y{\displaystyle y} — длине отрезка OC{\displaystyle OC} в выбранных единицах измерения. Отрезки OB{\displaystyle OB} и OC{\displaystyle OC} определяются линиями, проведёнными из точки A{\displaystyle A} параллельно осям Y′Y{\displaystyle Y’Y} и X′X{\displaystyle X’X} соответственно.

При этом координате x{\displaystyle x} приписывается знак минус, если точка B{\displaystyle B} лежит на луче OX′{\displaystyle OX’} (а не на луче OX{\displaystyle OX}, как на рисунке). Координате y{\displaystyle y} приписывается знак минус, если точка C{\displaystyle C} лежит на луче OY′{\displaystyle OY’}. Таким образом,OX′{\displaystyle OX’} и OY′{\displaystyle OY’} являются отрицательными направлениями осей координат (каждая ось координат рассматривается как числовая ось).

Ось X′X{\displaystyle X’X} называется осью абсцисс, а ось Y′Y{\displaystyle Y’Y} — осью ординат. Координата x{\displaystyle x} называется абсциссой точки A{\displaystyle A}, координата y{\displaystyle y} — ординатой точки A{\displaystyle A}.

Символически это записывают так:

A(x,y){\displaystyle A(x,\;y)}

или

A=(x,y){\displaystyle A=(x,\;y)}

или указывают принадлежность координат конкретной точке с помощью индекса:

xA,xB{\displaystyle x_{A},x_{B}}

и т. д.

  • В правосторонней системе координат положительное направление осей выбирают так, чтобы при направлении оси Y′Y{\displaystyle Y’Y} вверх, ось X′X{\displaystyle X’X} смотрела направо. Обычно принято пользоваться правосторонними системами координат (если обратное не оговорено или не очевидно — например, из чертежа; иногда по каким-то соображениям бывает удобнее всё же пользоваться левосторонней системой координат).
  • Четыре угла (I, II, III, IV), образованные осями координат X′X{\displaystyle X’X} и Y′Y{\displaystyle Y’Y}, называются координатными углами, четвертями или квадрантами <плоскости> (см. рис. 1).
    • Точки внутри координатного угла I имеют положительные абсциссы и ординаты.
    • Точки внутри координатного угла II имеют отрицательные абсциссы и положительные ординаты.
    • Точки внутри координатного угла III имеют отрицательные абсциссы и ординаты
    • Точки внутри координатного угла IV имеют положительные абсциссы и отрицательные ординаты.

Больше кубиков!

Предположим, что мы хотели бы отобразить на экране 10 наших кубов. Все кубы выглядят одинаково, но будут отличаться местоположением в мировом пространстве и углом поворота. Графическое представление куба уже определено, и для того, чтобы нарисовать еще несколько объектов нам уже не нужно менять буферы или массивы атрибутов. Единственное, что мы должны исправить для каждого объекта — это его матрицу модели, благодаря которой мы преобразуем локальные координаты куба в мировые.

Во-первых, давайте определим для каждого куба вектор перемещения, который задаст положение объекта в мировом пространстве. Мы запишем 10 позиций кубов в массиве glm::vec3:

Теперь, в рамках игрового цикла мы собираемся вызвать функцию glDrawArrays 10 раз, но при этом перед каждой визуализацией будем передавать в вершинный шейдер разные матрицы модели. Мы создадим внутри игрового цикла еще один небольшой цикл, который нарисует наш объект 10 раз с разными значениями матрицы модели

Обратите внимание, что для каждого контейнера мы также добавили небольшое вращение

Этот фрагмент кода будет обновлять матрицу модели при каждом изображении нового куба, и всего сделает это 10 раз. Сейчас мы должны видеть мир, заполненный десятью произвольно повернутыми кубами:

Отлично! Похоже, наш контейнер нашел несколько похожих на него друзей. Если вы застряли, то прежде чем продолжить посмотрите в чем может быть проблема и сравните свой код с исходным кодом, вершинным и фрагментным шейдером.

Система плоских прямоугольных систем координат Гаусса-Крюгера

Каждая система координат имеет свое теоретическое научное и практическое экономическое применение, как в глобальном, так и региональном масштабах. В некоторых конкретных случаях возможно использование референцных, местных  и условных систем координат, но которые через математические расчеты и вычисления все равно могут быть объединены между собой.

Геодезическая прямоугольная плоская система координат является проекцией отдельных шестиградусных зон эллипсоида. Вписав эту фигуру внутрь горизонтально расположенного цилиндра, каждая зона отдельно проецируется на внутреннюю цилиндрическую поверхность. Зоны такого сфероида ограничиваются меридианами с шагом в шесть градусов. При развертывании на плоскости получается проекция, которая имеет название в честь немецких ученых её разработавших Гаусса-Крюгера. В таком способе проецирования углы между любыми направлениями сохраняют свои величины. Поэтому иногда ее называют еще равноугольной. Ось абсцисс в зоне проходит по центру, через условный осевой меридиан (ось X), а ось ординат по линии экватора (ось Y). Длины линий вдоль осевого меридиана передается без искажений, а вдоль экваториальной линии с искажениями к краям зоны. 

Прямоугольные координаты вектора

Рис. 1

Для определения прямоугольных координат вектора (применимых для представления векторов любой размерности) можно исходить из того, что координаты вектора (направленного отрезка), начало которого находится в начале координат, совпадают с координатами его конца.

Таким образом, например, координаты (x,y){\displaystyle (x,y)} на рис.1 являются координатами вектора OA→{\displaystyle {\vec {OA}}}.

Для векторов (направленных отрезков), начало которых не совпадает с началом координат, прямоугольные координаты можно определить одним из двух способов:

  1. Вектор можно перенести так, чтобы его начало совпало с началом координат). Тогда его координаты определяются способом, описанным в начале параграфа: координаты вектора, перенесённого так, что его начало совпадает с началом координат, — это координаты его конца.
  2. Вместо этого можно просто вычесть из координат конца вектора (направленного отрезка) координаты его начала.

Для прямоугольных координат понятие координаты вектора совпадает с понятием ортогональной проекции вектора на направление соответствующей координатной оси.

В прямоугольных координатах очень просто записываются все операции над векторами:

Сложение и умножение на скаляр:

a+b=(a1+b1,a2+b2,a3+b3,…,an+bn){\displaystyle \mathbf {a} +\mathbf {b} =(a_{1}+b_{1},a_{2}+b_{2},a_{3}+b_{3},\dots ,a_{n}+b_{n})}

или

(a+b)i=ai+bi,{\displaystyle (\mathbf {a} +\mathbf {b} )_{i}=a_{i}+b_{i},}
c a=(c a1,c a2,c a3,…,c an){\displaystyle c\ \mathbf {a} =(c\ a_{1},c\ a_{2},c\ a_{3},\dots ,c\ a_{n})}

или

(c a)i=c ai.{\displaystyle (c\ \mathbf {a} )_{i}=c\ a_{i}.}
а отсюда и вычитание и деление на скаляр:
a−b=(a1−b1,a2−b2,a3−b3,…,an−bn){\displaystyle \mathbf {a} -\mathbf {b} =(a_{1}-b_{1},a_{2}-b_{2},a_{3}-b_{3},\dots ,a_{n}-b_{n})}

или

(a−b)i=ai−bi,{\displaystyle (\mathbf {a} -\mathbf {b} )_{i}=a_{i}-b_{i},}
aλ=(a1λ,a2λ,a3λ,…,anλ){\displaystyle {\frac {\mathbf {a} }{\lambda }}={\Big (}{\frac {a_{1}}{\lambda }},{\frac {a_{2}}{\lambda }},{\frac {a_{3}}{\lambda }},\dots ,{\frac {a_{n}}{\lambda }}{\Big )}}

или

(aλ)i=aiλ.{\displaystyle {\Big (}{\frac {\mathbf {a} }{\lambda }}{\Big )}_{i}={\frac {a_{i}}{\lambda }}.}

(Это верно для любой размерности n и даже, наравне с прямоугольными, для косоугольных координат).

Скалярное произведение:

a⋅b=a1b1+a2b2+a3b3+⋯+anbn{\displaystyle \mathbf {a} \cdot \mathbf {b} =a_{1}b_{1}+a_{2}b_{2}+a_{3}b_{3}+\dots +a_{n}b_{n}}

или

a⋅b=∑i=1naibi,{\displaystyle \mathbf {a} \cdot \mathbf {b} =\sum \limits _{i=1}^{n}a_{i}b_{i},}

(Только в прямоугольных координатах с единичным масштабом по всем осям).

Через скалярное произведение можно вычислить длину вектора

|a|=a⋅a{\displaystyle |\mathbf {a} |={\sqrt {\mathbf {a} \cdot \mathbf {a} }}}
и угол между векторами
∠(a,b)=arccosa⋅b|a|⋅|b|{\displaystyle \angle {(\mathbf {a} ,\mathbf {b} )}=\mathrm {arccos} {\frac {\mathbf {a} \cdot \mathbf {b} }{|\mathbf {a} |\cdot |\mathbf {b} |}}}

Внешнее произведение:

(a∧b)ij=aibj−ajbi{\displaystyle (\mathbf {a} \land \mathbf {b} )_{ij}=a_{i}b_{j}-a_{j}b_{i}}

для любой размерности пространства,

Векторное произведение (только для трехмерного же пространства, на котором оно и определено):

(a×b)x=aybz−azby{\displaystyle (\mathbf {a} \times \mathbf {b} )_{x}=a_{y}b_{z}-a_{z}b_{y}}
(a×b)y=azbx−axbz{\displaystyle (\mathbf {a} \times \mathbf {b} )_{y}=a_{z}b_{x}-a_{x}b_{z}}
(a×b)z=axby−aybx{\displaystyle (\mathbf {a} \times \mathbf {b} )_{z}=a_{x}b_{y}-a_{y}b_{x}}

Очевидно, всё это позволяет, если надо, свести все операции над векторами к достаточно простым операциям над числами.

Рейтинг автора
5
Материал подготовил
Степан Волков
Наш эксперт
Написано статей
141
Ссылка на основную публикацию
Похожие публикации