Unable to detect if a rectangle is touched in libgdx - input

I have a rectangle with a sprite on it and I have to detect if the touch position lies within the rectangle.
This is my code,
if (Gdx.input.isTouched())
{
int x1 = Gdx.input.getX();
int y1 = Gdx.input.getY();
Vector3 inputs = new Vector3(x1, y1, 0);
gamecam.unproject(inputs);
Gdx.app.log("x" + inputs.x, "y" + inputs.y);
Gdx.app.log("rect" + rectangle.x, "rect" + rectangle.y);
if(rectangle.contains(inputs.x,inputs.y))
{
Gdx.app.log("x" + inputs.x, "y" + inputs.y);
Gdx.app.log("rect" + rectangle, "rect" + rectangle.y);
}
}
Rectangle definition,
BodyDef bdef = new BodyDef();
bdef.type = BodyDef.BodyType.StaticBody;
b2body = screen.getWorld().createBody(bdef);
rectangle = new Rectangle();
rectangle.setHeight(55);
rectangle.setWidth(55);
PolygonShape head = new PolygonShape();
rectangle.setX(300);
rectangle.setY(10);
bdef.position.set((rectangle.getX() - rectangle.getWidth() / 2) / MyJungleGame.PPM, (rectangle.getY() - rectangle.getHeight() / 2) / MyJungleGame.PPM);
head.setAsBox(rectangle.getWidth() / 2 / MyJungleGame.PPM, rectangle.getHeight() / 2 / MyJungleGame.PPM);
FixtureDef fdef = new FixtureDef();
fdef.shape = head;
setPosition(b2body.getPosition().x - getWidth() / 2, b2body.getPosition().y - getHeight() / 2);
This is my output,
The small rectangle at the bottom of the screen is the rectangle I created. But, nothing happens when I click it. I checked the coordinates and here is the log,
x-0.925: y-0.5625
rect300.0: rect10.0
x-0.925: y-0.5625
rect300.0: rect10.0
x-0.925: y-0.5625
I tried checking the touch using the below method,
if (inputs.x > sprite.getX() && inputs.x < sprite.getX() + sprite.getWidth())
{
if (inputs.y > sprite.getY() && inputs.y < sprite.getY() + sprite.getHeight())
{
Gdx.app.log("sprite touched", "");
}
}
This too doesn't work. Any idea where I made the mistake ? Please help . Thanks in advance

Since you are using Box2D, to detect collisions via the common way is more complicated to new users.
However, looking on your code...
I would advice taking this coordinates in consideration with PPM of your world :
int x1 = Gdx.input.getX();
int y1 = Gdx.input.getY();
Vector3 inputs = new Vector3(x1, y1, 0);
Also, If you are going to build a collision system with box2d, you should use this : http://www.aurelienribon.com/blog/2011/07/box2d-tutorial-collision-filtering/

Related

Horizontal Bar Chart direction

