COMP261 Lecture 4 Graphs 3 of 3
Outline Graph display Different coordinate systems Location class Redraw graph under movements
Program Summary Load the files Store the information into a graph Roads: roadID-roadInfo.tab Nodes: nodeID-lat-lon.tab Road segments: roadSeg-roadID-length-nodeID-nodeID-coords.tab Store the information into a graph Data structure needed Display (part of) the graph in the drawing area Redraw the graph after movements (e.g. left, right, zoom in/out)
Display Graph
Display Graph Important parameters Size of the drawing area Location of the drawing area Scale of the drawn graph (zoom in/out) Different coordinate systems Drawing area: 800x800 pixels Locations in graph: latitude/longitude, x/y kms, … Transformation Graph area ↔ Drawing area Use origin location + scale
Location vs Pixels. ORIGIN: pixel coordinates: 0, 0 location: 15490.5, -4092.899 SCALE: 800 pixels 97.5 km
Location Class Provided to help display Three representations of a location/place/point latitude/longitude Absolute location on a sphere This is what is in the data Location fields: x/y in kilometers Relative location to Aukland center x kms to the east, y kms to the north Assume Auckland region is a flat plane (not quite true, but good enough) This is what you need for finding shortest paths Point (x/y in pixels): pixel coordinates for drawing points and lines mouse click positions y (north) AukCenter x (east)
Location Class Read lat/lon from data Transform to x/y kms and store in the object Formula already provided in the class For display, transform x/y kms to pixel coordinates Current origin and scale Look at the Location.java
Display Graph public void drawLocations(Graph g, Location origin, double scale) { for each location in g: Point pt = location.asPoint(origin, scale); drawPoint(pt); } public Point asPoint(Location origin, double scale) { int u = (int) ((x - origin.x) * scale); int v = (int) ((origin.y - y) * scale); return new Point(u, v);
Redraw Graph Under Movements public Point asPoint(Location origin, double scale) { int u = (int) ((x - origin.x) * scale); int v = (int) ((origin.y - y) * scale); return new Point(u, v); } Drawing requires transforming from x/y kms or lat/lon to pixel coordinates Depends on origin and scale Move left/right/up/down change origin Zoom in/out change both origin and scale How to adjust origin?
Redraw Graph Under Movements Zoom in/out from the current center Zoom in: zoom < 1 Zoom out: zoom > 1 dy = (height – height * zoom) / 2 old origin new origin dx = (width – width * zoom) / 2 width * zoom height width New origin = (origin.x + dx, origin.y + dy)
Redraw Graph Under Movements Notice: use the same coordinate system for all the calculations x/y kms Need to get xmin, xmax, ymin, ymax Pixel coordinates Need to transform back from Point to Location See the method newFromPoint(Point point, Location origin, double scale) in Location.java
Redraw Graph Under Movements Using the x/y kms Get the pixel width and height of the drawing area vertices ← {(0,0), (0,height), (width, 0), (width, height)} for i = 0 to 3: loc[i] ← Location.newFromPoint(vertices[i], origin, scale) locWidth ← loc[2].x – loc[0].x locHeight ← loc[1].y – loc[0].y dx ← (locWidth – locWidth * zoom) / 2 dy ← (locHeight – locHeight * zoom) / 2 newOrigin.x ← origin.x + dx newOrigin.y ← origin.y + dy
Redraw Graph Under Movements Using pixel coordinates directly? How about zoom out?
Summary of Display Load the Road, Node, Segment files Use Location object to represent the locations of the nodes and segments Convert lat/lon to x/y kms in the objects Store into a graph object Use data structures discussed before Set proper initial origin location and scale (e.g. 1) Auto-display the loaded graph using the origin and scale Under any movement Recalculate the origin and scale (depending on movement) Redraw the graph using the new origin and scale