diff --git a/Processing/Misc/Barebones/Barebones.pde b/Processing/Misc/Barebones/Barebones.pde new file mode 100644 index 0000000..30614f7 --- /dev/null +++ b/Processing/Misc/Barebones/Barebones.pde @@ -0,0 +1,40 @@ +int projectorWidth = 1920; +int projectorHeight = 1200; +int projectorOffset = 1842; + +int screenWidth = 1842; +int screenHeight = 1026; + +int displayU = 18; +int displayV = 22; + +int IDMax = 15; + +// Table Canvas Width and Height +int TABLE_IMAGE_HEIGHT = 1000; +int TABLE_IMAGE_WIDTH = 1000; + +// Arrays that holds ID information of rectilinear tile arrangement. +int tablePieceInput[][][] = new int[displayU][displayV][2]; + +void setup() { + size(screenWidth, screenHeight, P3D); + + // Initial Projection-Mapping Canvas + initializeProjection2D(); + + // Allows application to receive information from Colortizer via UDP + initUDP(); + +} + +void draw() { + + background(255); + fill(#FF0000); + rect(0,0,350, 350); + +// Exports table Graphic to Projector + projector = get(0, 0, TABLE_IMAGE_WIDTH, TABLE_IMAGE_HEIGHT); + +} diff --git a/Processing/Misc/Barebones/CONTROLS.pde b/Processing/Misc/Barebones/CONTROLS.pde new file mode 100644 index 0000000..017d3a5 --- /dev/null +++ b/Processing/Misc/Barebones/CONTROLS.pde @@ -0,0 +1,10 @@ +` + +void keyPressed() { + switch(key) { + + case '`': // "Enable Projection (`)" + toggle2DProjection(); + break; + } +} diff --git a/Processing/Misc/Barebones/PROJECTION.pde b/Processing/Misc/Barebones/PROJECTION.pde new file mode 100644 index 0000000..86aceb6 --- /dev/null +++ b/Processing/Misc/Barebones/PROJECTION.pde @@ -0,0 +1,185 @@ +// +// This is a script that allows one to open a new canvas for the purpose +// of simple 2D projection mapping, such as on a flat table surface +// +// Right now, only appears to work in windows... +// +// To use this example in the real world, you need a projector +// and a surface you want to project your Processing sketch onto. +// +// Simply press the 'c' key and drag the corners of the +// CornerPinSurface so that they +// match the physical surface's corners. The result will be an +// undistorted projection, regardless of projector position or +// orientation. +// +// You can also create more than one Surface object, and project +// onto multiple flat surfaces using a single projector. +// +// This extra flexbility can comes at the sacrifice of more or +// less pixel resolution, depending on your projector and how +// many surfaces you want to map. +// + +import javax.swing.JFrame; +import deadpixel.keystone.*; + +// Visualization may show 2D projection visualization, or not +boolean displayProjection2D = false; +//int projectorOffset = screenWidth; + +boolean testProjectorOnMac = false; + +// defines Keystone settings from xml file in parent folder +Keystone ks; + +// defines various drawing surfaces, all pre-calibrated, to project +CornerPinSurface surface; +PGraphics offscreen; +PImage projector; + +// New Application Window Parameters +PFrame proj2D = null; // f defines window to open new applet in +projApplet applet; // applet acts as new set of setup() and draw() functions that operate in parallel + +// Run Anything Needed to have Projection mapping work +void initializeProjection2D() { + println("Projector Info: " + projectorWidth + ", " + projectorHeight + ", " + projectorOffset); + //toggleProjection(getButtonIndex(buttonNames[21])); +} + +public class PFrame extends JFrame { + public PFrame() { + setBounds(0, 0, projectorWidth, projectorHeight ); + setLocation(projectorOffset, 0); + applet = new projApplet(); + setResizable(false); + setUndecorated(true); + setAlwaysOnTop(true); + add(applet); + applet.init(); + show(); + setTitle("Projection2D"); + } +} + +public void showProjection2D() { + if (proj2D == null) { + proj2D = new PFrame(); + } + proj2D.setVisible(true); +} + +public void closeProjection2D() { + proj2D.setVisible(false); +} + +public void resetProjection2D() { + initializeProjection2D(); + if (proj2D != null) { + proj2D.dispose(); + proj2D = new PFrame(); + if (displayProjection2D) { + showProjection2D(); + } else { + closeProjection2D(); + } + } +} + +public class projApplet extends PApplet { + public void setup() { + // Keystone will only work with P3D or OPENGL renderers, + // since it relies on texture mapping to deform + size(projectorWidth, projectorHeight, P2D); + + ks = new Keystone(this);; + + reset(); + } + + public void reset() { + surface = ks.createCornerPinSurface(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT, 20); + offscreen = createGraphics(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT); + + try{ + ks.load(); + } catch(RuntimeException e){ + println("No Keystone.xml. Save one first if you want to load one."); + } + } + + public void draw() { + + // Convert the mouse coordinate into surface coordinates + // this will allow you to use mouse events inside the + // surface from your screen. + PVector surfaceMouse = surface.getTransformedMouse(); + + // most likely, you'll want a black background to minimize + // bleeding around your projection area + background(0); + + // Draw the scene, offscreen + renderCanvas(offscreen, 0); + surface.render(offscreen); + + } + + void renderCanvas(PGraphics p, int x_offset) { + // Draw the scene, offscreen + p.beginDraw(); + p.clear(); + p.translate(x_offset, 0); + p.image(projector, 0, 0); + p.endDraw(); + } + + void keyPressed() { + switch(key) { + case 'c': + // enter/leave calibration mode, where surfaces can be warped + // and moved + ks.toggleCalibration(); + break; + + case 'l': + // loads the saved layout + ks.load(); + break; + + case 's': + // saves the layout + ks.save(); + break; + + case '`': + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + break; + } + } +} + +void toggle2DProjection() { + if (System.getProperty("os.name").substring(0,3).equals("Mac")) { + testProjectorOnMac = !testProjectorOnMac; + println("Test on Mac = " + testProjectorOnMac); + println("Projection Mapping Currently not Supported for MacOS"); + } else { + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + } +} + + diff --git a/Processing/Misc/Barebones/UDP.pde b/Processing/Misc/Barebones/UDP.pde new file mode 100644 index 0000000..972690d --- /dev/null +++ b/Processing/Misc/Barebones/UDP.pde @@ -0,0 +1,98 @@ +// Principally, this script ensures that a string is "caught" via UDP and coded into principal inputs of: +// - tablePieceInput[][] or tablePieceInput[][][2] (rotation) +// - UMax, VMax + + +int portIN = 6152; + +import hypermedia.net.*; +UDP udp; // define the UDP object + +boolean busyImporting = false; +boolean viaUDP = true; +boolean changeDetected = false; +boolean outputReady = false; + +void initUDP() { + if (viaUDP) { + udp = new UDP( this, portIN ); + //udp.log( true ); // <-- printout the connection activity + udp.listen( true ); + } +} + +void ImportData(String inputStr[]) { + if (inputStr[0].equals("COLORTIZER")) { + parseColortizerStrings(inputStr); + } + busyImporting = false; +} + +void parseColortizerStrings(String data[]) { + + for (int i=0 ; i unallocatedArrivalList; + public ArrayList unallocatedDepartureList; + public ArrayList unallocatedHubArrivalList; + public ArrayList unallocatedHubDepartureList; + boolean isHorizontalStreet; + public int[] unallocatedDemandSizeHistory; + public int missedDemand; + public int[] missedDemandHistory; + + public DemandStack() { + missedDemand = 0; + missedDemandHistory = new int[720]; + unallocatedArrivalList = new ArrayList(); + unallocatedDepartureList = new ArrayList(); + unallocatedHubArrivalList = new ArrayList(); + unallocatedHubDepartureList = new ArrayList(); + isHorizontalStreet = true; + unallocatedDemandSizeHistory = new int[720]; + for (int i = 0; i < 720; i++) + unallocatedDemandSizeHistory[i] = 0; + } + + public void init() { + missedDemand = 0; + missedDemandHistory = new int[720]; + unallocatedArrivalList = new ArrayList(); + unallocatedDepartureList = new ArrayList(); + unallocatedHubArrivalList = new ArrayList(); + unallocatedHubDepartureList = new ArrayList(); + isHorizontalStreet = true; + unallocatedDemandSizeHistory = new int[720]; + for (int i = 0; i < 720; i++) + unallocatedDemandSizeHistory[i] = 0; + } + + // Demand Generation + public void demandGen(int _numberOfDemand, int _updateInterval) { + //java.lang.System.out.println("test"); + if (UrbanAutonomous.simParam.currentTime % _updateInterval == 0) { + for (int i = 0; i < _numberOfDemand; i++) { + isHorizontalStreet = !isHorizontalStreet; + Demand tmpArrivalDemand = demandCreation(false); + Demand tmpDepartureDemand = demandCreation(true); + // Demand Clarification + if (UrbanAutonomous.simParam.hubEnable) { + if (isHubEffective(tmpArrivalDemand, tmpDepartureDemand)) { + unallocatedHubArrivalList.add(tmpArrivalDemand); + unallocatedHubDepartureList.add(tmpDepartureDemand);// departureDemand + } else{ + } + } + else { + unallocatedArrivalList.add(tmpArrivalDemand); + unallocatedDepartureList.add(tmpDepartureDemand);// departureDemand + } + } + } + } + + // DemandCreation + Demand demandCreation(boolean isDepartureDemand) { + while (true) { + Demand demandCandidate = demandCandidateGen(isHorizontalStreet, isDepartureDemand); + if (probabilityCheck(demandCandidate)) { + return demandCandidate; + } + } + } + + // Demand Candidate Generation + Demand demandCandidateGen(boolean isHorizontalStreet, boolean isDepartureDemand) { + Demand _demandCandidate; + if (isHorizontalStreet) { + int streetNumber = (int) random(UrbanAutonomous.simParam.maxY); + int y = streetNumber * 5 + 2; + int x = (int) random(5*UrbanAutonomous.simParam.maxX); + _demandCandidate = new Demand(x, y, streetNumber, isHorizontalStreet, isDepartureDemand); + } else { + int streetNumber = (int) random(UrbanAutonomous.simParam.maxX); + int x = streetNumber * 5 + 2; + int y = (int) random(5*UrbanAutonomous.simParam.maxY); + _demandCandidate = new Demand(x, y, streetNumber, isHorizontalStreet, isDepartureDemand); + } + return _demandCandidate; + } + + // probability check + boolean probabilityCheck(Demand _demandCandidate) { + boolean determination = false; + float sum = 0; + float avgProbability; + if (_demandCandidate.isDepartureDemand) { + if (_demandCandidate.isHorizontalStreet) { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 2].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 1].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 1].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 2].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } else { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x + - 2][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + - 1][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 1][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 2][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } + } else { + if (_demandCandidate.isHorizontalStreet) { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 2].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 1].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 1].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 2].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } else { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x + - 2][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + - 1][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 1][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 2][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } + } + if (sum != 0) { + avgProbability = sum * 100 / 4; + if ((int) random(1 / (avgProbability / 100)) == 0) + determination = true; + } + return determination; + } + + // DemandAllocation for Hub + public void demandHubAllocation() { + if (unallocatedHubListIsNotEmpty()) { + if (UrbanAutonomous.hubStack.hubPeripheralVehicleA.status == PeripheralVehicleStatus.STOP) { + for (int i = 0; i < unallocatedHubDepartureList.size(); i++) { + if (fromHubAtoB(unallocatedHubArrivalList.get(i), unallocatedHubDepartureList.get(i))) { + UrbanAutonomous.hubStack.hubPeripheralVehicleA.status = PeripheralVehicleStatus.DEPARTURE; + UrbanAutonomous.hubStack.hubPeripheralVehicleA.departureList + .add(unallocatedHubDepartureList.remove(i)); + UrbanAutonomous.hubStack.hubPeripheralVehicleA.reserveArrivalList + .add(unallocatedHubArrivalList.remove(i)); + } + } + } + if (UrbanAutonomous.hubStack.hubPeripheralVehicleB.status == PeripheralVehicleStatus.STOP) { + for (int i = 0; i < unallocatedHubDepartureList.size(); i++) { + if (fromHubBtoA(unallocatedHubArrivalList.get(i), unallocatedHubDepartureList.get(i))) { + UrbanAutonomous.hubStack.hubPeripheralVehicleB.status = PeripheralVehicleStatus.DEPARTURE; + UrbanAutonomous.hubStack.hubPeripheralVehicleB.departureList + .add(unallocatedHubDepartureList.remove(i)); + UrbanAutonomous.hubStack.hubPeripheralVehicleB.reserveArrivalList + .add(unallocatedHubArrivalList.remove(i)); + } + } + } + } + } + + boolean hubPeripheralVehicleIsEmpty(HubPeripheralVehicle v) { + boolean result = false; + if (v.arrivalList.size() == 0 && v.departureList.size() == 0 && v.reserveArrivalList.size() == 0) + result = true; + return result; + } + + boolean unallocatedHubListIsNotEmpty() { + boolean result = false; + if (unallocatedHubDepartureList.size() > 0 || unallocatedHubArrivalList.size() > 0) { + result = true; + } + return result; + } + //usage rate + public int usageRateCal(){ + int result=10; + int totalVehicle=UrbanAutonomous.simParam.numberOfVehicle; + int usingVehicle=0; + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + if(vehicle.departureList.size()==0&&vehicle.arrivalList.size()==0) + ; + else{ + usingVehicle++; + } + } + result = 100* usingVehicle/totalVehicle; + + if(result==0) + result=100; + + if(result<50){ + if(UrbanAutonomous.simParam.numberOfVehicle>1){ + //UrbanAutonomous.vehicleStack.vehicleList.remove(UrbanAutonomous.vehicleStack.vehicleList.size()-1); + int tmp=UrbanAutonomous.simParam.numberOfVehicle/3; + if(tmp>0) + UrbanAutonomous.simParam.numberOfVehicle=tmp; + else{ + UrbanAutonomous.simParam.numberOfVehicle=1; + } + + UrbanAutonomous.vehicleStack.vehicleGen(); + } + } + + return result; + + } + + // DemandAllocation except hub + public void demandAllocation() { + if (unallocatedDepartureList.size() > 0 || unallocatedArrivalList.size() > 0) { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + if (vehicle.arrivalList.size() == 0 && vehicle.departureList.size() == 0) { + while (vehicle.arrivalList.size() < UrbanAutonomous.simParam.capacityOfVehicle + && vehicle.departureList.size() < UrbanAutonomous.simParam.capacityOfVehicle) { + if (unallocatedDepartureList.size() > 0 || unallocatedArrivalList.size() > 0) { + vehicle.arrivalList.add(unallocatedArrivalList.get(0)); + vehicle.departureList.add(unallocatedDepartureList.get(0)); + unallocatedArrivalList.remove(0); + unallocatedDepartureList.remove(0); + } else { + break; + } + } + } + } + } + } + + // Hub effectiveCheck + boolean isHubEffective(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // fromHubA to fromHubB + boolean fromHubBtoA(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // fromHubA to fromHubB + boolean fromHubAtoB(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // DemandLifeTime + public void demandLifetimeControl() { + if (unallocatedArrivalList.size() > 0) { + Iterator iter = unallocatedArrivalList.iterator(); + while (iter.hasNext()) { + Demand tmpDemand = iter.next(); + if (tmpDemand.lifetime == 0) { + iter.remove(); + missedDemand++; + UrbanAutonomous.simParam.numberOfVehicle++; + UrbanAutonomous.vehicleStack.vehicleGen(); + // missedDemandHistory[UrbanAutonomous.simParam.currentTime/20]=missedDemand; + } else { + tmpDemand.lifetime -= 1; + } + } + missedDemandHistory[UrbanAutonomous.simParam.currentTime / 20] = missedDemand; + iter = unallocatedDepartureList.iterator(); + while (iter.hasNext()) { + Demand tmpDemand = iter.next(); + if (tmpDemand.lifetime == 0) { + iter.remove(); + } else { + tmpDemand.lifetime -= 1; + } + } + } + } +} diff --git a/Processing/Misc/UrbanAutonomous/Disp.java b/Processing/Misc/UrbanAutonomous/Disp.java new file mode 100644 index 0000000..36437dd --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/Disp.java @@ -0,0 +1,182 @@ + + +import processing.core.PApplet; +import processing.core.PConstants; +import processing.core.PGraphics; +//import com.y; + +public class Disp { + PApplet pa; + PGraphics p; + + //public Disp(PApplet _pa) { + public Disp(PGraphics _p,PApplet _pa) { + p = _p; + pa = _pa; + } + + // ShowALl + public void show() { + // showMap(); + p.beginDraw(); + oldshowMap(); + showUnallocatedDemand(); + showAllocatedDemand(); + showVehicle(); + showCongestion(); + if (UrbanAutonomous.simParam.hubEnable) { + showHub(); + showHubVehicle(); + showHubPeripheralVehicle(); + showHubRelocation(); + } + p.endDraw(); + } + //ShowHubRelocation + void showHubRelocation(){ + if (UrbanAutonomous.dragStatus == DragStatus.HUBA || UrbanAutonomous.dragStatus == DragStatus.HUBB) { + p.ellipseMode(PConstants.CENTER); + p.stroke(UrbanAutonomous.hubColor); + p.ellipse(pa.mouseX, pa.mouseY, 10, 10); + } + } + + // ShowMap + void oldshowMap() { + for (int y = 0; y < UrbanAutonomous.simParam.maxY; y++) + for (int x = 0; x < UrbanAutonomous.simParam.maxX; x++) + p.image(UrbanAutonomous.mapBlockStack.mapBlockArray[x][y].pg, x * 50, y * 50); + } + + void showMap() { + p.image(UrbanAutonomous.mapBlockStack.pg, 0, 0); + } + + // ShowDemand + // ShowUnallocatedDemand + void showUnallocatedDemand() { + for (Demand tmpDemand : UrbanAutonomous.demandStack.unallocatedArrivalList) { + showEachDemand(tmpDemand); + } + for (Demand tmpDemand : UrbanAutonomous.demandStack.unallocatedDepartureList) { + showEachDemand(tmpDemand); + } + } + + // ShowAllocatedDemand + void showAllocatedDemand() { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand tmpDemand : vehicle.arrivalList) { + showEachAllocatedDemand(tmpDemand); + } + for (Demand tmpDemand : vehicle.departureList) { + showEachAllocatedDemand(tmpDemand); + } + } + } + + void showEachAllocatedDemand(Demand tmpDemand) { + p.ellipseMode(PConstants.CENTER); + if (tmpDemand.isDepartureDemand) + p.fill(UrbanAutonomous.allocatedDepartureColor); + else + p.fill(UrbanAutonomous.allocatedArrivalColor); + p.ellipse(tmpDemand.x * 10 + 5, tmpDemand.y * 10 + 5, 10,10); + } + + void showEachDemand(Demand tmpDemand) { + p.ellipseMode(PConstants.CENTER); + if (tmpDemand.isDepartureDemand) + p.fill(UrbanAutonomous.unallocatedDepartureColor); + else + p.fill(UrbanAutonomous.unallocatedArrivalColor); + p.ellipse(tmpDemand.x * 10 + 5, tmpDemand.y * 10 + 5, 10, 10); + } + + // ShowVehicle + void showVehicle() { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.vehicleColor); + int vSize= (int)java.lang.Math.sqrt(UrbanAutonomous.simParam.capacityOfVehicle*100) ; + //p.ellipse(vehicle.x * 10 + 5, vehicle.y * 10 + 5, 5*UrbanAutonomous.simParam.capacityOfVehicle, 5*UrbanAutonomous.simParam.capacityOfVehicle); + p.ellipse(vehicle.x * 10 + 5, vehicle.y * 10 + 5, vSize,vSize); + } + } + + // Show Congestion + void showCongestion() { + int totalCongestionLevel = 0; + // Vehicle + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand position : vehicle.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + if (UrbanAutonomous.simParam.hubEnable) { + // HubVehicle + for (Coord position : UrbanAutonomous.hubStack.hubVehicleArray[0].movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + // HubPeripheralVehicle + for (Coord position : UrbanAutonomous.hubStack.hubPeripheralVehicleA.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + for (Coord position : UrbanAutonomous.hubStack.hubPeripheralVehicleB.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + UrbanAutonomous.simParam.totalCongestionLevel[UrbanAutonomous.simParam.currentTime / 20] = totalCongestionLevel; + UrbanAutonomous.simParam.currentTotalCongestionLevel = totalCongestionLevel; + } + + // oldShow Congestion + void oldshowCongestion() { + int totalCongestionLevel = 0; + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand position : vehicle.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + UrbanAutonomous.simParam.totalCongestionLevel[UrbanAutonomous.simParam.currentTime / 20] = totalCongestionLevel; + UrbanAutonomous.simParam.currentTotalCongestionLevel = totalCongestionLevel; + } + + // Show Hub + void showHub() { + p.ellipseMode(PConstants.CENTER); + p.rectMode(PConstants.CENTER); + for (int i = 0; i < UrbanAutonomous.hubStack.hubArray.length; i++) { + p.fill(UrbanAutonomous.hubColor); + p.ellipse(UrbanAutonomous.hubStack.hubArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubArray[i].y * 10 + 5, 15, 15); + p.fill(UrbanAutonomous.hubEffectiveLengthColor); + p.rect(UrbanAutonomous.hubStack.hubArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubArray[i].y * 10 + 5, + UrbanAutonomous.simParam.hubEffectiveLength * 10 * 2, UrbanAutonomous.simParam.hubEffectiveLength * 10 * 2); + } + } + + // Show HubVehicle + void showHubVehicle() { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.hubVehicleColor); + for (int i = 0; i < UrbanAutonomous.hubStack.hubVehicleArray.length; i++) { + p.ellipse(UrbanAutonomous.hubStack.hubVehicleArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubVehicleArray[i].y * 10 + 5, + 15, 15); + } + } + + // Show HubPeripheralVehicle + void showHubPeripheralVehicle() { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.hubPeripheralVehicleColor); + p.ellipse(UrbanAutonomous.hubStack.hubPeripheralVehicleA.x * 10 + 5, + UrbanAutonomous.hubStack.hubPeripheralVehicleA.y * 10 + 5, 15, 15); + p.ellipse(UrbanAutonomous.hubStack.hubPeripheralVehicleB.x * 10 + 5, + UrbanAutonomous.hubStack.hubPeripheralVehicleB.y * 10 + 5, 15, 15); + } +} diff --git a/Processing/Misc/UrbanAutonomous/DragStatus.java b/Processing/Misc/UrbanAutonomous/DragStatus.java new file mode 100644 index 0000000..20b1e51 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/DragStatus.java @@ -0,0 +1,16 @@ +public enum DragStatus { + NORMAL(1), + HUBA(2), + HUBB(3); + + private final int id; + + private DragStatus(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + +} diff --git a/Processing/Misc/UrbanAutonomous/FileControl.java b/Processing/Misc/UrbanAutonomous/FileControl.java new file mode 100644 index 0000000..f51a886 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/FileControl.java @@ -0,0 +1,16 @@ + +import processing.core.PApplet; + +public class FileControl extends PApplet { + public int [] customMap; + + public FileControl() { +// customMap = new int[(16*16)]; + customMap = new int[(UrbanAutonomous.simParam.maxX*UrbanAutonomous.simParam.maxY)]; + } + + public void outputCSV() { + String []outData=str(customMap); + saveStrings("customMap.txt", outData); + } + } \ No newline at end of file diff --git a/Processing/Misc/UrbanAutonomous/Hub.java b/Processing/Misc/UrbanAutonomous/Hub.java new file mode 100644 index 0000000..d31f003 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/Hub.java @@ -0,0 +1,48 @@ + +import java.util.ArrayList; + +public class Hub { + public int x; + public int y; + public boolean isHorizontalStreet; + public boolean isIntersection; + public int streetNumber; + public ArrayList unallocatedArrivalList; + public ArrayList hubVehicleWaitingList; + + public Hub(int _x, int _y) { + x = _x; + y = _y; + unallocatedArrivalList = new ArrayList(); + hubVehicleWaitingList = new ArrayList(); + paramUpdate(); + } + + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/HubPeripheralVehicle.java b/Processing/Misc/UrbanAutonomous/HubPeripheralVehicle.java new file mode 100644 index 0000000..3e2e6b3 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/HubPeripheralVehicle.java @@ -0,0 +1,237 @@ + +import java.util.ArrayList; + +import processing.core.PApplet; + +public class HubPeripheralVehicle { + public int x; + public int y; + public int streetNumber; + public boolean isHorizontalStreet; + public boolean isIntersection; + public boolean forHubA; + + public ArrayList departureList; + public ArrayList reserveArrivalList; + public ArrayList arrivalList; + public ArrayList movingHistoryList; + PApplet p; + public PeripheralVehicleStatus status; + + public HubPeripheralVehicle(int _x, int _y, PApplet _p, boolean _forHubA) { + status = PeripheralVehicleStatus.STOP; + x = _x; + y = _y; + p = _p; + forHubA = _forHubA; + departureList = new ArrayList(); + arrivalList = new ArrayList(); + reserveArrivalList = new ArrayList(); + movingHistoryList = new ArrayList(); + } + + // Parameter Update + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } + + // Vehicle Movement + public void move() { + paramUpdate(); + movingHistoryUpdate(); + switch (status) { + case STOP: + break; + case DEPARTURE: + eachMove(departureList); + break; + case TOHUB: + if (forHubA) + goToHub(UrbanAutonomous.hubStack.hubA); + else + goToHub(UrbanAutonomous.hubStack.hubB); + break; + case ARRIVAL: + eachMove(arrivalList); + break; + default: + break; + } + } + + void movingHistoryUpdate() { + Coord tmpVehiclePosition = new Coord(x, y); + if (status == PeripheralVehicleStatus.STOP) { + if (movingHistoryList.size() > 0) + movingHistoryList.remove(0); + } else if (movingHistoryList.size() >= UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + else + movingHistoryList.add(tmpVehiclePosition); + } + + void eachMove(ArrayList tmpList) { + if (isSamePoint(tmpList.get(0))) { + tmpList.remove(0); + if (tmpList.size() == 0) + if (status == PeripheralVehicleStatus.DEPARTURE) + status = PeripheralVehicleStatus.TOHUB; + else if (status == PeripheralVehicleStatus.ARRIVAL) + status = PeripheralVehicleStatus.STOP; + } else if (isSameStreet(tmpList.get(0))) { + if (tmpList.get(0).isHorizontalStreet) + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + else + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + } else { + if (isIntersection) { + if (tmpList.get(0).isHorizontalStreet) + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + else + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + } else { + if (isHorizontalStreet) { + if (tmpList.get(0).isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + } + } else { + if (tmpList.get(0).isHorizontalStreet) { + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + void goToHub(Hub tmpHub) { + if (isSamePoint(tmpHub)) { + tmpHub.hubVehicleWaitingList.addAll(reserveArrivalList); + reserveArrivalList = new ArrayList(); + if (tmpHub.unallocatedArrivalList.size() > 0) { + status = PeripheralVehicleStatus.ARRIVAL; + while (arrivalList.size() < UrbanAutonomous.simParam.capacityOfPeripheralVehicle + || tmpHub.unallocatedArrivalList.size() > 0) { + arrivalList.add(tmpHub.unallocatedArrivalList.remove(0)); + } + } else { + status = PeripheralVehicleStatus.STOP; + } + } else if (isSameStreet(tmpHub)) { + if (tmpHub.isHorizontalStreet) + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + else + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + } else { + if (isIntersection) { + if (tmpHub.isHorizontalStreet) + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + else + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + } else { + if (isHorizontalStreet) { + if (tmpHub.isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + } + } else { + if (tmpHub.isHorizontalStreet) { + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + boolean isSameStreet(Demand tmpDemand) { + boolean result = false; + if (tmpDemand.streetNumber == streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Demand tmpDemand) { + boolean result = false; + if (tmpDemand.x == x && tmpDemand.y == y) + result = true; + return result; + } + + boolean isSameStreet(Hub tmpDemand) { + boolean result = false; + if (tmpDemand.streetNumber == streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Hub tmpDemand) { + boolean result = false; + if (tmpDemand.x == x && tmpDemand.y == y) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/HubStack.java b/Processing/Misc/UrbanAutonomous/HubStack.java new file mode 100644 index 0000000..980eafb --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/HubStack.java @@ -0,0 +1,36 @@ +import processing.core.PApplet; + +public class HubStack { + public PApplet p; + public Hub hubA; + public Hub hubB; + public int ax,ay,bx,by; + public static HubVehicle hubVehicleA; + public Hub [] hubArray; + public HubVehicle [] hubVehicleArray; + public HubPeripheralVehicle hubPeripheralVehicleA,hubPeripheralVehicleB; + + public HubStack(PApplet _p) { + p=_p; + ax=72; + ay=7; + bx=7; + by=72; + hubA = new Hub(ax, ay); + hubB = new Hub(bx, by); + hubArray = new Hub[]{hubA,hubB}; + hubVehicleA = new HubVehicle(0,0,p); + hubVehicleArray = new HubVehicle[]{hubVehicleA}; + hubPeripheralVehicleA = new HubPeripheralVehicle(0,0,p,true); + hubPeripheralVehicleB = new HubPeripheralVehicle(0,0,p,false); + } + public void init(){ + hubA = new Hub(ax, ay); + hubB = new Hub(bx, by); + hubArray = new Hub[]{hubA,hubB}; + hubVehicleA = new HubVehicle(0,0,p); + hubVehicleArray = new HubVehicle[]{hubVehicleA}; + hubPeripheralVehicleA = new HubPeripheralVehicle(0,0,p,true); + hubPeripheralVehicleB = new HubPeripheralVehicle(0,0,p,false); + } +} diff --git a/Processing/Misc/UrbanAutonomous/HubVehicle.java b/Processing/Misc/UrbanAutonomous/HubVehicle.java new file mode 100644 index 0000000..8f24dd8 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/HubVehicle.java @@ -0,0 +1,167 @@ +import java.util.ArrayList; + + +import processing.core.PApplet; + +public class HubVehicle { + + public int x; + public int y; + public int streetNumber; + public boolean isHorizontalStreet; + public boolean isIntersection; + public boolean toHubA; + ArrayList arrivalList; + public ArrayList movingHistoryList; + PApplet p; + + public HubVehicle(int _x, int _y, PApplet _p) { + x = _x; + y = _y; + p = _p; + toHubA = false; + arrivalList = new ArrayList(); + movingHistoryList = new ArrayList(); + } + + // Parameter Update + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } + + // Vehicle Movement + public void move() { + paramUpdate(); + movingHistoryUpdate(); + eachMove(); + } + + void movingHistoryUpdate() { + Coord tmpVehiclePosition = new Coord(x, y); + if (!(isInHub())) + movingHistoryList.add(tmpVehiclePosition); + if (isInHub() && movingHistoryList.size() > 0) + movingHistoryList.remove(0); + if (movingHistoryList.size() >= UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + } + + boolean isInHub() { + boolean result = false; + if (UrbanAutonomous.hubStack.hubA.y == y && UrbanAutonomous.hubStack.hubA.y == y) + result = true; + if (UrbanAutonomous.hubStack.hubB.y == y && UrbanAutonomous.hubStack.hubB.y == y) + result = true; + return result; + } + + void eachMove() { + if (toHubA) + eachSubMove(UrbanAutonomous.hubStack.hubA); + else + eachSubMove(UrbanAutonomous.hubStack.hubB); + } + + boolean hubIsNotEmpty() { + boolean result = false; + if (UrbanAutonomous.hubStack.hubA.hubVehicleWaitingList.size() > 0 + || UrbanAutonomous.hubStack.hubB.hubVehicleWaitingList.size() > 0) + result = true; + return result; + } + + void eachSubMove(Hub hubX) { + if (isSamePoint(hubX)) { + hubX.unallocatedArrivalList.addAll(arrivalList); + if (hubIsNotEmpty()) { + toHubA = !toHubA; + arrivalList = new ArrayList(); + while (arrivalList.size() < UrbanAutonomous.simParam.hubDedicatedVehicleCapacity + && hubX.hubVehicleWaitingList.size() != 0) { + arrivalList.add(hubX.hubVehicleWaitingList.get(0)); + } + } + } else if (isSameStreet(hubX)) { + if (hubX.isHorizontalStreet) + x += (hubX.x - x) / p.abs(hubX.x - x); + else + y += (hubX.y - y) / p.abs(hubX.y - y); + } else { + if (isIntersection) { + if (hubX.isHorizontalStreet) + y += (hubX.y - y) / p.abs(hubX.y - y); + else + x += (hubX.x - x) / p.abs(hubX.x - x); + } else { + if (isHorizontalStreet) { + if (hubX.isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (hubX.x - x) / p.abs(hubX.x - x); + } + } else { + if (hubX.isHorizontalStreet) { + y += (hubX.y - y) / p.abs(hubX.y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + boolean isSameStreet(Hub hubA) { + boolean result = false; + if (hubA.streetNumber == streetNumber && hubA.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (hubA.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == hubA.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == hubA.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Hub hub) { + boolean result = false; + if (hub.x == x && hub.y == y) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/MapBlock.java b/Processing/Misc/UrbanAutonomous/MapBlock.java new file mode 100644 index 0000000..84e39dc --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/MapBlock.java @@ -0,0 +1,66 @@ + +import processing.core.PApplet; +import processing.core.PGraphics; + +public class MapBlock { + PApplet p; + int blockSize; + Tile[][] tileArray; + public PGraphics pg; + + public MapBlock() { + } + + public MapBlock(PApplet _p) { + p = _p; + } + + public MapBlock(PApplet _p, Tile[][] _tileArray) { + p = _p; + blockSize = 5; + tileArray = _tileArray; + gen(); + } + + void gen() { + if (pg == null) + pg = p.createGraphics(blockSize * 10, blockSize * 10); + pg.beginDraw(); + pg.background(255); + pg.stroke(255); + for (int y = 0; y < blockSize; y++) { + for (int x = 0; x < blockSize; x++) { + //for abstraction, delete road + if(x==2||y==2) + tileArray[x][y].tileType=tileArray[0][0].tileType; + + switch (tileArray[x][y].tileType) { + case HW: + pg.image(UrbanAutonomous.hwImg, x * 10, y * 10); + break; + case LW: + pg.image(UrbanAutonomous.lwImg, x * 10, y * 10); + break; + case HR: + pg.image(UrbanAutonomous.hrImg, x * 10, y * 10); + break; + case LR: + pg.image(UrbanAutonomous.lrImg, x * 10, y * 10); + break; + case ROAD: + pg.image(UrbanAutonomous.roadImg, x * 10, y * 10); + break; + case INTERSECTION: + pg.image(UrbanAutonomous.intersectionImg, x * 10, y * 10); + break; + case NONE: + pg.image(UrbanAutonomous.noneImg, x * 10, y * 10); + break; + default: + break; + } + } + } + pg.endDraw(); + } +} diff --git a/Processing/Misc/UrbanAutonomous/MapBlockBase.java b/Processing/Misc/UrbanAutonomous/MapBlockBase.java new file mode 100644 index 0000000..fc48c1a --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/MapBlockBase.java @@ -0,0 +1,66 @@ + + +import processing.core.PApplet; + +public class MapBlockBase { + MapBlockBase() {} + + //RandomMapBlock + Tile[][] randomTileArrayGen(PApplet p) { + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile,UrbanAutonomous.basicTile.noneTile }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[(int) p.random(4)]; + } + } + } + return tileArray; + } + + //SpecificTile + Tile[][] specificTileArrayGen(int number) { + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile,UrbanAutonomous.basicTile.noneTile + }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[number]; + } + } + } + return tileArray; + } + + Tile[][] specificTileArrayGen(PApplet p) { + int number=(int)p.random(4); + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile + }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[number]; + } + } + } + return tileArray; + } + } diff --git a/Processing/Misc/UrbanAutonomous/MapBlockBrushs.java b/Processing/Misc/UrbanAutonomous/MapBlockBrushs.java new file mode 100644 index 0000000..7ca548b --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/MapBlockBrushs.java @@ -0,0 +1,53 @@ +import processing.core.PApplet; +import processing.core.PGraphics; + +public class MapBlockBrushs extends MapBlockBase { + public MapBlock[] randomBrushs; + public MapBlock[] specificBrushs; + public MapBlock selectedBrush; + public int numberOfBrush; + public PGraphics pg; + PApplet p; + + public MapBlockBrushs(PApplet _p,int _numberOfBrush) { + p=_p; + randomBrushs = new MapBlock[_numberOfBrush]; + specificBrushs = new MapBlock[_numberOfBrush]; + numberOfBrush=_numberOfBrush; + randomBrushsGen(_numberOfBrush); + specificBrushsGen(); + selectedBrush = specificBrushs[0]; + } + + public void randomBrushsGen(int _numberOfBrush) { + for (int i=0; i<_numberOfBrush; i++) { + randomBrushs[i] = new MapBlock(p,randomTileArrayGen(p)); + } + } + public void randomBrushsGen() { + for (int i=0; i1130 && mouseX <1850) { + if (mouseY >150-50 && mouseY<150+50) { + UrbanAutonomous.simParam.currentTime=(mouseX-1130)*20 ; + } + } + //save file for custom map + if (mouseX > 200 && mouseX<300) + if (mouseY> 200 && mouseY<230) + UrbanAutonomous.fileControl.outputCSV(); + + //MAP + if (mouseX > 50 && mouseX<200) { + if (mouseY> 100 && mouseY<130) { + UrbanAutonomous.mapBlockStack.loadUrbanMap(); + UrbanAutonomous.mapBlockStack.updateCoordinate();// reflect change of mapblock to demand generation + UrbanAutonomous.mapBlockStack.mapImgCreation();//map image creation for display + } else if (mouseY> 150 && mouseY<180) { + UrbanAutonomous.mapBlockStack.loadRuralMap(); + UrbanAutonomous.mapBlockStack.updateCoordinate();// reflect change of mapblock to demand generation + UrbanAutonomous.mapBlockStack.mapImgCreation();//map image creation for display + } else if (mouseY> 200 && mouseY<230) { + UrbanAutonomous.mapBlockStack.noneMapGen(); + UrbanAutonomous.mapBlockStack.updateCoordinate();// reflect change of mapblock to demand generation + UrbanAutonomous.mapBlockStack.mapImgCreation();//map image creation for display + } + } + //MAP change brush + if (mouseX >50 && mouseX <200) { + if (mouseY >530 && mouseY<600) { + UrbanAutonomous.mapBlockBrushs.randomBrushsGen(); + UrbanAutonomous.mapBlockBrushs.brushImgCreation(); + } + } + //Map Brush select + if (mouseX >50 && mouseX <100) { + UrbanAutonomous.mapBlockBrushs.brushImgCreation(); + if (mouseY >250 && mouseY<300) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.specificBrushs[0]; + UrbanAutonomous.brushNumber=0; + } else if (mouseY >320 && mouseY<370) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.specificBrushs[1]; + UrbanAutonomous.brushNumber=1; + } else if (mouseY >390 && mouseY<440) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.specificBrushs[2]; + UrbanAutonomous.brushNumber=2; + } else if (mouseY >460 && mouseY<510) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.specificBrushs[3]; + UrbanAutonomous.brushNumber=3; + } + } else if (mouseX >150 && mouseX <200) { + UrbanAutonomous.mapBlockBrushs.brushImgCreation(); + if (mouseY >250 && mouseY<300) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.randomBrushs[0]; + } else if (mouseY >320 && mouseY<370) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.randomBrushs[1]; + } else if (mouseY >390 && mouseY<440) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.randomBrushs[2]; + } else if (mouseY >460 && mouseY<510) { + UrbanAutonomous.mapBlockBrushs.selectedBrush=UrbanAutonomous.mapBlockBrushs.randomBrushs[3]; + } + } + + + int offsetSecond=580; + //Fleet Demand + + if (mouseX > offsetSecond && mouseX<= offsetSecond+200) { + //Fleet Size + + //number of vehicle + if (mouseY>100 && mouseY <100+30) { + UrbanAutonomous.simParam.numberOfVehicle=(int)((mouseX-offsetSecond)/2); + UrbanAutonomous.vehicleStack.vehicleGen(); + } + + //capacity of vehicle + else if (mouseY>171 && mouseY<170+30) { + UrbanAutonomous.simParam.capacityOfVehicle=(int)((mouseX-offsetSecond)/2); + UrbanAutonomous.vehicleStack.vehicleGen(); + } else if (mouseY>520 && mouseY<520+30) { + //currentDemandSize + UrbanAutonomous.simParam.currentDemandSize=(int)((mouseX-offsetSecond)/2); + } else if (mouseY>630 && mouseY<630+30) { + //demandInterval + UrbanAutonomous.simParam.demandInterval=(int)((mouseX-offsetSecond)/2); + } else if (mouseY>700 && mouseY<700+30) { + //demandLifetime + UrbanAutonomous.simParam.demandLifetime=(int)((mouseX-offsetSecond)/2); + } + } + + //FleetPreset Button + if (mouseY>340 && mouseY<340+30) { + if (mouseX>420 && mouseX<420+100) { + //PEV + UrbanAutonomous.simParam.numberOfVehicle=80; + UrbanAutonomous.simParam.capacityOfVehicle=1; + UrbanAutonomous.vehicleStack.vehicleGen(); + } else if (mouseX>550 && mouseX<550+100) { + //Car + UrbanAutonomous.simParam.numberOfVehicle=20; + UrbanAutonomous.simParam.capacityOfVehicle=4; + UrbanAutonomous.vehicleStack.vehicleGen(); + } else if (mouseX>680 && mouseX<680+100) { + //Bus + UrbanAutonomous.simParam.numberOfVehicle=1; + UrbanAutonomous.simParam.capacityOfVehicle=80; + UrbanAutonomous.vehicleStack.vehicleGen(); + } + } + + //DemandSize preset + if (mouseX>300 && mouseX<780) { + if (mouseY > 450 && mouseY<480) { + UrbanAutonomous.simParam.demandSizeCustom=false; + } else if (mouseY > 520 && mouseY<550) { + UrbanAutonomous.simParam.demandSizeCustom=true; + } + } + } + } diff --git a/Processing/Misc/UrbanAutonomous/OperationWindow.java b/Processing/Misc/UrbanAutonomous/OperationWindow.java new file mode 100644 index 0000000..e2d7c2c --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/OperationWindow.java @@ -0,0 +1,35 @@ + +import processing.core.PApplet; + +public class OperationWindow extends PApplet { + //OperationDisp operationDisp; + public static OperationDisp operationDisp; + + public void setup() { + //fullscreen(); + operationDisp = new OperationDisp(this); + delay(500); + + } + public void draw() { + operationDisp.show(); + } + + public void mousePressed() { + //Vehicle Size + if (mouseY >250 && mouseY<300) { + if (mouseX >350 && mouseX <850) { + UrbanAutonomous.simParam.capacityOfVehicle=(mouseX-350)/10; + UrbanAutonomous.simParam.numberOfVehicle=1; + UrbanAutonomous.vehicleStack.vehicleGen(); + UrbanAutonomous.simParam.currentTime=4200; + } + } + //Time + else if (mouseY >350 && mouseY<400) { + if (mouseX >350 && mouseX <350+1440) { + UrbanAutonomous.simParam.currentTime=(mouseX-350)*10 ; + } + } + } + } diff --git a/Processing/Misc/UrbanAutonomous/PFrame.java b/Processing/Misc/UrbanAutonomous/PFrame.java new file mode 100644 index 0000000..abf18dd --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/PFrame.java @@ -0,0 +1,14 @@ + +import javax.swing.JFrame; + + + +public class PFrame extends JFrame { + public PFrame(int _x, int _y, int _width, int _height) { + setBounds(_x, _y, _width, _height); + UrbanAutonomous.opw = new OperationWindow(); + add(UrbanAutonomous.opw); + UrbanAutonomous.opw.init(); + setVisible(true); + } +} \ No newline at end of file diff --git a/Processing/Misc/UrbanAutonomous/PROJECTION.pde b/Processing/Misc/UrbanAutonomous/PROJECTION.pde new file mode 100644 index 0000000..a64e896 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/PROJECTION.pde @@ -0,0 +1,185 @@ +// +// This is a script that allows one to open a new canvas for the purpose +// of simple 2D projection mapping, such as on a flat table surface +// +// Right now, only appears to work in windows... +// +// To use this example in the real world, you need a projector +// and a surface you want to project your Processing sketch onto. +// +// Simply press the 'c' key and drag the corners of the +// CornerPinSurface so that they +// match the physical surface's corners. The result will be an +// undistorted projection, regardless of projector position or +// orientation. +// +// You can also create more than one Surface object, and project +// onto multiple flat surfaces using a single projector. +// +// This extra flexbility can comes at the sacrifice of more or +// less pixel resolution, depending on your projector and how +// many surfaces you want to map. +// + +import javax.swing.JFrame; +import deadpixel.keystone.*; + +// Visualization may show 2D projection visualization, or not +boolean displayProjection2D = false; +//int projectorOffset = screenWidth; + +boolean testProjectorOnMac = false; + +// defines Keystone settings from xml file in parent folder +Keystone ks; + +// defines various drawing surfaces, all pre-calibrated, to project +CornerPinSurface surface; +PGraphics offscreen; +PImage projector; + +// New Application Window Parameters +PFrameI proj2D = null; // f defines window to open new applet in +projApplet applet; // applet acts as new set of setup() and draw() functions that operate in parallel + +// Run Anything Needed to have Projection mapping work +void initializeProjection2D() { + println("Projector Info: " + projectorWidth + ", " + projectorHeight + ", " + projectorOffset); + //toggleProjection(getButtonIndex(buttonNames[21])); +} + +public class PFrameI extends JFrame { + public PFrameI() { + setBounds(0, 0, projectorWidth, projectorHeight ); + setLocation(projectorOffset, 0); + applet = new projApplet(); + setResizable(false); + setUndecorated(true); + setAlwaysOnTop(true); + add(applet); + applet.init(); + show(); + setTitle("Projection2D"); + } +} + +public void showProjection2D() { + if (proj2D == null) { + proj2D = new PFrameI(); + } + proj2D.setVisible(true); +} + +public void closeProjection2D() { + proj2D.setVisible(false); +} + +public void resetProjection2D() { + initializeProjection2D(); + if (proj2D != null) { + proj2D.dispose(); + proj2D = new PFrameI(); + if (displayProjection2D) { + showProjection2D(); + } else { + closeProjection2D(); + } + } +} + +public class projApplet extends PApplet { + public void setup() { + // Keystone will only work with P3D or OPENGL renderers, + // since it relies on texture mapping to deform + size(projectorWidth, projectorHeight, P2D); + + ks = new Keystone(this);; + + reset(); + } + + public void reset() { + surface = ks.createCornerPinSurface(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT, 20); + offscreen = createGraphics(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT); + + try{ + ks.load(); + } catch(RuntimeException e){ + println("No Keystone.xml. Save one first if you want to load one."); + } + } + + public void draw() { + + // Convert the mouse coordinate into surface coordinates + // this will allow you to use mouse events inside the + // surface from your screen. + PVector surfaceMouse = surface.getTransformedMouse(); + + // most likely, you'll want a black background to minimize + // bleeding around your projection area + background(0); + + // Draw the scene, offscreen + renderCanvas(offscreen, 0); + surface.render(offscreen); + + } + + void renderCanvas(PGraphics p, int x_offset) { + // Draw the scene, offscreen + p.beginDraw(); + p.clear(); + p.translate(x_offset, 0); + p.image(projector, 0, 0); + p.endDraw(); + } + + void keyPressed() { + switch(key) { + case 'c': + // enter/leave calibration mode, where surfaces can be warped + // and moved + ks.toggleCalibration(); + break; + + case 'l': + // loads the saved layout + ks.load(); + break; + + case 's': + // saves the layout + ks.save(); + break; + + case '`': + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + break; + } + } +} + +void toggle2DProjection() { + if (System.getProperty("os.name").substring(0,3).equals("Mac")) { + testProjectorOnMac = !testProjectorOnMac; + println("Test on Mac = " + testProjectorOnMac); + println("Projection Mapping Currently not Supported for MacOS"); + } else { + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + } +} + + diff --git a/Processing/Misc/UrbanAutonomous/PeripheralVehicleStatus.java b/Processing/Misc/UrbanAutonomous/PeripheralVehicleStatus.java new file mode 100644 index 0000000..95e32c4 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/PeripheralVehicleStatus.java @@ -0,0 +1,18 @@ + +public enum PeripheralVehicleStatus { + STOP(1), + DEPARTURE(2), + TOHUB(3), + ARRIVAL(4); + + private final int id; + + private PeripheralVehicleStatus(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + +} \ No newline at end of file diff --git a/Processing/Misc/UrbanAutonomous/SimParam.java b/Processing/Misc/UrbanAutonomous/SimParam.java new file mode 100644 index 0000000..7c4abde --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/SimParam.java @@ -0,0 +1,78 @@ + +public class SimParam { + public int maxX; + public int maxY; + + //Vehicle + public int numberOfVehicle; + public int capacityOfVehicle; + //Congestion + public int[] totalCongestionLevel; + public int currentTotalCongestionLevel; + public int vehicleHistorySize; + //Time + public int currentTime; //0-14400 + public int currentTimeZone; + //Demand + public int[] demandSizeArray; + public int currentDemandSize; + public int demandInterval;// unit:min (=#ofstep/10) + public int demandLifetime;// unit:min + public boolean demandSizeCustom; + //Hub + public boolean hubEnable; + public int hubEffectiveLength; + public int hubDedicatedVehicleCapacity; + public int capacityOfPeripheralVehicle; + //Map + public int mapType;// 0:urban,1:Rural,2:custom + + public int usagerate; + + public SimParam() { + usagerate=100; + maxX =18; + maxY =22; + hubEnable=false; + demandSizeCustom = false; + mapType = 2; + currentTimeZone = 0; + currentTime = -1; + capacityOfVehicle = 4; + numberOfVehicle = 1; + currentDemandSize = 0; + //demandInterval = 10; + demandInterval = 1; + vehicleHistorySize = 30; + currentTotalCongestionLevel = 0; + totalCongestionLevel = new int[720]; + //demandSizeArray = new int[] { 5, 5, 5, 5, 5, 10, 20, 50, 50, 20, 10, 10, 20, 10, 20, 30, 50, 50, 50, 30, 20, 10, 10, 10 }; + demandSizeArray = new int[] { 1, 1, 1, 1, 1, 2, 4, 10, 10, 4, 2, 2, 4, 2, 4, 6, 10, 10, 10, 6, 4, 2, 2, 2 }; + demandLifetime = 10; + hubEffectiveLength = 15; + hubDedicatedVehicleCapacity = 50; + capacityOfPeripheralVehicle=10; + } + + public void init(){ + UrbanAutonomous.vehicleStack.vehicleGen(); + UrbanAutonomous.demandStack.init(); + UrbanAutonomous.hubStack.init(); + currentTime=0; + } + + public void update() { + currentTime++; + if (currentTime >= 14400) + currentTime = 0; + // unallocatedDemandSizeHistory + if (currentTime % 20 == 0){ + UrbanAutonomous.demandStack.unallocatedDemandSizeHistory[currentTime / 20] = UrbanAutonomous.demandStack.unallocatedDepartureList.size(); + //usagerate=UrbanAutonomous.demandStack.usageRateCal(); + } + currentTimeZone = currentTime / 600;// 600step = 1hour + if (!demandSizeCustom) + currentDemandSize = demandSizeArray[currentTimeZone]; + } + +} diff --git a/Processing/Misc/UrbanAutonomous/Status.java b/Processing/Misc/UrbanAutonomous/Status.java new file mode 100644 index 0000000..f7ead1a --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/Status.java @@ -0,0 +1,16 @@ + +public enum Status { + CONFIG(1), + RUN(2), + STOP(3); + + private final int id; + + private Status(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + } diff --git a/Processing/Misc/UrbanAutonomous/Tile.java b/Processing/Misc/UrbanAutonomous/Tile.java new file mode 100644 index 0000000..38eef2e --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/Tile.java @@ -0,0 +1,11 @@ + +public class Tile { + public float [] departureProbabilityArray; + public float [] arrivalProbabilityArray; + public TileType tileType; + Tile(float [] departure, float [] arrival,TileType _tileType) { + departureProbabilityArray = departure; + arrivalProbabilityArray = arrival; + tileType=_tileType; + } + } \ No newline at end of file diff --git a/Processing/Misc/UrbanAutonomous/TileType.java b/Processing/Misc/UrbanAutonomous/TileType.java new file mode 100644 index 0000000..5ff1274 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/TileType.java @@ -0,0 +1,20 @@ + +public enum TileType { + HW(1), + LW(2), + HR(3), + LR(4), + ROAD(5), + INTERSECTION(6), + NONE(7); + + private final int id; + + private TileType(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + } \ No newline at end of file diff --git a/Processing/Misc/UrbanAutonomous/UDP.java b/Processing/Misc/UrbanAutonomous/UDP.java new file mode 100644 index 0000000..5a68c9d --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/UDP.java @@ -0,0 +1,881 @@ +/** + * (./) UDP.java v0.2 06/01/26 + * (by) Douglas Edric Stanley & Cousot Stéphane + * (cc) some right reserved + * + * Part of the Processing Libraries project, for the Atelier Hypermedia, art + * school of Aix-en-Provence, and for the Processing community of course. + * - require Java version 1.4 or later - + * -> http://hypermedia.loeil.org/processing/ + * -> http://www.processing.org/ + * + * THIS LIBRARY IS RELEASED UNDER A CREATIVE COMMONS LICENSE BY. + * -> http://creativecommons.org/licenses/by/2.5/ + */ + + + +import java.net.*; +import java.io.*; +import java.lang.reflect.Method; +import java.lang.reflect.InvocationTargetException; +import java.util.Date; +import java.text.SimpleDateFormat; + +import processing.core.*; + +/** + * Create and manage unicast, broadcast or multicast socket to send and receive + * datagram packets over the network. + *

