Rotating text not the position of the text in processing - java

i am trying to make a clock and have all the numbers in the correct place but they are all rotated e.g. 6 is upside down whereas 12 is correct. is there anyway to rotate just the text not the position of the text?
my code is
push();
textSize(48);
for (int i = 1; i < 13; i++) {
int offset = -15;
if (str(i).length() == 2) {
offset -= 14.5;
}
rotate(radians(30));
text(i, offset, -350);
//println(i*30);
}
pop();

Without seeing the code my hunch is you use rotate(), but probably you don't use pushMatrix()/popMatrix(); to isolate the coordinate space to local one that can be temporarily rotated.
I recommend reading the 2D Transformations tutorial
As the tutorial mentions, the order of transformations matters:
size(300, 300);
background(0);
stroke(255);
// center align text
textAlign(CENTER);
// global translation to center
translate(width / 2, height / 2);
int hours = 12;
// an angle section (360/12 = 30 degrees), but in radians
float angleIncrement = TWO_PI / hours;
// distance from center
float radius = 100;
for(int i = 0 ; i < hours; i++){
// calculate the angle for each hour, subtracting a bit because angle 0 points to the right, not top (12 o'clock)
// remember this offset: it may come in handy when drawing clock handles ;)
float angle = (angleIncrement * i) - (QUARTER_PI * 4/3);
// isolate coordinate space
pushMatrix();
// rotate from global center by each hour angle
rotate(angle);
// translate from locally rotated center based on radius
translate(radius, 0);
// undo local rotation so text is straight
rotate(-angle);
// render text
text(i+1,0,0);
// exit local coordinate system, back to global coordinates after this
popMatrix();
}
Here is the same example with a helper function to help visualise the coordinate systems:
void setup() {
size(300, 300);
background(0);
stroke(255);
// center align text
textAlign(CENTER);
drawCoordinateSystem("1.original cooordinates",60, 255);
// global translation to center
translate(width / 2, height / 2);
drawCoordinateSystem("2.global center",60, 64);
int hours = 12;
// an angle section (360/12 = 30 degrees), but in radians
float angleIncrement = TWO_PI / hours;
// distance from center
float radius = 100;
for (int i = 0; i < hours; i++) {
// calculate the angle for each hour, subtracting a bit because angle 0 points to the right, not top (12 o'clock)
// remember this offset: it may come in handy when drawing clock handles ;)
float angle = (angleIncrement * i) - (QUARTER_PI * 4/3);
// isolate coordinate space
pushMatrix();
// rotate from global center by each hour angle
rotate(angle);
if(i == 0){
drawCoordinateSystem("3.local+rotation",60, 127);
}
// translate from locally rotated center based on radius
translate(radius, 0);
if(i == 0){
drawCoordinateSystem("4.local+rot.+\ntrans.",60, 192);
}
// undo local rotation so text is straight
rotate(-angle);
if(i == 0){
drawCoordinateSystem("\n5.prev.\n-rot.",60, 255);
}
// render text
text(i+1, 0, 0);
// exit local coordinate system, back to global coordinates after this
popMatrix();
}
}
void drawCoordinateSystem(String label, float size, float alpha){
pushStyle();
textAlign(LEFT);
strokeWeight(3);
// x axis
stroke(192, 0, 0, alpha);
line(0, 0, size, 0);
// y axis
stroke(0, 192, 0, alpha);
line(0, 0, 0, size);
text(label, 10, 15);
popStyle();
}
Note that the indent is not required for pushMatrix()/popMatrix(), it's more of a visual cue to aid when you read code to remember coordinate system nesting.
This is over the top and you won't need the code bellow, but hopefully it's a fun visualisation:
PImage screenshot;
String[] labels = {"1.original cooordinates","2.global center\ntranslate(width / 2, height / 2)",
"3.local+rotation\npushMatrix();\nrotate(angle)",
"4.local+rot.+\ntrans.\ntranslate(radius, 0)","5.previous-rot.\nrotate(-angle)",""};
PMatrix2D[] systems = new PMatrix2D[labels.length];
PMatrix2D lerpMatrix = new PMatrix2D();
void setup() {
size(300, 300);
background(0);
stroke(255);
// center align text
textAlign(CENTER);
// "1.original cooordinates"
systems[0] = new PMatrix2D();
// global translation to center
translate(width / 2, height / 2);
// "2.global center"
systems[1] = systems[0].get();
systems[1].translate(width / 2, height / 2);
int hours = 12;
// an angle section (360/12 = 30 degrees), but in radians
float angleIncrement = TWO_PI / hours;
// distance from center
float radius = 100;
for (int i = 0; i < hours; i++) {
// calculate the angle for each hour, subtracting a bit because angle 0 points to the right, not top (12 o'clock)
// remember this offset: it may come in handy when drawing clock handles ;)
float angle = (angleIncrement * i) - (QUARTER_PI * 4/3);
// isolate coordinate space
pushMatrix();
// rotate from global center by each hour angle
rotate(angle);
if(i == 0){
// "3.local+rotation"
PMatrix2D local = new PMatrix2D();
local.apply(systems[1]);
local.rotate(angle);
systems[2] = local.get();
}
// translate from locally rotated center based on radius
translate(radius, 0);
if(i == 0){
// "4.local+rot.+\ntrans."
systems[3] = systems[2].get();
systems[3].translate(radius,0);
}
// undo local rotation so text is straight
rotate(-angle);
if(i == 0){
// "\n5.prev.\n-rot."
systems[4] = systems[3].get();
systems[4].rotate(-angle);
systems[5] = systems[4];
}
// render text
text(i+1, 0, 0);
// exit local coordinate system, back to global coordinates after this
popMatrix();
}
screenshot = get();
}
void draw(){
image(screenshot,0, 0);
animateCoordinateSystems();
text("mouse mouse on X axis", width / 2, height - 12);
}
void animateCoordinateSystems(){
float mapping = map(constrain(mouseX, 0, width), 0, width, 0.0, 1.0);
float globalT = (float)(labels.length -1) * mapping;
int index = (int)globalT;
float localT = globalT - index;
lerpMatrix(systems[index], systems[index+1], localT, lerpMatrix);
pushMatrix();
applyMatrix(lerpMatrix);
drawCoordinateSystem(labels[index] + (labels[index+1].length() > 0 ? "\ntransitions to\n" + labels[index+1] : ""),60, 255);
popMatrix();
}
void lerpMatrix(PMatrix2D from, PMatrix2D to, float t, PMatrix2D result){
result.m00 = lerp(from.m00, to.m00, t);
result.m01 = lerp(from.m01, to.m01, t);
result.m02 = lerp(from.m02, to.m02, t);
result.m10 = lerp(from.m10, to.m10, t);
result.m11 = lerp(from.m11, to.m11, t);
result.m12 = lerp(from.m12, to.m12, t);
}
void drawCoordinateSystem(String label, float size, float alpha){
pushStyle();
textAlign(LEFT);
strokeWeight(3);
// x axis
stroke(192, 0, 0, alpha);
line(0, 0, size, 0);
// y axis
stroke(0, 192, 0, alpha);
line(0, 0, 0, size);
text(label, 10, 15);
popStyle();
}

