I have made a game in Java that allows you to create and play your own worlds. While creating your world there is a wall entity that you can place. This wall entity can slide, but in order to slide it needs the direction (horizontal/Vertical), distance, and speed. Currently I am using a few JOptionPane to get those values everytime you place one of those blocks. My question is how can I get those values from the user without using a JOptionPane? (If you need any code please let me know).
This is what I have:
private void placeWall() {
int slidable = JOptionPane.showConfirmDialog(null, "Does This Block Slide?", "Slide", JOptionPane.YES_NO_OPTION);
if (slidable == 0) {
String[] options = { "Horizontal", "Vertical"};
int direction = JOptionPane.showOptionDialog(null, "Choose Direction", "Direction", JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE, null, options, 0);
int speed = getSpeed();
int distance = getDistance();
if (direction == 0)
wallSlidables.add(new SlideHorizontal(speed, distance));
else
wallSlidables.add(new SlideVertical(speed, distance));
}
}
Source Code: GitHub
Related
i'm doing a pac-man game in JAVA, right now the ghosts are moving (just by 1 square) only after pac-man moves and pac-man moving (also just by 1 square) only when one of the arrows on the keyboard is pressed, and i want to make the ghosts to move in constant speed no matter what (lets say for example, 2 squares per second)...
i have this loop, which basically working fine except the screen won't refresh itself:
while(true) {
isGot = redG.moves(packguy.getCurrentPanel().getLoc());
if (isGot)
while (true)
JOptionPane.showMessageDialog(frame, "you lost!");
if (steps == 2) {
pinkG = new Ghost(panelGrid[10][14], 0, 5);
}
if (steps > 1) {
isGot = pinkG.moves(packguy.getCurrentPanel().getLoc());
if (isGot)
while (true)
JOptionPane.showMessageDialog(frame, "you lost!");
if (steps == 3) {
orangeG = new Ghost(panelGrid[10][14], 0, 4);
}
if (steps > 2) {
isGot = orangeG.moves(packguy.getCurrentPanel().getLoc());
if (isGot)
while (true)
JOptionPane.showMessageDialog(frame, "you lost!");
if (steps == 4) {
cyanG = new Ghost(panelGrid[10][14], 0, 6);
}
if (steps > 3) {
isGot = cyanG.moves(packguy.getCurrentPanel().getLoc());
if (isGot)
while (true)
JOptionPane.showMessageDialog(frame, "you lost!");
}
}
}
framePaint();
//
try {
Thread.sleep(500);
}
catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
steps++;
}
the function framePaint() is a function i made which put on every square the thing that supposed to be in this square (rather it's ghost, pac-man himself...). First the function remove every object in each square, afterwards it is checking what's supposed to be in the square and put the match photo (which work pretty well). at the end of the function there is those lines:
frame.repaint();
frame.validate();
if im putting a JOptionPane.showMessageDialog(frame, "some message"); in the line where I put the \\ the screen does refreshing when i get the message...
can you all please help me figure this out?
advanced thanks :)
I assume you have a keylistener that reacts whenever a key is pressed. In that you calculate all the new positions.
Instead create a background thread that will periodically (two times per second?) calculate the positions. For the player object, use the last direction of movement to make pacman continue walking.
In the keylistener just set the direction for pacman and use that in the background thread. Whenever the background thread moved something on the screen, it shall call the component's repaint() method. The Swing framework will then call paintComponent() to really draw the game.
So for a school project, I have to create a game with a program called 'Processing'.
I am creating a main menu with the switch statement. For that I want to use the buttons 'Start', 'Help', and 'exit'.i would like to use those buttons to change the variables of the switch statement. Therefore I'm using "mousePressed". The problem is that which button I'm pressing, is giving me the same result as the 'exit' button. Could somebody give me tips on how I can structure my menu better or even make my button work? I am using a library on Processing called 'ControlP5' to make my buttons.
here is my code so far:
int mode; // 1: intro screen, 2: game , 3: game over
final int INTRO = 1;
final int PLAY = 2;
final int GAMEOVER = 3;
//==============================================================
void setup(){
size(1920,1080);
mode = 1;
}
//========================================================
void draw(){
if(mode == 1){
introScreen();
}
else if (mode == 2){
gameItself();
}
else if (mode == 3){
gameOver();
}
else println("mode error");{
}
}
void introScreen(){
mode = 1;
static int Page = 0;
import controlP5.*;
ControlP5 cp5;
cp5= new ControlP5(this);
switch(Page){
case 0: // main menu
cp5.addButton("Start").setValue(0).setPosition(1420,250).setSize(400,100);
cp5.addButton("Exit").setValue(0).setPosition(1420,650).setSize(400,100);
cp5.addButton("Help").setValue(0).setPosition(1420,450).setSize(400,100);
break;
case 1: //help menu
cp5.addButton("Back").setValue(0).setPosition(1420,450).setSize(400,100);
break;
}
public void Start(){
if(mousePressed){
mode = 2; // switching to the game itself
}
println("Start");
}
public void Exit(){
if(mousePressed){
exit(); }
println("Exit");
}
public void Help(){
Page = 1;
println("Help");
}
public void Back(){
if(mousePressed){
Page = 0;
}
println("Back");
}
void gameItself(){
// game and stuff
}
void gameOver(){
//gameover
}
Take a look at how the mousePressed event works. You may use this information useful.
To achieve your goal as to change the Page variable by clicking buttons, there are multiple options. First, I'll go with the easier one, the one which doesn't need an import but just check for coordinates. Then I'll do the same thing, but with controlP5.
1. Just checking where the clicks lands
I'll go with the most basic one: detecting the "click" and checking if it's coordinates are inside a button.
First, we'll add the mouseClicked() method. This method is called every time a mouse button is pressed.
// I'm typing this out of IDE si there may be some quirks to fix in the code
void mouseClicked() {
switch(Page) {
case 0:
if (mouseX > 1420 && mouseX < 1420+400 && mouseY > 250 && mouseY < 250+100) {
// You're in the main menu and Start was clicked
}
if (mouseX > 1420 && mouseX < 1420+400 && mouseY > 650 && mouseY < 650+100) {
// You're in the main menu and Exit was clicked
}
if (mouseX > 1420 && mouseX < 1420+400 && mouseY > 450 && mouseY < 450+100) {
// You're in the main menu and Help was clicked
}
// You should use 'else if' instead of 3 different if, but I coded it like that so it would be easier to see the small differences between the coordinates
case 1:
if (mouseX > 1420 && mouseX < 1420+400 && mouseY > 450 && mouseY < 450+100) {
// You're un the help menu and Back was clicked
}
}
}
As you can see, I just used the coordinates and size of your buttons to check if the click was located inside one. That's kind of ninja-ing my way out of this issue. I don't know how far into programming you are, or else I would recommand to build a class to handle user inputs, but this way is easy to manage for small exercises like homework.
2. Designing controlP5 buttons
I'm not a ControlP5 expert, so we'll keep close to the basics.
I'll be blunt, the code you provided is ripe with problems, and it's not so many lines, so instead of pointing where it goes wrong I'll give you some skeleton code which will work and on which you can build some understanding. I'll give you the tools and then you can make your project work.
When you design your buttons, if you design them all in the same object, they'll share some properties. For an example, all your buttons will be visible or invisible at the same time. You don't need to redraw them all the time, because they already handle this, so you need to manage them with another method.
You should design your buttons as global objects (as you did), and add them to the ControlP5 object which makes the most sense. You can have one button per object if you want, or many if they are linked together, for an example all the "menu" buttons which appears at the same time could be owned by the same object. Design your buttons in the setup() method if you design them only one time for the whole program. Of course, if this was more than an homework, you may want to avoid the buttons being globals, but it'll be much easier to keep them in memory for a short project.
The "name" of the button is also the name of the method that it'll try to call if you click on it. Two buttons cannot share the same "name". Buttons can have a set value which will be sent to the method that they call.
You don't need to use Processing's mouse events for the buttons to work. They are self-contained: they have their own events, like being clicked on or detecting when the mouse is over them. Here's the documentation for the full list of the methods included in the ControlP5 buttons.
You don't need to manage the buttons in the draw() loop. They manage themselves.
Here's some skeleton code to demonstrate what I just said. You can copy and paste it in a new Processing project and run it to see what's going on.
ControlP5 cp5;
ControlP5 flipVisibilityButton;
int Page = 0;
void setup() {
size(1920, 800);
textAlign(CENTER, CENTER);
textSize(60);
fill(255);
cp5 = new ControlP5(this); // this is ONE object, which will own buttons.
cp5.addButton("MenuButton0") // this is the name of the button, but also the name of the method it will call
.setValue(0) // this value will be sent to the method it calls
.setPosition(1420, 250)
.setSize(400, 100);
cp5.addButton("MenuButton1")
.setValue(1)
.setPosition(1420, 450)
.setSize(400, 100);
cp5.addButton("MenuButton2")
.setValue(2)
.setPosition(1420, 650)
.setSize(400, 100);
flipVisibilityButton = new ControlP5(this); // this is a different object which own it's own controls (a button in this case)
flipVisibilityButton.addButton("flipVisibility")
.setValue(2)
.setPosition(200, height/2)
.setSize(200, 100);
}
void draw() {
// No button management to see here
background(0);
// showing which button has been pressed while also keeping watch to see if the mouse is over one of the cp5 buttons
text(Page + "\n" + cp5.isMouseOver(), width/2, height/2);
}
void MenuButton0(int value) {
ChangePage(value);
}
void MenuButton1(int value) {
ChangePage(value);
}
void MenuButton2(int value) {
ChangePage(value);
}
void ChangePage(int value) {
Page = value;
}
void flipVisibility(int value) {
// When the buttons are invisible, they are also unclickable
cp5.setVisible(!cp5.isVisible());
}
You should be able to expand on this example to do your project, but if you have difficulties don't hesitate to comment here and ask further questions. Have fun!
So i'm working on a project for school, in which I have created a database with the information for all the chemicals on the periodic table, and upon running the program, the user is prompted to pick between a few options, such as search, sort, etc. Like this:
String[] options = new String[] {"Search", "Sort", "Add", "Delete", "Exit"};
int x=JOptionPane.showOptionDialog(null, "Choose one of the following:", "Virtual Periodic Table", JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE,
null, options, options[0]);
while (true)
{
if (options[x]=="Search")
{
searchMenu();
}
else if (options[x]=="Sort")
{
}
else if (options[x]=="Add")
{
}
else if (options[x]=="Delete")
{
}
else if (options[x]=="Exit")
{
break;
}
}
I am not quite finished, as of right now I am still working on the search option. Anyways, upon clicking the search option, I call a procedure which pops up another menu which prompts the user to specify what they would like to search by, like this:
String[] options = new String[] {"Name", "Symbol", "Atomic Number", "Atomic Mass", "# of Valence Electrons", "Go Back"};
int x=JOptionPane.showOptionDialog(null, "What would you like to search by?", "Virtual Periodic Table", JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE,
null, options, options[0]);
if (options[x]=="Name")
{
searchByName();
}
else if (options[x]=="Symbol")
{
}
else if (options[x]=="Atomic Number")
{
}
else if (options[x]=="Atomic Mass")
{
}
else if (options[x]=="# of Valence Electrons")
{
}
else if (options[x]=="Go Back")
{
}
Now, I am trying to figure out a way in which I can give the user the option to go back to the main menu so they can do something else with the data. For example if i decide to search but then i decide i want to actually sort, I can simply press "Go Back" and it will popup the previous menu, which was the main menu, so I can choose what I want to do next. I have added the button which says "Go Back" but i'm not quite sure how to make it so it actually gives command back to the main method which can popup the main menu again. I tried to put the search menu in a while loop and then making it break out of the loop if they were to click "Go Back" but it didn't no anything but close the entire program.
I'm still fairly new to GUI in Java, anybody know what i can do?
You must put the ShowOptionDialog inside the while loop, so it will be called again when you leave the searchMenu
So this is my first time working with the JOptionPane and I was wondering if someone could help explain how I could make both of my buttons do certain actions? For all intent and purposes have it just print out "Hi". Here is my code. So far it only prints out "Hi" if I click the "Uhh...." button but I want it to do the same when I click the "w00t!!" button as well. I know it has something to do with the parameter "JOptionPane.YES_NO_OPTION" but I'm not sure what exactly I have to do with it. Thanks for the help in advance!
Object[] options = {"Uhh....", "w00t!!"};
int selection = winnerPopup.showOptionDialog(null,
"You got within 8 steps of the goal! You win!!",
"Congratulations!", JOptionPane.YES_NO_OPTION,
JOptionPane.INFORMATION_MESSAGE, null,
options, options[0]);
if(selection == JOptionPane.YES_NO_OPTION)
{
System.out.println("Hi");
}
From the javadocs,
When one of the showXxxDialog methods returns an integer, the
possible values are:
YES_OPTION
NO_OPTION
CANCEL_OPTION
OK_OPTION
CLOSED_OPTION
So, your code should look something like,
if(selection == JOptionPane.YES_OPTION){
System.out.println("Hi");
}
else if(selection == JOptionPane.NO_OPTION){
System.out.println("wOOt!!");
}
But regardless, this logic is a bit bizarre so I would probably just roll my own dialog.
In JOPtionPane class there are some constants that represent the values of the buttons.
/** Return value from class method if YES is chosen. */
public static final int YES_OPTION = 0;
/** Return value from class method if NO is chosen. */
public static final int NO_OPTION = 1;
/** Return value from class method if CANCEL is chosen. */
public static final int CANCEL_OPTION = 2;
You changed the names of the buttons, and consequently, your first button "Uhh" has the value 0, and its button "w00t!" assumed a value of 1.
So, you can use this:
if(selection == JOptionPane.YES_OPTION)
{
System.out.println("Hi");
}
else if(selection == JOptionPane.NO_OPTION){
// do stuff
}
or maybe could be better use the swicht/case function:
switch (selection )
{
case 0:
{
break;
}
case 1:
{
break;
}
default:
{
break;
}
}
int selection = 0;
JOptionPane.showOptionDialog(null,
"You got within 8 steps of the goal! You win!!",
"Congratulations!", JOptionPane.YES_NO_OPTION,
JOptionPane.INFORMATION_MESSAGE, null,
options, options[0]);
if(selection == JOptionPane.YES_NO_OPTION)
{
System.out.println("Hi");
}
I have tp place a AutoCompleteField in one of my screen in Blackberry app. I have to show a place holder text to provide hint for user to enter the information.
Here is the below code of AutoCompleteField
BasicFilteredList filterList = new BasicFilteredList();
String[] address = { "T 115 Centro Galleria Shopping Centre, Cnr Old Collier and Walters Road Morley WA 1522",
"1423 SEAVIEW POINT POINT COOK VIC 2674",
"Lot 1498 Yarraman Road Wyndham Vale VIC 3795",
"Lot 3506 Witchmount Close Hillside VIC 4055",
"6 Paas Place Williamstown VIC 4233",
"Lot 99 14 James Close Sunbury VIC 4502",
"1 Charlotte Street Clayton South VIC 4779" };
filterList.addDataSet(1, address, "address", BasicFilteredList.COMPARISON_IGNORE_CASE);
AutoCompleteField autoCompleteField = new AutoCompleteField(filterList){
public void onSelect(Object selection, int SELECT_TRACKWHEEL_CLICK) {
ListField _list = getListField();
if (_list.getSelectedIndex() > -1) {
if(selectedText!=null){
BasicFilteredListResult result = (BasicFilteredListResult) selection;
selectedText.setText(result._object.toString());
}
}
}
};
add(autoCompleteField);
Anyone, please suggest me how could I implement the same.
Thanks.
You can use a similar technique to the one shown here for normal EditFields. Basically, you need to override the paint() method in an AutoCompleteField subclass. In paint(), you check and see if the field is empty, and if so, you manually draw the placeholder text you want.
The difference is that AutoCompleteField is a Manager with a BasicEditField inside of it. So, to draw the text properly, you need to figure out the x and y offsets of the edit field within the parent Manager (the AutoCompleteField).
So, replace your AutoCompleteField instance with an instance of this class:
private class CustomAutoCompleteField extends AutoCompleteField {
private int yOffset = 0;
private int xOffset = 0;
public CustomAutoCompleteField(BasicFilteredList filteredList) {
super(filteredList);
}
protected void paint(Graphics g) {
super.paint(g);
if (xOffset == 0) {
// initialize text offsets once
xOffset = getEditField().getContentLeft();
yOffset = getEditField().getContentTop();
}
String text = getEditField().getText();
if (text == null || text.length() == 0) {
int oldColor = g.getColor();
g.setColor(Color.GRAY);
g.drawText("enter text", xOffset, yOffset);
g.setColor(oldColor);
}
}
public void onSelect(Object selection, int SELECT_TRACKWHEEL_CLICK) {
ListField _list = getListField();
if (_list.getSelectedIndex() > -1) {
if(selectedText!=null){
BasicFilteredListResult result = (BasicFilteredListResult) selection;
selectedText.setText(result._object.toString());
}
}
}
}
I tested this on OS 5.0, with an instance that didn't have any margin or padding set. It's possible that with different layouts, you may need to adjust the logic for calculating the x and y offsets. But, the above code shows you the basic idea. Good luck.
Edit: the above code is presented with the caveat that your onSelect() method is clearly relying on code not shown. As is, the above code won't compile. I left onSelect() in there just to show that I'm essentially just replacing the anonymous class you originally had, and not doing anything different in your onSelect() method, as it's not directly related to the placeholder text issue.