This contact script is not being called when any 2 bodies come into contact with each other. I have tried simply calling the method whenever any object bodies come into contact but that does not work either.
world.setContactListener(new ContactListener() {
#Override
public void beginContact(Contact contact) {
Fixture f1 = contact.getFixtureA();
Fixture f2 = contact.getFixtureB();
Body b1 = f1.getBody();
Body b2 = f2.getBody();
if((b1.getUserData() == "player" && b2.getUserData() == "Enemy") || (b1.getUserData() == "player" && b2.getUserData() == "Enemy")) {
player.death();
hud.death();
}
}
#Override
public void endContact(Contact contact) {
}
#Override
public void preSolve(Contact contact, Manifold oldManifold) {
}
#Override
public void postSolve(Contact contact, ContactImpulse impulse) {
}
});
Make sure that the player and enemy bodies are defined as Dynamic Body.
Check your collision filtering.
Check if the body is active.
Also check if you properly set the userdata of each body.
Related
I want to make a jump like in the Mario game. When you are under the platform and you jump, you can then pass through the collider.
When a player's velocity is going down, colliders should wake up. I know that I should use ContactListener, but when I'm using the contact.setEnable(false) method nothing happens.
My contact listener (ground checker works perfectly)
world.setContactListener(new ContactListener() {
#Override
public void beginContact(Contact contact) {
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "groundChecker"){
character.isGrounded = true;
System.out.println(" Colliding");
}
}
#Override
public void endContact(Contact contact) {
}
#Override
public void preSolve(Contact contact, Manifold oldManifold) {
}
#Override
public void postSolve(Contact contact, ContactImpulse impulse) {
}
});
What and where should I put to get effect like this.
enter image description here
enter image description here
Collider should have only one side, have somebody deal with it?
Found a solution I hope it will be helpfull.
world.setContactListener(new ContactListener() {
#Override
public void beginContact(Contact contact) {
//setting isGrounded boolean variable in our character class, but we need to check "player" velocity, because we don't want to enable jumping when only ground will passed througt
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "groundChecker" && (contact.getFixtureB().getBody().getLinearVelocity().y < 0 || contact.getFixtureB().getBody().getLinearVelocity().y == 0)){
character.isGrounded = true;
}
}
#Override
public void endContact(Contact contact) {
}
#Override
public void preSolve(Contact contact, Manifold oldManifold) {
//we have to disable contact when our "player" fixture collide with "ground" fixture
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "player"){
contact.setEnabled(false);
}
//and we need to disable contact when our "groundChecker" will collide with "ground" and we need to check what velocity.y of player body is, when it is bigger than 0 contact should be falsed
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "groundChecker" && contact.getFixtureB().getBody().getLinearVelocity().y > 0){
contact.setEnabled(false);
}
}
#Override
public void postSolve(Contact contact, ContactImpulse impulse) {
}
});
We have to disable contact when our "player" fixture collide with "ground" fixture.
Like this.
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "player"){
contact.setEnabled(false);
}
And we need to disable contact when our "groundChecker" will collide with "ground" and we need to check what velocity.y of player body is, when it is bigger than 0, contact should be falsed.
if(contact.getFixtureA().getBody().getUserData() == "ground" && contact.getFixtureB().getUserData() == "groundChecker" && contact.getFixtureB().getBody().getLinearVelocity().y > 0){
contact.setEnabled(false);
}
Here is a demo of the above solution:
In my game I implement fling gesture detection. Everything work fine , but I want to modify fling detection
From documentation for fling: https://github.com/libgdx/libgdx/wiki/Gesture-detection
fling: A user dragged the finger across the screen, then lifted it. Useful to implement swipe gestures.
I want to modify this and fling to work without lifting touch, only when user drag some distance not lifting it.
Here is my code:
public class SimpleDirectionGestureDetector extends GestureDetector {
public interface DirectionListener {
void onLeft();
void onRight();
void onUp();
void onDown();
}
public SimpleDirectionGestureDetector(DirectionListener directionListener) {
super(new DirectionGestureListener(directionListener));
}
private static class DirectionGestureListener extends GestureAdapter{
DirectionListener directionListener;
public DirectionGestureListener(DirectionListener directionListener){
this.directionListener = directionListener;
}
#Override
public boolean fling(float velocityX, float velocityY, int button) {
if(Math.abs(velocityX)>Math.abs(velocityY)){
if(velocityX>0){
directionListener.onRight();
}else{
directionListener.onLeft();
}
}else{
if(velocityY>0){
directionListener.onDown();
}else{
directionListener.onUp();
}
}
return super.fling(velocityX, velocityY, button);
}
}
}
public SimpleDirectionGestureDetector gestureDetector = new SimpleDirectionGestureDetector(
new SimpleDirectionGestureDetector.DirectionListener() {
#Override
public void onUp() {
onUpSwipe();
}
#Override
public void onRight() {
onRightSwipe();
}
#Override
public void onLeft() {
onLeftSwipe();
}
#Override
public void onDown() {
onDownSwipe();
}
});
Any help would be appreciated
Thanks
How can I make the background agent execution to wait before all ImageOpened() events are fired (3 in this case) in order to update secondary live tile with custom images?
Edit 1:
In the OnInvoke() method of the ScheduledAgent I am calling my own create tile data function implemented in a shared library which in turn subscribes to 3 ImageOpened() events as I am trying to create custom images for all live tile templates i.e. small, medium and wide.
Since these being asynchronous events I have no way to check if all the events have completed successfully so that I can call NotifyComplete() to notify the background agent that its job is now done. So sometimes the tile gets updated while most of the times it doesn't. Also I am using the same function to update the live tiles every time the app is launched so there is no problem with its implementation. I have also tried to take care of all the memory limitations with the ScheduledAgent by disposing Bitmaps and calling GC.Collect() forcefully.
Please help in any possible way to fix this problem.
Add a new class that lets you create custom events -
public class SaveImageCompleteEventArgs : EventArgs
{
public bool Success { get; set; }
public Exception Exception { get; set; }
public string ImageFileName { get; set; }
public SaveImageCompleteEventArgs(bool success, string fileName)
{
Success = success;
ImageFileName = fileName;
}
}
Initialize the events and required variables in the file you are updating the custom live tile from -
public static int countTile = 3;
public event EventHandler<SaveImageCompleteEventArgs> SaveMediumImageComplete;
public event EventHandler<SaveImageCompleteEventArgs> SaveWideImageComplete;
public event EventHandler<SaveImageCompleteEventArgs> SaveSmallImageComplete;
public event EventHandler<SaveImageCompleteEventArgs> SaveAllImagesComplete;
Fire the completion event in the ImageOpened() event handlers for all the tiles and check if the SaveAllImagesComplete event needs to be fired-
public void OnBackgroundBmpOpenedMedium(object sender, RoutedEventArgs e)
{
if (SaveMediumImageComplete != null)
{
countTile -= 1;
CheckIfAllImagesOpened();
SaveMediumImageComplete(this, new SaveImageCompleteEventArgs(true, mediumTileImageUriIronMan));
}
}
private void CheckIfAllImagesOpened()
{
if (countTile == 0)
{
if (SaveAllImagesComplete != null)
{
var args1 = new SaveImageCompleteEventArgs(true, "");
SaveAllImagesComplete(this, args1);
}
}
}
In the ScheduledAgent file -
public static ManualResetEvent evt;
public bool IsPaused { get { return !evt.WaitOne(0); } }
In the OnInvoke() function -
evt = new ManualResetEvent(false);
Deployment.Current.Dispatcher.BeginInvoke(() =>
{
//Initialize secondary tile here
if (secondaryTile != null)
{
/*
obj is a object of a helper file that contains all the
functions responsible for updating the custom live tile
Call the function that is responsible for initializing all the
tile image bitmpas and that subscribes to the ImageOpened events
*/
obj.SaveMediumImageComplete += async (s, args) =>
{
if (!IsPaused)
evt.Set();
};
obj.SaveWideImageComplete += async (s, args) =>
{
if (!IsPaused)
evt.Set();
};
obj.SaveSmallImageComplete += async (s, args) =>
{
if (!IsPaused)
evt.Set();
};
obj.SaveAllImagesComplete += async (s, args) =>
{
try
{
if (args.Success)
obj.UpdateTileIcon();
}
catch (Exception) { }
finally
{
if (!IsPaused)
evt.Set();
}
};
}
});
evt.WaitOne();
NotifyComplete();
I've made a simple Media Player for an application I'm working on, the problem is that I thought that you could simply integrate JavaFX into Swing. Which is not the case. I have been searching for a solution to this problem and tried to use this website: http://docs.oracle.com/javafx/2/swing/jfxpub-swing.htm
The problem is that even though I have the website that explains how to put the code together, I still don't understand how. Here is the mediaplayer and I plan to integrate it into my Swing code, so that I can call the media player when a button is clicked. Here is all my code for the media player and if anyone can share some light on how to integrate it into my Swing code i.e my GUI, I would probably have to kiss you through the computer.
public class Player extends Application{
private boolean atEndOfMedia = false;
private final boolean repeat = false;
private boolean stopRequested = false;
private Duration duration;
private Label playTime;
private Slider volumeSlider;
#Override
public void start(final Stage stage) throws Exception {
stage.setTitle("Movie Player");//set title
Group root = new Group();//Group for buttons etc
final Media media = new Media("file:///Users/Paul/Downloads/InBruges.mp4");
final MediaPlayer playa = new MediaPlayer(media);
MediaView view = new MediaView(playa);
//Slide in and out and what causes that.
final Timeline slideIn = new Timeline();
final Timeline slideOut = new Timeline();
root.setOnMouseEntered(new javafx.event.EventHandler<javafx.scene.input.MouseEvent>() {
#Override
public void handle(MouseEvent t) {
slideIn.play();
}
});
root.setOnMouseExited(new javafx.event.EventHandler<javafx.scene.input.MouseEvent>() {
#Override
public void handle(MouseEvent t) {
slideOut.play();
}
});
final VBox vbox = new VBox();
final Slider slider = new Slider();
final Button playButton = new Button("|>");
root.getChildren().add(view);
root.getChildren().add(vbox);
vbox.getChildren().add(slider);
vbox.getChildren().add(playButton);
vbox.setAlignment(Pos.CENTER);
Scene scene = new Scene(root, 400, 400, Color.BLACK);
stage.setScene(scene);
stage.show();
// Play/Pause Button
playButton.setOnAction(new EventHandler<ActionEvent>() {
#Override
public void handle(ActionEvent e) {
Status status = playa.getStatus();
if (status == Status.UNKNOWN || status == Status.HALTED)
{
// don't do anything in these states
return;
}
if ( status == Status.PAUSED
|| status == Status.READY
|| status == Status.STOPPED)
{
// rewind the movie if we're sitting at the end
if (atEndOfMedia) {
playa.seek(playa.getStartTime());
atEndOfMedia = false;
}
playa.play();
} else {
playa.pause();
}
}
});
//Listeners and Shit for Play Button
playa.setOnPlaying(new Runnable() {
#Override
public void run() {
if (stopRequested) {
playa.pause();
stopRequested = false;
} else {
playButton.setText("||");
}
}
});
playa.setOnPaused(new Runnable() {
#Override
public void run() {
playButton.setText(">");
}
});
playa.play();
playa.setOnReady(new Runnable() {
#Override
public void run(){
int v = playa.getMedia().getWidth();
int h = playa.getMedia().getHeight();
stage.setMinWidth(v);
stage.setMinHeight(h);
vbox.setMinSize(v, 100);
vbox.setTranslateY(h-50);
//slider and graphical slide in/out
slider.setMin(0.0);
slider.setValue(0.0);
slider.setMax(playa.getTotalDuration().toSeconds());
slideOut.getKeyFrames().addAll(
new KeyFrame(new Duration(0),
new KeyValue(vbox.translateYProperty(), h-100),
new KeyValue(vbox.opacityProperty(), 0.9)
),
new KeyFrame(new Duration(300),
new KeyValue(vbox.translateYProperty(), h),
new KeyValue(vbox.opacityProperty(), 0.0)
)
);
slideIn.getKeyFrames().addAll(
new KeyFrame(new Duration(0),
new KeyValue(vbox.translateYProperty(), h),
new KeyValue(vbox.opacityProperty(), 0.0)
),
new KeyFrame(new Duration(300),
new KeyValue(vbox.translateYProperty(), h-100),
new KeyValue(vbox.opacityProperty(), 0.9)
)
);
}
});
//Slider being current and ability to click on slider.
playa.currentTimeProperty().addListener(new ChangeListener<Duration>(){
#Override
public void changed(ObservableValue<? extends Duration> observableValue, Duration duration, Duration current){
slider.setValue(current.toSeconds());
}
});
slider.setOnMouseClicked(new javafx.event.EventHandler<javafx.scene.input.MouseEvent>() {
#Override
public void handle(javafx.scene.input.MouseEvent t) {
playa.seek(Duration.seconds(slider.getValue()));
}
});
}
Use JFXPanel:
public class Test {
private static void initAndShowGUI() {
// This method is invoked on Swing thread
JFrame frame = new JFrame("FX");
final JFXPanel fxPanel = new JFXPanel();
frame.add(fxPanel);
frame.setVisible(true);
Platform.runLater(new Runnable() {
#Override
public void run() {
initFX(fxPanel);
}
});
}
private static void initFX(JFXPanel fxPanel) {
// This method is invoked on JavaFX thread
Scene scene = createScene();
fxPanel.setScene(scene);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
initAndShowGUI();
}
});
}
}
where method createScene() is start(final Stage stage) from your code.
Just instead of putting scene to stage you return it.
I am making an mp3 player, with several JLists in my JFrame. When I right click on a JList item, a popup with some options for that song appears. But when this popup is visible, and I minimise my JFrame, this popup stays visible! Also, when the popup is visible, and I drag my JFrame to somewhere else on the screen, the popup stays on it's original position (so it does not stay on the same position relative to the JFrame)... Can someone please help me out with this? I tried to strip down this class as much as possible :)
I would be really grateful if someone could help me out !!
Joe
public class playListPanel extends JPanel implements MouseListener {
private DefaultListModel model;
private Interface interFace;
private JList list;
private boolean emptyPlaylist;
private ArrayList<Song> currentPlayList;
private Song rightClickedSong;
private JPopupMenu popup;
private Point panelLocation;
public playListPanel(Interface interFace) // Interface extends JFrame,
// playListPanel is a part of
// this JFrame.
{
this.interFace = interFace;
this.panelLocation = new Point(559, 146);
setBackground(SystemColor.controlHighlight);
setBorder(new TitledBorder(null, "", TitledBorder.LEADING,
TitledBorder.TOP, null, null));
setBounds((int) panelLocation.getX(), (int) panelLocation.getY(), 698,
368);
setLayout(null);
currentPlayList = new ArrayList<Song>();
model = new DefaultListModel();
list = new JList(model);
list.setVisible(true);
list.addMouseListener(this);
JScrollPane scrollPane = new JScrollPane(list);
scrollPane.setBounds(5, 5, 688, 357);
add(scrollPane);
emptyPlaylist = true;
}
private void openMenuPopup(Point point)
{
removePopup();
popup = new JPopupMenu();
int x = (int) point.getX();
int y = (int) point.getY();
popup.setLocation((int) (x+panelLocation.getX()),(int) (y+panelLocation.getY()));
//popup.setLabel("popup voor playlist");
JMenuItem removeSong;
popup.add(removeSong = new JMenuItem("Remove Song from Playlist", new ImageIcon("image.jpg")));
ActionListener menuListener = new ActionListener()
{
public void actionPerformed(ActionEvent event)
{
if(event.getActionCommand().equals("Remove Song from Playlist"))
{
System.out.println("Remove Song from Playlist");
interFace.getPlaylistManager().removeOneSong(rightClickedSong);
removePopup();
}
};
//ADD THE LISTENERS TO THE MENU ITEMS
removeSong.addActionListener(menuListener);
popup.setVisible(true);
}
public void removePopup()
{
if(popup!==null)
{
popup.setVisible(false);
System.out.println("popup removed");
}
}
private int getRow(Point point) {
return list.locationToIndex(point);
}
public void refreshPlayList(ArrayList<Song> playlist) {
this.currentPlayList = playlist;
model.clear();
for (Song song : playlist) {
model.add(model.getSize(), song.getPlaylistString());
}
list.setVisible(true);
}
public void highlightSong(int index) {
list.setSelectedIndex(index);
}
public int getRowOfList(Point point) {
return list.locationToIndex(point);
}
#Override
public void mouseClicked(MouseEvent e) {
interFace.getPlaylistManager().doubleClickOnPlaylist(e);
}
#Override
public void mouseEntered(MouseEvent arg0) {
}
#Override
public void mouseExited(MouseEvent arg0) {
}
#Override
public void mousePressed(MouseEvent e) {
if (SwingUtilities.isRightMouseButton(e)) {
rightClickedSong = currentPlayList.get(getRow(e.getPoint()));
openMenuPopup(e.getPoint());
System.out.println("should open popup at "
+ e.getPoint().toString());
}
}
#Override
public void mouseReleased(MouseEvent arg0) {
}
}
There are some basic flaws in the way you are handling click for showing popup.
It is not advisable to call popup.setVisible in simple scenarios like this. Instead, you may rely on its default behavior. Also, better to use e.isPopupTrigger() than to check SwingUtilities.isRightMouseButton(e) to show popup.
You may do something like the following :
//at classlevel,
private JPopupMenu popup = new JPopupMenu();
//create a Popuplistener
PopupListener pl = new PopupListener();
list.addMouseListener(pl);
//Implementation of your popuplistener
class PopupListener extends MouseAdapter {
public void mousePressed(MouseEvent e) {
maybeShowPopup(e);
}
public void mouseReleased(MouseEvent e) {
maybeShowPopup(e);
}
private void maybeShowPopup(MouseEvent e) {
if (e.isPopupTrigger())
//e.getSource - and construct your popup as required.
//and then.
popup.show(((JApplet) e.getComponent()).getContentPane(), e
.getX(), e.getY());
}
}