void doRender(Renderer::RenderContext& renderContext) {
                const Model::BrushFace* face = m_helper.face();
                const Mat4x4 fromFace = face->fromTexCoordSystemMatrix(Vec2f::Null, Vec2f::One, true);
                
                const Plane3& boundary = face->boundary();
                const Mat4x4 toPlane = planeProjectionMatrix(boundary.distance, boundary.normal);
                const Mat4x4 fromPlane = invertedMatrix(toPlane);

                const Vec2f originPosition(toPlane * fromFace * Vec3(m_helper.originInFaceCoords()));
                const Vec2f faceCenterPosition(toPlane * m_helper.face()->boundsCenter());

                const Color& handleColor = pref(Preferences::HandleColor);
                const Color& highlightColor = pref(Preferences::SelectedHandleColor);

                Renderer::ActiveShader shader(renderContext.shaderManager(), Renderer::Shaders::VaryingPUniformCShader);
                const Renderer::MultiplyModelMatrix toWorldTransform(renderContext.transformation(), fromPlane);
                {
                    const Mat4x4 translation = translationMatrix(Vec3(originPosition));
                    const Renderer::MultiplyModelMatrix centerTransform(renderContext.transformation(), translation);
                    if (m_highlight)
                        shader.set("Color", highlightColor);
                    else
                        shader.set("Color", handleColor);
                    m_outer.render();
                }
                
                {
                    const Mat4x4 translation = translationMatrix(Vec3(faceCenterPosition));
                    const Renderer::MultiplyModelMatrix centerTransform(renderContext.transformation(), translation);
                    shader.set("Color", highlightColor);
                    m_center.render();
                }
            }
Beispiel #2
0
const m4x4f NAMESPACE::Trackball::matrix() const
{
  if (m_Walkthrough) {
    return (m_Rotation.toMatrix()*translationMatrix(-m_Translation));
  }
  else {
    return (
      translationMatrix(m_Translation)
      * translationMatrix(m_Center)
      * m_Rotation.toMatrix()
      * translationMatrix(-m_Center)
      );
  }
}
void ScreenSpaceFramebuffer::render(){
    glm::vec2 resolution = OsEng.windowWrapper().currentWindowResolution();
    glm::vec4 size = _size.value();

    float xratio = _originalViewportSize.x / (size.z-size.x);
    float yratio = _originalViewportSize.y / (size.w-size.y);;

    if(!_renderFunctions.empty()){
        glViewport (-size.x*xratio, -size.y*yratio, _originalViewportSize.x*xratio, _originalViewportSize.y*yratio);
        GLint defaultFBO = _framebuffer->getActiveObject();
        _framebuffer->activate();
        
        glClearColor (0.0f, 0.0f, 0.0f, 0.0f);
        glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        glEnable(GL_ALPHA_TEST);
        for(auto renderFunction : _renderFunctions){
            (*renderFunction)();
        }
        _framebuffer->deactivate();

        glBindFramebuffer(GL_FRAMEBUFFER, defaultFBO);
        glViewport (0, 0, resolution.x, resolution.y);
        
        glm::mat4 rotation = rotationMatrix();
        glm::mat4 translation = translationMatrix();
        glm::mat4 scale = scaleMatrix();
        scale = glm::scale(scale, glm::vec3((1.0/xratio), -(1.0/yratio), 1.0f));
        glm::mat4 modelTransform = rotation*translation*scale;
        draw(modelTransform);
    }
}
Beispiel #4
0
Mesh::Mesh(const std::vector<Point3D>& verts,
           const std::vector<std::vector<int>>& faces)
    : m_verts(verts), m_faces(faces) {
  Point3D smallPoint(m_verts[0][0], m_verts[0][1], m_verts[0][2]);
  Point3D largePoint(m_verts[0][0], m_verts[0][1], m_verts[0][2]);

  // Get the minimum and maximum coordinates
  for (const auto& vert : m_verts) {
    for (auto i = 0; i < 3; ++i) {
      largePoint[i] = std::max(largePoint[i], vert[i]);
      smallPoint[i] = std::min(smallPoint[i], vert[i]);
    }
  }
  lowerBound = smallPoint;
  boundsRange = largePoint - smallPoint;
  // Enforce a minimum size (e.g. for planes)
  double MIN_SIZE = 0.2;
  for (auto i = 0; i < 3; ++i) {
    boundsRange[i] = std::max(boundsRange[i], MIN_SIZE);
  }

  // Translate to put lower corner at origin
  Matrix4x4 xlate = translationMatrix(
      -lowerBound[0], -lowerBound[1], -lowerBound[2]);
  // And scale down to get unit cube
  Matrix4x4 scale = scaleMatrix(
      1/boundsRange[0], 1/boundsRange[1], 1/boundsRange[2]);
  boundingCubeInverse = scale * xlate;//xlate * scale;
}
//! [2]
void BasicOperations::paintEvent(QPaintEvent *)
{
    double pi = 3.14;

    double a    = pi/180 * 45.0;
    double sina = sin(a);
    double cosa = cos(a);

    QMatrix translationMatrix(1, 0, 0, 1, 50.0, 50.0);
    QMatrix rotationMatrix(cosa, sina, -sina, cosa, 0, 0);
    QMatrix scalingMatrix(0.5, 0, 0, 1.0, 0, 0);

    QMatrix matrix;
    matrix =  scalingMatrix * rotationMatrix * translationMatrix;

    QPainter painter(this);
    painter.setPen(QPen(Qt::blue, 1, Qt::DashLine));
    painter.drawRect(0, 0, 100, 100);

    painter.setMatrix(matrix);

    painter.setFont(QFont("Helvetica", 24));
    painter.setPen(QPen(Qt::black, 1));
    painter.drawText(20, 10, "QMatrix");
}
Beispiel #6
0
        void Brush::moveBoundary(Face& face, const Vec3f& delta, bool lockTexture) {
            assert(canMoveBoundary(face, delta));

            const Mat4f pointTransform = translationMatrix(delta);
            face.transform(pointTransform, Mat4f::Identity, false, false);
            rebuildGeometry();
        }