Related

How to draw lines pointing to mouse in Processing

I am trying to make a program where there are lines in a grid pointing towards the mouse like magnets. I am a beginner in Processing, can someone point me towards a tutorial on how to do that or give me some code and explain what it does?
int x1 = 0;
int x2 = 0;
int y1 = 0;
int y2 = 0;
void setup() {
size(200, 200);
}
void draw() {
background(255, 255, 0);
x1 = (mouseX + 100) / 2;
y1 = (mouseY + 100) / 2;
x2 = -1 * x1 + 200;
y2 = -1 * y1 + 200;
line(x1, y1, x2, y2);
}
There's plenty of solutions for this project. One of the easiest is to use Processing's PVector class.
The PVector class can be used for two or three dimensional vectors. A vector is an entity that has both magnitude and direction. The PVector class, however, stores the components of the vector (x,y for 2D, and x,y,z for 3D). The magnitude and direction are calculated from the components and can be accessed via the methods mag() and heading().
A two dimensional vector in Processing is defined through x and y components:
PVector v = new PVector(xComponent, yComponent);
With some mathematical formulae, you can determine magnitude and direction using the x- and y-components. But we don't need to determine these.
Below, I've attached completed solution code. Most of it should make sense to you. But it's worth understanding what is going on with PVector.
A nested for loop within void draw() contains x and y variables that represent the coordinates of each grid vertex.
We first define PVector v as a vector given by an x-component of mouseX - x, or the difference between the x-positions of the mouse and each grid point. Similarly, the y-component given by mouseY - y has the same difference.
Creating a variable PVector u initialized from v.setMag(15) holds a PVector that has the same direction as v, but with a length of just 15.
Now to draw the lines. Vectors represent an offset, not a position (in this case), so drawing a line from a grid point to an offset of a grid point is key.
Hence line(x, y, x + u.x, y + u.y), where u.x and u.y are the x- and y-components of the vector u.
void setup() {
size(600, 600); // Set the size of the canvas to 600x600.
}
void draw() {
background(255);
stroke(200); // Set the stroke color to black
int distVertLine = width / 10; // This variable defines the distance between each subsequent vertical line.
for(int i = 0; i < width; i += distVertLine) {
line(i, 0, i, height); // Draw a line at x=i starting at the top of the canvas (y=0) and going to the bottom (y=height)
}
int distHorizLine = height / 10; // This variable defines the distance between each subsequent vertical line.
for(int i = 0; i < width; i += distHorizLine) {
line(0, i, width, i); // Draw a line at y=i starting at the left of the canvas (x=0) and going to the right (x=width)
}
stroke(0); // Set the stroke to black.
// Use a nested for loop to iterate through all grid vertices.
for(int x = 0; x <= width; x += width/10) {
for(int y = 0; y <= height; y += height/10) {
PVector v = new PVector(mouseX - x, mouseY - y); // Define a vector that points in the direction of the mouse from each grid point.
PVector u = v.setMag(15); // Make the vector have a length of 15 units.
line(x, y, x + u.x, y + u.y); // Draw a line from the grid vertex to the terminal point given by the vector.
}
}
}
The answer already given by Ben Myers is excellent! The code below has a few small modifications:
the two for loops for the grid lines have been combined (since width and height are equal);
the construction of the vector is combined with setting the magnitude;
some minor changes to colors and comments.
Modified code:
void setup() {
// Set the size of the canvas to 600x600 pixels.
size(600, 600);
}
void draw() {
// There are 10x10 grid cells that each have a size of 60x60 pixels.
int gridSize = width / 10;
// Set the background color to anthracite and the stroke color to orange.
background(56, 62, 66);
stroke(235, 113, 52);
// Draw vertical and horizontal grid lines.
for (int lineIndex = 0; lineIndex < gridSize; lineIndex++) {
line(lineIndex * gridSize, 0, lineIndex * gridSize, height);
line(0, lineIndex * gridSize, width, lineIndex * gridSize);
}
// Set the stroke color to blue.
stroke(0, 139, 225);
// Use a nested for loop to iterate through all grid cells.
for (int x = 0; x <= width; x += gridSize) {
for (int y = 0; y <= height; y += gridSize) {
// Define a vector that points in the direction of the mouse from
// each grid point and set the vector length to 15 units.
PVector vector = new PVector(mouseX - x, mouseY - y).setMag(15);
// Draw a line from the grid point to the end point using the vector.
line(x, y, x + vector.x, y + vector.y);
}
}
}

