There are surely a million different problems in this sketch, but go easy since it's my first try at processing (and java). If you find more than what this post is about, let me know. I'll appreciate any help.
Like a previous post, this sketch is meant to plot the position of a high altitude balloon transmitting it's position from an xbee. The string the xbee receives is saved using a serial capture to a file, and this sketch reads in each line using BufferedReader. The problem is the sketch tries to load the file when there's a partial string, leading to an error. Is there a way to force it to wait until the string has loaded?
Here's a sample of the transmitted data:
!!!47.6696,-71.4853,0.16,249.91,162.50,6
!!!47.6696,-71.4853,0.45,249.91,162.50,6
Here's the sketch, and the throw message is below:
BufferedReader reader;
import googlemapper.*;
import controlP5.*;
double mapCenterLat = 42.66656;
double mapCenterLon = -72.4831;
int zoomLevel =10;
String mapType = GoogleMapper.MAPTYPE_ROADMAP;
int mapWidth=640;
int mapHeight=480;
String inBuffer;
Boolean isGPSActive;
ArrayList<Double> lat = new ArrayList<Double>();
ArrayList<Double> lng = new ArrayList<Double>();
Double newLat;
Double newLng;
float cent_lat = 0;
float cent_lng = 0;
int x;
ControlP5 cp5;
int zoomSlider=15;
Slider abc;
PImage map;
GoogleMapper gMapper;
public void setup() {
//start reading the file with fake info
reader = createReader("serialcapture.txt");
//sets the window size to 640x480
size(640, 480);
smooth();
//creates new controls using the P5 Library
cp5 = new ControlP5(this);
cp5.addSlider("zoomSlider")
.setPosition(50, 100)
.setSize(40, 200)
.setRange(3, 21)
.setNumberOfTickMarks(18);
cp5.addButton("refresh")
.setValue(0)
.setPosition(50, 80)
.setSize(40, 19);
//sets the zoomlevel
zoomLevel=zoomSlider;
}
long interval = millis();
//function to run when refresh button is pressed
void refresh() {
loop();
println("refreshing map");
try {
interval = millis();
zoomLevel=zoomSlider;
if (cent_lat != 0) {
mapCenterLat = gMapper.y2lat(cent_lat);
mapCenterLon = gMapper.x2lon(cent_lng);
}
gMapper = new GoogleMapper(mapCenterLat, mapCenterLon, zoomLevel, mapType, mapWidth, mapHeight);
map = gMapper.getMap();
image(map, 0, 0);
lat.clear();
lng.clear();
reader.close();
reader = createReader("serialcapture.txt");
inBuffer = reader.readLine();
drawcourse(inBuffer);
cent_lat = 0;
cent_lng = 0;
}
catch(Exception e) {
e.printStackTrace();
}
x=0;
}
void draw() {
inBuffer = null;
//reads the data from the serial and stores it in a buffer
if (mousePressed && keyPressed) {
if (key == 'c' || key == 'C') {
cent_lat = mouseY;
cent_lng = mouseX;
}
}
try {
inBuffer = reader.readLine();
}
catch (IOException e) {
e.printStackTrace();
inBuffer = null;
delay(250);
}
if (inBuffer != null) {
drawcourse(inBuffer);
}
else return;
}
void drawcourse(String inBuffer) {
//*****display iteration in top left
background(0);
image(map, 0, 0);
fill(0);
textSize(16);
text("position: "+x, 10, 20);
x++;
inBuffer = inBuffer.substring(3);
//println(inBuffer);//for debugging inBuffer read
String[] op = inBuffer.split(",");
//only when we get valid data, split it to get coordinates
if (op.length==6) {
newLat = Double.valueOf(op[0]); //get latitude
newLng = Double.valueOf(op[1]); //get longitude
lat.add(newLat.doubleValue());
lng.add(newLng.doubleValue());
isGPSActive=true;
}
for (int i=1; i < lat.size()-1 ; i++)
{
if (lat.get(i)==null) return;
else {
float lat1 = (float) gMapper.lat2y(lat.get(i));
float lng1 = (float) gMapper.lon2x(lng.get(i));
float lat2 = (float) gMapper.lat2y(lat.get(i+1));
float lng2 = (float) gMapper.lon2x(lng.get(i+1));
stroke(0);
strokeWeight(2);
line(lng1, lat1, lng2, lat2);//draws the latest position on the screen
//ellipse(lng2, lat2, 5, 5);
//println(lat1+"-"+lng1+"|"+lat2+"-"+lng2);//debug output to see line positions
}
}
}
Error message:
Exception in thread "Animation Thread" java.lang.StringIndexOutOfBoundsException: String index out of range: -1
at java.lang.String.substring(String.java:1937)
at java.lang.String.substring(String.java:1904)
at googlemapper_testing__01.drawcourse(googlemapper_testing__01.java:135)
at googlemapper_testing__01.draw(googlemapper_testing__01.java:120)
at processing.core.PApplet.handleDraw(PApplet.java:2266)
at processing.core.PGraphicsJava2D.requestDraw(PGraphicsJava2D.java:243)
I'm creating a tool to track a weather balloon, but I'm stuck on a pretty basic part: drawing a line.
I have the file of fake GPS info being read to mimic the serial input, and then display the information in a line on the map created by googlemapper. I keep getting this error: "The method line(float, float, float, float) in the type PApplet is not applicable for the arguments (double, double, double, double)" and I know it's because of the doubles not working well with the draw function. How can I convert things so that this works?
The googlemapper library returns a double, but how can I convert this since everything I've tried so far returns "Type mismatch: cannot convert from double to int"
Here is my code:
BufferedReader reader;
import googlemapper.*;
import controlP5.*;
import guicomponents.*;
double mapCenterLat = 42.66656;
double mapCenterLon = -72.4831;
int zoomLevel =15;
String mapType = GoogleMapper.MAPTYPE_ROADMAP;
int mapWidth=640;
int mapHeight=480;
String inBuffer;
Boolean isGPSActive;
ArrayList<Double> lat ;
ArrayList<Double> lng ;
Double newLat;
Double newLng;
ControlP5 cp5;
int zoomSlider=7;
Slider abc;
PImage map;
GoogleMapper gMapper;
public void setup() {
//start reading the file with fake info
reader = createReader("C:/Documents and Settings/DWarren/My Documents/Processing/googlemapper_testing/fakegps.txt");
//sets the window size to 640x480
size(640, 480);
//creates new controls using the P5 Library
cp5 = new ControlP5(this);
cp5.addSlider("zoomSlider")
.setPosition(50, 100)
.setSize(40, 200)
.setRange(3, 21)
.setNumberOfTickMarks(9);
cp5.addButton("refresh")
.setValue(0)
.setPosition(50, 80)
.setSize(40, 19);
//sets the zoomlevel
zoomLevel=zoomSlider;
//loads the google map
gMapper = new GoogleMapper(mapCenterLat, mapCenterLon, zoomLevel, mapType, mapWidth, mapHeight);
//loads it to cache
map = gMapper.getMap();
//displays it
image(map, 0, 0);
}
long interval = millis();
//function to run when refresh button is pressed
public void refresh(int theValue) {
println("refreshing map");
try {
interval = millis();
zoomLevel=zoomSlider;
gMapper = new GoogleMapper(mapCenterLat, mapCenterLon, zoomLevel, mapType, mapWidth, mapHeight);
map = gMapper.getMap();
image(map, 0, 0);
}
catch(Exception e) {
e.printStackTrace();
}
}
void draw() {
try {
String inBuffer = reader.readLine();
}
catch (IOException e) {
e.printStackTrace();
inBuffer = null;
}
//String inBuffer = myPort.readString();
println(inBuffer);
String[] op = inBuffer.split(",");
//only when we get valid data, split it to get coordinates