void CTouchFreeCamera::Update(float dt)
{
	if(m_isDragging)
	{
		float deltaX = m_dragPosition.x - m_mousePosition.x;
		float deltaY = m_dragPosition.y - m_mousePosition.y;
		m_cameraHAngle = m_dragHAngle + deltaX * 0.015f;
		m_cameraVAngle = m_dragVAngle + deltaY * 0.015f;
		m_cameraVAngle = std::min<float>(m_cameraVAngle, M_PI / 2);
		m_cameraVAngle = std::max<float>(m_cameraVAngle, -M_PI / 2);
	}

	CMatrix4 yawMatrix(CMatrix4::MakeAxisYRotation(m_cameraHAngle));
	CMatrix4 pitchMatrix(CMatrix4::MakeAxisXRotation(m_cameraVAngle));
	CMatrix4 rotationMatrix = yawMatrix * pitchMatrix;

	if(m_isStrafingLeft || m_isStrafingRight)
	{
		CVector3 rightVector = CVector3(1, 0, 0) * rotationMatrix;
		float direction = m_isStrafingLeft ? (-1.0f) : (1.0f);
		m_cameraPosition += (rightVector * direction * MOVE_SPEED * dt);
	}
	if(m_isMovingForward || m_isMovingBackward)
	{
		CVector3 forwardVector = CVector3(0, 0, 1) * rotationMatrix;
		float direction = m_isMovingForward ? (-1.0f) : (1.0f);
		m_cameraPosition += (forwardVector * direction * MOVE_SPEED * dt);
	}

	CMatrix4 translationMatrix(CMatrix4::MakeTranslation(-m_cameraPosition.x, -m_cameraPosition.y, -m_cameraPosition.z));
	CMatrix4 totalMatrix = translationMatrix * rotationMatrix;

	SetViewMatrix(totalMatrix);
}
void OverlayRenderer::render(RenderContext& context, const float viewWidth, const float viewHeight) {
    if (m_vbo == NULL)
        m_vbo = new Vbo(GL_ARRAY_BUFFER, 0xFFFF);
    if (m_compass == NULL)
        m_compass = new CompassRenderer();

    glClear(GL_DEPTH_BUFFER_BIT);

    const Mat4f projection = orthoMatrix(0.0f, 1000.0f, -viewWidth / 2.0f, viewHeight / 2.0f, viewWidth / 2.0f, -viewHeight / 2.0f);
    const Mat4f view = viewMatrix(Vec3f::PosY, Vec3f::PosZ) * translationMatrix(500.0f * Vec3f::PosY);
    Renderer::ApplyTransformation ortho(context.transformation(), projection, view);

    const Mat4f compassTransformation = translationMatrix(Vec3f(-viewWidth / 2.0f + 50.0f, 0.0f, -viewHeight / 2.0f + 50.0f)) * scalingMatrix(2.0f);
    Renderer::ApplyModelMatrix applyCompassTranslate(context.transformation(), compassTransformation);

    m_compass->render(*m_vbo, context);
}
Beispiel #9
0
        void Compass::doRender(RenderContext& renderContext) {
            const Camera& camera = renderContext.camera();
            const Camera::Viewport& viewport = camera.unzoomedViewport();
            const int viewWidth = viewport.width;
            const int viewHeight = viewport.height;
            
            const Mat4x4f projection = orthoMatrix(0.0f, 1000.0f, -viewWidth / 2.0f, viewHeight / 2.0f, viewWidth / 2.0f, -viewHeight / 2.0f);
            const Mat4x4f view = viewMatrix(Vec3f::PosY, Vec3f::PosZ) * translationMatrix(500.0f * Vec3f::PosY);
            const ReplaceTransformation ortho(renderContext.transformation(), projection, view);
            
            const Mat4x4f compassTransformation = translationMatrix(Vec3f(-viewWidth / 2.0f + 55.0f, 0.0f, -viewHeight / 2.0f + 55.0f)) * scalingMatrix<4>(2.0f);
            const MultiplyModelMatrix compass(renderContext.transformation(), compassTransformation);
            const Mat4x4f cameraTransformation = cameraRotationMatrix(camera);

            glAssert(glClear(GL_DEPTH_BUFFER_BIT));
            renderBackground(renderContext);
            glAssert(glClear(GL_DEPTH_BUFFER_BIT));
            doRenderCompass(renderContext, cameraTransformation);
        }