Problem drawling points around rotating plane in Processing?

I'm prototyping a script to plot equally spaced points around a rotating plane and Processing is producing unexpected results?
This is my code:
int WHITE = 255;
int BLACK = 0;
void setup() {
size(500, 500);
}
void draw() {
background(WHITE);
translate(width/2, height/2); // move origin to center of window
// center ellipse
noStroke();
fill(255, 0, 0);
ellipse(0, 0, 10, 10); // center point, red
// satellite ellipses
fill(BLACK);
int points = 4;
for (int i = 0; i < points; i++) {
rotate(i * (TWO_PI / points));
ellipse(0, 100, 10, 10); // after plane rotation, plot point of size(10, 10), 100 points above y axis
}
}
When points = 4 I get the output I would expect, but when points = 5 // also when points = 3 or > 4, I get an output that is missing plotted points but still spaced correctly.
Why is this happening?
You're rotating too much: you don't want to rotate by i * angle at every iteration, because if we do we end up rotating so much that points end up overlapping. For example, with the code as is, with 3 points we want to place them at 0, 120, and 240 degrees (or, 120, 240, 360). But that's not what happens:
when i=0 we rotate by 0 degrees. So far so good.
when i=1 we rotate by 120 degrees on top of 0. Still good.
when i=2 we rotate by 240 degrees on top of 120. That's 120 degrees too far!
That's clearly not what we want, so just rotate by the fixed angle TAU / points and things'll work as expected:
for (int i = 0; i < points; i++) {
rotate(TAU / points);
ellipse(0, 100, 10, 10);
}
Alternatively, keep the incrementing angle, but then place the points without using rotate(), by using trigonometry to compute the placement:
float x = 0, y = 100, nx, ny, angle;
for (int i = 0; i < points; i++) {
angle = i * TAU / points;
nx = x * cos(a) - y * sin(a);
ny = x * sin(a) + y * cos(a);
ellipse(nx, ny, 10, 10);
}