Is it possible to create Horizontal Bar Chart and draw bars from right to left? Just make mirror reflection. I can't use rotate in my xml because label also will be reversed.
You can change the render from HorizontalBarChartRenderer to your customed render, and override function :protected void drawDataSet(Canvas c, IBarDataSet dataSet, int index);
add these lines after " // initialize the buffer"
BarBuffer buffer = mBarBuffers[index];
buffer.setPhases(phaseX, phaseY);
buffer.setDataSet(index);
buffer.setInverted(mChart.isInverted(dataSet.getAxisDependency()));
buffer.setBarWidth(mChart.getBarData().getBarWidth());
buffer.feed(dataSet);
trans.pointValuesToPixel(buffer.buffer);
final boolean isSingleColor = dataSet.getColors().size() == 1;
if (isSingleColor) {
mRenderPaint.setColor(dataSet.getColor());
}
for (int j = 0; j < buffer.size(); j += 4) {
if (!mViewPortHandler.isInBoundsTop(buffer.buffer[j + 3]))
break;
if (!mViewPortHandler.isInBoundsBottom(buffer.buffer[j + 1]))
continue;
if (!isSingleColor) {
// Set the color for the currently drawn value. If the index
// is out of bounds, reuse colors.
mRenderPaint.setColor(dataSet.getColor(j / 4));
}
// NEWLY ADDED CODE BELOW
float left = buffer.buffer[j];
float right = buffer.buffer[j + 2];
float midLine = (mViewPortHandler.contentLeft() + mViewPortHandler.contentRight()) / 2;
buffer.buffer[j] = midLine + (midLine - right);
buffer.buffer[j + 2] = midLine + (midLine - left);
look like this:

Calculating Center of mass of body being tracked using kinect?

I am working on Kinect for my research project . I have worked previously to calculate the joint angle of kinect and the joint coordinates. I would like to calculate the center of mass of the body which is being tracked.
Any idea would be appreciated and code snippets would be immensely helpful.
I owe a lot to stack overflow without the community help it would had not been possible to do such a thing.
Thanks in Advance
Please find the code where i want to include this center of mass function. This function tracks the skeleton.
Skeleton GetFirstSkeleton(AllFramesReadyEventArgs e)
{
using (SkeletonFrame skeletonFrameData = e.OpenSkeletonFrame())
{
if (skeletonFrameData == null)
{
return null;
}
skeletonFrameData.CopySkeletonDataTo(allSkeletons);
//get the first tracked skeleton
Skeleton first = (from s in allSkeletons
where s.TrackingState == SkeletonTrackingState.Tracked
select s).FirstOrDefault();
return first;
}
I have tried using this code in my code but its not getting accustomed , can any one please help me include the center of mass code.
oreach (SkeletonData data in skeletonFrame.Skeletons) {
SkeletonFrame allskeleton = e.SkeletonFrame;
// Count passive and active person up to six in the group
int numberOfSkeletonsT = (from s in allskeleton.Skeletons
where s.TrackingState == SkeletonTrackingState.Tracked select s).Count();
int numberOfSkeletonsP = (from s in allskeleton.Skeletons
where s.TrackingState == SkeletonTrackingState.PositionOnly select s).Count();
// Count passive and active person up to six in the group
int totalSkeletons = numberOfSkeletonsP + numberOfSkeletonsT;
//Console.WriteLine("TotalSkeletons = " + totalSkeletons);
//======================================================
if (data.TrackingState == SkeletonTrackingState.PositionOnly)
{
foreach (Joint joint in data.Joints)
{
if (joint.Position.Z != 0)
{
double centerofmassX = com.Position.X;
double centerofmassY = com.Position.Y;
double centerofmassZ = com.Position.Z;
Console.WriteLine( centerofmassX + centerofmassY + centerofmassZ );
}
}
See a couple of resources here:
http://mathwiki.ucdavis.edu/Calculus/Vector_Calculus/Multiple_Integrals/Moments_and_Centers_of_Mass#Three-Dimensional_Solids
http://www.slideshare.net/GillianWinters/center-of-mass-presentation
http://en.wikipedia.org/wiki/Locating_the_center_of_mass
Basically no matter what, you are going to need to find the mass of your user. This can be a simple input, then you can determine how much weight the person puts on each foot and use the equations described at all of these sources. Another option may be to use plumb lines on a planar shape representation of the user in 2D, However that won't be the actually accurate 3D center of mass.
Here is an example of how to find what amount of mass is on each foot. using the equation found on http://www.vitutor.com/geometry/distance/line_plane.html
Vector3 v = new Vector3(skeleton.Joints[JointType.Head].Position.X, skeleton.Joints[JointType.Head].Position.Y, skeleton.Joints[JointType.Head].Position.Z);
double mass;
double leftM, rightM;
double A = sFrame.FloorClipPlane.X,
B = sFrame.FloorClipPlane.Y,
C = sFrame.FloorClipPlane.Z;
//find angle
double angle = Math.ASin(Math.Abs(A * v.X + B * v.Y * C * v.Z)/(Math.Sqrt(A * A + B * B + C * C) * Math.Sqrt(v.X * v.X + v.Y * v.Y + v.Z * v.Z)));
if (angle == 90.0)
{
leftM = mass / 2.0;
rightM = mass / 2.0;
}
double distanceFrom90 = 90.0 - angle;
if (distanceFrom90 > 0)
{
double leftMultiple = distanceFrom90 / 90.0;
leftM = mass * leftMultiple;
rightM = mass - leftM;
}
else
{
double rightMultiple = distanceFrom90 / 90.0;
rightM = rightMultiple * mass;
leftM = mass - rightMultiple;
}
This is of course assuming that the user is on both feet, but you could modify the code to create a new plane based off the users feet instead of the automatic one generated by Kinect.
The code to then find the center of mass you have to choose a datum. I would choose the head as that is the top of the person, and you can measure down from it easily. Using the steps found here:
double distanceFromDatumLeft = Math.Sqrt(Math.Pow(headX - footLeftX, 2) + Math.Pow(headY - footLeftY, 2) + Math.Pow(headZ - footLeftZ, 2));
double distanceFromDatumLeft = Math.Sqrt(Math.Pow(headX - footRightX, 2) + Math.Pow(headY - footRightY, 2) + Math.Pow(headZ - footRightZ, 2));
double momentLeft = distanceFromDatumLeft * leftM;
double momentRight = distanceFromDatumRight * rightM;
double momentSum = momentLeft + momentRight;
//measured in units from the datum
double centerOfGravity = momentSum / mass;
You then can of course show this on the screen by passing a point to plot that is centerOfGravity points below the head.

how to use skeletal joint to act as cursor using bounds (No gestures)

I just want to be able to do something when my skeletal joint (x,y,z) coordinates are over the x,y,z coordinates of the button . . I have the following code but somehow it doesnt work properly . .as soon as my hand moves it will do something without my hand reaching the button
if (skeletonFrame != null)
{
//int skeletonSlot = 0;
Skeleton[] skeletonData = new Skeleton[skeletonFrame.SkeletonArrayLength];
skeletonFrame.CopySkeletonDataTo(skeletonData);
Skeleton playerSkeleton = (from s in skeletonData where s.TrackingState == SkeletonTrackingState.Tracked select s).FirstOrDefault();
if (playerSkeleton != null)
{
Joint rightHand = playerSkeleton.Joints[JointType.HandRight];
handPosition = new Vector2((((0.5f * rightHand.Position.X) + 0.5f) * (640)), (((-0.5f * rightHand.Position.Y) + 0.5f) * (480)));
var rightHands = playerSkeleton.Joints[JointType.HandRight];
var rightHandsX = rightHands.Position.X;
var rightHandsY = rightHands.Position.Y;
var rightHandsZ = rightHands.Position.Z;
if (Math.Sqrt(Math.Pow(rightHandsX - position.X, 2) + Math.Pow(rightHandsY - position.Y, 2)) < 20)
{
// Exit();
}
if (Math.Sqrt(Math.Pow(rightHandsX - start_bttn.Bounds.X, 1) + Math.Pow(rightHandsY - start_bttn.Bounds.Y, 1)) < 10)
{
currentGameState = GameState.Selection;
// Exit();
}
if ((rightHandsX < GraphicsDevice.Viewport.Width / 2 + 150 && rightHandsX > GraphicsDevice.Viewport.Width / 2 - 75) && (rightHandsY > GraphicsDevice.Viewport.Height / 2 && rightHandsY < GraphicsDevice.Viewport.Height / 2 + 50))
{
currentGameState = GameState.Selection;
}
}
Here is my hand tracking function. See if it does what you want, or gets you closer...
private void TrackHandMovement(Skeleton skeleton)
{
Joint leftHand = skeleton.Joints[JointType.HandLeft];
Joint rightHand = skeleton.Joints[JointType.HandRight];
Joint leftShoulder = skeleton.Joints[JointType.ShoulderLeft];
Joint rightShoulder = skeleton.Joints[JointType.ShoulderRight];
Joint rightHip = skeleton.Joints[JointType.HipRight];
// the right hand joint is being tracked
if (rightHand.TrackingState == JointTrackingState.Tracked)
{
// the hand is sufficiently in front of the shoulder
if (rightShoulder.Position.Z - rightHand.Position.Z > 0.4)
{
double xScaled = (rightHand.Position.X - leftShoulder.Position.X) / ((rightShoulder.Position.X - leftShoulder.Position.X) * 2) * SystemParameters.PrimaryScreenWidth;
double yScaled = (rightHand.Position.Y - rightShoulder.Position.Y) / (rightHip.Position.Y - rightShoulder.Position.Y) * SystemParameters.PrimaryScreenHeight;
// the hand has moved enough to update screen position (jitter control / smoothing)
if (Math.Abs(rightHand.Position.X - xPrevious) > MoveThreshold || Math.Abs(rightHand.Position.Y - yPrevious) > MoveThreshold)
{
RightHandX = xScaled;
RightHandY = yScaled;
xPrevious = rightHand.Position.X;
yPrevious = rightHand.Position.Y;
// reset the tracking timer
trackingTimerCounter = 10;
}
}
}
}
There is a bit of math in there to translate the hand position to the screen position. Different strokes for different folks, but my logic is:
Shoulders = top of screen
Hips = bottom of screen
Left Should = left most on screen
To get the right most screen position, I take the distance between the left & right shoulder and add it to the right shoulder.

Getting minimum number of MKMapRects from a MKPolygon

So I have a function that takes two MKMapRect's and the second intersects with the first one. So the function creates an MKPolygon that is the first rect without the intersecting parts:
-(void) polygons:(MKMapRect)fullRect exclude:(MKMapRect)excludeArea{
NSLog(#"Y is: %f height: %f",excludeArea.origin.y,excludeArea.size.height);
double top = excludeArea.origin.y - fullRect.origin.y;
double lft = excludeArea.origin.x - fullRect.origin.x;
double btm = (fullRect.origin.y + fullRect.size.height) - (excludeArea.origin.y + excludeArea.size.height);
double rgt = (fullRect.origin.x + fullRect.size.width) - (excludeArea.origin.x + excludeArea.size.width);
double ot = fullRect.origin.y, it = (ot + top);
double ol = fullRect.origin.x, il = (ol + lft);
double ob = (fullRect.origin.y + fullRect.size.height), ib = (ob - btm);
double or = (fullRect.origin.x + fullRect.size.width), ir = (or - rgt);
MKMapPoint points[11] = {{ol,it}, {ol,ot}, {or,ot}, {or,ob}, {ol,ob}, {ol,it}, {il,it}, {ir,it}, {ir,ib}, {il,ib}, {il,it}};
MKPolygon *polygon = [MKPolygon polygonWithPoints:points count:11];
}
And my question is now how do I get the minimum number of MKMapRects from this MKPolygon? I have done some googling as well as looking through the forum but havn't found anything.
EDIT:
So the goal is the following:
I have a MKMapRect rect1, then I have a list of rectangles, rectList, which is MKMapRects intersecting with rect1 and what I want to do is create a rectilinear MKPolygon of rect1, remove the surface of all MKMapRects in rectList from rect1 and then create the minimum number of MKMaprects from the created rectilinear MKPolygon.
Right now the problem is the following: I am able to create a polygon when removing one MKMapRect from rect1 but I dont know how to remove the following maprects from rect1 and I dont know how to extract the minimum set of MkMapRects from the polygon created.
Best regards
Peep
I'm not sure if this is what you're looking for or if I understand the question fully, but if all you need to know is the minimum number of rectangles in a polygon that's created by subtracting one rectangle from another you should be able to do it by checking the number of corner points in the second rectangle that are contained in the first rectangle. In pseudo code:
int minNumRects(MKRect r1, MKRect r2) {
int numPointsContained = 0;
for (Point p in r2) {
if (MKMapRectContainsPoint(r1, p)) {
numPointsContained++;
}
}
if (numPointsContained == 1) {
return 2;
} else if (numPointsContained == 2) {
return 3;
} else if (numPointsContained == 4) {
return 4;
} else {
return 0;
}
}
P.S. - This assumes that the rectangles are axis-aligned but as far as I know that's the case with MKRects

Dynamic grid using FlashDevelop & Actionscript 2.0

I'm new to actionscript. What I'm tryin to do is simulate traffic flow near a 2 lane intersection, following Wolfram's rule 184. To begin with, I'm trying to create a grid (8x8 of which the intersection is between the middle two rows and the middle two columns, like a plus sign) whose cells have the following attributes:
color = white;
car = false;
when clicked:
color = red;
car = true (a car is present);
So, after the user clicks cells to position the cars initially and presses the start button, the simulation will begin.
Here's my code so far (apologies for incorrect formatting):
class Main
{
private var parent:MovieClip;
public static function main(mc:MovieClip)
{
var app = new Main(mc);
}
public function Main(mc:MovieClip)
{
this.parent = mc;
//grid settings
var Cell:MovieClip = mc.createEmptyMovieClip("cell", mc.getNextHighestDepth());
var x:Number = 0;
var y:Number = 0;
var color:Number = 0xffffff;
var car:Boolean = false;
for (y = 0; y < 3 * Stage.height / 8; y += Stage.height / 8)
{
for (x = 3*Stage.width/8; x < 5*Stage.width/8; x+=Stage.width/8)
{
UI.drawRect(Cell, x, y, (Stage.width / 8) - 5, (Stage.height / 8) - 5, color, 100);
}
}
for (y = 3*Stage.height/8; y < 5 * Stage.height / 8; y += Stage.height / 8)
{
for (x = 0; x < Stage.width; x+=Stage.width/8)
{
UI.drawRect(Cell, x, y, (Stage.width / 8)-5, (Stage.height / 8)-5, color, 100);
}
}
for (y = 5*Stage.height/8; y < Stage.height; y += Stage.height / 8)
{
for (x = 3*Stage.width/8; x < 5*Stage.width/8; x+=Stage.width/8)
{
UI.drawRect(Cell, x, y, (Stage.width / 8)-5, (Stage.height / 8)-5, color, 100);
}
}
Cell.onMouseDown()
{
Cell.color = UI.RED;
Cell.car = true;
}
}
}
I know there's quite a few things gone wrong here. First of all, the cell color doesn't change on mouse down. Do i need to make movie clip for each cell in the for loops? I think it would be easier to make a grid of objects with given attributes, but i don't know how to do that. Would really appreciate if someone helps me out.
From what I can tell, issue with your current approach is that using drawRect() literally draws pixels on to the stage, which means you'll have no reference to those shapes in future frames. right now, you've got one MovieClip that has been drawn many times. What you need is a lot of MovieClips so you have a reference to each cell that you can update/edit every frame.
Your best bet is to do the following (I'll just provide pseudo because I'm a bit shaky on AS2 syntax):
A) Create an array to hold all of the Cells. Call it:
var Cells:Array = new Array();
B) During each step of the loops in your constructor, do 4 things.
1) Create a new MovieClip `var tempCell:MovieClip = new MovieClip();
2) Draw a rectangle on to each MovieClip: A tutorial for the graphics API in AS2 http://www.actionscript.org/resources/articles/727/1/Drawing-shapes-with-AS2/Page1.html
3) Add an event listenerto each MovieClip that points to a common event handler. This listener listens for mouse clicks on that MovieClip (or MOUSE_DOWN)
4) and use Cells.push(tempClip) to add that new MovieClip to your array so you now have one object that contains a reference to all of your cells.
C) Create an click event handler that redraws the cell that has been clicked. Try MouseEvent.target
You have another option to using the graphics API to draw rectangles, and that is to simply add and remove stock graphics from your Flash library. You'll have to draw these graphics in Flash and then 'Export for Actionscript' to call them up.
Hope this points you in the right direction!
J