Beispiel #10
0
V3R SymmetryOperation::getReducedVector(const Kernel::IntMatrix &matrix,
                                        const V3R &vector) const {
  Kernel::IntMatrix translationMatrix(3, 3, false);

  for (size_t i = 0; i < order(); ++i) {
    Kernel::IntMatrix tempMatrix(3, 3, true);

    for (size_t j = 0; j < i; ++j) {
      tempMatrix *= matrix;
    }

    translationMatrix += tempMatrix;
  }

  return (translationMatrix * vector) *
         RationalNumber(1, static_cast<int>(order()));
}
Beispiel #11
0
void Renderable::setMatrix() {
#ifdef OPENGL_ES1
	glTranslatef(posx, posy, posz);
	glRotatef(rot, rotx, roty, rotz);
	glScalef(scalex, scaley, scalez);
#else
    Mat16 tmp = translationMatrix(posx, posy, posz);
	currentModelViewMatrix = multiplyMatrix(currentModelViewMatrix, tmp);
    tmp = rotationMatrix(rot / 180 * M_PI, rotx, roty, rotz);
    currentModelViewMatrix = multiplyMatrix(currentModelViewMatrix, tmp);
    tmp = scaleMatrix(scalex, scaley, scalez);
    currentModelViewMatrix = multiplyMatrix(currentModelViewMatrix, tmp);

    glUniformMatrix4fv(shaderModelViewMatrix, 1, GL_FALSE, currentModelViewMatrix.m);
    glUniformMatrix3fv(shaderNormalMatrix, 1, GL_FALSE, transposedInverseMatrix9(currentModelViewMatrix).m);
#endif
}
GLC_Matrix4x4 GLC_PullManipulator::doManipulate(const GLC_Point3d& newPoint, const GLC_Vector3d& projectionDirection)
{
	// Project the given point on the sliding plane with the given direction
	GLC_Point3d projectedPoint;
	GLC_Line3d projectionLine(newPoint, projectionDirection);
	glc::lineIntersectPlane(projectionLine, GLC_AbstractManipulator::m_SliddingPlane, &projectedPoint);

	// Project the point on the pulling direction
	projectedPoint= glc::project(projectedPoint, GLC_Line3d(GLC_AbstractManipulator::previousPosition(), m_PullDirection));

	// Compute the translation matrix
	GLC_Matrix4x4 translationMatrix(projectedPoint - GLC_AbstractManipulator::m_PreviousPosition);

	// Update previous position to this position
	GLC_AbstractManipulator::m_PreviousPosition= projectedPoint;
	return translationMatrix;
}
Beispiel #13
0
static void fpsCameraViewMatrix(GLFWwindow *window, float *view)
{
	// initial camera config
	static float position[] = { 0.0f, 0.3f, 1.5f };
	static float rotation[] = { 0.0f, 0.0f };

	// mouse look
	static double lastMouse[] = { 0.0, 0.0 };
	double mouse[2];
	glfwGetCursorPos(window, &mouse[0], &mouse[1]);
	if (glfwGetMouseButton(window, GLFW_MOUSE_BUTTON_LEFT) == GLFW_PRESS)
	{
		rotation[0] += (float)(mouse[1] - lastMouse[1]) * -0.2f;
		rotation[1] += (float)(mouse[0] - lastMouse[0]) * -0.2f;
	}
	lastMouse[0] = mouse[0];
	lastMouse[1] = mouse[1];

	float rotationY[16], rotationX[16], rotationYX[16];
	rotationMatrix(rotationX, rotation[0], 1.0f, 0.0f, 0.0f);
	rotationMatrix(rotationY, rotation[1], 0.0f, 1.0f, 0.0f);
	multiplyMatrices(rotationYX, rotationY, rotationX);

	// keyboard movement (WSADEQ)
	float speed = (glfwGetKey(window, GLFW_KEY_LEFT_SHIFT) == GLFW_PRESS) ? 0.1f : 0.01f;
	float movement[3] = {0};
	if (glfwGetKey(window, GLFW_KEY_W) == GLFW_PRESS) movement[2] -= speed;
	if (glfwGetKey(window, GLFW_KEY_S) == GLFW_PRESS) movement[2] += speed;
	if (glfwGetKey(window, GLFW_KEY_A) == GLFW_PRESS) movement[0] -= speed;
	if (glfwGetKey(window, GLFW_KEY_D) == GLFW_PRESS) movement[0] += speed;
	if (glfwGetKey(window, GLFW_KEY_E) == GLFW_PRESS) movement[1] -= speed;
	if (glfwGetKey(window, GLFW_KEY_Q) == GLFW_PRESS) movement[1] += speed;

	float worldMovement[3];
	transformPosition(worldMovement, rotationYX, movement);
	position[0] += worldMovement[0];
	position[1] += worldMovement[1];
	position[2] += worldMovement[2];

	// construct view matrix
	float inverseRotation[16], inverseTranslation[16];
	transposeMatrix(inverseRotation, rotationYX);
	translationMatrix(inverseTranslation, -position[0], -position[1], -position[2]);
	multiplyMatrices(view, inverseRotation, inverseTranslation); // = inverse(translation(position) * rotationYX);
}
Beispiel #14
0
        void RotateHandle::render(Model::RotateHandleHit* hit, Renderer::Vbo& vbo, Renderer::RenderContext& renderContext, float angle) {
            Preferences::PreferenceManager& prefs = Preferences::PreferenceManager::preferences();
            const float distance = renderContext.camera().distanceTo(position());
            const float factor = prefs.getFloat(Preferences::HandleScalingFactor) * distance;

            const Mat4f matrix = translationMatrix(position()) * scalingMatrix(factor);
            Renderer::ApplyModelMatrix applyTranslation(renderContext.transformation(), matrix);

            glDisable(GL_DEPTH_TEST);
            glDisable(GL_CULL_FACE);
            glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);

            Renderer::SetVboState activateVbo(vbo, Renderer::Vbo::VboActive);
            if (hit != NULL) {
                renderAxis(hit, vbo, renderContext);
                renderRing(hit, vbo, renderContext, angle);
            } else {
                Vec3f xAxis, yAxis, zAxis;
                axes(renderContext.camera().position(), xAxis, yAxis, zAxis);

                Renderer::ActivateShader coloredShader(renderContext.shaderManager(), Renderer::Shaders::ColoredHandleShader);

                Renderer::AxisFigure axisFigure(m_axisLength);
                axisFigure.setAxes(true, true, true);
                axisFigure.setXColor(prefs.getColor(Preferences::XColor));
                axisFigure.setYColor(prefs.getColor(Preferences::YColor));
                axisFigure.setZColor(prefs.getColor(Preferences::ZColor));
                axisFigure.render(vbo, renderContext);

                Renderer::ActivateShader shader(renderContext.shaderManager(), Renderer::Shaders::HandleShader);
                shader.setUniformVariable("Color", Color(1.0f, 1.0f, 1.0f, 0.25f));

                Renderer::RingFigure(Axis::AX, yAxis, zAxis, m_ringRadius, m_ringThickness, 8).render(vbo, renderContext);
                Renderer::RingFigure(Axis::AY, xAxis, zAxis, m_ringRadius, m_ringThickness, 8).render(vbo, renderContext);
                Renderer::RingFigure(Axis::AZ, xAxis, yAxis, m_ringRadius, m_ringThickness, 8).render(vbo, renderContext);
            }

            glEnable(GL_CULL_FACE);
            glEnable(GL_DEPTH_TEST);
        }