curveVertex() not drawling in Processing?

I'm trying to create a script that drawls a curve through 'n' vertexes equally spaced around the center of an ellipse.
The reason I'm not just drawling an ellipse around the center ellipse is because I eventually want to connect a micro-controller to Processing where the data points acquired from the 'n' amount of sensors will vary the height ('y') of each vertex, creating constantly changing, irregular curves around the center ellipse such as this possible curve:
Essentially, this is supposed to be a data visualizer, but I cannot figure out why this is not working or how to achieve this effect after going through examples and the documentation on https://processing.org/reference/.
Here is my code:
color WHITE = color(255);
color BLACK = color(0);
void setup() {
size(500, 500);
}
void draw() {
background(WHITE);
translate(width/2, height/2); // move origin to center of window
// center ellipse
noStroke();
fill(color(255, 0, 0));
ellipse(0, 0, 10, 10); // center point, red
fill(BLACK);
int n = 10;
int y = 100;
float angle = TWO_PI / n;
beginShape();
for (int i = 0; i < n; i++) {
rotate(angle);
curveVertex(0, y);
}
endShape();
}
The matrix operations like rotate do not transform the single vertices in a shape. The current matrix is applied to the entire shape when it is draw (at endShape). You've to calculate all the vertex coordinates:
Create a ArrayList of PVector, fill it with points and draw it in a loop:
color WHITE = color(255);
color BLACK = color(0);
ArrayList<PVector> points = new ArrayList<PVector>();
void setup() {
size(500, 500);
int n = 10;
int radius = 100;
for (int i = 0; i <= n; i++) {
float angle = TWO_PI * (float)i/n;
points.add(new PVector(cos(angle)*radius, sin(angle)*radius));
}
}
void draw() {
background(WHITE);
translate(width/2, height/2);
noFill();
stroke(255, 0, 0);
beginShape();
PVector last = points.get(points.size()-1);
curveVertex(last.x, last.y);
for (int i = 0; i < points.size(); i++) {
PVector p = points.get(i);
curveVertex(p.x, p.y);
}
PVector first = points.get(0);
curveVertex(first.x, first.y);
endShape();
}

Kinect & Processing: Passing skeleton hand data to mouse position

