/************************************************************************************ * Copyright (C) 2008 by Politehnica University of Bucharest and Rutgers University * All rights reserved. * Refer to LICENSE for terms and conditions of use. ***********************************************************************************/ package vnsim.gui; import java.awt.geom.Point2D; import javax.media.opengl.GL; import javax.media.opengl.GLAutoDrawable; import javax.media.opengl.GLCanvas; import javax.media.opengl.GLCapabilities; import javax.media.opengl.GLEventListener; import javax.media.opengl.glu.GLU; import javax.swing.JPanel; import com.sun.opengl.util.Animator; import com.sun.opengl.util.GLUT; import vnsim.applications.trafficview.SimulatedCarInfo; import vnsim.core.CarInfo; import vnsim.map.object.Cross; import vnsim.map.object.Globals; import vnsim.map.object.Point; import vnsim.map.object.Road; import vnsim.map.utils.GPSutil; import vnsim.vehicular.simulator.intersections.DirectedRoadSegment; import vnsim.vehicular.simulator.intersections.IntersectionWithTrafficLights; public class DriverView extends JPanel implements GLEventListener { /* * NEAR VIEW Panel that contains an OpenGL canvas */ private GLCanvas canvas; private int carList, carListOut, earthList; // display // lists(only // calculated at // compilation time) private float xCamera, yCamera, zCamera, xToSee, yToSee, distanceToLook, visualField; // camera private float previosPosX, previosPosY;// old position of the // carReceivingMsg and public SimulatedCarInfo currentCar; static final long serialVersionUID = 1; /** * * @param w * @param h */ public DriverView(int w, int h) { super(); // creates an OpenGL canvas and sets it's properties GLCapabilities capabilities = new GLCapabilities(); capabilities.setHardwareAccelerated(true); capabilities.setDoubleBuffered(true); canvas = new GLCanvas(); canvas.addGLEventListener(this); canvas.setSize(w, h); canvas.setVisible(true); Animator anim = new Animator(canvas); // for animating the display this.add(canvas); // adds the canvas to the container this.setSize(w, h); anim.start(); this.previosPosX = 0; // to remember the carReceivingMsg's previous // position this.previosPosY = 0; // helps determining the direction in witch the // carReceivingMsg moves } /** * */ public void init(GLAutoDrawable glDrawable) { this.xCamera = 0.0f; // set the initial position // of the camera this.yCamera = 0.0f; this.zCamera = 20.0f; this.xToSee = 10.0f; this.yToSee = 10.0f; this.visualField = 2000.0f; this.distanceToLook = 50.0f; GL myGL = glDrawable.getGL(); // OpenGL initialization GLU myGLU = new GLU(); int width = canvas.getWidth(); int height = canvas.getHeight(); myGL.glClearColor(0.7f, 0.7f, 1.0f, 0.0f); // the ambiental color myGL.glShadeModel(GL.GL_FASTEST); myGL.glMatrixMode(GL.GL_PROJECTION); myGL.glLoadIdentity(); myGLU.gluPerspective(60.0f, (double) width / height, 0.01f, visualField); myGL.glMatrixMode(GL.GL_MODELVIEW); myGL.glLoadIdentity(); myGLU.gluLookAt(xCamera, yCamera, zCamera, xToSee, yToSee, 0.0, 0.0, 0.0, 1.0); glDrawable.setAutoSwapBufferMode(false); // i will call // swapBuffers // manualy in // display bildList(glDrawable); } /** * */ public void display(GLAutoDrawable glDrawable) { float x, y; Road currentRoad; Point currentPoint; short pt; int i; GL myGL = glDrawable.getGL(); glDrawable.swapBuffers(); myGL.glClear(GL.GL_COLOR_BUFFER_BIT); currentRoad = null; currentPoint = null; float auxx, auxy, x2, y2, sinAlfa, cosAlfa, dx, dy; pt = 0; // if i began to receive data from the gps if (Globals.demo.mv.currentCar != null) { try { // I get the current position of the carReceivingMsg on the road currentCar = Globals.demo.mv.currentCar; currentRoad = Globals.map.roads.get(currentCar.getRoadIdx()); currentPoint = (Point) currentRoad.points.get(currentCar.getPointIdx()); // I calculate the distance in meters on x and on y axis // from the point of minimum latitude and longitude y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); // I use the last position and the current position to calculate // where to put the camera and in what // direction to look setCamera(glDrawable, (double) x, (double) y, (double) previosPosX, (double) previosPosY, currentRoad.laneNo, currentCar.getLane(), currentCar.getDirection()); // i draw the grass (green square in the xoy plane, centered on // the current position) myGL.glPushMatrix(); myGL.glTranslatef(x, y, -1.0f); myGL.glCallList(earthList); myGL.glPopMatrix(); /* * i = 0; while (i < currentRoad.crosses.size()) { // for every * road with witch the current road has a // cross, i draw that * road rd2 = (short) ((Cross) currentRoad.crosses .get((int) * i)).getCrossRoadIndex(); drawRoad(rd2, myGL); i++; } */ drawNearbyRoads(currentCar.getRoadIdx(), myGL); // last, i draw // the current // road // i draw the carReceivingMsg on it's current position myGL.glPushMatrix(); myGL.glTranslatef(x, y, 0.0f); myGL.glCallList(carList); myGL.glPopMatrix(); } catch (Exception e) { System.err.println("NearView Error: "); e.printStackTrace(); } // Semaphores Integer idx; IntersectionWithTrafficLights tpI; DirectedRoadSegment drS; int tempPointIdx; int laneNr; int dist = 300; for (i = 0; i < Globals.map.lightsIndices.size(); i++) { idx = Globals.map.lightsIndices.get(i); tpI = (IntersectionWithTrafficLights) Globals.map.allIntersections.get(idx.intValue()); currentRoad = (Road) Globals.map.roads.get(tpI.segments.get(0).roadIndex); currentPoint = currentRoad.points.get(tpI.segments.get(0).pointIndex); y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); currentRoad = (Road) Globals.map.roads.get(Globals.demo.mv.currentCar.getRoadIdx()); currentPoint = (Point) currentRoad.points.get(Globals.demo.mv.currentCar.getPointIdx()); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); dist = (int) Math.sqrt(((x2 - x) * (x2 - x) + (y2 - y) * (y2 - y))); if (dist > 300) { continue; } for (int j = 0; j < tpI.segments.size(); j++) { drS = tpI.segments.get(j); if (drS.isExitOnly()) continue; currentRoad = (Road) Globals.map.roads.get(drS.roadIndex); laneNr = currentRoad.laneNo; if (drS.direction) { tempPointIdx = drS.pointIndex + 4; while (currentRoad.points.size() <= tempPointIdx) { tempPointIdx--; } currentPoint = (Point) currentRoad.points.get(tempPointIdx); } else { tempPointIdx = drS.pointIndex - 4; while (tempPointIdx < 0) { tempPointIdx++; } currentPoint = (Point) currentRoad.points.get(tempPointIdx); } y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); currentPoint = (Point) currentRoad.points.get(drS.pointIndex); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); if ((x2 != x) || (y2 != y)) { sinAlfa = (float) ((y2 - y) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x)))); cosAlfa = (float) ((x2 - x) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x)))); dx = (float) (laneNr * 20 * sinAlfa); dy = (float) (laneNr * 20 * cosAlfa); x2 = dx + x; y2 = y - dy; x = x - dx; y = y + dy; int color; int timp; myGL.glPushMatrix(); timp = (int) (Globals.engine.crtTime / Globals.engine.fps); color = tpI.segments.get(j).getLightInfo().getColor((timp % tpI.cycleLength)); MyColor semaphoreColor = MyColor.chooseSemaphoreColor(color); myGL.glColor3f(semaphoreColor.getRed(), semaphoreColor.getGreen(), semaphoreColor.getBlue()); myGL.glLineWidth(4.0f); myGL.glBegin(GL.GL_LINES); { myGL.glVertex3f(x, y, 3.0f); myGL.glVertex3f(x2, y2, 3.0f); } myGL.glEnd(); myGL.glPopMatrix(); } } } // //endSemaphores // print neighbors currentCar = Globals.demo.mv.currentCar; double offset; int dir; Point p2, p; for (i = 0; i < currentCar.trafficDB.size(); i++) { CarInfo elem = (CarInfo) currentCar.trafficDB.get(i); currentRoad = (Road) Globals.map.roads.get(elem.getRoadIdx()); pt = elem.getPointIdx(); offset = elem.getOffset(); p = (Point) currentRoad.points.get(pt); y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, p); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, p); y2 = y; x2 = x; pt++; dir = (int) elem.getDirection(); try { p2 = (Point) currentRoad.points.get(pt); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, p2); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, p2); if (dir == 0) { auxx = x; auxy = y; x = x2; y = y2; x2 = auxx; y2 = auxy; offset = p2.getDistance() - p.getDistance() - offset; } offset = offset * 1000; laneNr = currentRoad.laneNo; int ln = elem.getLane(); if ((x2 != x) || (y2 != y)) { sinAlfa = (float) ((y2 - y) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x)))); cosAlfa = (float) ((x2 - x) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x)))); x = x + (float) (cosAlfa * offset); y = y + (float) (sinAlfa * offset); dx = (float) (((laneNr + 1 - ln) * 20 - 11) * sinAlfa); dy = (float) (((laneNr + 1 - ln) * 20 - 11) * cosAlfa); x = x + dx; y = y - dy; // System.out.println("Car "+sourceRoadIdx+":"+elem+" // road:"+currentRoad+"; point "+sourcePointIdx+" gets // printed at: // x="+x+"y="+y);sourceRoadIdx++; } } catch (Exception e) { } myGL.glPushMatrix(); myGL.glTranslatef(x, y, 0.0f); myGL.glScalef(2.0f, 2.0f, 2.0f); myGL.glCallList(carList); myGL.glPopMatrix(); } } // end neighbors synchronized (Globals.mutex) { Globals.flag = 0; Globals.mutex.notify(); } } /** * * @param myGL * @param myGLU * @param myGLUT */ private void buildList_Car(GL myGL, GLU myGLU, GLUT myGLUT) { carList = myGL.glGenLists(4); myGL.glNewList(carList, GL.GL_COMPILE); { myGL.glColor3f(0.2f, 0.2f, 1.0f); myGLUT.glutSolidSphere(2.0, 10, 10); } myGL.glEndList(); } /** * The car out is a sphere. * * @param myGL * @param myGLU * @param myGLUT */ private void buildList_CarOut(GL myGL, GLU myGLU, GLUT myGLUT) { carListOut = carList + 1; myGL.glNewList(carListOut, GL.GL_COMPILE); { myGL.glColor3f(0.7f, 0.0f, 0.0f); myGLUT.glutSolidSphere(2.0f, 10, 10); } myGL.glEndList(); } /** * The grass is a green square. * * @param myGL * @param myGLU * @param myGLUT */ private void buildList_Earth(GL myGL, GLU myGLU, GLUT myGLUT) { earthList = carListOut + 1; myGL.glNewList(earthList, GL.GL_COMPILE); { // i build the "grass", a green square myGL.glColor3f(0.0f, 0.4f, 0.0f); myGL.glBegin(GL.GL_QUADS); myGL.glVertex3f(-1000.0f, -1000.0f, 0.0f); myGL.glVertex3f(1000.0f, -1000.0f, 0.0f); myGL.glVertex3f(1000.0f, 1000.0f, 0.0f); myGL.glVertex3f(-1000.0f, 1000.0f, 0.0f); myGL.glEnd(); } myGL.glEndList(); } /** * * @param glDrawable */ private void bildList(GLAutoDrawable glDrawable) { GL myGL = glDrawable.getGL(); GLUT myGLUT = new GLUT(); GLU myGLU = new GLU(); buildList_Car(myGL, myGLU, myGLUT); buildList_CarOut(myGL, myGLU, myGLUT); buildList_Earth(myGL, myGLU, myGLUT); } /** * * @param rd * @param myGL */ void drawNearbyRoads(int rd, GL myGL) { int ii, j; Road mainRoad = Globals.map.roads.get(rd); Road currentRoad; Point currentPoint; short rdIdx; ii = 0; byte[] ri; float x, y, x2, y2; while (ii <= mainRoad.crosses.size()) { // for every road with witch the current road has a cross, i // draw that road if (ii == mainRoad.crosses.size()) { currentRoad = Globals.map.roads.get(rd); } else { rdIdx = (short) ((Cross) mainRoad.crosses.get((int) ii)).getCrossRoadIndex(); currentRoad = Globals.map.roads.get(rdIdx); } ri = currentRoad.getRoadinfo(); MyColor roadColor = MyColor.chooseRoadColor(ri[1]); int laneNr = currentRoad.laneNo; y = 0.0f; x = 0.0f; j = 0; double sinAlfa, cosAlfa; if ((currentRoad.points.size() > 0) && (j == 0)) { currentPoint = (Point) currentRoad.points.get(0); y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); } float dx, dy; while (j < currentRoad.points.size() - 1) { y2 = y; x2 = x; currentPoint = (Point) currentRoad.points.get(j + 1); y = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); currentPoint = (Point) currentRoad.points.get(j); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); sinAlfa = (y2 - y) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x))); cosAlfa = (x2 - x) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x))); dx = (float) (laneNr * 2 * sinAlfa); dy = (float) (laneNr * 2 * cosAlfa); myGL.glPushMatrix(); myGL.glColor3f(roadColor.getRed(), roadColor.getGreen(), roadColor.getBlue()); int laneWidth = 10; switch (currentRoad.oneWay) { case 0: myGL.glTranslatef(x, y, 0.0f); laneWidth = 20; break; case 1: myGL.glTranslatef(x - (dx / 2), y + (dy / 2), 0.0f); break; case 2: myGL.glTranslatef(x + (dx / 2), y - (dy / 2), 0.0f); break; } myGL.glBegin(GL.GL_POLYGON); { for (int ll = 0; ll < 8; ll++) { x2 = (float) (laneWidth * laneNr * (Math.cos((double) (45 * ll * Math.PI / 180)))); y2 = (float) (laneWidth * laneNr * (Math.sin((double) (45 * ll * Math.PI / 180)))); myGL.glVertex3f(x2, y2, 0.0f); } } myGL.glEnd(); myGL.glPopMatrix(); j++; } ii++; } ii = 0; while (ii <= mainRoad.crosses.size()) { // for every road with witch the current road has a cross, i // draw that road if (ii == mainRoad.crosses.size()) { currentRoad = Globals.map.roads.get(rd); } else { rdIdx = (short) ((Cross) mainRoad.crosses.get((int) ii)).getCrossRoadIndex(); currentRoad = Globals.map.roads.get(rdIdx); } ri = currentRoad.getRoadinfo(); MyColor roadColor = MyColor.chooseRoadColor(ri[1]); int laneNr = currentRoad.laneNo; x2 = 0; y2 = 0; j = 0; double sinAlfa, cosAlfa; if ((currentRoad.points.size() > 0) && (j == 0)) { currentPoint = (Point) currentRoad.points.get(0); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); } float dx, dy; while (j < currentRoad.points.size() - 1) { y = y2; x = x2; currentPoint = (Point) currentRoad.points.get(j + 1); y2 = (float) GPSutil.getMetersLatitude(Globals.map.minPoint, currentPoint); x2 = (float) GPSutil.getMetersLongitude(Globals.map.minPoint, currentPoint); if ((x2 != x) || (y2 != y)) { sinAlfa = (y2 - y) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x))); cosAlfa = (x2 - x) / (Math.sqrt((y2 - y) * (y2 - y) + (x2 - x) * (x2 - x))); myGL.glPushMatrix(); myGL.glTranslatef(x, y, 0); myGL.glColor3f(roadColor.getRed(), roadColor.getGreen(), roadColor.getBlue()); myGL.glBegin(GL.GL_QUADS); { dx = (float) (laneNr * 20 * sinAlfa); dy = (float) (laneNr * 20 * cosAlfa); switch (currentRoad.oneWay) { case 0: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); break; case 1: myGL.glVertex3f(0.0f, 0.0f, 0.0f); myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); myGL.glVertex3f(x2 - x, y2 - y, 0.0f); break; case 2: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(0.0f, 0.0f, 0.0f); myGL.glVertex3f(x2 - x, y2 - y, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); break; } } myGL.glEnd(); myGL.glLineWidth(0.25f); myGL.glColor3f(0.3f, 0.3f, 0.3f); myGL.glBegin(GL.GL_LINES); { myGL.glVertex3f(0.0f, 0.0f, 0.0f); myGL.glVertex3f(x2 - x, y2 - y, 0.0f); for (int ln = 1; ln < laneNr; ln++) { dx = (float) (ln * 20 * sinAlfa); dy = (float) (ln * 20 * cosAlfa); if (j % 4 != 0) { myGL.glLineWidth(0.15f); switch (currentRoad.oneWay) { case 0: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); break; case 1: myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); break; case 2: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); break; } } } dx = (float) (laneNr * 20 * sinAlfa); dy = (float) (laneNr * 20 * cosAlfa); myGL.glLineWidth(0.25f); switch (currentRoad.oneWay) { case 0: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); break; case 1: myGL.glVertex3f(dx, 0.0f - dy, 0.0f); myGL.glVertex3f(x2 - x + dx, y2 - y - dy, 0.0f); break; case 2: myGL.glVertex3f(0.0f - dx, dy, 0.0f); myGL.glVertex3f(x2 - x - dx, y2 - y + dy, 0.0f); break; } } myGL.glEnd(); myGL.glPopMatrix(); } j++; } ii++; } } /** * * @param A * @param B * @param C * @return */ private Point2D.Float solve2Degree(float A, float B, float C) { float delta = B * B - 4 * A * C; return new Point2D.Float((0 - B - delta) / 2 / A, (0 - B + delta) / 2 / A); } /** * * @param glDrawable * @param xc * @param yc * @param xp * @param yp * @param laneNr * @param ln * @param dir */ public void setCamera(GLAutoDrawable glDrawable, double xc, double yc, double xp, double yp, int laneNr, int ln, int dir) { // i place the camera on the current postion of the carReceivingMsg and // i make it look in front double A, B, C, a, b; double x1, x2, y1, y2; GL myGL = glDrawable.getGL(); GLU myGLU = new GLU(); double dx = 0, dy = 0, cosAlfa, sinAlfa; if ((xc != xp) || (yc != yp)) { sinAlfa = (float) ((yc - yp) / (Math.sqrt((yc - yp) * (yc - yp) + (xc - xp) * (xc - xp)))); cosAlfa = (float) ((xc - xp) / (Math.sqrt((yc - yp) * (yc - yp) + (xc - xp) * (xc - xp)))); dx = (float) (((laneNr + 1 - ln) * 20 - 11) * sinAlfa); dy = (float) (((laneNr + 1 - ln) * 20 - 11) * cosAlfa); } xCamera = (float) xc; yCamera = (float) yc; // i calculate the point at "distanceToLook" in front of the // carReceivingMsg(on // the direction determined by the previous position and the current // one) if ((xc == xp) && (yc == yp)) { // nothing to do. I am in the same spot } else { // xCamera=(float)(xp+((xc-xp)/2)); // yCamera=(float)(yp+((yc-yp)/2)); if (yc == yp) { // simpler cases if (xp < xc) { xToSee = (float) (xc + distanceToLook); yToSee = (float) (yc); } else { xToSee = (float) (xc - distanceToLook); yToSee = (float) (yc); } } else { if (xc == xp) { if (yp < yc) { xToSee = (float) (xc); yToSee = (float) (yc + distanceToLook); } else { xToSee = (float) xc; yToSee = (float) (yc - distanceToLook); } } else { // i solve a second degree equation to determine the // points at distanceToLook from the current // position and on the right direction a = (yp - yc) / (xp - xc); b = yc - xc * a; A = 1 + a * a; B = 2 * a * b - 2 * xc - 2 * yc * a; C = (double) xc * xc + b * b - 2 * yc * b + yc * yc - distanceToLook * distanceToLook; Point2D.Float sol = solve2Degree((float) A, (float) B, (float) C); x1 = sol.getX(); x2 = sol.getY(); y1 = a * x1 + b; y2 = a * x2 + b; // i choose the one that is front of the carReceivingMsg if (((yp >= yc) && (yc >= y1) && (xp <= xc) && (xc <= x1)) || ((yp >= yc) && (yc >= y1) && (xp >= xc) && (xc >= x1)) || ((yp <= yc) && (yc <= y1) && (xp <= xc) && (xc <= x1)) || ((yp <= yc) && (yc <= y1) && (xp >= xc) && (xc >= x1))) { xToSee = (float) x1; yToSee = (float) y1; } if (((yp >= yc) && (yc >= y2) && (xp <= xc) && (xc <= x2)) || ((yp >= yc) && (yc >= y2) && (xp >= xc) && (xc >= x2)) || ((yp <= yc) && (yc <= y2) && (xp <= xc) && (xc <= x2)) || ((yp <= yc) && (yc <= y2) && (xp >= xc) && (xc >= x2))) { xToSee = (float) x2; yToSee = (float) y2; } } } previosPosX = (float) xc; // the current position is saved for the // next iteration previosPosY = (float) yc; // The camera needs to be tilted in front, so now the normal // direction of the camera should also be calculated float D; float X, Y; X = xToSee; Y = yToSee; xc = (double) xToSee; yc = (double) yToSee; xp = (double) previosPosX; yp = (double) previosPosY; D = (float) (zCamera * zCamera) / distanceToLook; if (yc == yp) { // simpler cases if (xp < xc) { X = (float) (xc + D); Y = (float) yc; } else { X = (float) (xc - D); Y = (float) yc; } } else { if (xc == xp) { if (yp < yc) { X = (float) xc; Y = (float) (yc + D); } else { X = (float) xc; Y = (float) (yc + D); } } else { // i solve a second degree equation to determine the // points at distanceToLook from the current position // and on the right direction a = (yp - yc) / (xp - xc); b = yc - xc * a; A = 1 + a * a; B = 2 * a * b - 2 * xc - 2 * yc * a; C = (double) xc * xc + b * b - 2 * yc * b + yc * yc - D * D; Point2D.Float sol = solve2Degree((float) A, (float) B, (float) C); x1 = sol.getX(); x2 = sol.getY(); y1 = a * x1 + b; y2 = a * x2 + b; // i choose the one that is front of the carReceivingMsg if (((yp >= yc) && (yc >= y1) && (xp <= xc) && (xc <= x1)) || ((yp >= yc) && (yc >= y1) && (xp >= xc) && (xc >= x1)) || ((yp <= yc) && (yc <= y1) && (xp <= xc) && (xc <= x1)) || ((yp <= yc) && (yc <= y1) && (xp >= xc) && (xc >= x1))) { X = (float) x1; Y = (float) y1; } if (((yp >= yc) && (yc >= y2) && (xp <= xc) && (xc <= x2)) || ((yp >= yc) && (yc >= y2) && (xp >= xc) && (xc >= x2)) || ((yp <= yc) && (yc <= y2) && (xp <= xc) && (xc <= x2)) || ((yp <= yc) && (yc <= y2) && (xp >= xc) && (xc >= x2))) { X = (float) x2; Y = (float) y2; } } } myGL.glMatrixMode(GL.GL_MODELVIEW); myGL.glLoadIdentity(); myGLU.gluLookAt(xCamera + dx, yCamera - dy, zCamera, xToSee + dx, yToSee - dy, 0.0, (float) (xToSee - X), (float) (yToSee - Y), zCamera); } } public void displayChanged(GLAutoDrawable arg0, boolean arg1, boolean arg2) { // TODO Auto-generated method stub } public void reshape(GLAutoDrawable arg0, int arg1, int arg2, int arg3, int arg4) { // TODO Auto-generated method stub } }