Beispiel #15
0
        bool Brush::canMoveBoundary(const Face& face, const Vec3f& delta) const {

            const Mat4f pointTransform = translationMatrix(delta);
            BrushGeometry testGeometry(m_worldBounds);

            Face testFace(face);
            testFace.transform(pointTransform, Mat4f::Identity, false, false);

            FaceSet droppedFaces;
            FaceList::const_iterator it, end;
            for (it = m_faces.begin(), end = m_faces.end(); it != end; ++it) {
                Face* otherFace = *it;
                if (otherFace != &face)
                    testGeometry.addFace(*otherFace, droppedFaces);
            }

            BrushGeometry::CutResult result = testGeometry.addFace(testFace, droppedFaces);
            bool inWorldBounds = m_worldBounds.contains(testGeometry.bounds);

            m_geometry->restoreFaceSides();

            return inWorldBounds && result == BrushGeometry::Split && droppedFaces.empty();
        }
 void EntityModelRenderer::render(ShaderProgram& shaderProgram, Transformation& transformation, const Vec3f& position, const Quatf& rotation) {
     const Mat4f matrix = translationMatrix(position) * rotationMatrix(rotation);
     ApplyModelMatrix applyMatrix(transformation, matrix);
     render(shaderProgram);
 }
Beispiel #17
0
std::set<const Model*> UniformGrid::getModels(const Ray& ray) const {
  std::set<const Model*> models;

  Point3D nextT(0, 0, 0);

  // The point *within* the grid where the ray first intersected it
  Point3D rayStartPoint(0, 0, 0);

  if (!inGrid(ray.start)) {
    const auto& sp = startPoint;
    // Not in the grid: We will use a cube the sz of whole grid to find
    // the point of entry into the grid
    auto gridCubeInverse = (translationMatrix(sp[0], sp[0], sp[0]) *
                           gridSizeScaleMatrix).invert();
    HitRecord hr;
    if (!utilityCube.intersects(ray, &hr, gridCubeInverse)) {
      // Does not intersect the grid even
      return models;
    }
    nextT[0] = hr.t;
    nextT[1] = hr.t;
    nextT[2] = hr.t;
    rayStartPoint = ray.at(hr.t);
  }
  else {
    rayStartPoint = ray.start;
  }

  // Place in the grid we are currently stepping through
  CellCoord gridCoord = coordAt(rayStartPoint);

  Vector3D dir(
      std::abs(ray.dir[0]), std::abs(ray.dir[1]), std::abs(ray.dir[2]));

  // These values are in units of t: how far we must go to travel a whole cell
  Vector3D dt(
    isZero(dir[0]) ? 0 : cellSize / dir[0],
    isZero(dir[1]) ? 0 : cellSize / dir[1],
    isZero(dir[2]) ? 0 : cellSize / dir[2]
  );
  {
    // The bottom left corner of the cell we are starting in
    Point3D gsp = pointAt(gridCoord); // "Grid start point"

    // Determine how far, in units of t, we have to go in any direction
    // to reach the next cell
    // If we are going "forwards" in a coordinate then we need to travel to
    // gsp + cellSize. If we are going "backwards" in a coordinate then we need
    // to travel to only gsp.
    for (int i = 0; i < 3; ++i) {
      if (isZero(dir[i])) {
        nextT[i] = -1;
        continue;
      }
      if (ray.dir[i] < 0) {
        nextT[i] += (rayStartPoint[i] - gsp[i]) / dir[i];
      }
      else {
        nextT[i] += (gsp[i] + cellSize - rayStartPoint[i]) / dir[i];
      }
    }
  }

  // Which direction in the grid to move when we hit a "next" value
  CellCoord incs(
    (ray.dir[0] > 0) ? 1 : -1,
    (ray.dir[1] > 0) ? 1 : -1,
    (ray.dir[2] > 0) ? 1 : -1
  );

  // Check if a coord is still valid
  auto coordOk = [&] (int coord) -> bool {
    return 0 <= coord && coord < sideLength;
  };
  auto smaller = [] (double a, double b) -> bool {
    return (b < 0) || a <= b;
  };

  while (coordOk(gridCoord.x) && coordOk(gridCoord.y) && coordOk(gridCoord.z)) {
    for (const Model* model : cells[indexFor(gridCoord)].models) {
      models.insert(model);
    }

    for (int i = 0; i < 3; ++i) {
      if (nextT[i] < 0) continue;
      const auto a = nextT[(i + 1) % 3];
      const auto b = nextT[(i + 2) % 3];
      if (smaller(nextT[i], a) && smaller(nextT[i], b)) {
        nextT[i] += dt[i];
        gridCoord[i] += incs[i];
        break;
      }
    }
  }

  return models;
}
Beispiel #18
0
bool UniformGrid::intersectsCell(const Model& model, const CellCoord& coord) {
  // Left side
  // Bottom left point
  Point3D p0 = pointAt(coord);
  Point3D p1(p0[0], p0[1] + cellSize, p0[2]);
  Point3D p2(p0[0], p0[1] + cellSize, p0[2] + cellSize);
  Point3D p3(p0[0], p0[1], p0[2] + cellSize);

  // Right side
  Point3D p4(p0[0] + cellSize, p0[1], p0[2]);
  Point3D p5(p0[0] + cellSize, p0[1] + cellSize, p0[2]);
  Point3D p6(p0[0] + cellSize, p0[1] + cellSize, p0[2] + cellSize);
  Point3D p7(p0[0] + cellSize, p0[1], p0[2] + cellSize);

  const std::vector<Point3D> pts = {p0, p1, p2, p3, p4, p5, p6, p7};

  auto cellMat = translationMatrix(p0[0], p0[1], p0[2]) * cellSizeScaleMatrix;
  // But we need the inverse of course
  cellMat = cellMat.invert();

  // Check if a pt is in the cell
  auto inCell = [&] (const Point3D& pt) -> bool {
    return p0[0] <= pt[0] && pt[0] <= (p0[0] + cellSize) &&
           p0[1] <= pt[1] && pt[1] <= (p0[1] + cellSize) &&
           p0[2] <= pt[2] && pt[2] <= (p0[2] + cellSize);
  };

  // First, we need to get the 8 points of the bounding box
  auto bbox = model.getBoundingBox();

  auto inBoundingBox = [&bbox] (const Point3D& pt) -> bool {
    // We are in the box if we are in between all the opposite parallel planes
    const auto c1 = bbox[0]; // Bottom back left corner
    const auto v1a = bbox[1] - c1; // Bottom back left to bottom back right
    const auto v1b = bbox[3] - c1; // Bottom back left to top back left
    const auto v1c = bbox[4] - c1; // Bottom back left to bottom front left
    const auto n1 = v1a.cross(v1b); // Back face
    const auto n2 = v1b.cross(v1c); // Left face
    const auto n3 = v1c.cross(v1a); // Bottom face

    const auto c2 = bbox[6]; // Top front right corner
    const auto v2a = bbox[5] - c2; // Top front right to bottom front right
    const auto v2b = bbox[7] - c2; // Top front right to top front left
    const auto v2c = bbox[2] - c2; // Top front right to top back right
    // We want this to be opposite sign (i.e. not pointing inwards)
    // so we do the opposite cross as above
    const auto n4 = v2b.cross(v2a); // Front face
    const auto n5 = v2c.cross(v2b); // Top face
    const auto n6 = v2a.cross(v2c); // Right face

    return betweenPlanes(n1, c1, n4, c2, pt) &&
           betweenPlanes(n2, c1, n6, c2, pt) &&
           betweenPlanes(n3, c1, n5, c2, pt);
  };

  // A corner of the bbox being inside the cell implies an intersection
  // between the bbox and the cell.
  for (const auto& pt : bbox) {
    if (inCell(pt)) {
      return true;
    }
  }

  // Similarly, a corner of cell inside bbox implies intersection
  for (const auto& pt : pts) {
    if (inBoundingBox(pt)) {
      return true;
    }
  }

  // Check if any of the 12 lines from bbox intersect this cell
  HitRecord hr;
  for (size_t i = 0; i < 8; ++i) {
    // This is the vector of one edge
    Vector3D v = bbox[(i % 4 == 0) ? i + 3 : i - 1] - bbox[i];
    Ray ray(bbox[i] - v, bbox[i]);
    if (utilityCube.intersects(ray, &hr, cellMat) && 1 <= hr.t && hr.t <= 2) {
      // This edge of the bounding box intersects our cell cube.
      return true;
    }
  }
  for (size_t i = 0; i < 4; ++i) {
    Vector3D v = bbox[i + 4] - bbox[i];
    Ray ray(bbox[i] - v, bbox[i]);
    if (utilityCube.intersects(ray, &hr, cellMat) && 1 <= hr.t && hr.t <= 2) {
      // This edge of the bounding box intersects our cell cube.
      return true;
    }
  }

  // Now check if any of the 12 lines from this cell intersect the model
  for (size_t i = 0; i < pts.size(); ++i) {
    Vector3D v = pts[(i % 4 == 0) ? i + 3 : i - 1] - pts[i];
    // Note: We are doing pts[i] - v and checking for t between 1 and 2.
    // This is equivalent to checking between 0 and 1 without doing the
    // subtraction, *but* we have an epsilon check in the intersects code.
    // For this case, we do *not* want to bother with epsilon check, so we
    // will check from 1 to 2 to avoid it.
    if (model.intersects(Ray(pts[i] - v, pts[i]), &hr)) {
      if (1 <= hr.t && hr.t <= 2) {
        return true;
      }
    }
  }

  // Now we have to check the struts between the two sides
  for (size_t i = 0; i < 4; ++i) {
    Vector3D v = pts[i + 4] - pts[i];
    if (model.intersects(Ray(pts[i] - v, pts[i]), &hr)) {
      if (1 <= hr.t && hr.t <= 2) {
        return true;
      }
    }
  }

  return false;
}
void ScreenSpaceImage::render() {
    draw(rotationMatrix() * translationMatrix() * scaleMatrix());
}
Beispiel #20
0
 /*!
  \param x Value of x translation
  \param y Value of y translation
  \param z Value of z translation
  */
 Matrix4& translate(T const & x, T const & y, T const & z=0) {
     Matrix4 tmp = translationMatrix(x, y, z);
     tmp *= *this;
     *this = tmp;
     return (*this);
 }