I've been working on this a while and feel so close! Should be easy, but I'm still new to this.
The skeleton hand data is being passed in as joints[KinectPV2.JointType_HandLeft] and can be accessed through joint.getX() and joint.getY(). I want to pass this data into the update function to replace mouseX and mouseY. I'm guessing I have to create global variables to access it within the update function or maybe I have to pass the skeleton data as parameters into the update function? How can I replace the mouse position data with the hand position?
import KinectPV2.*;
KinectPV2 kinect;
private class MyFluidData implements DwFluid2D.FluidData{
// update() is called during the fluid-simulation update step.
#Override
public void update(DwFluid2D fluid) {
float px, py, vx, vy, radius, vscale, temperature;
radius = 15;
vscale = 10;
px = width/2;
py = 50;
vx = 1 * +vscale;
vy = 1 * vscale;
radius = 40;
temperature = 1f;
fluid.addDensity(px, py, radius, 0.2f, 0.3f, 0.5f, 1.0f);
fluid.addTemperature(px, py, radius, temperature);
particles.spawn(fluid, px, py, radius, 100);
boolean mouse_input = mousePressed;
// add impulse: density + velocity, particles
if(mouse_input && mouseButton == LEFT){
radius = 15;
vscale = 15;
px = mouseX;
py = height-mouseY;
vx = (mouseX - pmouseX) * +vscale;
vy = (mouseY - pmouseY) * -vscale;
fluid.addDensity (px, py, radius, 0.25f, 0.0f, 0.1f, 1.0f);
fluid.addVelocity(px, py, radius, vx, vy);
particles.spawn(fluid, px, py, radius*2, 300);
}
// add impulse: density + temperature, particles
if(mouse_input && mouseButton == CENTER){
radius = 15;
vscale = 15;
px = mouseX;
py = height-mouseY;
temperature = 2f;
fluid.addDensity(px, py, radius, 0.25f, 0.0f, 0.1f, 1.0f);
fluid.addTemperature(px, py, radius, temperature);
particles.spawn(fluid, px, py, radius, 100);
}
// particles
if(mouse_input && mouseButton == RIGHT){
px = mouseX;
py = height - 1 - mouseY; // invert
radius = 50;
particles.spawn(fluid, px, py, radius, 300);
}
}
}
int viewport_w = 1280;
int viewport_h = 720;
int viewport_x = 230;
int viewport_y = 0;
int gui_w = 200;
int gui_x = 20;
int gui_y = 20;
int fluidgrid_scale = 3;
DwFluid2D fluid;
// render targets
PGraphics2D pg_fluid;
//texture-buffer, for adding obstacles
PGraphics2D pg_obstacles;
// custom particle system
MyParticleSystem particles;
// some state variables for the GUI/display
int BACKGROUND_COLOR = 0;
boolean UPDATE_FLUID = true;
boolean DISPLAY_FLUID_TEXTURES = false;
boolean DISPLAY_FLUID_VECTORS = false;
int DISPLAY_fluid_texture_mode = 0;
boolean DISPLAY_PARTICLES = true;
public void settings() {
size(viewport_w, viewport_h, P2D);
smooth(4);
}
public void setup() {
surface.setLocation(viewport_x, viewport_y);
// main library context
DwPixelFlow context = new DwPixelFlow(this);
context.print();
context.printGL();
// fluid simulation
fluid = new DwFluid2D(context, viewport_w, viewport_h, fluidgrid_scale);
// set some simulation parameters
fluid.param.dissipation_density = 0.999f;
fluid.param.dissipation_velocity = 0.99f;
fluid.param.dissipation_temperature = 0.80f;
fluid.param.vorticity = 0.10f;
fluid.param.timestep = 0.25f;
fluid.param.gridscale = 8f;
// interface for adding data to the fluid simulation
MyFluidData cb_fluid_data = new MyFluidData();
fluid.addCallback_FluiData(cb_fluid_data);
// pgraphics for fluid
pg_fluid = (PGraphics2D) createGraphics(viewport_w, viewport_h, P2D);
pg_fluid.smooth(4);
pg_fluid.beginDraw();
pg_fluid.background(BACKGROUND_COLOR);
pg_fluid.endDraw();
// pgraphics for obstacles
pg_obstacles = (PGraphics2D) createGraphics(viewport_w, viewport_h, P2D);
pg_obstacles.smooth(4);
pg_obstacles.beginDraw();
pg_obstacles.clear();
float radius;
radius = 200;
pg_obstacles.stroke(64);
pg_obstacles.strokeWeight(1);
pg_obstacles.fill(0);
pg_obstacles.rect(1*width/2f, 1*height/4f, radius, radius/2, 10);
pg_obstacles.stroke(64);
pg_obstacles.strokeWeight(1);
pg_obstacles.fill(0);
pg_obstacles.rect(1*width/3.5f, 1*height/2.5f, radius, radius/2, 10);
//// border-obstacle
//pg_obstacles.strokeWeight(20);
//pg_obstacles.stroke(64);
//pg_obstacles.noFill();
//pg_obstacles.rect(0, 0, pg_obstacles.width, pg_obstacles.height);
pg_obstacles.endDraw();
fluid.addObstacles(pg_obstacles);
// custom particle object
particles = new MyParticleSystem(context, 1024 * 1024);
kinect = new KinectPV2(this);
//Enables depth and Body tracking (mask image)
kinect.enableDepthMaskImg(true);
kinect.enableSkeletonDepthMap(true);
kinect.init();
background(0);
frameRate(60);
}
public void draw() {
PImage imgC = kinect.getDepthMaskImage();
image(imgC, 0, 0, 320, 240);
//get the skeletons as an Arraylist of KSkeletons
ArrayList<KSkeleton> skeletonArray = kinect.getSkeletonDepthMap();
//individual joints
for (int i = 0; i < skeletonArray.size(); i++) {
KSkeleton skeleton = (KSkeleton) skeletonArray.get(i);
//if the skeleton is being tracked compute the skleton joints
if (skeleton.isTracked()) {
KJoint[] joints = skeleton.getJoints();
color col = skeleton.getIndexColor();
fill(col);
stroke(col);
drawHandState(joints[KinectPV2.JointType_HandRight]);
drawHandState(joints[KinectPV2.JointType_HandLeft]);
}
}
// update simulation
if(UPDATE_FLUID){
fluid.addObstacles(pg_obstacles);
fluid.update();
particles.update(fluid);
}
// clear render target
pg_fluid.beginDraw();
pg_fluid.background(BACKGROUND_COLOR);
pg_fluid.endDraw();
// render fluid stuff
if(DISPLAY_FLUID_TEXTURES){
// render: density (0), temperature (1), pressure (2), velocity (3)
fluid.renderFluidTextures(pg_fluid, DISPLAY_fluid_texture_mode);
}
if(DISPLAY_FLUID_VECTORS){
// render: velocity vector field
fluid.renderFluidVectors(pg_fluid, 10);
}
if( DISPLAY_PARTICLES){
// render: particles; 0 ... points, 1 ...sprite texture, 2 ... dynamic points
particles.render(pg_fluid, BACKGROUND_COLOR);
}
// display
image(pg_fluid , 320, 0);
image(pg_obstacles, 320, 0);
// display number of particles as text
//String txt_num_particles = String.format("Particles %,d", particles.ALIVE_PARTICLES);
//fill(0, 0, 0, 220);
//noStroke();
//rect(10, height-10, 160, -30);
//fill(255,128,0);
//text(txt_num_particles, 20, height-20);
// info
//String txt_fps = String.format(getClass().getName()+ " [size %d/%d] [frame %d] [fps %6.2f]", fluid.fluid_w, fluid.fluid_h, fluid.simulation_step, frameRate);
//surface.setTitle(txt_fps);
}
//draw a ellipse depending on the hand state
void drawHandState(KJoint joint) {
noStroke();
handState(joint.getState());
//println(joint.getState());
pushMatrix();
translate(joint.getX(), joint.getY(), joint.getZ());
//println(joint.getX(), joint.getY(), joint.getZ());
ellipse(joint.getX(), joint.getY(), 70, 70);
popMatrix();
}
/*
Different hand state
KinectPV2.HandState_Open
KinectPV2.HandState_Closed
KinectPV2.HandState_Lasso
KinectPV2.HandState_NotTracked
*/
//Depending on the hand state change the color
void handState(int handState) {
switch(handState) {
case KinectPV2.HandState_Open:
fill(0, 255, 0);
break;
case KinectPV2.HandState_Closed:
fill(255, 0, 0);
break;
case KinectPV2.HandState_Lasso:
fill(0, 0, 255);
break;
case KinectPV2.HandState_NotTracked:
fill(100, 100, 100);
break;
}
}
I'm guessing I have to create global variables to access it within the update function or maybe I have to pass the skeleton data as parameters into the update function?
What happened when you tried those approaches?
Either approach sounds fine. You could store the variables in a sketch-level variable, set those variables from the kinect code, then use those variables in your drawing code. Or you could pass the variables as a parameter to the drawing code. Either should work fine. I'd probably go for the first approach because it sounds easier to me, but that's just my personal preference.
I suggest working in smaller chunks. Create a separate program that ignores the kinect for now. Create a hard-coded sketch-level variable that holds the same type of information you'd get from the kinect. Then write drawing code that uses that hard-coded variable to draw the frame. Get that working perfectly before you try adding the kinect code back in.
Then if you get stuck on a specific step, you can post a MCVE and we can go from there. Good luck.