+ * The socket type is define at his initialyzation by the passed IP address. + * To reach a host (interface) within a network, you need to specified the kind + * of address: + *

    + *
  • An unicast address refer to a unique host within a subnet.
  • + *
  • A broadcast address allow you to call every host within a subnet. + *
  • + *
  • A multicast address allows to call a specific group of hosts within + * the subnet. A multicast group is specified by a IP address in the range + * 224.0.0.0 (reserved, should not be used) to + * 239.255.255.255 inclusive, and by a standard UDP port number. + *
    + * notes: the complete reference of special multicast addresses should be + * found in the latest available version of the "Assigned Numbers RFC" + *
  • + *
+ * A packet sent to a unicast or broadcast address is only delivered to the + * host identified by that address. To the contrary, when packet is send to a + * multicast address, all interfaces identified by that address receive the data + * . + *

+ * To perform actions on receive and/or timeout events, you must implement + * specific method(s) in your code. This method will be automatically called + * when the socket receive incoming data or a timeout event. By default, the + * "receive handler" is typically receive(byte[] data) but you can + * retrieve more informations about the datagram packet, see + * {@link UDP#setReceiveHandler(String name)} for more informations. In the same + * logic, the default "timeout handler" is explicitly timeout(). + *

+ * + * note: currently applets are not allowed to use multicast sockets + * + * + * @version 0.1 + * @author Cousot Stéphane - stef@ubaa.net + * @author Douglas Edric Stanley - http://www.abstractmachine.net/ + */ +public class UDP implements Runnable { + + + // the current unicast/multicast datagram socket + DatagramSocket ucSocket = null; + MulticastSocket mcSocket = null; + + boolean log = false; // enable/disable output log + boolean listen = false; // true, if the socket waits for packets + int timeout = 0; // reception timeout > 0=infinite timeout + int size = 65507; // the socket buffer size in bytes + InetAddress group = null; // the multicast's group address to join + + // the reception Thread > wait automatically for incoming datagram packets + // without blocking the current Thread. + Thread thread = null; + + // the parent object (could be an application, a componant, etc...) + Object owner = null; + + // the default "receive handler" and "timeout handler" methods name. + // these methods must be implemented (by the owner) to be called + // automatically when the socket receive incoming datas or a timeout event + String receiveHandler = "receive"; + String timeoutHandler = "timeout"; + + // the log "header" to be set for debugging. Because log is disable by + // default, this value is automatically replaced by the principal socket + // settings when a new instance of UDP is created. + String header = ""; + + ///////////////////////////////// fields /////////////////////////////// + + /** + * The default socket buffer length in bytes. + */ + public static final int BUFFER_SIZE = 65507; + + + ///////////////////////////// constructors //////////////////////////// + + /** + * Create a new datagram socket and binds it to an available port and every + * address on the local host machine. + * + * @param owner the target object to be call by the receive handler + */ + public UDP( Object owner ) { + this( owner, 0 ); + } + + /** + * Create a new datagram socket and binds it to the specified port on the + * local host machine. + *

+ * Pass zero as port number, will let the system choose an + * available port. + * + * @param owner the target object to be call by the receive handler + * @param port local port to bind + */ + public UDP( Object owner, int port ) { + this( owner, port, null ); + } + + /** + * Create a new datagram socket and binds it to the specified port on the + * specified local address or multicast group address. + *

+ * Pass zero as port number, will let the system choose an + * available port. The absence of an address, explicitly null + * as IP address will assign the socket to the Unspecified Address (Also + * called anylocal or wildcard address). To set up the socket as multicast + * socket, pass the group address to be joined. If this address is not a + * valid multicast address, a broadcast socket will be created by default. + * + * @param owner the target object to be call by the receive handler + * @param port local port to bind + * @param ip host address or group address + */ + public UDP( Object owner, int port, String ip ) { + + this.owner = owner; + + // register this object to the PApplet, + // if it's used with Processing + try { + if ( owner instanceof PApplet ) ((PApplet)owner).registerMethod("dispose", this); + } + catch( NoClassDefFoundError e ) {;} + + // open a new socket to the specified port/address + // and join the group if the multicast socket is required + try { + + InetAddress addr = InetAddress.getByName(ip); + InetAddress host = (ip==null) ? (InetAddress)null: addr; + + if ( !addr.isMulticastAddress() ) { + ucSocket = new DatagramSocket( port, host ); // as broadcast + log( "bound socket to host:"+address()+", port: "+port() ); + } + else { + mcSocket = new MulticastSocket( port ); // as multicast + mcSocket.joinGroup( addr ); + this.group = addr; + log( "bound multicast socket to host:"+address()+ + ", port: "+port()+", group:"+group ); + } + } + catch( IOException e ) { + // caught SocketException & UnknownHostException + error( "opening socket failed!"+ + "\n\t> address:"+ip+", port:"+port+" [group:"+group+"]"+ + "\n\t> "+e.getMessage() + ); + } + catch( IllegalArgumentException e ) { + error( "opening socket failed!"+ + "\n\t> bad arguments: "+e.getMessage() + ); + } + catch( SecurityException e ) { + error( (isMulticast()?"could not joined the group":"warning")+ + "\n\t> "+e.getMessage() ); + } + + } + + /////////////////////////////// methods /////////////////////////////// + + /** + * Close the socket. This method is automatically called by Processing when + * the PApplet shuts down. + * + * @see UDP#close() + */ + public void dispose() { + close(); + } + + /** + * Close the actuel datagram socket and all associate resources. + */ + public void close() { + if ( isClosed() ) return; + + int port = port(); + String ip = address(); + + // stop listening if needed + //listen( false ); + + // close the socket + try { + if ( isMulticast() ) { + if ( group!=null ) { + mcSocket.leaveGroup( group ); + log( "leave group < address:"+group+" >" ); + } + mcSocket.close(); + mcSocket = null; + } + else { + ucSocket.close(); + ucSocket = null; + } + } + catch( IOException e ) { + error( "Error while closing the socket!\n\t> " + e.getMessage() ); + } + catch( SecurityException e ) {;} + finally { + log( "close socket < port:"+port+", address:"+ip+" >\n" ); + } + } + + /** + * Returns whether the current socket is closed or not. + * @return boolean + **/ + public boolean isClosed() { + if ( isMulticast() ) return mcSocket==null ? true : mcSocket.isClosed(); + return ucSocket==null ? true : ucSocket.isClosed(); + } + + /** + * Return the actual socket's local port, or -1 if the socket is closed. + * @return int + */ + public int port() { + if ( isClosed() ) return -1; + return isMulticast()? mcSocket.getLocalPort() : ucSocket.getLocalPort(); + } + + /** + * Return the actual socket's local address, or null if the + * address correspond to any local address. + * + * @return String + */ + public String address() { + if ( isClosed() ) return null; + + InetAddress laddr = isMulticast() ? mcSocket.getLocalAddress(): + ucSocket.getLocalAddress(); + return laddr.isAnyLocalAddress() ? null : laddr.getHostAddress(); + } + + /** + * Send message to the current socket. Explicitly, send message to the + * multicast group/port or to itself. + * + * @param message the message to be send + * + * @see UDP#send(String message, String ip) + * @see UDP#send(String message, String ip, int port) + * + * @return boolean + */ + public boolean send( String message ) { + return send( message.getBytes() ); + } + + /** + * Send data to the current socket. Explicitly, send data to the multicast + * group/port or to itself. + * + * @param buffer data to be send + * + * @see UDP#send(byte[] data, String ip) + * @see UDP#send(byte[] data, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer ) { + // probably if the group could not be joined for a security reason + if ( isMulticast() && group==null ) return false; + + String ip = isMulticast() ? group.getHostAddress() : address(); + return send( buffer, ip, port() ); + } + + /** + * Send message to the requested IP address, to the current socket port. + * + * @param message the message to be send + * @param ip the destination host's IP address + * + * @see UDP#send(String message) + * @see UDP#send(String message, String ip, int port) + * + * @return boolean + */ + public boolean send( String message, String ip ) { + return send( message.getBytes(), ip ); + } + + /** + * Send data to the requested IP address, to the current socket port. + * + * @param buffer data to be send + * @param ip the destination host's IP address + * + * @see UDP#send(byte[] buffer) + * @see UDP#send(byte[] buffer, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer, String ip ) { + return send( buffer, ip, port() ); + } + + /** + * Send message to the requested IP address and port. + *

+ * A null IP address will assign the packet address to the + * local host. Use this method to send message to another application by + * passing null as the destination address. + * + * @param message the message to be send + * @param ip the destination host's IP address + * @param port the destination host's port + * + * @see UDP#send(String message) + * @see UDP#send(String message, String ip) + * + * @return boolean + */ + public boolean send( String message, String ip, int port ) { + return send( message.getBytes(), ip, port ); + } + + /** + * Send data to the requested IP address and port. + *

+ * A null IP address will assign the packet address to the + * local host. Use this method to send data to another application by + * passing null as the destination address. + * + * @param buffer data to be send + * @param ip the destination host's IP address + * @param port the destination host's port + * + * @see UDP#send(byte[] buffer, String ip) + * @see UDP#send(byte[] buffer, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer, String ip, int port ) { + + boolean success = false; + DatagramPacket pa = null; + + try { + + pa = new DatagramPacket( buffer, buffer.length, InetAddress.getByName(ip), port ); + + // send + if ( isMulticast() ) mcSocket.send( pa ); + else ucSocket.send( pa ); + + success = true; + log( "send packet -> address:"+pa.getAddress()+ + ", port:"+ pa.getPort() + + ", length: "+ pa.getLength() + ); + } + catch( IOException e ) { + error( "could not send message!"+ + "\t\n> port:"+port+ + ", ip:"+ip+ + ", buffer size: "+size+ + ", packet length: "+pa.getLength()+ + "\t\n> "+e.getMessage() + ); + } + finally{ return success; } + } + + /** + * Set the maximum size of the packet that can be sent or receive on the + * current socket. This value must be greater than 0, otherwise the buffer + * size is set to the his default value. + *

+ * return true if the new buffer value have been correctly set, + * false otherwise. + *

+ * note : this method has no effect if the socket is listening. To define + * a new buffer size, call this method before implementing a new buffer in + * memory. Explicitly before calling a receive methods. + * + * @param size the buffer size value in bytes or n<=0 + * @return boolean + * @see UDP#getBuffer() + */ + public boolean setBuffer( int size ) { + boolean done = false; + + // do nothing if listening (block the thread otherwise) + if ( isListening() ) return done; + + try { + // set the SO_SNDBUF and SO_RCVBUF value + if ( isMulticast() ) { + mcSocket.setSendBufferSize( size>0 ? size : BUFFER_SIZE ); + mcSocket.setReceiveBufferSize( size>0 ? size : BUFFER_SIZE ); + } + else { + ucSocket.setSendBufferSize( size>0 ? size : BUFFER_SIZE ); + ucSocket.setReceiveBufferSize( size>0 ? size : BUFFER_SIZE ); + } + // set the current buffer size + this.size = size>0 ? size : BUFFER_SIZE; + done = true; + } + catch( SocketException e ) { + error( "could not set the buffer!"+ + "\n> "+e.getMessage() + ); + } + finally{ return done; } + } + + /** + * Return the actual socket buffer length + * @return int + * @see UDP#setBuffer(int size) + */ + public int getBuffer() { + return size; + } + + /** + * Returns whether the socket wait for incoming data or not. + * @return boolean + */ + public boolean isListening() { + return listen; + } + + + /** + * Start/stop waiting constantly for incoming data. + * + * @param on the required listening status. + * + * @see UDP#listen() + * @see UDP#listen(int millis) + * @see UDP#setReceiveHandler(String name) + */ + public void listen( boolean on ) { + + listen = on; + timeout = 0; + + // start + if ( on && thread==null && !isClosed() ) { + thread = new Thread( this ); + thread.start(); + } + // stop + if ( !on && thread!=null ) { + send( new byte[0] ); // unblock the thread with a dummy message + thread.interrupt(); + thread = null; + } + } + + /** + * Set the socket reception timeout and wait one time for incoming data. + * If the timeout period occured, the owner timeout() method is + * automatically called. + * + * @param millis the required timeout value in milliseconds. + * + * @see UDP#listen() + * @see UDP#listen(boolean on) + */ + public void listen( int millis ) { + if ( isClosed() ) return; + + listen = true; + timeout = millis; + + // unblock the thread with a dummy message, if already listening + if ( thread!=null ) send( new byte[0] ); + if ( thread==null ) { + thread = new Thread( this ); + thread.start(); + } + } + + /** + * Wait for incoming data, and call the appropriate handlers each time a + * message is received. If the owner's class own the appropriate target + * handler, this method send it the receive message as byte[], the sender + * IP address and port. + *

+ * This method force the current Thread to be ceased for a + * temporary period. If you prefer listening without blocking the current + * thread, use the {@link UDP#listen(int millis)} or + * {@link UDP#listen(boolean on)} method instead. + * + * @see UDP#listen() + * @see UDP#listen(boolean on) + * @see UDP#setReceiveHandler(String name) + */ + public void listen() { + try { + + byte[] buffer = new byte[ size ]; + DatagramPacket pa = new DatagramPacket(buffer,buffer.length); + + // wait + if ( isMulticast() ) { + mcSocket.setSoTimeout( timeout ); + mcSocket.receive( pa ); // <-- block the Thread + } + else { + ucSocket.setSoTimeout( timeout ); + ucSocket.receive( pa ); // <-- block + } + + + log( "receive packet <- from "+pa.getAddress()+ + ", port:"+ pa.getPort() + + ", length: "+ pa.getLength() + ); + + + // get the required data only (not all the buffer) + // and send it to the appropriate target handler, if needed + if ( pa.getLength()!=0 ) { + + byte[] data = new byte[ pa.getLength() ]; + System.arraycopy( pa.getData(), 0, data, 0, data.length ); + + try { + // try with one argument first > byte[] + callReceiveHandler( data ); + } + catch( NoSuchMethodException e ) { + // try with many argument > byte[], String, int + callReceiveHandler( data, + pa.getAddress().getHostAddress(), + pa.getPort() + ); + } + } + } + catch( NullPointerException e ) { + // *socket=null from the close() method; + listen = false; + thread = null; + } + catch( IOException e ) { + + listen = false; + thread = null; + + if ( e instanceof SocketTimeoutException ) callTimeoutHandler(); + else { + // do not print "Socket closed" error + // if the method close() has been called + if ( ucSocket!=null && mcSocket!=null ) + error( "listen failed!\n\t> "+e.getMessage() ); + } + } + } + + /** + * Wait for incoming datagram packets. This method is called automaticlly, + * you do not need to call it. + */ + public void run() { + while ( listen ) listen(); + } + + /** + * Register the target's receive handler. + *

+ * By default, this method name is "receive" with one argument + * representing the received data as byte[]. For more + * flexibility, you can change this method with another useful method by + * passing his name. You could get more informations by implementing two + * additional arguments, a String representing the sender IP + * address and a int representing the sender port : + *

+	 * void myCustomReceiveHandler(byte[] message, String ip, int port) {
+	 *	// do something here...
+	 * }
+	 * 
+ * + * @param name the receive handler name + * @see UDP#setTimeoutHandler(String name) + */ + public void setReceiveHandler( String name ) { + this.receiveHandler = name; + } + + /** + * Call the default receive target handler method. + * + * @param data the data to be passed + * @throws NoSuchMethodException + */ + private void callReceiveHandler( byte[] data ) + throws NoSuchMethodException { + + Class[] types; // arguments class types + Object[] values; // arguments values + Method method; + + try { + types = new Class[]{ data.getClass() }; + values = new Object[]{ data }; + method = owner.getClass().getMethod(receiveHandler, types); + method.invoke( owner, values ); + } + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Call the receive target handler implemented with the optional arguments. + * + * @param data the data to be passed + * @param ip the IP adress to be passed + * @param port the port number to be passed + */ + private void callReceiveHandler( byte[] data, String ip, int port ) { + + Class[] types; // arguments class types + Object[] values; // arguments values + Method method; + + try { + types = new Class[]{ data.getClass(), + ip.getClass(), + Integer.TYPE + }; + values = new Object[]{ data, + ip, + new Integer(port) + }; + method = owner.getClass().getMethod(receiveHandler, types); + method.invoke( owner, values ); + } + catch( NoSuchMethodException e ) {;} + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Register the target's timeout handler. By default, this method name is + * "timeout" with no argument. + * + * @param name the timeout handler name + * @see UDP#setReceiveHandler(String name) + */ + public void setTimeoutHandler( String name ) { + this.timeoutHandler = name; + } + + /** + * Call the timeout target method when the socket received a timeout event. + * The method name to be implemented in your code is timeout(). + */ + private void callTimeoutHandler() { + try { + Method m = owner.getClass().getDeclaredMethod(timeoutHandler, null); + m.invoke( owner, null ); + } + catch( NoSuchMethodException e ) {;} + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Returns whether the opened datagram socket is a multicast socket or not. + * @return boolean + */ + public boolean isMulticast() { + return ( mcSocket!=null ); + } + + /** + * Returns whether the multicast socket is joined to a group address. + * @return boolean + */ + public boolean isJoined() { + return ( group!=null ); + } + + /** + * Returns whether the opened socket send broadcast message socket or not. + * @return boolean + */ + public boolean isBroadcast() { + boolean result = false; + try { + result = (ucSocket==null) ? false : ucSocket.getBroadcast(); + } + catch( SocketException e ) { error( e.getMessage() ); } + finally { return result; } + } + + /** + * Enables or disables the ability of the current process to send broadcast + * messages. + * @return boolean + */ + public boolean broadcast( boolean on ) { + boolean done = false; + try { + if ( ucSocket!=null ) { + ucSocket.setBroadcast( on ); + done = isBroadcast(); + } + } + catch( SocketException e ) { error( e.getMessage() ); } + finally { return done; } + } + + /** + * Enable or disable the multicast socket loopback mode. By default loopback + * is enable. + *
+ * Setting loopback to false means this multicast socket does not want to + * receive the data that it sends to the multicast group. + * + * @param on local loopback of multicast datagrams + */ + public void loopback( boolean on ) { + try { + if ( isMulticast() ) mcSocket.setLoopbackMode( !on ); + } + catch( SocketException e ) { + error( "could not set the loopback mode!\n\t>"+e.getMessage() ); + } + } + + /** + * Returns whether the multicast socket loopback mode is enable or not. + * @return boolean + */ + public boolean isLoopback() { + try { + if ( isMulticast() && !isClosed() ) + return !mcSocket.getLoopbackMode(); + } + catch( SocketException e ) { + error( "could not get the loopback mode!\n\t> "+e.getMessage() ); + } + return false; + } + + /** + * Control the life-time of a datagram in the network for multicast packets + * in order to indicates the scope of the multicasts (ie how far the packet + * will travel). + *

+ * The TTL value must be in range of 0 to 255 inclusive. The larger the + * number, the farther the multicast packets will travel (by convention): + *

+	 * 0	-> restricted to the same host
+	 * 1	-> restricted to the same subnet (default)
+	 * <32	-> restricted to the same site
+	 * <64	-> restricted to the same region
+	 * <128	-> restricted to the same continent
+	 * <255	-> no restriction
+	 * 
+ * The default value is 1, meaning that the datagram will not go beyond the + * local subnet. + *

+ * return true if no error occured. + * + * @param ttl the "Time to Live" value + * @return boolean + * @see UDP#getTimeToLive() + */ + public boolean setTimeToLive( int ttl ) { + try { + if ( isMulticast() && !isClosed() ) mcSocket.setTimeToLive( ttl ); + return true; + } + catch( IOException e ) { + error( "setting the default \"Time to Live\" value failed!"+ + "\n\t> "+e.getMessage() ); + } + catch( IllegalArgumentException e ) { + error( "\"Time to Live\" value must be in the range of 0-255" ); + } + return false; + } + + /** + * Return the "Time to Live" value or -1 if an error occurred (or if + * the current socket is not a multicast socket). + * + * @return int + * @see UDP#setTimeToLive(int ttl) + */ + public int getTimeToLive() { + try { + if ( isMulticast() && !isClosed() ) + return mcSocket.getTimeToLive(); + } + catch( IOException e ) { + error( "could not retrieve the current time-to-live value!"+ + "\n\t> "+ e.getMessage() ); + } + return -1; + } + + /** + * Enable or disable output process log. + */ + public void log( boolean on ) { + log = on; + } + + /** + * Output message to the standard output stream. + * @param out the output message + */ + private void log( String out ) { + + Date date = new Date(); + + // define the "header" to retrieve at least the principal socket + // informations : the host/port where the socket is bound. + if ( !log && header.equals("") ) + header = "-- UDP session started at "+date+" --\n-- "+out+" --\n"; + + // print out + if ( log ) { + + String pattern = "yy-MM-dd HH:mm:ss.S Z"; + String sdf = new SimpleDateFormat(pattern).format( date ); + System.out.println( header+"["+sdf+"] "+out ); + header = ""; // forget header + } + } + + /** + * Output error messages to the standard error stream. + * @param err the error string + */ + private void error( String err ) { + System.err.println( err ); + } +} diff --git a/Processing/Misc/UrbanAutonomous/UDP.pde b/Processing/Misc/UrbanAutonomous/UDP.pde new file mode 100644 index 0000000..972690d --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/UDP.pde @@ -0,0 +1,98 @@ +// Principally, this script ensures that a string is "caught" via UDP and coded into principal inputs of: +// - tablePieceInput[][] or tablePieceInput[][][2] (rotation) +// - UMax, VMax + + +int portIN = 6152; + +import hypermedia.net.*; +UDP udp; // define the UDP object + +boolean busyImporting = false; +boolean viaUDP = true; +boolean changeDetected = false; +boolean outputReady = false; + +void initUDP() { + if (viaUDP) { + udp = new UDP( this, portIN ); + //udp.log( true ); // <-- printout the connection activity + udp.listen( true ); + } +} + +void ImportData(String inputStr[]) { + if (inputStr[0].equals("COLORTIZER")) { + parseColortizerStrings(inputStr); + } + busyImporting = false; +} + +void parseColortizerStrings(String data[]) { + + for (int i=0 ; i 1tile 33.3m -> 2.128km-square +//1tile/0.1min +//1 simulation sec = 0.1min -> 10sec = 1min, 600sec(10min)=60min(1h) 240min(4h)=24h +//0.1 simulation sec = 0.1min ->1min=1h 24min = 24h +//1step =0.1min , 10step 1min , 600step 1h, 14400step =24h +//start time 00:00~24:00, 0:00->0step[0.1min](currentTime), 24:00-> 14400step[0.1min](currentTime) + +//View +//AllocatedDepartureDemand:pink +//unallocatedDepartureDemand:red +//AllocatedArrivalDemand:light blue +//unallocatedArrivalDemand:blue + + +int projectorWidth = 1920; +int projectorHeight = 1200; +int projectorOffset = 1842; + +int screenWidth = 1842; +int screenHeight = 1026; + +public static int displayU = 18; +public static int displayV = 22; + +int IDMax = 15; + +// Table Canvas Width and Height +int TABLE_IMAGE_HEIGHT = 1000; +int TABLE_IMAGE_WIDTH = 1000; + +// Arrays that holds ID information of rectilinear tile arrangement. +public static int tablePieceInput[][][] = new int[displayU][displayV][2]; + + +public static DragStatus dragStatus; +public static OperationWindow opw; +public static Status status; +public static PImage hwImg, lwImg, hrImg, lrImg, roadImg, intersectionImg, noneImg, backgroundImg, congestionImg,sideDisplayImg; +public static Tile[][] simCoordinate; +public static int vehicleColor; +public static int allocatedDepartureColor; +public static int unallocatedDepartureColor; +public static int allocatedArrivalColor; +public static int unallocatedArrivalColor; +public static int hubColor; +public static int hubVehicleColor; +public static int hubPeripheralVehicleColor; +public static int hubEffectiveLengthColor; +public static PGraphics legendPg, demandPg; +public static int brushNumber; + + // Temporary + public static SimParam simParam; + public static MapBlock mapBlock; + public static BasicTile basicTile; + public static MapBlockBrushs mapBlockBrushs; + public static MapBlockStack mapBlockStack; + public static Disp disp; + public static DemandStack demandStack; + public static VehicleStack vehicleStack; + // public static OperationDisp operationDisp; + public static FileControl fileControl; + // public static Hub hubA, hubB; + public static HubStack hubStack; + // public static HubVehicle hubVehicle; + public static UDPSocket udpSocket; + + PGraphics captionG,mainG; + + public void setup() { + mainG=createGraphics(1000,1200); + + //size(screenWidth, screenHeight, P3D); + + // Initial Projection-Mapping Canvas + initializeProjection2D(); + + // Allows application to receive information from Colortizer via UDP + initUDP(); + + + // SimulationWindow + size(1000, 1000); + + // OperationWindow + //new PFrame(1000, 0, 1900, 875); + new PFrame(0, 0, 1842, 1026); + + // Status + status = Status.CONFIG; + dragStatus = DragStatus.NORMAL; + + // Load Image + loadTileImage(); + //backgroundImg = loadImage("operationWindow.jpg"); + backgroundImg = loadImage("operationWindow.png"); + sideDisplayImg = loadImage("sideDisplay.jpg"); + + // Legend Symbol + //vehicleColor = color(255, 128, 0, 255); + vehicleColor = color(255, 255, 255, 255); + allocatedDepartureColor = color(0, 128, 0, 255); + unallocatedDepartureColor = color(0, 128, 0, 255); + allocatedArrivalColor = color(0, 0, 255, 255); + unallocatedArrivalColor = color(0, 0, 255, 255); + //allocatedDepartureColor = color(0, 255, 127, 127); + //unallocatedDepartureColor = color(0, 128, 0, 127); + //allocatedArrivalColor = color(0, 255, 255, 127); + //unallocatedArrivalColor = color(0, 0, 255, 127); + hubColor = color(0, 255, 0, 200); + hubEffectiveLengthColor = color(0, 255, 0, 64); + hubVehicleColor = color(142, 0, 204, 200); + hubPeripheralVehicleColor = color(200, 255, 200, 200); + + // Temporary + simParam = new SimParam(); + udpSocket = new UDPSocket(this); + + hubStack = new HubStack(this); + + brushNumber = 0; + basicTile = new BasicTile(); + mapBlockBrushs = new MapBlockBrushs(this, 5); + mapBlockStack = new MapBlockStack(this); + //disp = new Disp(this); + disp = new Disp(mainG,this); + demandStack = new DemandStack(); + simCoordinate = new Tile[UrbanAutonomous.simParam.maxX*5][UrbanAutonomous.simParam.maxY*5]; + vehicleStack = new VehicleStack(); + + //mapBlockStack.loadRuralMap(); + + mapBlockStack.updateCoordinate();// reflect change of mapblock to demand + // generation + mapBlockStack.mapImgCreation();// map image creation for display + mapBlockBrushs.brushImgCreation();// brush image creation for operation + // display + legendSymbolImgCreation(); // create legend symbol image for operation + // display + demandGenerationImgCreation(); // create demand image for operation + // display + fileControl = new FileControl(); + } + + public void draw() { + if(simParam.mapType==2){ //custom map + mapBlockStack.customMapGen(); + mapBlockStack.updateCoordinate();// reflect change of mapblock to // // // demand // generation + mapBlockStack.mapImgCreation();// map image creation for display + } + // Exports table Graphic to Projector + projector = get(0, 0, TABLE_IMAGE_WIDTH, TABLE_IMAGE_HEIGHT); + + simParam.update(); + + demandStack.demandLifetimeControl(); + demandStack.demandGen(simParam.currentDemandSize, simParam.demandInterval * 10);// numberOfDemand,DemandGenerationInterval(steps) + demandStack.demandAllocation(); + demandStack.demandHubAllocation(); + vehicleStack.allVehicleMovement(); + simParam.usagerate=UrbanAutonomous.demandStack.usageRateCal(); + + hubStack.hubVehicleA.move(); + hubStack.hubPeripheralVehicleA.move(); + hubStack.hubPeripheralVehicleB.move(); + + // Display + disp.show(); + + //image(mainG,180,0,725,725); + image(mainG,180,0,905,1090); + image(sideDisplayImg,0,0,180,1000); + //image(mainG,0,0,1000,1200); + } + + void loadTileImage() { + hwImg = loadImage("hwTile.png"); + lwImg = loadImage("lwTile.png"); + hrImg = loadImage("hrTile.png"); + lrImg = loadImage("lrTile.png"); + roadImg = loadImage("roadTile.png"); + intersectionImg = loadImage("intersectionTile.png"); + noneImg = loadImage("noneTile.png"); + congestionImg = loadImage("congestion.png"); + } + + void keyPressed() { + switch(key) { + case '`': // "Enable Projection (`)" + toggle2DProjection(); + break; + } + } + public void mousePressed() { + int x = (int) (mouseX / 50); + int y = (int) (mouseY / 50); + + if (simParam.mapType == 2) { + mapBlockStack.mapBlockArray[x][y] = mapBlockBrushs.selectedBrush; + fileControl.customMap[UrbanAutonomous.simParam.maxX * y + x] = brushNumber; + mapBlockStack.updateCoordinate();// reflect change of mapblock to // // // demand // generation + mapBlockStack.mapImgCreation();// map image creation for display + } + // Hub Relocation + hubRelocation(); + } + + void hubRelocation() { + if (dist(hubStack.hubA.x * 10, hubStack.hubA.y * 10, mouseX, mouseY) < 20) { + dragStatus = DragStatus.HUBA; + } else if (dist(hubStack.hubB.x * 10, hubStack.hubB.y * 10, mouseX, mouseY) < 20) { + dragStatus = DragStatus.HUBB; + } + } + + public void mouseReleased() { + if (dragStatus == DragStatus.HUBA) { + hubStack.ax = modifyHubPoint(mouseX); + hubStack.ay = modifyHubPoint(mouseY); + hubStack.init(); + } else if (dragStatus == DragStatus.HUBB) { + hubStack.bx = modifyHubPoint(mouseX); + hubStack.by = modifyHubPoint(mouseY); + hubStack.init(); + } + dragStatus = DragStatus.NORMAL; + } + + int modifyHubPoint(int x) { + int result = 0; + result = x / 10 / 5 * 5 + 2; + return result; + } + + void legendSymbolImgCreation() { + int offset = 0; + legendPg = createGraphics(20, 180); + legendPg.beginDraw(); + legendPg.background(255); + legendPg.stroke(255); + legendPg.stroke(1); + + // LandUse + legendPg.image(hwImg, offset, 0, 20, 20); + legendPg.image(lwImg, offset, 20, 20, 20); + legendPg.image(hrImg, offset, 40, 20, 20); + legendPg.image(lrImg, offset, 60, 20, 20); + + legendPg.ellipseMode(CENTER); + // allocated departure + legendPg.fill(allocatedDepartureColor); + legendPg.ellipse(offset + 10, 90, 10, 10); + // unallocated departure + legendPg.fill(unallocatedDepartureColor); + legendPg.ellipse(offset + 10, 110, 10, 10); + // allocated arrival + legendPg.fill(allocatedArrivalColor); + legendPg.ellipse(offset + 10, 130, 10, 10); + // unallocated arrival + legendPg.fill(unallocatedArrivalColor); + legendPg.ellipse(offset + 10, 150, 10, 10); + // Vehicle(fleet) + legendPg.fill(vehicleColor); + legendPg.ellipse(offset + 10, 170, 10, 10); + legendPg.endDraw(); + } + + void demandGenerationImgCreation() { + int offset = 150; + demandPg = createGraphics(870, 260); + demandPg.beginDraw(); + // demandPg.background(255); + demandPg.clear(); + demandPg.stroke(255); + demandPg.stroke(1); + demandPg.image(hwImg, 0, 0, 50, 50); + demandPg.image(lwImg, 0, 70, 50, 50); + demandPg.image(hrImg, 0, 140, 50, 50); + demandPg.image(lrImg, 0, 210, 50, 50); + + for (int i = 0; i < 720; i++) { + demandPg.line(offset + i, 20 - (basicTile.hwTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 20); + demandPg.line(offset + i, 50 - (basicTile.hwTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 50); + demandPg.line(offset + i, 90 - (basicTile.lwTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 90); + demandPg.line(offset + i, 120 - (basicTile.lwTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 120); + demandPg.line(offset + i, 160 - (basicTile.hrTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 160); + demandPg.line(offset + i, 190 - (basicTile.hrTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 190); + demandPg.line(offset + i, 230 - (basicTile.lrTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 230); + demandPg.line(offset + i, 260 - (basicTile.lrTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 260); + } + demandPg.endDraw(); + } + diff --git a/Processing/Misc/UrbanAutonomous/Vehicle.java b/Processing/Misc/UrbanAutonomous/Vehicle.java new file mode 100644 index 0000000..e45f7ac --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/Vehicle.java @@ -0,0 +1,141 @@ + +import java.util.ArrayList; + + +import processing.core.PApplet; + +public class Vehicle extends PApplet{ + public int x; + public int y; + public int streetNumber; + public boolean isHorizontalStreet; + public boolean isIntersection; + public ArrayList departureList; + public ArrayList arrivalList; + public ArrayList movingHistoryList; + + Vehicle(int _x, int _y, boolean _isHorizontalStreet, boolean _isIntersection) { + x=_x; + y=_y; + isHorizontalStreet=_isHorizontalStreet; + isIntersection=_isIntersection; + departureList = new ArrayList (); + arrivalList = new ArrayList (); + movingHistoryList = new ArrayList (); + } + + //Parameter Update + void paramUpdate() { + isHorizontalStreet=false; + isIntersection=false; + streetNumber=0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet=true; + streetNumber=((y+5-2)/5)-1; + } else { + streetNumber=((x+5-2)/5)-1; + } + if (isVerticalStreetCheck()&&isHorizontalStreetCheck()) + isIntersection=true; + } + + boolean isHorizontalStreetCheck() { + boolean result=false; + if ((y-2+5)%5==0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result=false; + if ((x-2+5)%5==0) + result = true; + return result; + } + + //Vehicle Movement + void move() { + paramUpdate(); + movingHistoryUpdate(); + if (departureList.size()>0 || arrivalList.size()>0) { + if (departureList.size()>0) { + eachMove(departureList); + } else { + eachMove(arrivalList); + } + } + } + + void movingHistoryUpdate() { + Demand tmpVehiclePosition=new Demand(x, y); + if (!(departureList.size()==0&&arrivalList.size()==0)) + movingHistoryList.add(tmpVehiclePosition); + if (departureList.size()==0&&arrivalList.size()==0&&movingHistoryList.size()>0) + movingHistoryList.remove(0); + if (movingHistoryList.size()>=UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + } + + void eachMove(ArrayList tmpList) { + if (isSamePoint(tmpList.get(0))) { + tmpList.remove(0); + } else if (isSameStreet(tmpList.get(0))) { + if (tmpList.get(0).isHorizontalStreet) + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + else + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + } else { + if (isIntersection) { + if (tmpList.get(0).isHorizontalStreet) + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + else + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + } else { + if (isHorizontalStreet) { + if (tmpList.get(0).isHorizontalStreet) { + if (x>77) { + x-=1; + } else { + x+=1; + } + } else { + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + } + } else { + if (tmpList.get(0).isHorizontalStreet) { + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + } else { + if (y>77) { + y-=1; + } else { + y+=1; + } + } + } + } + } + } + + boolean isSameStreet(Demand tmpDemand) { + boolean result=false; + if (tmpDemand.streetNumber==streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result=true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y-2+5)/5)-1)==tmpDemand.streetNumber) + result=true; + } else { + if ((((x-2+5)/5)-1)==tmpDemand.streetNumber) + result=true; + } + } + return result; + } + + boolean isSamePoint(Demand tmpDemand) { + boolean result=false; + if (tmpDemand.x==x && tmpDemand.y == y) + result=true; + return result; + } + } diff --git a/Processing/Misc/UrbanAutonomous/VehicleStack.java b/Processing/Misc/UrbanAutonomous/VehicleStack.java new file mode 100644 index 0000000..4d6deaf --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/VehicleStack.java @@ -0,0 +1,60 @@ + +import java.util.ArrayList; + + +import processing.core.PApplet; + +public class VehicleStack extends PApplet{ + public ArrayList vehicleList; + public boolean isHorizontalStreet; + public VehicleStack() { + vehicleGen(); + isHorizontalStreet =true; + } + public void vehicleGen() { + vehicleList = new ArrayList (); + for (int i=0; i unallocatedArrivalList; + public ArrayList unallocatedDepartureList; + public ArrayList unallocatedHubArrivalList; + public ArrayList unallocatedHubDepartureList; + boolean isHorizontalStreet; + public int[] unallocatedDemandSizeHistory; + public int missedDemand; + public int[] missedDemandHistory; + + public DemandStack() { + missedDemand = 0; + missedDemandHistory = new int[720]; + unallocatedArrivalList = new ArrayList(); + unallocatedDepartureList = new ArrayList(); + unallocatedHubArrivalList = new ArrayList(); + unallocatedHubDepartureList = new ArrayList(); + isHorizontalStreet = true; + unallocatedDemandSizeHistory = new int[720]; + for (int i = 0; i < 720; i++) + unallocatedDemandSizeHistory[i] = 0; + } + + public void init() { + missedDemand = 0; + missedDemandHistory = new int[720]; + unallocatedArrivalList = new ArrayList(); + unallocatedDepartureList = new ArrayList(); + unallocatedHubArrivalList = new ArrayList(); + unallocatedHubDepartureList = new ArrayList(); + isHorizontalStreet = true; + unallocatedDemandSizeHistory = new int[720]; + for (int i = 0; i < 720; i++) + unallocatedDemandSizeHistory[i] = 0; + } + + // Demand Generation + public void demandGen(int _numberOfDemand, int _updateInterval) { + //java.lang.System.out.println("test"); + if (UrbanAutonomous.simParam.currentTime % _updateInterval == 0) { + for (int i = 0; i < _numberOfDemand; i++) { + isHorizontalStreet = !isHorizontalStreet; + Demand tmpArrivalDemand = demandCreation(false); + Demand tmpDepartureDemand = demandCreation(true); + // Demand Clarification + if (UrbanAutonomous.simParam.hubEnable) { + if (isHubEffective(tmpArrivalDemand, tmpDepartureDemand)) { + unallocatedHubArrivalList.add(tmpArrivalDemand); + unallocatedHubDepartureList.add(tmpDepartureDemand);// departureDemand + } else{ + } + } + else { + unallocatedArrivalList.add(tmpArrivalDemand); + unallocatedDepartureList.add(tmpDepartureDemand);// departureDemand + } + } + } + } + + // DemandCreation + Demand demandCreation(boolean isDepartureDemand) { + while (true) { + Demand demandCandidate = demandCandidateGen(isHorizontalStreet, isDepartureDemand); + if (probabilityCheck(demandCandidate)) { + return demandCandidate; + } + } + } + + // Demand Candidate Generation + Demand demandCandidateGen(boolean isHorizontalStreet, boolean isDepartureDemand) { + Demand _demandCandidate; + if (isHorizontalStreet) { + int streetNumber = (int) random(UrbanAutonomous.simParam.maxY); + int y = streetNumber * 5 + 2; + int x = (int) random(5*UrbanAutonomous.simParam.maxX); + _demandCandidate = new Demand(x, y, streetNumber, isHorizontalStreet, isDepartureDemand); + } else { + int streetNumber = (int) random(UrbanAutonomous.simParam.maxX); + int x = streetNumber * 5 + 2; + int y = (int) random(5*UrbanAutonomous.simParam.maxY); + _demandCandidate = new Demand(x, y, streetNumber, isHorizontalStreet, isDepartureDemand); + } + return _demandCandidate; + } + + // probability check + boolean probabilityCheck(Demand _demandCandidate) { + boolean determination = false; + float sum = 0; + float avgProbability; + if (_demandCandidate.isDepartureDemand) { + if (_demandCandidate.isHorizontalStreet) { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 2].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 1].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 1].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 2].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } else { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x + - 2][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + - 1][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 1][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 2][_demandCandidate.y].departureProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } + } else { + if (_demandCandidate.isHorizontalStreet) { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 2].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + - 1].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 1].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x][_demandCandidate.y + + 2].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } else { + sum = UrbanAutonomous.simCoordinate[_demandCandidate.x + - 2][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + - 1][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 1][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone] + + UrbanAutonomous.simCoordinate[_demandCandidate.x + + 2][_demandCandidate.y].arrivalProbabilityArray[UrbanAutonomous.simParam.currentTimeZone]; + } + } + if (sum != 0) { + avgProbability = sum * 100 / 4; + if ((int) random(1 / (avgProbability / 100)) == 0) + determination = true; + } + return determination; + } + + // DemandAllocation for Hub + public void demandHubAllocation() { + if (unallocatedHubListIsNotEmpty()) { + if (UrbanAutonomous.hubStack.hubPeripheralVehicleA.status == PeripheralVehicleStatus.STOP) { + for (int i = 0; i < unallocatedHubDepartureList.size(); i++) { + if (fromHubAtoB(unallocatedHubArrivalList.get(i), unallocatedHubDepartureList.get(i))) { + UrbanAutonomous.hubStack.hubPeripheralVehicleA.status = PeripheralVehicleStatus.DEPARTURE; + UrbanAutonomous.hubStack.hubPeripheralVehicleA.departureList + .add(unallocatedHubDepartureList.remove(i)); + UrbanAutonomous.hubStack.hubPeripheralVehicleA.reserveArrivalList + .add(unallocatedHubArrivalList.remove(i)); + } + } + } + if (UrbanAutonomous.hubStack.hubPeripheralVehicleB.status == PeripheralVehicleStatus.STOP) { + for (int i = 0; i < unallocatedHubDepartureList.size(); i++) { + if (fromHubBtoA(unallocatedHubArrivalList.get(i), unallocatedHubDepartureList.get(i))) { + UrbanAutonomous.hubStack.hubPeripheralVehicleB.status = PeripheralVehicleStatus.DEPARTURE; + UrbanAutonomous.hubStack.hubPeripheralVehicleB.departureList + .add(unallocatedHubDepartureList.remove(i)); + UrbanAutonomous.hubStack.hubPeripheralVehicleB.reserveArrivalList + .add(unallocatedHubArrivalList.remove(i)); + } + } + } + } + } + + boolean hubPeripheralVehicleIsEmpty(HubPeripheralVehicle v) { + boolean result = false; + if (v.arrivalList.size() == 0 && v.departureList.size() == 0 && v.reserveArrivalList.size() == 0) + result = true; + return result; + } + + boolean unallocatedHubListIsNotEmpty() { + boolean result = false; + if (unallocatedHubDepartureList.size() > 0 || unallocatedHubArrivalList.size() > 0) { + result = true; + } + return result; + } + //usage rate + public int usageRateCal(){ + int result=10; + int totalVehicle=UrbanAutonomous.simParam.numberOfVehicle; + int usingVehicle=0; + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + if(vehicle.departureList.size()==0&&vehicle.arrivalList.size()==0) + ; + else{ + usingVehicle++; + } + } + result = 100* usingVehicle/totalVehicle; + + if(result==0) + result=100; + + if(result<50){ + if(UrbanAutonomous.simParam.numberOfVehicle>1){ + //UrbanAutonomous.vehicleStack.vehicleList.remove(UrbanAutonomous.vehicleStack.vehicleList.size()-1); + int tmp=UrbanAutonomous.simParam.numberOfVehicle/3; + if(tmp>0) + UrbanAutonomous.simParam.numberOfVehicle=tmp; + else{ + UrbanAutonomous.simParam.numberOfVehicle=1; + } + + UrbanAutonomous.vehicleStack.vehicleGen(); + } + } + + return result; + + } + + // DemandAllocation except hub + public void demandAllocation() { + if (unallocatedDepartureList.size() > 0 || unallocatedArrivalList.size() > 0) { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + if (vehicle.arrivalList.size() == 0 && vehicle.departureList.size() == 0) { + while (vehicle.arrivalList.size() < UrbanAutonomous.simParam.capacityOfVehicle + && vehicle.departureList.size() < UrbanAutonomous.simParam.capacityOfVehicle) { + if (unallocatedDepartureList.size() > 0 || unallocatedArrivalList.size() > 0) { + vehicle.arrivalList.add(unallocatedArrivalList.get(0)); + vehicle.departureList.add(unallocatedDepartureList.get(0)); + unallocatedArrivalList.remove(0); + unallocatedDepartureList.remove(0); + } else { + break; + } + } + } + } + } + } + + // Hub effectiveCheck + boolean isHubEffective(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // fromHubA to fromHubB + boolean fromHubBtoA(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // fromHubA to fromHubB + boolean fromHubAtoB(Demand arrivalDemand, Demand departureDemand) { + boolean result = false; + if (arrivalDemand.x > UrbanAutonomous.hubStack.hubB.x - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.x < UrbanAutonomous.hubStack.hubB.x + UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y > UrbanAutonomous.hubStack.hubB.y - UrbanAutonomous.simParam.hubEffectiveLength + && arrivalDemand.y < UrbanAutonomous.hubStack.hubB.y + UrbanAutonomous.simParam.hubEffectiveLength) + if (departureDemand.x > UrbanAutonomous.hubStack.hubA.x - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.x < UrbanAutonomous.hubStack.hubA.x + UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y > UrbanAutonomous.hubStack.hubA.y - UrbanAutonomous.simParam.hubEffectiveLength + && departureDemand.y < UrbanAutonomous.hubStack.hubA.y + UrbanAutonomous.simParam.hubEffectiveLength) + result = true; + return result; + } + + // DemandLifeTime + public void demandLifetimeControl() { + if (unallocatedArrivalList.size() > 0) { + Iterator iter = unallocatedArrivalList.iterator(); + while (iter.hasNext()) { + Demand tmpDemand = iter.next(); + if (tmpDemand.lifetime == 0) { + iter.remove(); + missedDemand++; + UrbanAutonomous.simParam.numberOfVehicle++; + UrbanAutonomous.vehicleStack.vehicleGen(); + // missedDemandHistory[UrbanAutonomous.simParam.currentTime/20]=missedDemand; + } else { + tmpDemand.lifetime -= 1; + } + } + missedDemandHistory[UrbanAutonomous.simParam.currentTime / 20] = missedDemand; + iter = unallocatedDepartureList.iterator(); + while (iter.hasNext()) { + Demand tmpDemand = iter.next(); + if (tmpDemand.lifetime == 0) { + iter.remove(); + } else { + tmpDemand.lifetime -= 1; + } + } + } + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/Disp.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/Disp.java new file mode 100644 index 0000000..36437dd --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/Disp.java @@ -0,0 +1,182 @@ + + +import processing.core.PApplet; +import processing.core.PConstants; +import processing.core.PGraphics; +//import com.y; + +public class Disp { + PApplet pa; + PGraphics p; + + //public Disp(PApplet _pa) { + public Disp(PGraphics _p,PApplet _pa) { + p = _p; + pa = _pa; + } + + // ShowALl + public void show() { + // showMap(); + p.beginDraw(); + oldshowMap(); + showUnallocatedDemand(); + showAllocatedDemand(); + showVehicle(); + showCongestion(); + if (UrbanAutonomous.simParam.hubEnable) { + showHub(); + showHubVehicle(); + showHubPeripheralVehicle(); + showHubRelocation(); + } + p.endDraw(); + } + //ShowHubRelocation + void showHubRelocation(){ + if (UrbanAutonomous.dragStatus == DragStatus.HUBA || UrbanAutonomous.dragStatus == DragStatus.HUBB) { + p.ellipseMode(PConstants.CENTER); + p.stroke(UrbanAutonomous.hubColor); + p.ellipse(pa.mouseX, pa.mouseY, 10, 10); + } + } + + // ShowMap + void oldshowMap() { + for (int y = 0; y < UrbanAutonomous.simParam.maxY; y++) + for (int x = 0; x < UrbanAutonomous.simParam.maxX; x++) + p.image(UrbanAutonomous.mapBlockStack.mapBlockArray[x][y].pg, x * 50, y * 50); + } + + void showMap() { + p.image(UrbanAutonomous.mapBlockStack.pg, 0, 0); + } + + // ShowDemand + // ShowUnallocatedDemand + void showUnallocatedDemand() { + for (Demand tmpDemand : UrbanAutonomous.demandStack.unallocatedArrivalList) { + showEachDemand(tmpDemand); + } + for (Demand tmpDemand : UrbanAutonomous.demandStack.unallocatedDepartureList) { + showEachDemand(tmpDemand); + } + } + + // ShowAllocatedDemand + void showAllocatedDemand() { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand tmpDemand : vehicle.arrivalList) { + showEachAllocatedDemand(tmpDemand); + } + for (Demand tmpDemand : vehicle.departureList) { + showEachAllocatedDemand(tmpDemand); + } + } + } + + void showEachAllocatedDemand(Demand tmpDemand) { + p.ellipseMode(PConstants.CENTER); + if (tmpDemand.isDepartureDemand) + p.fill(UrbanAutonomous.allocatedDepartureColor); + else + p.fill(UrbanAutonomous.allocatedArrivalColor); + p.ellipse(tmpDemand.x * 10 + 5, tmpDemand.y * 10 + 5, 10,10); + } + + void showEachDemand(Demand tmpDemand) { + p.ellipseMode(PConstants.CENTER); + if (tmpDemand.isDepartureDemand) + p.fill(UrbanAutonomous.unallocatedDepartureColor); + else + p.fill(UrbanAutonomous.unallocatedArrivalColor); + p.ellipse(tmpDemand.x * 10 + 5, tmpDemand.y * 10 + 5, 10, 10); + } + + // ShowVehicle + void showVehicle() { + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.vehicleColor); + int vSize= (int)java.lang.Math.sqrt(UrbanAutonomous.simParam.capacityOfVehicle*100) ; + //p.ellipse(vehicle.x * 10 + 5, vehicle.y * 10 + 5, 5*UrbanAutonomous.simParam.capacityOfVehicle, 5*UrbanAutonomous.simParam.capacityOfVehicle); + p.ellipse(vehicle.x * 10 + 5, vehicle.y * 10 + 5, vSize,vSize); + } + } + + // Show Congestion + void showCongestion() { + int totalCongestionLevel = 0; + // Vehicle + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand position : vehicle.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + if (UrbanAutonomous.simParam.hubEnable) { + // HubVehicle + for (Coord position : UrbanAutonomous.hubStack.hubVehicleArray[0].movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + // HubPeripheralVehicle + for (Coord position : UrbanAutonomous.hubStack.hubPeripheralVehicleA.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + for (Coord position : UrbanAutonomous.hubStack.hubPeripheralVehicleB.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + UrbanAutonomous.simParam.totalCongestionLevel[UrbanAutonomous.simParam.currentTime / 20] = totalCongestionLevel; + UrbanAutonomous.simParam.currentTotalCongestionLevel = totalCongestionLevel; + } + + // oldShow Congestion + void oldshowCongestion() { + int totalCongestionLevel = 0; + for (Vehicle vehicle : UrbanAutonomous.vehicleStack.vehicleList) { + for (Demand position : vehicle.movingHistoryList) { + p.image(UrbanAutonomous.congestionImg, position.x * 10, position.y * 10); + totalCongestionLevel++; + } + } + UrbanAutonomous.simParam.totalCongestionLevel[UrbanAutonomous.simParam.currentTime / 20] = totalCongestionLevel; + UrbanAutonomous.simParam.currentTotalCongestionLevel = totalCongestionLevel; + } + + // Show Hub + void showHub() { + p.ellipseMode(PConstants.CENTER); + p.rectMode(PConstants.CENTER); + for (int i = 0; i < UrbanAutonomous.hubStack.hubArray.length; i++) { + p.fill(UrbanAutonomous.hubColor); + p.ellipse(UrbanAutonomous.hubStack.hubArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubArray[i].y * 10 + 5, 15, 15); + p.fill(UrbanAutonomous.hubEffectiveLengthColor); + p.rect(UrbanAutonomous.hubStack.hubArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubArray[i].y * 10 + 5, + UrbanAutonomous.simParam.hubEffectiveLength * 10 * 2, UrbanAutonomous.simParam.hubEffectiveLength * 10 * 2); + } + } + + // Show HubVehicle + void showHubVehicle() { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.hubVehicleColor); + for (int i = 0; i < UrbanAutonomous.hubStack.hubVehicleArray.length; i++) { + p.ellipse(UrbanAutonomous.hubStack.hubVehicleArray[i].x * 10 + 5, UrbanAutonomous.hubStack.hubVehicleArray[i].y * 10 + 5, + 15, 15); + } + } + + // Show HubPeripheralVehicle + void showHubPeripheralVehicle() { + p.ellipseMode(PConstants.CENTER); + p.fill(UrbanAutonomous.hubPeripheralVehicleColor); + p.ellipse(UrbanAutonomous.hubStack.hubPeripheralVehicleA.x * 10 + 5, + UrbanAutonomous.hubStack.hubPeripheralVehicleA.y * 10 + 5, 15, 15); + p.ellipse(UrbanAutonomous.hubStack.hubPeripheralVehicleB.x * 10 + 5, + UrbanAutonomous.hubStack.hubPeripheralVehicleB.y * 10 + 5, 15, 15); + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/DragStatus.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/DragStatus.java new file mode 100644 index 0000000..20b1e51 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/DragStatus.java @@ -0,0 +1,16 @@ +public enum DragStatus { + NORMAL(1), + HUBA(2), + HUBB(3); + + private final int id; + + private DragStatus(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/FileControl.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/FileControl.java new file mode 100644 index 0000000..5e32ee7 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/FileControl.java @@ -0,0 +1,16 @@ + +import processing.core.PApplet; + +public class FileControl extends PApplet { + public int [] customMap; + + public FileControl() { +// customMap = new int[(16*16)]; + customMap = new int[(UrbanAutonomous.simParam.maxX*UrbanAutonomous.simParam.maxY)]; + } + + public void outputCSV() { + String []outData=str(customMap); + saveStrings("customMap.txt", outData); + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/Hub.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/Hub.java new file mode 100644 index 0000000..d31f003 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/Hub.java @@ -0,0 +1,48 @@ + +import java.util.ArrayList; + +public class Hub { + public int x; + public int y; + public boolean isHorizontalStreet; + public boolean isIntersection; + public int streetNumber; + public ArrayList unallocatedArrivalList; + public ArrayList hubVehicleWaitingList; + + public Hub(int _x, int _y) { + x = _x; + y = _y; + unallocatedArrivalList = new ArrayList(); + hubVehicleWaitingList = new ArrayList(); + paramUpdate(); + } + + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/HubPeripheralVehicle.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubPeripheralVehicle.java new file mode 100644 index 0000000..3e2e6b3 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubPeripheralVehicle.java @@ -0,0 +1,237 @@ + +import java.util.ArrayList; + +import processing.core.PApplet; + +public class HubPeripheralVehicle { + public int x; + public int y; + public int streetNumber; + public boolean isHorizontalStreet; + public boolean isIntersection; + public boolean forHubA; + + public ArrayList departureList; + public ArrayList reserveArrivalList; + public ArrayList arrivalList; + public ArrayList movingHistoryList; + PApplet p; + public PeripheralVehicleStatus status; + + public HubPeripheralVehicle(int _x, int _y, PApplet _p, boolean _forHubA) { + status = PeripheralVehicleStatus.STOP; + x = _x; + y = _y; + p = _p; + forHubA = _forHubA; + departureList = new ArrayList(); + arrivalList = new ArrayList(); + reserveArrivalList = new ArrayList(); + movingHistoryList = new ArrayList(); + } + + // Parameter Update + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } + + // Vehicle Movement + public void move() { + paramUpdate(); + movingHistoryUpdate(); + switch (status) { + case STOP: + break; + case DEPARTURE: + eachMove(departureList); + break; + case TOHUB: + if (forHubA) + goToHub(UrbanAutonomous.hubStack.hubA); + else + goToHub(UrbanAutonomous.hubStack.hubB); + break; + case ARRIVAL: + eachMove(arrivalList); + break; + default: + break; + } + } + + void movingHistoryUpdate() { + Coord tmpVehiclePosition = new Coord(x, y); + if (status == PeripheralVehicleStatus.STOP) { + if (movingHistoryList.size() > 0) + movingHistoryList.remove(0); + } else if (movingHistoryList.size() >= UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + else + movingHistoryList.add(tmpVehiclePosition); + } + + void eachMove(ArrayList tmpList) { + if (isSamePoint(tmpList.get(0))) { + tmpList.remove(0); + if (tmpList.size() == 0) + if (status == PeripheralVehicleStatus.DEPARTURE) + status = PeripheralVehicleStatus.TOHUB; + else if (status == PeripheralVehicleStatus.ARRIVAL) + status = PeripheralVehicleStatus.STOP; + } else if (isSameStreet(tmpList.get(0))) { + if (tmpList.get(0).isHorizontalStreet) + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + else + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + } else { + if (isIntersection) { + if (tmpList.get(0).isHorizontalStreet) + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + else + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + } else { + if (isHorizontalStreet) { + if (tmpList.get(0).isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (tmpList.get(0).x - x) / p.abs(tmpList.get(0).x - x); + } + } else { + if (tmpList.get(0).isHorizontalStreet) { + y += (tmpList.get(0).y - y) / p.abs(tmpList.get(0).y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + void goToHub(Hub tmpHub) { + if (isSamePoint(tmpHub)) { + tmpHub.hubVehicleWaitingList.addAll(reserveArrivalList); + reserveArrivalList = new ArrayList(); + if (tmpHub.unallocatedArrivalList.size() > 0) { + status = PeripheralVehicleStatus.ARRIVAL; + while (arrivalList.size() < UrbanAutonomous.simParam.capacityOfPeripheralVehicle + || tmpHub.unallocatedArrivalList.size() > 0) { + arrivalList.add(tmpHub.unallocatedArrivalList.remove(0)); + } + } else { + status = PeripheralVehicleStatus.STOP; + } + } else if (isSameStreet(tmpHub)) { + if (tmpHub.isHorizontalStreet) + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + else + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + } else { + if (isIntersection) { + if (tmpHub.isHorizontalStreet) + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + else + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + } else { + if (isHorizontalStreet) { + if (tmpHub.isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (tmpHub.x - x) / p.abs(tmpHub.x - x); + } + } else { + if (tmpHub.isHorizontalStreet) { + y += (tmpHub.y - y) / p.abs(tmpHub.y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + boolean isSameStreet(Demand tmpDemand) { + boolean result = false; + if (tmpDemand.streetNumber == streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Demand tmpDemand) { + boolean result = false; + if (tmpDemand.x == x && tmpDemand.y == y) + result = true; + return result; + } + + boolean isSameStreet(Hub tmpDemand) { + boolean result = false; + if (tmpDemand.streetNumber == streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == tmpDemand.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Hub tmpDemand) { + boolean result = false; + if (tmpDemand.x == x && tmpDemand.y == y) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/HubStack.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubStack.java new file mode 100644 index 0000000..980eafb --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubStack.java @@ -0,0 +1,36 @@ +import processing.core.PApplet; + +public class HubStack { + public PApplet p; + public Hub hubA; + public Hub hubB; + public int ax,ay,bx,by; + public static HubVehicle hubVehicleA; + public Hub [] hubArray; + public HubVehicle [] hubVehicleArray; + public HubPeripheralVehicle hubPeripheralVehicleA,hubPeripheralVehicleB; + + public HubStack(PApplet _p) { + p=_p; + ax=72; + ay=7; + bx=7; + by=72; + hubA = new Hub(ax, ay); + hubB = new Hub(bx, by); + hubArray = new Hub[]{hubA,hubB}; + hubVehicleA = new HubVehicle(0,0,p); + hubVehicleArray = new HubVehicle[]{hubVehicleA}; + hubPeripheralVehicleA = new HubPeripheralVehicle(0,0,p,true); + hubPeripheralVehicleB = new HubPeripheralVehicle(0,0,p,false); + } + public void init(){ + hubA = new Hub(ax, ay); + hubB = new Hub(bx, by); + hubArray = new Hub[]{hubA,hubB}; + hubVehicleA = new HubVehicle(0,0,p); + hubVehicleArray = new HubVehicle[]{hubVehicleA}; + hubPeripheralVehicleA = new HubPeripheralVehicle(0,0,p,true); + hubPeripheralVehicleB = new HubPeripheralVehicle(0,0,p,false); + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/HubVehicle.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubVehicle.java new file mode 100644 index 0000000..8f24dd8 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/HubVehicle.java @@ -0,0 +1,167 @@ +import java.util.ArrayList; + + +import processing.core.PApplet; + +public class HubVehicle { + + public int x; + public int y; + public int streetNumber; + public boolean isHorizontalStreet; + public boolean isIntersection; + public boolean toHubA; + ArrayList arrivalList; + public ArrayList movingHistoryList; + PApplet p; + + public HubVehicle(int _x, int _y, PApplet _p) { + x = _x; + y = _y; + p = _p; + toHubA = false; + arrivalList = new ArrayList(); + movingHistoryList = new ArrayList(); + } + + // Parameter Update + void paramUpdate() { + isHorizontalStreet = false; + isIntersection = false; + streetNumber = 0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet = true; + streetNumber = ((y + 5 - 2) / 5) - 1; + } else { + streetNumber = ((x + 5 - 2) / 5) - 1; + } + if (isVerticalStreetCheck() && isHorizontalStreetCheck()) + isIntersection = true; + } + + boolean isHorizontalStreetCheck() { + boolean result = false; + if ((y - 2 + 5) % 5 == 0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result = false; + if ((x - 2 + 5) % 5 == 0) + result = true; + return result; + } + + // Vehicle Movement + public void move() { + paramUpdate(); + movingHistoryUpdate(); + eachMove(); + } + + void movingHistoryUpdate() { + Coord tmpVehiclePosition = new Coord(x, y); + if (!(isInHub())) + movingHistoryList.add(tmpVehiclePosition); + if (isInHub() && movingHistoryList.size() > 0) + movingHistoryList.remove(0); + if (movingHistoryList.size() >= UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + } + + boolean isInHub() { + boolean result = false; + if (UrbanAutonomous.hubStack.hubA.y == y && UrbanAutonomous.hubStack.hubA.y == y) + result = true; + if (UrbanAutonomous.hubStack.hubB.y == y && UrbanAutonomous.hubStack.hubB.y == y) + result = true; + return result; + } + + void eachMove() { + if (toHubA) + eachSubMove(UrbanAutonomous.hubStack.hubA); + else + eachSubMove(UrbanAutonomous.hubStack.hubB); + } + + boolean hubIsNotEmpty() { + boolean result = false; + if (UrbanAutonomous.hubStack.hubA.hubVehicleWaitingList.size() > 0 + || UrbanAutonomous.hubStack.hubB.hubVehicleWaitingList.size() > 0) + result = true; + return result; + } + + void eachSubMove(Hub hubX) { + if (isSamePoint(hubX)) { + hubX.unallocatedArrivalList.addAll(arrivalList); + if (hubIsNotEmpty()) { + toHubA = !toHubA; + arrivalList = new ArrayList(); + while (arrivalList.size() < UrbanAutonomous.simParam.hubDedicatedVehicleCapacity + && hubX.hubVehicleWaitingList.size() != 0) { + arrivalList.add(hubX.hubVehicleWaitingList.get(0)); + } + } + } else if (isSameStreet(hubX)) { + if (hubX.isHorizontalStreet) + x += (hubX.x - x) / p.abs(hubX.x - x); + else + y += (hubX.y - y) / p.abs(hubX.y - y); + } else { + if (isIntersection) { + if (hubX.isHorizontalStreet) + y += (hubX.y - y) / p.abs(hubX.y - y); + else + x += (hubX.x - x) / p.abs(hubX.x - x); + } else { + if (isHorizontalStreet) { + if (hubX.isHorizontalStreet) { + if (x > 77) { + x -= 1; + } else { + x += 1; + } + } else { + x += (hubX.x - x) / p.abs(hubX.x - x); + } + } else { + if (hubX.isHorizontalStreet) { + y += (hubX.y - y) / p.abs(hubX.y - y); + } else { + if (y > 77) { + y -= 1; + } else { + y += 1; + } + } + } + } + } + } + + boolean isSameStreet(Hub hubA) { + boolean result = false; + if (hubA.streetNumber == streetNumber && hubA.isHorizontalStreet == isHorizontalStreet) + result = true; + else if (isIntersection) { + if (hubA.isHorizontalStreet) { + if ((((y - 2 + 5) / 5) - 1) == hubA.streetNumber) + result = true; + } else { + if ((((x - 2 + 5) / 5) - 1) == hubA.streetNumber) + result = true; + } + } + return result; + } + + boolean isSamePoint(Hub hub) { + boolean result = false; + if (hub.x == x && hub.y == y) + result = true; + return result; + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlock.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlock.java new file mode 100644 index 0000000..84e39dc --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlock.java @@ -0,0 +1,66 @@ + +import processing.core.PApplet; +import processing.core.PGraphics; + +public class MapBlock { + PApplet p; + int blockSize; + Tile[][] tileArray; + public PGraphics pg; + + public MapBlock() { + } + + public MapBlock(PApplet _p) { + p = _p; + } + + public MapBlock(PApplet _p, Tile[][] _tileArray) { + p = _p; + blockSize = 5; + tileArray = _tileArray; + gen(); + } + + void gen() { + if (pg == null) + pg = p.createGraphics(blockSize * 10, blockSize * 10); + pg.beginDraw(); + pg.background(255); + pg.stroke(255); + for (int y = 0; y < blockSize; y++) { + for (int x = 0; x < blockSize; x++) { + //for abstraction, delete road + if(x==2||y==2) + tileArray[x][y].tileType=tileArray[0][0].tileType; + + switch (tileArray[x][y].tileType) { + case HW: + pg.image(UrbanAutonomous.hwImg, x * 10, y * 10); + break; + case LW: + pg.image(UrbanAutonomous.lwImg, x * 10, y * 10); + break; + case HR: + pg.image(UrbanAutonomous.hrImg, x * 10, y * 10); + break; + case LR: + pg.image(UrbanAutonomous.lrImg, x * 10, y * 10); + break; + case ROAD: + pg.image(UrbanAutonomous.roadImg, x * 10, y * 10); + break; + case INTERSECTION: + pg.image(UrbanAutonomous.intersectionImg, x * 10, y * 10); + break; + case NONE: + pg.image(UrbanAutonomous.noneImg, x * 10, y * 10); + break; + default: + break; + } + } + } + pg.endDraw(); + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBase.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBase.java new file mode 100644 index 0000000..fc48c1a --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBase.java @@ -0,0 +1,66 @@ + + +import processing.core.PApplet; + +public class MapBlockBase { + MapBlockBase() {} + + //RandomMapBlock + Tile[][] randomTileArrayGen(PApplet p) { + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile,UrbanAutonomous.basicTile.noneTile }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[(int) p.random(4)]; + } + } + } + return tileArray; + } + + //SpecificTile + Tile[][] specificTileArrayGen(int number) { + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile,UrbanAutonomous.basicTile.noneTile + }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[number]; + } + } + } + return tileArray; + } + + Tile[][] specificTileArrayGen(PApplet p) { + int number=(int)p.random(4); + Tile[][] tileArray=new Tile[5][5]; + Tile [] basicTileArray= { + UrbanAutonomous.basicTile.hwTile, UrbanAutonomous.basicTile.lwTile, UrbanAutonomous.basicTile.hrTile, UrbanAutonomous.basicTile.lrTile + }; + for (int y=0; y<5; y++) { + for (int x=0; x<5; x++) { + if (x==2&&y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.intersectionTile; + else if (x==2||y==2) + tileArray[x][y]=UrbanAutonomous.basicTile.roadTile; + else { + tileArray[x][y]=basicTileArray[number]; + } + } + } + return tileArray; + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBrushs.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBrushs.java new file mode 100644 index 0000000..61bb580 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/MapBlockBrushs.java @@ -0,0 +1,53 @@ +import processing.core.PApplet; +import processing.core.PGraphics; + +public class MapBlockBrushs extends MapBlockBase { + public MapBlock[] randomBrushs; + public MapBlock[] specificBrushs; + public MapBlock selectedBrush; + public int numberOfBrush; + public PGraphics pg; + PApplet p; + + public MapBlockBrushs(PApplet _p,int _numberOfBrush) { + p=_p; + randomBrushs = new MapBlock[_numberOfBrush]; + specificBrushs = new MapBlock[_numberOfBrush]; + numberOfBrush=_numberOfBrush; + randomBrushsGen(_numberOfBrush); + specificBrushsGen(); + selectedBrush = specificBrushs[0]; + } + + public void randomBrushsGen(int _numberOfBrush) { + for (int i=0; i<_numberOfBrush; i++) { + randomBrushs[i] = new MapBlock(p,randomTileArrayGen(p)); + } + } + public void randomBrushsGen() { + for (int i=0; i250 && mouseY<300) { + if (mouseX >350 && mouseX <850) { + UrbanAutonomous.simParam.capacityOfVehicle=(mouseX-350)/10; + UrbanAutonomous.simParam.numberOfVehicle=1; + UrbanAutonomous.vehicleStack.vehicleGen(); + UrbanAutonomous.simParam.currentTime=4200; + } + } + //Time + else if (mouseY >350 && mouseY<400) { + if (mouseX >350 && mouseX <350+1440) { + UrbanAutonomous.simParam.currentTime=(mouseX-350)*10 ; + } + } + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/PFrame.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/PFrame.java new file mode 100644 index 0000000..2532419 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/PFrame.java @@ -0,0 +1,14 @@ + +import javax.swing.JFrame; + + + +public class PFrame extends JFrame { + public PFrame(int _x, int _y, int _width, int _height) { + setBounds(_x, _y, _width, _height); + UrbanAutonomous.opw = new OperationWindow(); + add(UrbanAutonomous.opw); + UrbanAutonomous.opw.init(); + setVisible(true); + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/PeripheralVehicleStatus.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/PeripheralVehicleStatus.java new file mode 100644 index 0000000..9c4478c --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/PeripheralVehicleStatus.java @@ -0,0 +1,18 @@ + +public enum PeripheralVehicleStatus { + STOP(1), + DEPARTURE(2), + TOHUB(3), + ARRIVAL(4); + + private final int id; + + private PeripheralVehicleStatus(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/SimParam.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/SimParam.java new file mode 100644 index 0000000..7c4abde --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/SimParam.java @@ -0,0 +1,78 @@ + +public class SimParam { + public int maxX; + public int maxY; + + //Vehicle + public int numberOfVehicle; + public int capacityOfVehicle; + //Congestion + public int[] totalCongestionLevel; + public int currentTotalCongestionLevel; + public int vehicleHistorySize; + //Time + public int currentTime; //0-14400 + public int currentTimeZone; + //Demand + public int[] demandSizeArray; + public int currentDemandSize; + public int demandInterval;// unit:min (=#ofstep/10) + public int demandLifetime;// unit:min + public boolean demandSizeCustom; + //Hub + public boolean hubEnable; + public int hubEffectiveLength; + public int hubDedicatedVehicleCapacity; + public int capacityOfPeripheralVehicle; + //Map + public int mapType;// 0:urban,1:Rural,2:custom + + public int usagerate; + + public SimParam() { + usagerate=100; + maxX =18; + maxY =22; + hubEnable=false; + demandSizeCustom = false; + mapType = 2; + currentTimeZone = 0; + currentTime = -1; + capacityOfVehicle = 4; + numberOfVehicle = 1; + currentDemandSize = 0; + //demandInterval = 10; + demandInterval = 1; + vehicleHistorySize = 30; + currentTotalCongestionLevel = 0; + totalCongestionLevel = new int[720]; + //demandSizeArray = new int[] { 5, 5, 5, 5, 5, 10, 20, 50, 50, 20, 10, 10, 20, 10, 20, 30, 50, 50, 50, 30, 20, 10, 10, 10 }; + demandSizeArray = new int[] { 1, 1, 1, 1, 1, 2, 4, 10, 10, 4, 2, 2, 4, 2, 4, 6, 10, 10, 10, 6, 4, 2, 2, 2 }; + demandLifetime = 10; + hubEffectiveLength = 15; + hubDedicatedVehicleCapacity = 50; + capacityOfPeripheralVehicle=10; + } + + public void init(){ + UrbanAutonomous.vehicleStack.vehicleGen(); + UrbanAutonomous.demandStack.init(); + UrbanAutonomous.hubStack.init(); + currentTime=0; + } + + public void update() { + currentTime++; + if (currentTime >= 14400) + currentTime = 0; + // unallocatedDemandSizeHistory + if (currentTime % 20 == 0){ + UrbanAutonomous.demandStack.unallocatedDemandSizeHistory[currentTime / 20] = UrbanAutonomous.demandStack.unallocatedDepartureList.size(); + //usagerate=UrbanAutonomous.demandStack.usageRateCal(); + } + currentTimeZone = currentTime / 600;// 600step = 1hour + if (!demandSizeCustom) + currentDemandSize = demandSizeArray[currentTimeZone]; + } + +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/Status.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/Status.java new file mode 100644 index 0000000..f7ead1a --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/Status.java @@ -0,0 +1,16 @@ + +public enum Status { + CONFIG(1), + RUN(2), + STOP(3); + + private final int id; + + private Status(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/Tile.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/Tile.java new file mode 100644 index 0000000..a60174a --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/Tile.java @@ -0,0 +1,11 @@ + +public class Tile { + public float [] departureProbabilityArray; + public float [] arrivalProbabilityArray; + public TileType tileType; + Tile(float [] departure, float [] arrival,TileType _tileType) { + departureProbabilityArray = departure; + arrivalProbabilityArray = arrival; + tileType=_tileType; + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/TileType.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/TileType.java new file mode 100644 index 0000000..5df9eeb --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/TileType.java @@ -0,0 +1,20 @@ + +public enum TileType { + HW(1), + LW(2), + HR(3), + LR(4), + ROAD(5), + INTERSECTION(6), + NONE(7); + + private final int id; + + private TileType(final int id) { + this.id = id; + } + + public int getId() { + return id; + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/UDP.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/UDP.java new file mode 100644 index 0000000..5a68c9d --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/UDP.java @@ -0,0 +1,881 @@ +/** + * (./) UDP.java v0.2 06/01/26 + * (by) Douglas Edric Stanley & Cousot Stéphane + * (cc) some right reserved + * + * Part of the Processing Libraries project, for the Atelier Hypermedia, art + * school of Aix-en-Provence, and for the Processing community of course. + * - require Java version 1.4 or later - + * -> http://hypermedia.loeil.org/processing/ + * -> http://www.processing.org/ + * + * THIS LIBRARY IS RELEASED UNDER A CREATIVE COMMONS LICENSE BY. + * -> http://creativecommons.org/licenses/by/2.5/ + */ + + + +import java.net.*; +import java.io.*; +import java.lang.reflect.Method; +import java.lang.reflect.InvocationTargetException; +import java.util.Date; +import java.text.SimpleDateFormat; + +import processing.core.*; + +/** + * Create and manage unicast, broadcast or multicast socket to send and receive + * datagram packets over the network. + *

+ * The socket type is define at his initialyzation by the passed IP address. + * To reach a host (interface) within a network, you need to specified the kind + * of address: + *

    + *
  • An unicast address refer to a unique host within a subnet.
  • + *
  • A broadcast address allow you to call every host within a subnet. + *
  • + *
  • A multicast address allows to call a specific group of hosts within + * the subnet. A multicast group is specified by a IP address in the range + * 224.0.0.0 (reserved, should not be used) to + * 239.255.255.255 inclusive, and by a standard UDP port number. + *
    + * notes: the complete reference of special multicast addresses should be + * found in the latest available version of the "Assigned Numbers RFC" + *
  • + *
+ * A packet sent to a unicast or broadcast address is only delivered to the + * host identified by that address. To the contrary, when packet is send to a + * multicast address, all interfaces identified by that address receive the data + * . + *

+ * To perform actions on receive and/or timeout events, you must implement + * specific method(s) in your code. This method will be automatically called + * when the socket receive incoming data or a timeout event. By default, the + * "receive handler" is typically receive(byte[] data) but you can + * retrieve more informations about the datagram packet, see + * {@link UDP#setReceiveHandler(String name)} for more informations. In the same + * logic, the default "timeout handler" is explicitly timeout(). + *

+ * + * note: currently applets are not allowed to use multicast sockets + * + * + * @version 0.1 + * @author Cousot Stéphane - stef@ubaa.net + * @author Douglas Edric Stanley - http://www.abstractmachine.net/ + */ +public class UDP implements Runnable { + + + // the current unicast/multicast datagram socket + DatagramSocket ucSocket = null; + MulticastSocket mcSocket = null; + + boolean log = false; // enable/disable output log + boolean listen = false; // true, if the socket waits for packets + int timeout = 0; // reception timeout > 0=infinite timeout + int size = 65507; // the socket buffer size in bytes + InetAddress group = null; // the multicast's group address to join + + // the reception Thread > wait automatically for incoming datagram packets + // without blocking the current Thread. + Thread thread = null; + + // the parent object (could be an application, a componant, etc...) + Object owner = null; + + // the default "receive handler" and "timeout handler" methods name. + // these methods must be implemented (by the owner) to be called + // automatically when the socket receive incoming datas or a timeout event + String receiveHandler = "receive"; + String timeoutHandler = "timeout"; + + // the log "header" to be set for debugging. Because log is disable by + // default, this value is automatically replaced by the principal socket + // settings when a new instance of UDP is created. + String header = ""; + + ///////////////////////////////// fields /////////////////////////////// + + /** + * The default socket buffer length in bytes. + */ + public static final int BUFFER_SIZE = 65507; + + + ///////////////////////////// constructors //////////////////////////// + + /** + * Create a new datagram socket and binds it to an available port and every + * address on the local host machine. + * + * @param owner the target object to be call by the receive handler + */ + public UDP( Object owner ) { + this( owner, 0 ); + } + + /** + * Create a new datagram socket and binds it to the specified port on the + * local host machine. + *

+ * Pass zero as port number, will let the system choose an + * available port. + * + * @param owner the target object to be call by the receive handler + * @param port local port to bind + */ + public UDP( Object owner, int port ) { + this( owner, port, null ); + } + + /** + * Create a new datagram socket and binds it to the specified port on the + * specified local address or multicast group address. + *

+ * Pass zero as port number, will let the system choose an + * available port. The absence of an address, explicitly null + * as IP address will assign the socket to the Unspecified Address (Also + * called anylocal or wildcard address). To set up the socket as multicast + * socket, pass the group address to be joined. If this address is not a + * valid multicast address, a broadcast socket will be created by default. + * + * @param owner the target object to be call by the receive handler + * @param port local port to bind + * @param ip host address or group address + */ + public UDP( Object owner, int port, String ip ) { + + this.owner = owner; + + // register this object to the PApplet, + // if it's used with Processing + try { + if ( owner instanceof PApplet ) ((PApplet)owner).registerMethod("dispose", this); + } + catch( NoClassDefFoundError e ) {;} + + // open a new socket to the specified port/address + // and join the group if the multicast socket is required + try { + + InetAddress addr = InetAddress.getByName(ip); + InetAddress host = (ip==null) ? (InetAddress)null: addr; + + if ( !addr.isMulticastAddress() ) { + ucSocket = new DatagramSocket( port, host ); // as broadcast + log( "bound socket to host:"+address()+", port: "+port() ); + } + else { + mcSocket = new MulticastSocket( port ); // as multicast + mcSocket.joinGroup( addr ); + this.group = addr; + log( "bound multicast socket to host:"+address()+ + ", port: "+port()+", group:"+group ); + } + } + catch( IOException e ) { + // caught SocketException & UnknownHostException + error( "opening socket failed!"+ + "\n\t> address:"+ip+", port:"+port+" [group:"+group+"]"+ + "\n\t> "+e.getMessage() + ); + } + catch( IllegalArgumentException e ) { + error( "opening socket failed!"+ + "\n\t> bad arguments: "+e.getMessage() + ); + } + catch( SecurityException e ) { + error( (isMulticast()?"could not joined the group":"warning")+ + "\n\t> "+e.getMessage() ); + } + + } + + /////////////////////////////// methods /////////////////////////////// + + /** + * Close the socket. This method is automatically called by Processing when + * the PApplet shuts down. + * + * @see UDP#close() + */ + public void dispose() { + close(); + } + + /** + * Close the actuel datagram socket and all associate resources. + */ + public void close() { + if ( isClosed() ) return; + + int port = port(); + String ip = address(); + + // stop listening if needed + //listen( false ); + + // close the socket + try { + if ( isMulticast() ) { + if ( group!=null ) { + mcSocket.leaveGroup( group ); + log( "leave group < address:"+group+" >" ); + } + mcSocket.close(); + mcSocket = null; + } + else { + ucSocket.close(); + ucSocket = null; + } + } + catch( IOException e ) { + error( "Error while closing the socket!\n\t> " + e.getMessage() ); + } + catch( SecurityException e ) {;} + finally { + log( "close socket < port:"+port+", address:"+ip+" >\n" ); + } + } + + /** + * Returns whether the current socket is closed or not. + * @return boolean + **/ + public boolean isClosed() { + if ( isMulticast() ) return mcSocket==null ? true : mcSocket.isClosed(); + return ucSocket==null ? true : ucSocket.isClosed(); + } + + /** + * Return the actual socket's local port, or -1 if the socket is closed. + * @return int + */ + public int port() { + if ( isClosed() ) return -1; + return isMulticast()? mcSocket.getLocalPort() : ucSocket.getLocalPort(); + } + + /** + * Return the actual socket's local address, or null if the + * address correspond to any local address. + * + * @return String + */ + public String address() { + if ( isClosed() ) return null; + + InetAddress laddr = isMulticast() ? mcSocket.getLocalAddress(): + ucSocket.getLocalAddress(); + return laddr.isAnyLocalAddress() ? null : laddr.getHostAddress(); + } + + /** + * Send message to the current socket. Explicitly, send message to the + * multicast group/port or to itself. + * + * @param message the message to be send + * + * @see UDP#send(String message, String ip) + * @see UDP#send(String message, String ip, int port) + * + * @return boolean + */ + public boolean send( String message ) { + return send( message.getBytes() ); + } + + /** + * Send data to the current socket. Explicitly, send data to the multicast + * group/port or to itself. + * + * @param buffer data to be send + * + * @see UDP#send(byte[] data, String ip) + * @see UDP#send(byte[] data, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer ) { + // probably if the group could not be joined for a security reason + if ( isMulticast() && group==null ) return false; + + String ip = isMulticast() ? group.getHostAddress() : address(); + return send( buffer, ip, port() ); + } + + /** + * Send message to the requested IP address, to the current socket port. + * + * @param message the message to be send + * @param ip the destination host's IP address + * + * @see UDP#send(String message) + * @see UDP#send(String message, String ip, int port) + * + * @return boolean + */ + public boolean send( String message, String ip ) { + return send( message.getBytes(), ip ); + } + + /** + * Send data to the requested IP address, to the current socket port. + * + * @param buffer data to be send + * @param ip the destination host's IP address + * + * @see UDP#send(byte[] buffer) + * @see UDP#send(byte[] buffer, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer, String ip ) { + return send( buffer, ip, port() ); + } + + /** + * Send message to the requested IP address and port. + *

+ * A null IP address will assign the packet address to the + * local host. Use this method to send message to another application by + * passing null as the destination address. + * + * @param message the message to be send + * @param ip the destination host's IP address + * @param port the destination host's port + * + * @see UDP#send(String message) + * @see UDP#send(String message, String ip) + * + * @return boolean + */ + public boolean send( String message, String ip, int port ) { + return send( message.getBytes(), ip, port ); + } + + /** + * Send data to the requested IP address and port. + *

+ * A null IP address will assign the packet address to the + * local host. Use this method to send data to another application by + * passing null as the destination address. + * + * @param buffer data to be send + * @param ip the destination host's IP address + * @param port the destination host's port + * + * @see UDP#send(byte[] buffer, String ip) + * @see UDP#send(byte[] buffer, String ip, int port) + * + * @return boolean + */ + public boolean send( byte[] buffer, String ip, int port ) { + + boolean success = false; + DatagramPacket pa = null; + + try { + + pa = new DatagramPacket( buffer, buffer.length, InetAddress.getByName(ip), port ); + + // send + if ( isMulticast() ) mcSocket.send( pa ); + else ucSocket.send( pa ); + + success = true; + log( "send packet -> address:"+pa.getAddress()+ + ", port:"+ pa.getPort() + + ", length: "+ pa.getLength() + ); + } + catch( IOException e ) { + error( "could not send message!"+ + "\t\n> port:"+port+ + ", ip:"+ip+ + ", buffer size: "+size+ + ", packet length: "+pa.getLength()+ + "\t\n> "+e.getMessage() + ); + } + finally{ return success; } + } + + /** + * Set the maximum size of the packet that can be sent or receive on the + * current socket. This value must be greater than 0, otherwise the buffer + * size is set to the his default value. + *

+ * return true if the new buffer value have been correctly set, + * false otherwise. + *

+ * note : this method has no effect if the socket is listening. To define + * a new buffer size, call this method before implementing a new buffer in + * memory. Explicitly before calling a receive methods. + * + * @param size the buffer size value in bytes or n<=0 + * @return boolean + * @see UDP#getBuffer() + */ + public boolean setBuffer( int size ) { + boolean done = false; + + // do nothing if listening (block the thread otherwise) + if ( isListening() ) return done; + + try { + // set the SO_SNDBUF and SO_RCVBUF value + if ( isMulticast() ) { + mcSocket.setSendBufferSize( size>0 ? size : BUFFER_SIZE ); + mcSocket.setReceiveBufferSize( size>0 ? size : BUFFER_SIZE ); + } + else { + ucSocket.setSendBufferSize( size>0 ? size : BUFFER_SIZE ); + ucSocket.setReceiveBufferSize( size>0 ? size : BUFFER_SIZE ); + } + // set the current buffer size + this.size = size>0 ? size : BUFFER_SIZE; + done = true; + } + catch( SocketException e ) { + error( "could not set the buffer!"+ + "\n> "+e.getMessage() + ); + } + finally{ return done; } + } + + /** + * Return the actual socket buffer length + * @return int + * @see UDP#setBuffer(int size) + */ + public int getBuffer() { + return size; + } + + /** + * Returns whether the socket wait for incoming data or not. + * @return boolean + */ + public boolean isListening() { + return listen; + } + + + /** + * Start/stop waiting constantly for incoming data. + * + * @param on the required listening status. + * + * @see UDP#listen() + * @see UDP#listen(int millis) + * @see UDP#setReceiveHandler(String name) + */ + public void listen( boolean on ) { + + listen = on; + timeout = 0; + + // start + if ( on && thread==null && !isClosed() ) { + thread = new Thread( this ); + thread.start(); + } + // stop + if ( !on && thread!=null ) { + send( new byte[0] ); // unblock the thread with a dummy message + thread.interrupt(); + thread = null; + } + } + + /** + * Set the socket reception timeout and wait one time for incoming data. + * If the timeout period occured, the owner timeout() method is + * automatically called. + * + * @param millis the required timeout value in milliseconds. + * + * @see UDP#listen() + * @see UDP#listen(boolean on) + */ + public void listen( int millis ) { + if ( isClosed() ) return; + + listen = true; + timeout = millis; + + // unblock the thread with a dummy message, if already listening + if ( thread!=null ) send( new byte[0] ); + if ( thread==null ) { + thread = new Thread( this ); + thread.start(); + } + } + + /** + * Wait for incoming data, and call the appropriate handlers each time a + * message is received. If the owner's class own the appropriate target + * handler, this method send it the receive message as byte[], the sender + * IP address and port. + *

+ * This method force the current Thread to be ceased for a + * temporary period. If you prefer listening without blocking the current + * thread, use the {@link UDP#listen(int millis)} or + * {@link UDP#listen(boolean on)} method instead. + * + * @see UDP#listen() + * @see UDP#listen(boolean on) + * @see UDP#setReceiveHandler(String name) + */ + public void listen() { + try { + + byte[] buffer = new byte[ size ]; + DatagramPacket pa = new DatagramPacket(buffer,buffer.length); + + // wait + if ( isMulticast() ) { + mcSocket.setSoTimeout( timeout ); + mcSocket.receive( pa ); // <-- block the Thread + } + else { + ucSocket.setSoTimeout( timeout ); + ucSocket.receive( pa ); // <-- block + } + + + log( "receive packet <- from "+pa.getAddress()+ + ", port:"+ pa.getPort() + + ", length: "+ pa.getLength() + ); + + + // get the required data only (not all the buffer) + // and send it to the appropriate target handler, if needed + if ( pa.getLength()!=0 ) { + + byte[] data = new byte[ pa.getLength() ]; + System.arraycopy( pa.getData(), 0, data, 0, data.length ); + + try { + // try with one argument first > byte[] + callReceiveHandler( data ); + } + catch( NoSuchMethodException e ) { + // try with many argument > byte[], String, int + callReceiveHandler( data, + pa.getAddress().getHostAddress(), + pa.getPort() + ); + } + } + } + catch( NullPointerException e ) { + // *socket=null from the close() method; + listen = false; + thread = null; + } + catch( IOException e ) { + + listen = false; + thread = null; + + if ( e instanceof SocketTimeoutException ) callTimeoutHandler(); + else { + // do not print "Socket closed" error + // if the method close() has been called + if ( ucSocket!=null && mcSocket!=null ) + error( "listen failed!\n\t> "+e.getMessage() ); + } + } + } + + /** + * Wait for incoming datagram packets. This method is called automaticlly, + * you do not need to call it. + */ + public void run() { + while ( listen ) listen(); + } + + /** + * Register the target's receive handler. + *

+ * By default, this method name is "receive" with one argument + * representing the received data as byte[]. For more + * flexibility, you can change this method with another useful method by + * passing his name. You could get more informations by implementing two + * additional arguments, a String representing the sender IP + * address and a int representing the sender port : + *

+	 * void myCustomReceiveHandler(byte[] message, String ip, int port) {
+	 *	// do something here...
+	 * }
+	 * 
+ * + * @param name the receive handler name + * @see UDP#setTimeoutHandler(String name) + */ + public void setReceiveHandler( String name ) { + this.receiveHandler = name; + } + + /** + * Call the default receive target handler method. + * + * @param data the data to be passed + * @throws NoSuchMethodException + */ + private void callReceiveHandler( byte[] data ) + throws NoSuchMethodException { + + Class[] types; // arguments class types + Object[] values; // arguments values + Method method; + + try { + types = new Class[]{ data.getClass() }; + values = new Object[]{ data }; + method = owner.getClass().getMethod(receiveHandler, types); + method.invoke( owner, values ); + } + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Call the receive target handler implemented with the optional arguments. + * + * @param data the data to be passed + * @param ip the IP adress to be passed + * @param port the port number to be passed + */ + private void callReceiveHandler( byte[] data, String ip, int port ) { + + Class[] types; // arguments class types + Object[] values; // arguments values + Method method; + + try { + types = new Class[]{ data.getClass(), + ip.getClass(), + Integer.TYPE + }; + values = new Object[]{ data, + ip, + new Integer(port) + }; + method = owner.getClass().getMethod(receiveHandler, types); + method.invoke( owner, values ); + } + catch( NoSuchMethodException e ) {;} + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Register the target's timeout handler. By default, this method name is + * "timeout" with no argument. + * + * @param name the timeout handler name + * @see UDP#setReceiveHandler(String name) + */ + public void setTimeoutHandler( String name ) { + this.timeoutHandler = name; + } + + /** + * Call the timeout target method when the socket received a timeout event. + * The method name to be implemented in your code is timeout(). + */ + private void callTimeoutHandler() { + try { + Method m = owner.getClass().getDeclaredMethod(timeoutHandler, null); + m.invoke( owner, null ); + } + catch( NoSuchMethodException e ) {;} + catch( IllegalAccessException e ) { error(e.getMessage()); } + catch( InvocationTargetException e ) { e.printStackTrace(); } + } + + /** + * Returns whether the opened datagram socket is a multicast socket or not. + * @return boolean + */ + public boolean isMulticast() { + return ( mcSocket!=null ); + } + + /** + * Returns whether the multicast socket is joined to a group address. + * @return boolean + */ + public boolean isJoined() { + return ( group!=null ); + } + + /** + * Returns whether the opened socket send broadcast message socket or not. + * @return boolean + */ + public boolean isBroadcast() { + boolean result = false; + try { + result = (ucSocket==null) ? false : ucSocket.getBroadcast(); + } + catch( SocketException e ) { error( e.getMessage() ); } + finally { return result; } + } + + /** + * Enables or disables the ability of the current process to send broadcast + * messages. + * @return boolean + */ + public boolean broadcast( boolean on ) { + boolean done = false; + try { + if ( ucSocket!=null ) { + ucSocket.setBroadcast( on ); + done = isBroadcast(); + } + } + catch( SocketException e ) { error( e.getMessage() ); } + finally { return done; } + } + + /** + * Enable or disable the multicast socket loopback mode. By default loopback + * is enable. + *
+ * Setting loopback to false means this multicast socket does not want to + * receive the data that it sends to the multicast group. + * + * @param on local loopback of multicast datagrams + */ + public void loopback( boolean on ) { + try { + if ( isMulticast() ) mcSocket.setLoopbackMode( !on ); + } + catch( SocketException e ) { + error( "could not set the loopback mode!\n\t>"+e.getMessage() ); + } + } + + /** + * Returns whether the multicast socket loopback mode is enable or not. + * @return boolean + */ + public boolean isLoopback() { + try { + if ( isMulticast() && !isClosed() ) + return !mcSocket.getLoopbackMode(); + } + catch( SocketException e ) { + error( "could not get the loopback mode!\n\t> "+e.getMessage() ); + } + return false; + } + + /** + * Control the life-time of a datagram in the network for multicast packets + * in order to indicates the scope of the multicasts (ie how far the packet + * will travel). + *

+ * The TTL value must be in range of 0 to 255 inclusive. The larger the + * number, the farther the multicast packets will travel (by convention): + *

+	 * 0	-> restricted to the same host
+	 * 1	-> restricted to the same subnet (default)
+	 * <32	-> restricted to the same site
+	 * <64	-> restricted to the same region
+	 * <128	-> restricted to the same continent
+	 * <255	-> no restriction
+	 * 
+ * The default value is 1, meaning that the datagram will not go beyond the + * local subnet. + *

+ * return true if no error occured. + * + * @param ttl the "Time to Live" value + * @return boolean + * @see UDP#getTimeToLive() + */ + public boolean setTimeToLive( int ttl ) { + try { + if ( isMulticast() && !isClosed() ) mcSocket.setTimeToLive( ttl ); + return true; + } + catch( IOException e ) { + error( "setting the default \"Time to Live\" value failed!"+ + "\n\t> "+e.getMessage() ); + } + catch( IllegalArgumentException e ) { + error( "\"Time to Live\" value must be in the range of 0-255" ); + } + return false; + } + + /** + * Return the "Time to Live" value or -1 if an error occurred (or if + * the current socket is not a multicast socket). + * + * @return int + * @see UDP#setTimeToLive(int ttl) + */ + public int getTimeToLive() { + try { + if ( isMulticast() && !isClosed() ) + return mcSocket.getTimeToLive(); + } + catch( IOException e ) { + error( "could not retrieve the current time-to-live value!"+ + "\n\t> "+ e.getMessage() ); + } + return -1; + } + + /** + * Enable or disable output process log. + */ + public void log( boolean on ) { + log = on; + } + + /** + * Output message to the standard output stream. + * @param out the output message + */ + private void log( String out ) { + + Date date = new Date(); + + // define the "header" to retrieve at least the principal socket + // informations : the host/port where the socket is bound. + if ( !log && header.equals("") ) + header = "-- UDP session started at "+date+" --\n-- "+out+" --\n"; + + // print out + if ( log ) { + + String pattern = "yy-MM-dd HH:mm:ss.S Z"; + String sdf = new SimpleDateFormat(pattern).format( date ); + System.out.println( header+"["+sdf+"] "+out ); + header = ""; // forget header + } + } + + /** + * Output error messages to the standard error stream. + * @param err the error string + */ + private void error( String err ) { + System.err.println( err ); + } +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/UDPSocket.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/UDPSocket.java new file mode 100644 index 0000000..d6da939 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/UDPSocket.java @@ -0,0 +1,201 @@ + +import processing.core.PApplet; +import processing.data.JSONObject; + +public class UDPSocket { + UDP udp; + PApplet p; + + public UDPSocket(PApplet _p) { + p = _p; + udp = new UDP(this, 5500); + udp.log(true); // <-- printout the connection activity + udp.listen(true); + } + + public void receive(byte[] data, String ip, int port) { // <-- extended + String dataStr = new String(data); + dataStr = new String(p.trim(dataStr)); + p.println("receive: \"" + dataStr + "\" from " + ip + " on port " + port); + String[] list = new String[] { dataStr }; + p.saveStrings("json.txt", list); + JSONObject json = p.loadJSONObject("json.txt"); + + mapUpdate(json); + vehicleUpdate(json); + demandUpdate(json); + hubUpdate(json); + demandGenerationUpdate(json); + resetUpdate(json); + timeUpdate(json); + // UrbanAutonomous.simParam.numberOfVehicle = p.parseInt(dataStr); + // UrbanAutonomous.vehicleStack.vehicleGen(); + + } + + void timeUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("time")) { + tmpStr = json.getString("time"); + UrbanAutonomous.simParam.currentTime = Integer.parseInt(tmpStr); + } + } + void resetUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("reset")) { + tmpStr = json.getString("reset"); + if(p.parseBoolean(tmpStr)) + UrbanAutonomous.simParam.init(); + } + } + void hubUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("hubDedicatedVehicleCapacity")) { + tmpStr = json.getString("hubDedicatedVehicleCapacity"); + UrbanAutonomous.simParam.hubDedicatedVehicleCapacity= Integer.parseInt(tmpStr); + UrbanAutonomous.hubStack.init(); + } else if (!json.isNull("capacityOfPeripheralVehicle")) { + tmpStr = json.getString("capacityOfPeripheralVehicle"); + UrbanAutonomous.simParam.capacityOfPeripheralVehicle = Integer.parseInt(tmpStr); + UrbanAutonomous.hubStack.init(); + } else if (!json.isNull("hubA")) { + tmpStr = json.getString("hubA"); + String[] nums = p.split(tmpStr, ','); + UrbanAutonomous.hubStack.ax = Integer.parseInt(nums[0])*5+2; + UrbanAutonomous.hubStack.ay = Integer.parseInt(nums[1])*5+2; + UrbanAutonomous.hubStack.init(); + } else if (!json.isNull("hubB")) { + tmpStr = json.getString("hubB"); + String[] nums = p.split(tmpStr, ','); + UrbanAutonomous.hubStack.bx = Integer.parseInt(nums[0])*5+2; + UrbanAutonomous.hubStack.by = Integer.parseInt(nums[1])*5+2; + UrbanAutonomous.hubStack.init(); + } + } + void demandUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("demandInterval")) { + tmpStr = json.getString("demandInterval"); + UrbanAutonomous.simParam.demandInterval = Integer.parseInt(tmpStr); + } else if (!json.isNull("demandLifetime")) { + tmpStr = json.getString("demandLifetime"); + UrbanAutonomous.simParam.demandLifetime= Integer.parseInt(tmpStr); + } else if (!json.isNull("currentDemandSize")) { + tmpStr = json.getString("currentDemandSize"); + UrbanAutonomous.simParam.currentDemandSize= Integer.parseInt(tmpStr); + } else if (!json.isNull("demandSizeCustom")) { + tmpStr = json.getString("demandSizeCustom"); + UrbanAutonomous.simParam.demandSizeCustom= p.parseBoolean(tmpStr); + } + } + void vehicleUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("fleetSize")) { + tmpStr = json.getString("fleetSize"); + UrbanAutonomous.simParam.numberOfVehicle = Integer.parseInt(tmpStr); + UrbanAutonomous.vehicleStack.vehicleGen(); + } else if (!json.isNull("vehicleCapacity")) { + tmpStr = json.getString("vehicleCapacity"); + UrbanAutonomous.simParam.capacityOfVehicle = Integer.parseInt(tmpStr); + UrbanAutonomous.vehicleStack.vehicleGen(); + } else if (!json.isNull("vehicleHistorySize")) { + tmpStr = json.getString("vehicleHistorySize"); + UrbanAutonomous.simParam.vehicleHistorySize = Integer.parseInt(tmpStr); + UrbanAutonomous.vehicleStack.vehicleGen(); + } + } + + void mapUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("mapType")) { + tmpStr = json.getString("mapType"); + UrbanAutonomous.simParam.mapType = Integer.parseInt(tmpStr); + if (UrbanAutonomous.simParam.mapType == 0) { + UrbanAutonomous.mapBlockStack.loadUrbanMap(); + } else if (UrbanAutonomous.simParam.mapType == 1) { + UrbanAutonomous.mapBlockStack.loadRuralMap(); + } else if (UrbanAutonomous.simParam.mapType == 2) { + UrbanAutonomous.mapBlockStack.noneMapGen(); + } + UrbanAutonomous.mapBlockStack.updateCoordinate();// reflect change of // // // // mapblock to demand // // // // generation + UrbanAutonomous.mapBlockStack.mapImgCreation(); // map image creation for // // // // display + } + } + + void demandGenerationUpdate(JSONObject json) { + String tmpStr; + if (!json.isNull("hwArrival")) { + tmpStr = json.getString("hwArrival"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.hwTile.arrivalProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("lwArrival")) { + tmpStr = json.getString("lwArrival"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.lwTile.arrivalProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("hrArrival")) { + tmpStr = json.getString("hrArrival"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.hrTile.arrivalProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("lrArrival")) { + tmpStr = json.getString("lrArrival"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.lrTile.arrivalProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("hwDeparture")) { + tmpStr = json.getString("hwDeparture"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.hwTile.departureProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("lwDeparture")) { + tmpStr = json.getString("lwDeparture"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.lwTile.departureProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("hrDeparture")) { + tmpStr = json.getString("hrDeparture"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.hrTile.departureProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("lrDeparture")) { + tmpStr = json.getString("lrDeparture"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.basicTile.lrTile.departureProbabilityArray[i] = Float.parseFloat(nums[i]); + } + } + if (!json.isNull("totalDemand")) { + tmpStr = json.getString("totalDemand"); + String[] nums = p.split(tmpStr, ','); + float[] tmp = new float[24]; + for (int i = 0; i < nums.length; i++) { + UrbanAutonomous.simParam.demandSizeArray[i] = Integer.parseInt(nums[i]); + } + } + } + +} diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/UrbanAutonomous.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/UrbanAutonomous.java new file mode 100644 index 0000000..b996133 --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/UrbanAutonomous.java @@ -0,0 +1,621 @@ +import processing.core.*; +import processing.data.*; +import processing.event.*; +import processing.opengl.*; + +import javax.swing.JFrame; +import deadpixel.keystone.*; +import hypermedia.net.*; + +import java.util.HashMap; +import java.util.ArrayList; +import java.io.File; +import java.io.BufferedReader; +import java.io.PrintWriter; +import java.io.InputStream; +import java.io.OutputStream; +import java.io.IOException; + +public class UrbanAutonomous extends PApplet { + +//laptop resolution 1920 x 1080 +//16blocks x 16blocks +//1block = 5tiles x 5tiles +//1tile = 10pixels x 10pixels +//Simulation Window: 800 x 800pixels +//Operation Window: x pixels + +//vehicle speed 20km/h 20,000m/60min 2000m/6min 333m/min 33.3m/0.1min +//1block 133.3m -> 1tile 33.3m -> 2.128km-square +//1tile/0.1min +//1 simulation sec = 0.1min -> 10sec = 1min, 600sec(10min)=60min(1h) 240min(4h)=24h +//0.1 simulation sec = 0.1min ->1min=1h 24min = 24h +//1step =0.1min , 10step 1min , 600step 1h, 14400step =24h +//start time 00:00~24:00, 0:00->0step[0.1min](currentTime), 24:00-> 14400step[0.1min](currentTime) + +//View +//AllocatedDepartureDemand:pink +//unallocatedDepartureDemand:red +//AllocatedArrivalDemand:light blue +//unallocatedArrivalDemand:blue + + +int projectorWidth = 1920; +int projectorHeight = 1200; +int projectorOffset = 1842; + +int screenWidth = 1842; +int screenHeight = 1026; + +public static int displayU = 18; +public static int displayV = 22; + +int IDMax = 15; + +// Table Canvas Width and Height +int TABLE_IMAGE_HEIGHT = 1000; +int TABLE_IMAGE_WIDTH = 1000; + +// Arrays that holds ID information of rectilinear tile arrangement. +public static int tablePieceInput[][][] = new int[displayU][displayV][2]; + + +public static DragStatus dragStatus; +public static OperationWindow opw; +public static Status status; +public static PImage hwImg, lwImg, hrImg, lrImg, roadImg, intersectionImg, noneImg, backgroundImg, congestionImg,sideDisplayImg; +public static Tile[][] simCoordinate; +public static int vehicleColor; +public static int allocatedDepartureColor; +public static int unallocatedDepartureColor; +public static int allocatedArrivalColor; +public static int unallocatedArrivalColor; +public static int hubColor; +public static int hubVehicleColor; +public static int hubPeripheralVehicleColor; +public static int hubEffectiveLengthColor; +public static PGraphics legendPg, demandPg; +public static int brushNumber; + + // Temporary + public static SimParam simParam; + public static MapBlock mapBlock; + public static BasicTile basicTile; + public static MapBlockBrushs mapBlockBrushs; + public static MapBlockStack mapBlockStack; + public static Disp disp; + public static DemandStack demandStack; + public static VehicleStack vehicleStack; + // public static OperationDisp operationDisp; + public static FileControl fileControl; + // public static Hub hubA, hubB; + public static HubStack hubStack; + // public static HubVehicle hubVehicle; + public static UDPSocket udpSocket; + + PGraphics captionG,mainG; + + public void setup() { + mainG=createGraphics(1000,1200); + + //size(screenWidth, screenHeight, P3D); + + // Initial Projection-Mapping Canvas + initializeProjection2D(); + + // Allows application to receive information from Colortizer via UDP + initUDP(); + + + // SimulationWindow + size(1000, 1000); + + // OperationWindow + //new PFrame(1000, 0, 1900, 875); + new PFrame(0, 0, 1842, 1026); + + // Status + status = Status.CONFIG; + dragStatus = DragStatus.NORMAL; + + // Load Image + loadTileImage(); + //backgroundImg = loadImage("operationWindow.jpg"); + backgroundImg = loadImage("operationWindow.png"); + sideDisplayImg = loadImage("sideDisplay.jpg"); + + // Legend Symbol + //vehicleColor = color(255, 128, 0, 255); + vehicleColor = color(255, 255, 255, 255); + allocatedDepartureColor = color(0, 128, 0, 255); + unallocatedDepartureColor = color(0, 128, 0, 255); + allocatedArrivalColor = color(0, 0, 255, 255); + unallocatedArrivalColor = color(0, 0, 255, 255); + //allocatedDepartureColor = color(0, 255, 127, 127); + //unallocatedDepartureColor = color(0, 128, 0, 127); + //allocatedArrivalColor = color(0, 255, 255, 127); + //unallocatedArrivalColor = color(0, 0, 255, 127); + hubColor = color(0, 255, 0, 200); + hubEffectiveLengthColor = color(0, 255, 0, 64); + hubVehicleColor = color(142, 0, 204, 200); + hubPeripheralVehicleColor = color(200, 255, 200, 200); + + // Temporary + simParam = new SimParam(); + udpSocket = new UDPSocket(this); + + hubStack = new HubStack(this); + + brushNumber = 0; + basicTile = new BasicTile(); + mapBlockBrushs = new MapBlockBrushs(this, 5); + mapBlockStack = new MapBlockStack(this); + //disp = new Disp(this); + disp = new Disp(mainG,this); + demandStack = new DemandStack(); + simCoordinate = new Tile[UrbanAutonomous.simParam.maxX*5][UrbanAutonomous.simParam.maxY*5]; + vehicleStack = new VehicleStack(); + + //mapBlockStack.loadRuralMap(); + + mapBlockStack.updateCoordinate();// reflect change of mapblock to demand + // generation + mapBlockStack.mapImgCreation();// map image creation for display + mapBlockBrushs.brushImgCreation();// brush image creation for operation + // display + legendSymbolImgCreation(); // create legend symbol image for operation + // display + demandGenerationImgCreation(); // create demand image for operation + // display + fileControl = new FileControl(); + } + + public void draw() { + if(simParam.mapType==2){ //custom map + mapBlockStack.customMapGen(); + mapBlockStack.updateCoordinate();// reflect change of mapblock to // // // demand // generation + mapBlockStack.mapImgCreation();// map image creation for display + } + // Exports table Graphic to Projector + projector = get(0, 0, TABLE_IMAGE_WIDTH, TABLE_IMAGE_HEIGHT); + + simParam.update(); + + demandStack.demandLifetimeControl(); + demandStack.demandGen(simParam.currentDemandSize, simParam.demandInterval * 10);// numberOfDemand,DemandGenerationInterval(steps) + demandStack.demandAllocation(); + demandStack.demandHubAllocation(); + vehicleStack.allVehicleMovement(); + simParam.usagerate=UrbanAutonomous.demandStack.usageRateCal(); + + hubStack.hubVehicleA.move(); + hubStack.hubPeripheralVehicleA.move(); + hubStack.hubPeripheralVehicleB.move(); + + // Display + disp.show(); + + //image(mainG,180,0,725,725); + image(mainG,180,0,905,1090); + image(sideDisplayImg,0,0,180,1000); + //image(mainG,0,0,1000,1200); + } + + public void loadTileImage() { + hwImg = loadImage("hwTile.png"); + lwImg = loadImage("lwTile.png"); + hrImg = loadImage("hrTile.png"); + lrImg = loadImage("lrTile.png"); + roadImg = loadImage("roadTile.png"); + intersectionImg = loadImage("intersectionTile.png"); + noneImg = loadImage("noneTile.png"); + congestionImg = loadImage("congestion.png"); + } + + public void keyPressed() { + switch(key) { + case '`': // "Enable Projection (`)" + toggle2DProjection(); + break; + } + } + public void mousePressed() { + int x = (int) (mouseX / 50); + int y = (int) (mouseY / 50); + + if (simParam.mapType == 2) { + mapBlockStack.mapBlockArray[x][y] = mapBlockBrushs.selectedBrush; + fileControl.customMap[UrbanAutonomous.simParam.maxX * y + x] = brushNumber; + mapBlockStack.updateCoordinate();// reflect change of mapblock to // // // demand // generation + mapBlockStack.mapImgCreation();// map image creation for display + } + // Hub Relocation + hubRelocation(); + } + + public void hubRelocation() { + if (dist(hubStack.hubA.x * 10, hubStack.hubA.y * 10, mouseX, mouseY) < 20) { + dragStatus = DragStatus.HUBA; + } else if (dist(hubStack.hubB.x * 10, hubStack.hubB.y * 10, mouseX, mouseY) < 20) { + dragStatus = DragStatus.HUBB; + } + } + + public void mouseReleased() { + if (dragStatus == DragStatus.HUBA) { + hubStack.ax = modifyHubPoint(mouseX); + hubStack.ay = modifyHubPoint(mouseY); + hubStack.init(); + } else if (dragStatus == DragStatus.HUBB) { + hubStack.bx = modifyHubPoint(mouseX); + hubStack.by = modifyHubPoint(mouseY); + hubStack.init(); + } + dragStatus = DragStatus.NORMAL; + } + + public int modifyHubPoint(int x) { + int result = 0; + result = x / 10 / 5 * 5 + 2; + return result; + } + + public void legendSymbolImgCreation() { + int offset = 0; + legendPg = createGraphics(20, 180); + legendPg.beginDraw(); + legendPg.background(255); + legendPg.stroke(255); + legendPg.stroke(1); + + // LandUse + legendPg.image(hwImg, offset, 0, 20, 20); + legendPg.image(lwImg, offset, 20, 20, 20); + legendPg.image(hrImg, offset, 40, 20, 20); + legendPg.image(lrImg, offset, 60, 20, 20); + + legendPg.ellipseMode(CENTER); + // allocated departure + legendPg.fill(allocatedDepartureColor); + legendPg.ellipse(offset + 10, 90, 10, 10); + // unallocated departure + legendPg.fill(unallocatedDepartureColor); + legendPg.ellipse(offset + 10, 110, 10, 10); + // allocated arrival + legendPg.fill(allocatedArrivalColor); + legendPg.ellipse(offset + 10, 130, 10, 10); + // unallocated arrival + legendPg.fill(unallocatedArrivalColor); + legendPg.ellipse(offset + 10, 150, 10, 10); + // Vehicle(fleet) + legendPg.fill(vehicleColor); + legendPg.ellipse(offset + 10, 170, 10, 10); + legendPg.endDraw(); + } + + public void demandGenerationImgCreation() { + int offset = 150; + demandPg = createGraphics(870, 260); + demandPg.beginDraw(); + // demandPg.background(255); + demandPg.clear(); + demandPg.stroke(255); + demandPg.stroke(1); + demandPg.image(hwImg, 0, 0, 50, 50); + demandPg.image(lwImg, 0, 70, 50, 50); + demandPg.image(hrImg, 0, 140, 50, 50); + demandPg.image(lrImg, 0, 210, 50, 50); + + for (int i = 0; i < 720; i++) { + demandPg.line(offset + i, 20 - (basicTile.hwTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 20); + demandPg.line(offset + i, 50 - (basicTile.hwTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 50); + demandPg.line(offset + i, 90 - (basicTile.lwTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 90); + demandPg.line(offset + i, 120 - (basicTile.lwTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 120); + demandPg.line(offset + i, 160 - (basicTile.hrTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 160); + demandPg.line(offset + i, 190 - (basicTile.hrTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 190); + demandPg.line(offset + i, 230 - (basicTile.lrTile.departureProbabilityArray[i / 30] * 100 / 5), offset + i, + 230); + demandPg.line(offset + i, 260 - (basicTile.lrTile.arrivalProbabilityArray[i / 30] * 100 / 5), offset + i, + 260); + } + demandPg.endDraw(); + } + +// +// This is a script that allows one to open a new canvas for the purpose +// of simple 2D projection mapping, such as on a flat table surface +// +// Right now, only appears to work in windows... +// +// To use this example in the real world, you need a projector +// and a surface you want to project your Processing sketch onto. +// +// Simply press the 'c' key and drag the corners of the +// CornerPinSurface so that they +// match the physical surface's corners. The result will be an +// undistorted projection, regardless of projector position or +// orientation. +// +// You can also create more than one Surface object, and project +// onto multiple flat surfaces using a single projector. +// +// This extra flexbility can comes at the sacrifice of more or +// less pixel resolution, depending on your projector and how +// many surfaces you want to map. +// + + + + +// Visualization may show 2D projection visualization, or not +boolean displayProjection2D = false; +//int projectorOffset = screenWidth; + +boolean testProjectorOnMac = false; + +// defines Keystone settings from xml file in parent folder +Keystone ks; + +// defines various drawing surfaces, all pre-calibrated, to project +CornerPinSurface surface; +PGraphics offscreen; +PImage projector; + +// New Application Window Parameters +PFrameI proj2D = null; // f defines window to open new applet in +projApplet applet; // applet acts as new set of setup() and draw() functions that operate in parallel + +// Run Anything Needed to have Projection mapping work +public void initializeProjection2D() { + println("Projector Info: " + projectorWidth + ", " + projectorHeight + ", " + projectorOffset); + //toggleProjection(getButtonIndex(buttonNames[21])); +} + +public class PFrameI extends JFrame { + public PFrameI() { + setBounds(0, 0, projectorWidth, projectorHeight ); + setLocation(projectorOffset, 0); + applet = new projApplet(); + setResizable(false); + setUndecorated(true); + setAlwaysOnTop(true); + add(applet); + applet.init(); + show(); + setTitle("Projection2D"); + } +} + +public void showProjection2D() { + if (proj2D == null) { + proj2D = new PFrameI(); + } + proj2D.setVisible(true); +} + +public void closeProjection2D() { + proj2D.setVisible(false); +} + +public void resetProjection2D() { + initializeProjection2D(); + if (proj2D != null) { + proj2D.dispose(); + proj2D = new PFrameI(); + if (displayProjection2D) { + showProjection2D(); + } else { + closeProjection2D(); + } + } +} + +public class projApplet extends PApplet { + public void setup() { + // Keystone will only work with P3D or OPENGL renderers, + // since it relies on texture mapping to deform + size(projectorWidth, projectorHeight, P2D); + + ks = new Keystone(this);; + + reset(); + } + + public void reset() { + surface = ks.createCornerPinSurface(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT, 20); + offscreen = createGraphics(TABLE_IMAGE_HEIGHT, TABLE_IMAGE_HEIGHT); + + try{ + ks.load(); + } catch(RuntimeException e){ + println("No Keystone.xml. Save one first if you want to load one."); + } + } + + public void draw() { + + // Convert the mouse coordinate into surface coordinates + // this will allow you to use mouse events inside the + // surface from your screen. + PVector surfaceMouse = surface.getTransformedMouse(); + + // most likely, you'll want a black background to minimize + // bleeding around your projection area + background(0); + + // Draw the scene, offscreen + renderCanvas(offscreen, 0); + surface.render(offscreen); + + } + + public void renderCanvas(PGraphics p, int x_offset) { + // Draw the scene, offscreen + p.beginDraw(); + p.clear(); + p.translate(x_offset, 0); + p.image(projector, 0, 0); + p.endDraw(); + } + + public void keyPressed() { + switch(key) { + case 'c': + // enter/leave calibration mode, where surfaces can be warped + // and moved + ks.toggleCalibration(); + break; + + case 'l': + // loads the saved layout + ks.load(); + break; + + case 's': + // saves the layout + ks.save(); + break; + + case '`': + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + break; + } + } +} + +public void toggle2DProjection() { + if (System.getProperty("os.name").substring(0,3).equals("Mac")) { + testProjectorOnMac = !testProjectorOnMac; + println("Test on Mac = " + testProjectorOnMac); + println("Projection Mapping Currently not Supported for MacOS"); + } else { + if (displayProjection2D) { + displayProjection2D = false; + closeProjection2D(); + } else { + displayProjection2D = true; + showProjection2D(); + } + } +} + + +// Principally, this script ensures that a string is "caught" via UDP and coded into principal inputs of: +// - tablePieceInput[][] or tablePieceInput[][][2] (rotation) +// - UMax, VMax + + +int portIN = 6152; + + +UDP udp; // define the UDP object + +boolean busyImporting = false; +boolean viaUDP = true; +boolean changeDetected = false; +boolean outputReady = false; + +public void initUDP() { + if (viaUDP) { + udp = new UDP( this, portIN ); + //udp.log( true ); // <-- printout the connection activity + udp.listen( true ); + } +} + +public void ImportData(String inputStr[]) { + if (inputStr[0].equals("COLORTIZER")) { + parseColortizerStrings(inputStr); + } + busyImporting = false; +} + +public void parseColortizerStrings(String data[]) { + + for (int i=0 ; i departureList; + public ArrayList arrivalList; + public ArrayList movingHistoryList; + + Vehicle(int _x, int _y, boolean _isHorizontalStreet, boolean _isIntersection) { + x=_x; + y=_y; + isHorizontalStreet=_isHorizontalStreet; + isIntersection=_isIntersection; + departureList = new ArrayList (); + arrivalList = new ArrayList (); + movingHistoryList = new ArrayList (); + } + + //Parameter Update + void paramUpdate() { + isHorizontalStreet=false; + isIntersection=false; + streetNumber=0; + if (isHorizontalStreetCheck()) { + isHorizontalStreet=true; + streetNumber=((y+5-2)/5)-1; + } else { + streetNumber=((x+5-2)/5)-1; + } + if (isVerticalStreetCheck()&&isHorizontalStreetCheck()) + isIntersection=true; + } + + boolean isHorizontalStreetCheck() { + boolean result=false; + if ((y-2+5)%5==0) + result = true; + return result; + } + + boolean isVerticalStreetCheck() { + boolean result=false; + if ((x-2+5)%5==0) + result = true; + return result; + } + + //Vehicle Movement + void move() { + paramUpdate(); + movingHistoryUpdate(); + if (departureList.size()>0 || arrivalList.size()>0) { + if (departureList.size()>0) { + eachMove(departureList); + } else { + eachMove(arrivalList); + } + } + } + + void movingHistoryUpdate() { + Demand tmpVehiclePosition=new Demand(x, y); + if (!(departureList.size()==0&&arrivalList.size()==0)) + movingHistoryList.add(tmpVehiclePosition); + if (departureList.size()==0&&arrivalList.size()==0&&movingHistoryList.size()>0) + movingHistoryList.remove(0); + if (movingHistoryList.size()>=UrbanAutonomous.simParam.vehicleHistorySize) + movingHistoryList.remove(0); + } + + void eachMove(ArrayList tmpList) { + if (isSamePoint(tmpList.get(0))) { + tmpList.remove(0); + } else if (isSameStreet(tmpList.get(0))) { + if (tmpList.get(0).isHorizontalStreet) + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + else + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + } else { + if (isIntersection) { + if (tmpList.get(0).isHorizontalStreet) + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + else + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + } else { + if (isHorizontalStreet) { + if (tmpList.get(0).isHorizontalStreet) { + if (x>77) { + x-=1; + } else { + x+=1; + } + } else { + x += (tmpList.get(0).x - x)/ abs(tmpList.get(0).x - x) ; + } + } else { + if (tmpList.get(0).isHorizontalStreet) { + y += (tmpList.get(0).y - y)/ abs(tmpList.get(0).y - y) ; + } else { + if (y>77) { + y-=1; + } else { + y+=1; + } + } + } + } + } + } + + boolean isSameStreet(Demand tmpDemand) { + boolean result=false; + if (tmpDemand.streetNumber==streetNumber && tmpDemand.isHorizontalStreet == isHorizontalStreet) + result=true; + else if (isIntersection) { + if (tmpDemand.isHorizontalStreet) { + if ((((y-2+5)/5)-1)==tmpDemand.streetNumber) + result=true; + } else { + if ((((x-2+5)/5)-1)==tmpDemand.streetNumber) + result=true; + } + } + return result; + } + + boolean isSamePoint(Demand tmpDemand) { + boolean result=false; + if (tmpDemand.x==x && tmpDemand.y == y) + result=true; + return result; + } + } diff --git a/Processing/Misc/UrbanAutonomous/build-tmp/source/VehicleStack.java b/Processing/Misc/UrbanAutonomous/build-tmp/source/VehicleStack.java new file mode 100644 index 0000000..4d6deaf --- /dev/null +++ b/Processing/Misc/UrbanAutonomous/build-tmp/source/VehicleStack.java @@ -0,0 +1,60 @@ + +import java.util.ArrayList; + + +import processing.core.PApplet; + +public class VehicleStack extends PApplet{ + public ArrayList vehicleList; + public boolean isHorizontalStreet; + public VehicleStack() { + vehicleGen(); + isHorizontalStreet =true; + } + public void vehicleGen() { + vehicleList = new ArrayList (); + for (int i=0; i