Beispiel #21
0
void SceneNode::translate(const Vector3D& amount)
{
  Matrix4x4 t = translationMatrix(amount);
  m_trans = m_trans * t;
  m_invtrans = t.invert() * m_invtrans;
}
void AtmosphereSample::Update(double CurrTime, double ElapsedTime)
{
    SampleBase::Update(CurrTime, ElapsedTime);

    m_fElapsedTime = static_cast<float>(ElapsedTime);

    const auto& SCDesc = m_pSwapChain->GetDesc();
    // Set world/view/proj matrices and global shader constants
    float aspectRatio = (float)SCDesc.Width / SCDesc.Height;

    float3 CamZ = normalize( m_f3CameraDir );
    float3 CamX = normalize( cross( float3( 0, 1, 0 ), CamZ ) );
    float3 CamY = normalize( cross( CamZ, CamX ) );

    m_mCameraView =
        translationMatrix( -m_f3CameraPos ) *
        ViewMatrixFromBasis( CamX, CamY, CamZ );


    // This projection matrix is only used to set up directions in view frustum
    // Actual near and far planes are ignored
    float FOV = (float)M_PI/4.f;
    float4x4 mTmpProj = Projection(FOV, aspectRatio, 50.f, 500000.f, m_bIsDXDevice);

    float fEarthRadius = AirScatteringAttribs().fEarthRadius;
    float3 EarthCenter(0, -fEarthRadius, 0);
    float fNearPlaneZ, fFarPlaneZ;
    ComputeApproximateNearFarPlaneDist(m_f3CameraPos,
                                       m_mCameraView,
                                       mTmpProj,
                                       EarthCenter,
                                       fEarthRadius,
                                       fEarthRadius + m_fMinElevation,
                                       fEarthRadius + m_fMaxElevation,
                                       fNearPlaneZ,
                                       fFarPlaneZ);
    fNearPlaneZ = std::max(fNearPlaneZ, 50.f);
    fFarPlaneZ  = std::max(fFarPlaneZ, fNearPlaneZ+100.f);
    fFarPlaneZ  = std::max(fFarPlaneZ, 1000.f);

    m_mCameraProj = Projection(FOV, aspectRatio, fNearPlaneZ, fFarPlaneZ, m_bIsDXDevice);

#if 0
    if( m_bAnimateSun )
    {
        auto &LightOrientationMatrix = *m_pDirLightOrienationCamera->GetParentMatrix();
        float3 RotationAxis( 0.5f, 0.3f, 0.0f );
        float3 LightDir = m_pDirLightOrienationCamera->GetLook() * -1;
        float fRotationScaler = ( LightDir.y > +0.2f ) ? 50.f : 1.f;
        float4x4 RotationMatrix = float4x4RotationAxis(RotationAxis, 0.02f * (float)deltaSeconds * fRotationScaler);
        LightOrientationMatrix = LightOrientationMatrix * RotationMatrix;
        m_pDirLightOrienationCamera->SetParentMatrix(LightOrientationMatrix);
    }

    float dt = (float)ElapsedTime;
    if (m_Animate && dt > 0 && dt < 0.2f)
    {
        float3 axis;
        float angle = 0;
        AxisAngleFromRotation(axis, angle, m_SpongeRotation);
        if (length(axis) < 1.0e-6f) 
            axis[1] = 1;
        angle += m_AnimationSpeed * dt;
        if (angle >= 2.0f*FLOAT_PI)
            angle -= 2.0f*FLOAT_PI;
        else if (angle <= 0)
            angle += 2.0f*FLOAT_PI;
        m_SpongeRotation = RotationFromAxisAngle(axis, angle);
    }
#endif
    UpdateGUI();
}
void AtmosphereSample::RenderShadowMap(IDeviceContext *pContext,
                                        LightAttribs &LightAttribs, 
                                        const float4x4 &mCameraView, 
                                        const float4x4 &mCameraProj )
{
    ShadowMapAttribs& ShadowMapAttribs = LightAttribs.ShadowAttribs;

    float3 v3DirOnLight = (float3&)LightAttribs.f4DirOnLight;
    float3 v3LightDirection = -v3DirOnLight;

    // Declare working vectors
    float3 vLightSpaceX, vLightSpaceY, vLightSpaceZ;

    // Compute an inverse vector for the direction on the sun
    vLightSpaceZ = v3LightDirection;
    // And a vector for X light space
    vLightSpaceX = float3( 1.0f, 0.0, 0.0 );
    // Compute the cross products
    vLightSpaceY = cross(vLightSpaceX, vLightSpaceZ);
    vLightSpaceX = cross(vLightSpaceZ, vLightSpaceY);
    // And then normalize them
    vLightSpaceX = normalize( vLightSpaceX );
    vLightSpaceY = normalize( vLightSpaceY );
    vLightSpaceZ = normalize( vLightSpaceZ );

    // Declare a world to light space transformation matrix
    // Initialize to an identity matrix
    float4x4 WorldToLightViewSpaceMatr =
        ViewMatrixFromBasis( vLightSpaceX, vLightSpaceY, vLightSpaceZ );

    ShadowMapAttribs.mWorldToLightViewT = transposeMatrix( WorldToLightViewSpaceMatr );

    float3 f3CameraPosInLightSpace = m_f3CameraPos * WorldToLightViewSpaceMatr;

    float fMainCamNearPlane, fMainCamFarPlane;
    GetNearFarPlaneFromProjMatrix( mCameraProj, fMainCamNearPlane, fMainCamFarPlane, m_bIsDXDevice);

    for(int i=0; i < MAX_CASCADES; ++i)
        ShadowMapAttribs.fCascadeCamSpaceZEnd[i] = +FLT_MAX;

    // Render cascades
    for(int iCascade = 0; iCascade < m_TerrainRenderParams.m_iNumShadowCascades; ++iCascade)
    {
        auto &CurrCascade = ShadowMapAttribs.Cascades[iCascade];
        float4x4 CascadeFrustumProjMatrix;
        float &fCascadeFarZ = ShadowMapAttribs.fCascadeCamSpaceZEnd[iCascade];
        float fCascadeNearZ = (iCascade == 0) ? fMainCamNearPlane : ShadowMapAttribs.fCascadeCamSpaceZEnd[iCascade-1];
        fCascadeFarZ = fMainCamFarPlane;

        if (iCascade < m_TerrainRenderParams.m_iNumShadowCascades-1) 
        {
            float ratio = fMainCamFarPlane / fMainCamNearPlane;
            float power = (float)(iCascade+1) / (float)m_TerrainRenderParams.m_iNumShadowCascades;
            float logZ = fMainCamNearPlane * pow(ratio, power);
        
            float range = fMainCamFarPlane - fMainCamNearPlane;
            float uniformZ = fMainCamNearPlane + range * power;

            fCascadeFarZ = m_fCascadePartitioningFactor * (logZ - uniformZ) + uniformZ;
        }

        float fMaxLightShaftsDist = 3e+5f;
        // Ray marching always starts at the camera position, not at the near plane.
        // So we must make sure that the first cascade used for ray marching covers the camera position
        CurrCascade.f4StartEndZ.x = (iCascade == m_PPAttribs.m_iFirstCascade) ? 0 : std::min(fCascadeNearZ, fMaxLightShaftsDist);
        CurrCascade.f4StartEndZ.y = std::min(fCascadeFarZ, fMaxLightShaftsDist);
        CascadeFrustumProjMatrix = mCameraProj;
        SetNearFarClipPlanes( CascadeFrustumProjMatrix, fCascadeNearZ, fCascadeFarZ, m_bIsDXDevice );

        float4x4 CascadeFrustumViewProjMatr = mCameraView * CascadeFrustumProjMatrix;
        float4x4 CascadeFrustumProjSpaceToWorldSpace = inverseMatrix(CascadeFrustumViewProjMatr);
        float4x4 CascadeFrustumProjSpaceToLightSpace = CascadeFrustumProjSpaceToWorldSpace * WorldToLightViewSpaceMatr;

        // Set reference minimums and maximums for each coordinate
        float3 f3MinXYZ(f3CameraPosInLightSpace), f3MaxXYZ(f3CameraPosInLightSpace);
        
        // First cascade used for ray marching must contain camera within it
        if( iCascade != m_PPAttribs.m_iFirstCascade )
        {
            f3MinXYZ = float3(+FLT_MAX, +FLT_MAX, +FLT_MAX);
            f3MaxXYZ = float3(-FLT_MAX, -FLT_MAX, -FLT_MAX);
        }

        for(int iClipPlaneCorner=0; iClipPlaneCorner < 8; ++iClipPlaneCorner)
        {
            float3 f3PlaneCornerProjSpace( (iClipPlaneCorner & 0x01) ? +1.f : - 1.f, 
                                           (iClipPlaneCorner & 0x02) ? +1.f : - 1.f,
                                            // Since we use complimentary depth buffering, 
                                            // far plane has depth 0
                                           (iClipPlaneCorner & 0x04) ? 1.f : (m_bIsDXDevice ? 0.f : -1.f));
            float3 f3PlaneCornerLightSpace = f3PlaneCornerProjSpace * CascadeFrustumProjSpaceToLightSpace;
            f3MinXYZ = min(f3MinXYZ, f3PlaneCornerLightSpace);
            f3MaxXYZ = max(f3MaxXYZ, f3PlaneCornerLightSpace);
        }

        // It is necessary to ensure that shadow-casting patches, which are not visible 
        // in the frustum, are still rendered into the shadow map
        f3MinXYZ.z -= AirScatteringAttribs().fEarthRadius * sqrt(2.f);
        
        // Align cascade extent to the closest power of two
        float fShadowMapDim = (float)m_uiShadowMapResolution;
        float fCascadeXExt = (f3MaxXYZ.x - f3MinXYZ.x) * (1 + 1.f/fShadowMapDim);
        float fCascadeYExt = (f3MaxXYZ.y - f3MinXYZ.y) * (1 + 1.f/fShadowMapDim);
        const float fExtStep = 2.f;
        fCascadeXExt = pow( fExtStep, ceil( log(fCascadeXExt)/log(fExtStep) ) );
        fCascadeYExt = pow( fExtStep, ceil( log(fCascadeYExt)/log(fExtStep) ) );
        // Align cascade center with the shadow map texels to alleviate temporal aliasing
        float fCascadeXCenter = (f3MaxXYZ.x + f3MinXYZ.x)/2.f;
        float fCascadeYCenter = (f3MaxXYZ.y + f3MinXYZ.y)/2.f;
        float fTexelXSize = fCascadeXExt / fShadowMapDim;
        float fTexelYSize = fCascadeXExt / fShadowMapDim;
        fCascadeXCenter = floor(fCascadeXCenter/fTexelXSize) * fTexelXSize;
        fCascadeYCenter = floor(fCascadeYCenter/fTexelYSize) * fTexelYSize;
        // Compute new cascade min/max xy coords
        f3MaxXYZ.x = fCascadeXCenter + fCascadeXExt/2.f;
        f3MinXYZ.x = fCascadeXCenter - fCascadeXExt/2.f;
        f3MaxXYZ.y = fCascadeYCenter + fCascadeYExt/2.f;
        f3MinXYZ.y = fCascadeYCenter - fCascadeYExt/2.f;

        CurrCascade.f4LightSpaceScale.x =  2.f / (f3MaxXYZ.x - f3MinXYZ.x);
        CurrCascade.f4LightSpaceScale.y =  2.f / (f3MaxXYZ.y - f3MinXYZ.y);
        CurrCascade.f4LightSpaceScale.z =  
                    (m_bIsDXDevice ? 1.f : 2.f) / (f3MaxXYZ.z - f3MinXYZ.z);
        // Apply bias to shift the extent to [-1,1]x[-1,1]x[0,1] for DX or to [-1,1]x[-1,1]x[-1,1] for GL
        // Find bias such that f3MinXYZ -> (-1,-1,0) for DX or (-1,-1,-1) for GL
        CurrCascade.f4LightSpaceScaledBias.x = -f3MinXYZ.x * CurrCascade.f4LightSpaceScale.x - 1.f;
        CurrCascade.f4LightSpaceScaledBias.y = -f3MinXYZ.y * CurrCascade.f4LightSpaceScale.y - 1.f;
        CurrCascade.f4LightSpaceScaledBias.z = -f3MinXYZ.z * CurrCascade.f4LightSpaceScale.z + (m_bIsDXDevice ? 0.f : -1.f);

        float4x4 ScaleMatrix = scaleMatrix( CurrCascade.f4LightSpaceScale.x, CurrCascade.f4LightSpaceScale.y, CurrCascade.f4LightSpaceScale.z );
        float4x4 ScaledBiasMatrix = translationMatrix( CurrCascade.f4LightSpaceScaledBias.x, CurrCascade.f4LightSpaceScaledBias.y, CurrCascade.f4LightSpaceScaledBias.z ) ;

        // Note: bias is applied after scaling!
        float4x4 CascadeProjMatr = ScaleMatrix * ScaledBiasMatrix;
        //D3DXMatrixOrthoOffCenterLH( &m_LightOrthoMatrix, MinX, MaxX, MinY, MaxY, MaxZ, MinZ);

        // Adjust the world to light space transformation matrix
        float4x4 WorldToLightProjSpaceMatr = WorldToLightViewSpaceMatr * CascadeProjMatr;
        float4x4 ProjToUVScale, ProjToUVBias;
        if( m_bIsDXDevice )
        {
            ProjToUVScale = scaleMatrix( 0.5f, -0.5f, 1.f );
            ProjToUVBias = translationMatrix( 0.5f, 0.5f, 0.f );
        }
        else
        {
            ProjToUVScale = scaleMatrix( 0.5f, 0.5f, 0.5f );
            ProjToUVBias = translationMatrix( 0.5f, 0.5f, 0.5f );
        }

        float4x4 WorldToShadowMapUVDepthMatr = WorldToLightProjSpaceMatr * ProjToUVScale * ProjToUVBias;
        ShadowMapAttribs.mWorldToShadowMapUVDepthT[iCascade] = transposeMatrix( WorldToShadowMapUVDepthMatr );

        m_pImmediateContext->SetRenderTargets( 0, nullptr, m_pShadowMapDSVs[iCascade] );
        m_pImmediateContext->ClearDepthStencil( m_pShadowMapDSVs[iCascade], CLEAR_DEPTH_FLAG, 1.f );

        // Render terrain to shadow map
        {
            MapHelper<CameraAttribs> CamAttribs( m_pImmediateContext, m_pcbCameraAttribs, MAP_WRITE, MAP_FLAG_DISCARD );
            CamAttribs->mViewProjT = transposeMatrix( WorldToLightProjSpaceMatr );
        }

        m_EarthHemisphere.Render(m_pImmediateContext, m_TerrainRenderParams, m_f3CameraPos, WorldToLightProjSpaceMatr, nullptr, nullptr, nullptr, true);
    }

    pContext->SetRenderTargets( 0, nullptr, nullptr );
}
Beispiel #24
0
void App::update(float delta_time) {
	if (anim_play) frame_count++;

	if (!hide_gui) gui();

	// autoreload frag shader (every 60 frames)
	if (shader_filepath && shader_file_autoreload && (frame_count % 60) == 0) {
		struct stat attr;
		if (!stat(shader_filepath, &attr)) { // file exists
			if (attr.st_mtime > shader_file_mtime) { // file has been modified
				shader_file_mtime = (int)attr.st_mtime;
				reloadShader();
			}
		}
	}

	// update camera (-z: forward, y: up)
	camera_euler_angles += 2.0f*delta_time
		* v3(-movement_command.rotate.x, -movement_command.rotate.y, 0.0f);
	camera_euler_angles.x = fminf(fmaxf(-0.5f*(float)M_PI, camera_euler_angles.x), 0.5f*(float)M_PI); // clamp
	mat3 rot_x = rotationMatrix(v3(1.0f, 0.0f, 0.0f), camera_euler_angles.x);
	mat3 rot_y = rotationMatrix(v3(0.0f, 1.0f, 0.0f), camera_euler_angles.y);
	mat3 rot_z = rotationMatrix(v3(0.0f, 0.0f, 1.0f), camera_euler_angles.z);
	mat3 rot = rot_y * rot_x * rot_z;
	camera_location += rot * (8.0f*delta_time*movement_command.move);
	mat4 view_to_world = translationMatrix(camera_location) * m4(rot);
	mat4 world_to_view = m4(transpose(rot)) * translationMatrix(-camera_location);

	// bind textures
	for (int tsi = 0; tsi < (int)ARRAY_COUNT(texture_slots); tsi++) {
		glActiveTexture(GL_TEXTURE0+tsi);
		glBindTexture(texture_slots[tsi].target, texture_slots[tsi].texture);
	}

	// draw fullscreen triangle(s)
	glClearColor(0.2f, 0.21f, 0.22f, 1.0f);
	glClear(GL_COLOR_BUFFER_BIT);
	{ BindShader bind_shader(shader);
		if (!compile_error_log) {
			for (int i = 0; i < uniform_count; i++) {
				uniforms[i].apply();
			}
		}

		// apply builtin uniforms
		u_time = (float)frame_count / 60.0f;
		glUniform1f(shader.getUniformLocation(u_time_name), u_time);
		vec2 u_resolution = v2(video.pixel_scale*video.width, video.pixel_scale*video.height);
		glUniform2fv(shader.getUniformLocation(u_resolution_name), 1, u_resolution.e);
		glUniformMatrix4fv(shader.getUniformLocation(u_view_to_world_name), 1, GL_FALSE, view_to_world.e);
		glUniformMatrix4fv(shader.getUniformLocation(u_world_to_view_name), 1, GL_FALSE, world_to_view.e);

		if (single_triangle_mode) {
			{ BindArrayBuffer bind_array_buffer(single_triangle_vbo);
				glEnableVertexAttribArray(VAT_POSITION);
				glVertexAttribPointer(VAT_POSITION, 2, GL_FLOAT, GL_FALSE, 0, (GLvoid*)0);
				glDrawArrays(GL_TRIANGLES, 0, 3);
				glDisableVertexAttribArray(VAT_POSITION);
			}
		} else {
			{ BindArrayBuffer bind_array_buffer(two_triangles_vbo);
				glEnableVertexAttribArray(VAT_POSITION);
				glVertexAttribPointer(VAT_POSITION, 2, GL_FLOAT, GL_FALSE, 0, (GLvoid*)0);
				glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
				glDisableVertexAttribArray(VAT_POSITION);
			}
		}
	}
}