Centering map or camera 2D game

I've tried so many solutions that it's possible that my code is a bit mixed up, but whatever I try, it just won't work.
Basically I made a map with Tiled, where my player can run around and bump into stuff. I want the whole map to be visible for the whole time (it's 20 by 15, 64 pixels a tile). The camera doesn't need to move around or follow the player, it has to stay still at the center of the map.
The problem is that the map only shows in the upper right corner of the screen. When I centered the camera to the map itself it messed up the collission detection, (bumping into trees while they were not visible & walking through visible trees). So what I want to do is center the map to 0,0 where my camera also is (at least I think..).
Another thing I'd like to accomplish is that the size of the map gets resized to match different mobile phones. Tried to accomplish this with the stretchviewport, but haven't been able to test this.
public class PlayScreen implements Screen {
TiledMap map;
OrthogonalTiledMapRenderer mapRenderer;
OrthographicCamera cam;
float unitScale = 1 / 64f;
OrthogonalTiledMapRenderer renderer = new OrthogonalTiledMapRenderer(map, unitScale);
Viewport viewport;
public void show() {
map = new TmxMapLoader().load("maps/map.tmx");
mapRenderer = new OrthogonalTiledMapRenderer(map);
cam = new OrthographicCamera(Gdx.graphics.getWidth() / 2, Gdx.graphics.getHeight() / 2);
cam.setToOrtho(false);
viewport = new StretchViewport(1280, 960, cam);
bounds = new ArrayList<Rectangle>();
for(int i = 0; i < 20; i++){
for(int j = 0; j < 15; j++){
TiledMapTileLayer cur = (TiledMapTileLayer) map.getLayers().get(1);
Cell cell = new Cell();
Vector3 center = new Vector3(cur.getWidth() * cur.getTileWidth() / 2, cur.getHeight() * cur.getTileHeight() / 2, 0);
cam.position.set(Gdx.graphics.getWidth() / 2, Gdx.graphics.getHeight() / 2, 0);
cam.update();
if(cur.getCell(i,j) != null){ //null = first layer != --> if its not
cell = cur.getCell(i, j);
System.out.println(i + ", " + j + ", " + cell.getTile().getId());
bounds.add(new Rectangle(i * 64, j * 64, 64 , 64));
}
}
}
public void render(float delta) {
Gdx.gl.glClearColor(1, 1, 1, 1);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
mapRenderer.setView(cam);
mapRenderer.render();
cam.position.set(0, 0, 0);
cam.update();
batch.setProjectionMatrix(cam.combined);
batch.begin();
batch.draw(player.getCurrentFrame(), player.getPosition().x , player.getPosition().y);
player.update();
for(int i = 0; i < bounds.size(); i++){
if(bounds.get(i).overlaps(player.getBounds())){
int x = (int)bounds.get(i).x / 64;
int y = (int)bounds.get(i).y / 64;
TiledMapTileLayer cur = (TiledMapTileLayer)map.getLayers().get(1);
Cell cell = cur.getCell(x, y);
if(cell.getTile().getProperties().containsKey("blocked")){
System.out.println("bush");
}
player.reAdjust();
}
}
batch.end();
}
public void resize(int width, int height) {
viewport.update(width, height);
}
Nevermind, I deleted: cam.position.set(0, 0, 0); and everything seems to work just fine. Guess I already made some changes what caused it to work, just didn't see it cause this was still around.

Categories