Хорошо, я понял это. По сути, я нарисовал четырехугольники, которые действуют как «всплывающие» вырезы, угол наклона которых определяется текущим поворотом просмотра. Затем я отключаю тест глубины при выполнении рисования, чтобы они не врезались в трехмерную местность, на которой они нарисованы. Преимущество этого подхода заключается в том, что мне не нужно вычислять значение шкалы - об этом позаботились, потому что я рисую обычные квадраты в окне перспективы.
Во-первых, мне нужно определить угол обзора по шкале от 0 (над головой) до pi / 2 (с уровня земли). Я делаю это с помощью этого уравнения:
viewingAngle = (currentRotation / 90.0) * M_PI_2;
currentRotation - это просто угол, который я использую в glRotatef. Учитывая угол обзора, я могу рассчитать вертикальную высоту и глубину «всплывающего» края четырехугольника. По сути, это простая тригонометрия отсюда. Представьте себе, что вы видите всплывающее отверстие сбоку. У этого есть фиксированное основание, и у этого есть край, который поднимается от горизонтального положения до вертикального положения. Этот край обводит контур кругового квадранта. И в любой заданной точке он образует прямоугольный треугольник, который можно использовать для вычисления значений положения.
Если вы знаете угол (как видно из фрагмента выше) и гипотенузу (которая в данном случае является y-высотой текстуры всплывающего изображения, как если бы она лежала ровно), то вы можете выбрать противоположную сторону сторона треугольника путем умножения греха на угол, умноженный на гипотенузу. Это значение соответствует глубине, на которой всплывающий край должен быть поднят над землей. Поскольку sin (угол) = противоположность / гипотенуза, я могу определить «противоположность» следующим образом:
popUpValueZ = sinf(viewingAngle) * imageHeight;
Далее мне нужно было вычислить размер y всплывающего изображения. В воображаемом треугольнике выше это соответствует стороне, прилегающей к углу всплывающего окна. Таким образом, косинус используется для вычисления его значения:
popUpValueY = cosf(viewingAngle) * imageHeight;
Теперь я могу использовать popUpValueY и popUpValueZ для определения моих вершин. Они будут действовать как высота и глубина моего квадроцикла соответственно. По мере того как угол обзора становится ниже земли, значение Z увеличивается от земли, а значение Y становится все короче и короче, так что оно начинает напоминать вертикальную плоскость, а не горизонтальную.
Другая вещь, которую я должен был сделать:
glDisable(GL_DEPTH_TEST);
Я обнаружил, что эти всплывающие «псевдоспрайты» борются с трехмерной местностью, поэтому я просто отключил тест глубины, прежде чем рисовать их. Таким образом, они масштабируются точно так, как должны, исходя из своего положения в окне перспективы, но они всегда появляются поверх всего, что нарисовано раньше, чем они. В моем конкретном случае я хочу, чтобы эти спрайты были перекрыты ландшафтом, нарисованным перед ним, поэтому я просто включил проверку глубины при рисовании более близкого ландшафта.