This program is designed in the end to make a slot machine like thing that will be integrated into a friend's game, still in pre alpha stages and will be for a long time or maybe forever. (he's only using it for a class project ATM)
package SlotMachine;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Random;
import java.awt.Color;
public class SlotGui{
static Random one = new Random();
static Random two = new Random();
static Random three = new Random();
static Random four = new Random();
static Random five = new Random();
static Random six = new Random();
static Random seven = new Random();
static Random eight = new Random();
static Random nine = new Random();
static int st = one.nextInt(10);
static int nd = two.nextInt(10);
static int trd = three.nextInt(10);
static int frth = four.nextInt(10);
static int fth = five.nextInt(10);
static int sxth = six.nextInt(10);
static int svth = seven.nextInt(10);
static int eth = eight.nextInt(10);
static int nth = nine.nextInt(10);
static int coins = 15;
static JTextField money = new JTextField(Integer.toString(coins));
static JLabel blueLabel = new JLabel();
static JLabel slotOne = new JLabel();
static JLabel slotTwo = new JLabel();
static JLabel slotThree = new JLabel();
static JLabel slotFour = new JLabel();
static JLabel slotFive = new JLabel();
static JLabel slotSix = new JLabel();
static JLabel slotSeven = new JLabel();
static JLabel slotEight = new JLabel();
static JLabel slotNine = new JLabel();
static Icon lever = new ImageIcon("lever.jpg");
static Icon a = new ImageIcon("0.jpg");
static Icon b = new ImageIcon("1.jpg");
static Icon c = new ImageIcon("2.jpg");
static Icon d = new ImageIcon("3.jpg");
static Icon ee = new ImageIcon("4.jpg");
static Icon f = new ImageIcon("5.jpg");
static Icon g = new ImageIcon("6.jpg");
static Icon h = new ImageIcon("7.jpg");
static Icon i = new ImageIcon("8.jpg");
static Icon j = new ImageIcon("9.jpg");
static JButton startLever = new JButton(lever);
static Color backGround = new Color (0,0,0);
public static void slotVisualSet(JLabel slot,int Xval, int Yval, int h, int w){
slot.setOpaque(true);
slot.setLocation(Xval,Yval);
slot.setSize(h,w);
slot.setVisible(true);
}
public static void slotLogic(JLabel slotLab,int slotNum){
if (slotNum == 0){
slotLab.setIcon(a);
} else if (slotNum == 1){
slotLab.setIcon(b);
} else if (slotNum == 2){
slotLab.setIcon(c);
} else if (slotNum == 3){
slotLab.setIcon(d);
} else if (slotNum == 4){
slotLab.setIcon(ee);
} else if (slotNum == 5){
slotLab.setIcon(f);
} else if (slotNum == 6){
slotLab.setIcon(g);
} else if (slotNum == 7){
slotLab.setIcon(h);
} else if (slotNum == 8){
slotLab.setIcon(i);
} else if (slotNum == 9){
slotLab.setIcon(j);
}
}
public static void makeWindow(){
//creating the window
JFrame windo = new JFrame ();
windo.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
windo.setExtendedState(JFrame.MAXIMIZED_BOTH);
windo.setVisible(true);
//creating the components of the window
money.setOpaque(true);
money.setLocation(500,900);
money.setSize(60,20);
blueLabel.setOpaque(true);
blueLabel.setBackground(backGround);
blueLabel.setPreferredSize(new Dimension(1000, 1000));
blueLabel.setVisible(true);
blueLabel.setLayout(null);
//setting the coordinates and sizes of the slots
slotVisualSet(slotOne,100,100,225,225);
slotVisualSet(slotTwo,350,100,225,225);
slotVisualSet(slotThree,600,100,225,225);
slotVisualSet(slotFour,100,350,225,225);
slotVisualSet(slotFive,350,350,225,225);
slotVisualSet(slotSix,600,350,225,225);
slotVisualSet(slotSeven,100,600,225,225);
slotVisualSet(slotEight,350,600,225,225);
slotVisualSet(slotNine,600,600,225,225);
startLever.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
int st = one.nextInt(10);
int nd = two.nextInt(10);
int trd = three.nextInt(10);
int frth = four.nextInt(10);
int fth = five.nextInt(10);
int sxth = six.nextInt(10);
int svth = seven.nextInt(10);
int eth = eight.nextInt(10);
int nth = nine.nextInt(10);
coins = coins - 5;
money.setText(Integer.toString(coins));
// making the slots change pictures when the lever is pulled
slotLogic(slotOne,st);
slotLogic(slotTwo,nd);
slotLogic(slotThree,trd);
slotLogic(slotFour,frth);
slotLogic(slotFive,fth);
slotLogic(slotSix,sxth);
slotLogic(slotSeven,svth);
slotLogic(slotEight,eth);
slotLogic(slotNine,nth);
if ((st == nd) && (nd == trd)){
coins = coins + 30;
}else if((frth == fth) && (fth == sxth)){
coins = coins + 30;
}else if ((svth == eth) && (eth == nth)){
coins = coins + 30;
} else if ((st == fth) && (fth == nth)){
coins = coins + 100;
}else if ((svth == fth) && (fth == trd)){
coins = coins + 100;
}
}
});
startLever.setSize(183,275);
startLever.setLocation(1000,300);
windo.add(startLever);
windo.add(money);
windo.add(blueLabel);
windo.add(slotOne);
windo.add(slotTwo);
windo.add(slotThree);
windo.add(slotFour);
windo.add(slotFive);
windo.add(slotSix);
windo.add(slotSeven);
windo.add(slotEight);
windo.add(slotNine);
}
public static void main(String[] args) {
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
makeWindow();
}
} );
}
}
There are three bugs here, I have been looking for answers forever and have not been able to find any, so help would be much appreciated.
The ninth slot does not go listen to the placement parameters for some reason and just sits on the side.
The slots do not always appear after you click the button that is supposed to change the images (maybe I need to use something other than JLabels for this?)
The background doesn't change colour.
There are so many issues with that code that are problematic, let me enumerate some:
Trying to set location of a component on a non-null layout using container
Trying to use set location at all and not use layout managers. That's what they're there for, to make it easy to create complex GUI's without fussing with exact positioning.
Not using arrays.
Over use of static. None of the fields should be static. Edit: except for the background color which could very well be a constant, a static final variable named BACKGROUND.
Using nine Random objects. One would work just fine and would be a lot less confusing.
.... etc...
posting code for a "friend's" class project.
I think that the best fix-up for this code is to trash it, and instead try to re-write the code from scratch using arrays, using layout managers, avoiding static variables. Start over and you could create a nice GUI and quickly too, and learn quite a bit in the process.
Edit 2
Consider using a GridLayout using JPanel to hold your 3 x 3 grid of JLabels.
Consider using a BorderLayout for your overall GUI, placing the GridLayout JPanel into the BorderLayout.CENTER position.
The play button could go in a JPanel that is placed in the main GUI BorderLayout.EAST position.
The bet window could go in a JPanel that is located in the main GUI in the BorderLayout.SOUTH position.
Again use of arrays will simplify and shrink your code, making it much easier to debug and to enhance.
The same goes for use of layout managers as they will make it easier for you to debug, enhance and modify your GUI.
Related
New programmer here, I have been working for a few days on this bit of code that is meant to create a UI where I input a basement's perimeter length (textfield integer), if a new pump is needed (combobox string), if there is an outlet nearby (combobox string), and how many hours It will take to prepare a site (textfield integer), and I calculate my costs to complete a job. I was able to set up a UI where I can enter the inputs and press a button to calculate but I'm having trouble connecting the button I made to the formula I made to generate a price. Here is my code:
package packagepackage;
import packagepackage.HintTextFieldUI;
import java.awt.*;
import java.awt.BorderLayout;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class CP_GUI implements ActionListener {
String[] sumpo = {"New sump pump","Existing sump pump"};
String[] electo = {"There is an outlet within 6 feet of sump pump","There is no outlet nearby, or I do not need a new one"};
Integer estimatex = 0;
String esto = String.valueOf(estimatex);
public volatile String estimatoof = "Estimated Cost: ${}".format(esto);
private JComboBox sump = new JComboBox(sumpo);
private JComboBox elec = new JComboBox(electo);
private JTextField linear = new JTextField();
private JTextField prep = new JTextField();
private JLabel title = new JLabel("Drain Tile Calculator");
private JButton calculate = new JButton("Calculate!");
public JLabel estimate = new JLabel(estimatoof);
private JFrame frame = new JFrame();
private JPanel panel = new JPanel();
public CP_GUI() {
linear.addActionListener(this);
calculate.addActionListener(this);
elec.addActionListener(this);
sump.addActionListener(this);
prep.addActionListener(this);
// the panel with the button and text
JPanel panel = new JPanel();
panel.setBorder(BorderFactory.createEmptyBorder(400, 400, 100, 100));
panel.setLayout(new GridLayout(0, 1));
panel.add(linear);
panel.add(sump);
panel.add(elec);
panel.add(prep);
frame.add(panel, BorderLayout.CENTER);
panel.add(title);
calculate.addActionListener(this);
panel.add(calculate);
// set up the frame and display it
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setTitle("Drain Tile Calculator");
frame.pack();
frame.setVisible(true);
linear.setUI(new HintTextFieldUI("Perimeter length", true));
prep.setUI(new HintTextFieldUI("Hours of preptime", true));}
// create one Frame
public static void main(String[] args) {
new CP_GUI();
}
#Override
public void actionPerformed(ActionEvent e){
// TODO Auto-generated method stub
if(e.getSource()==linear) {String input = linear.getText();
Integer pars = Integer.parseInt(input);
Integer distVar = pars *= 13;
estimatex += distVar;
} else if (e.getSource()==sump) {String inputa = sump.getToolTipText();
int sumpa = 0;
if(inputa == "New sump pump" | inputa == "yes") {
sumpa += 260;}
estimatex += sumpa;
} else if (e.getSource()==elec) {String inputb =elec.getToolTipText();
int eleca = 0;
if("There is an outlet within 6 feet of the sump pump".equals(inputb)) {
eleca += 1;
}
eleca *= 280;
estimatex += eleca;
}
else if (e.getSource()==prep) {String inputc = prep.getText();
int parsa = Integer.parseInt(inputc);
int prepCost = parsa += 1;
prepCost *= 110;
estimatex += prepCost;
} else if (e.getSource()==linear) {
String disto = linear.getText();
int di = Integer.parseInt(disto);
di *= 13;
String pumpo = (String)sump.getSelectedItem();
int sumpo = 0;
if ("New sump pump".equals(pumpo)) {
sumpo += 260;
}
String ele = (String)elec.getSelectedItem();
int elc = Integer.parseInt(ele);
elc *= 280;
String clea = prep.getText();
int cla = Integer.parseInt(clea);
cla += 1;
cla *= 110;
int cali = 0;
cali += di;
cali += sumpo;
cali += elc;
cali += cla;
estimatex = cali;
}
}
}
Edit: Made the suggested edits made so far and now the UI opens and works, the only issue is that the estimated price does not show up. Am I connecting the action listener correctly?
Your "primary" problem is right here...
String disto = String.valueOf(linear);
where linear is a JTextField, so the above call will generate something like...
javax.swing.JTextField[,0,0,0x0,invalid,layout=javax.swing.plaf.basic.BasicTextUI$UpdateHandler,alignmentX=0.0,alignmentY=0.0,border=com.apple.laf.AquaTextFieldBorder#4e323305,flags=288,maximumSize=,minimumSize=,preferredSize=,caretColor=javax.swing.plaf.ColorUIResource[r=0,g=0,b=0],disabledTextColor=javax.swing.plaf.ColorUIResource[r=128,g=128,b=128],editable=true,margin=javax.swing.plaf.InsetsUIResource[top=0,left=0,bottom=0,right=0],selectedTextColor=com.apple.laf.AquaImageFactory$SystemColorProxy[r=0,g=0,b=0],selectionColor=com.apple.laf.AquaImageFactory$SystemColorProxy[r=165,g=205,b=255],columns=0,columnWidth=0,command=,horizontalAlignment=LEADING]
which is obviously not what you're looking for.
You should probably be just doing something like...
String disto = linear.getText();
pumpo == "New sump pump" is also not how you compare a String in Java, you should be using "New sump pump".equals(pumpo) ... but I suspect you're going to have the same issues as mentioned above.
I really recommend you take the time to read through Creating a GUI With Swing as well as taking the time to come to grips with the core basics of the language
Hey guys I'm very new to Java and started in July with an intro to Java class.
I am currently working on a project which is a translator with arrays. The main applet shows 10 words in english that when typed into a JTextField outputs the spanish translation of that work. And vice versa. The program also shows a picture associated with that word.
The program is all done in that case, the only portion I am missing currently is that if a user inputs ANY other word than the 20 given words (10 spanish and 10 english) the JTextArea where translations are displayed is supposed to show "That word is not in the dictionary".
I'm having issues creating an ELSE statement that shows this error message. Here is the complete code. I'm not sure what to do to make it so eg
if (textFieldWord.!equals(englishWords[english])){
translate.setText("That word is not in the Dictionary");}
Here is the complete code - - - -
import java.awt.*;
import java.applet.*;
import javax.swing.*;
import java.awt.event.*;
import java.util.*;
public class DictionaryArrays extends JApplet implements ActionListener{
String[] spanishWords = {"biblioteca","reloj",
"alarma", "volcan", "ventana",
"autobus", "raton", "lago", "vaca", "encendedor"};
String[] englishWords = {"library", "clock", "alarm",
"volcano", "window", "bus", "rat",
"lake","cow","lighter"};
String textFieldWord;
Image[] photos;
ImageIcon icon;
ImageIcon icontwo;
JButton getTranslation;
JTextField entry;
JLabel imageviewer;
TextArea translate;
static int defaultX = 10;
static int defaultY = 10;
static int defaultW = 780;
static int defaultH = 50;
public void init() {
photos = new Image[10];
photos[0] = getImage(getCodeBase(), "library.jpg");
photos[1] = getImage(getCodeBase(), "clock.jpg");
photos[2] = getImage(getCodeBase(), "alarm.jpg");
photos[3] = getImage(getCodeBase(), "volcano.jpg");
photos[4] = getImage(getCodeBase(), "window.jpg");
photos[5] = getImage(getCodeBase(), "bus.jpg");
photos[6] = getImage(getCodeBase(), "rat.jpg");
photos[7] = getImage(getCodeBase(), "lake.jpg");
photos[8] = getImage(getCodeBase(), "cow.jpg");
photos[9] = getImage(getCodeBase(), "lighter.jpg");
final JPanel outer = new JPanel(new BorderLayout());
JPanel inner = new JPanel(new BorderLayout());
JPanel viewer = new JPanel(new BorderLayout());
JPanel visualviewer = new JPanel(new BorderLayout());
// here is the main component we want to see
// when the outer panel is added to the null layout
//JButton toSpanish = new JButton("English to Spanish");
//JButton toEnglish = new JButton("Spanish to English");
final JLabel list = new JLabel("<HTML><FONT COLOR=RED>English</FONT> - library, clock, alarm, volcano, window, bus, rat, lake, cow, lighter"
+"<BR><FONT COLOR=RED>Spanish</FONT> - biblioteca, reloj, alarma, volcan, ventana, autobus, raton, lago, vaca, encendedor<BR>");
translate = new TextArea("Your translation will show here");
imageviewer = new JLabel(icon);
viewer.add("West",translate);
visualviewer.add("East",imageviewer);
inner.add("Center",list);
//inner.add("West",toSpanish);
//inner.add("East", toEnglish);
outer.add("Center", inner);
JPanel c = (JPanel)getContentPane();
final JPanel nullLayoutPanel = new JPanel();
nullLayoutPanel.setLayout(null);
c.add("Center", nullLayoutPanel);
// set the bounds of the panels manually
nullLayoutPanel.add(outer);
nullLayoutPanel.add(viewer);
nullLayoutPanel.add(visualviewer);
outer.setBounds(defaultX, defaultY, defaultW, defaultH);
viewer.setBounds(20, 75, 300, 300);
visualviewer.setBounds(485, 75, 300, 300);
JPanel controlPanel = new JPanel(new FlowLayout(FlowLayout.CENTER, 10, 10));
entry = new JTextField("Enter English or Spanish word to translate here");
entry.addActionListener(this);
entry.addMouseListener(new MouseAdapter(){
#Override
public void mouseClicked(MouseEvent e){
entry.setText("");
}});
getTranslation = new JButton("Translate");
getTranslation.addActionListener(this);
controlPanel.add(entry);
controlPanel.add(getTranslation);
c.add("South", controlPanel);
viewer.setBackground(Color.blue);
controlPanel.setBackground(Color.red);
inner.setBackground(Color.yellow);
visualviewer.setBackground(Color.black);
outer.setBackground(Color.black);
}
public void paint(Graphics g) {
super.paint(g);
}
public void actionPerformed (ActionEvent ae){
if(ae.getSource()==getTranslation){
textFieldWord=(entry.getText().toLowerCase());
for (int english = 0; english < spanishWords.length; english++){
if (textFieldWord.equals(englishWords[english])){
translate.setText(spanishWords[english]);
icon= new ImageIcon(photos[english]);
imageviewer.setIcon(icon);
break;
}
}
for (int spanish = 0; spanish < englishWords.length; spanish++){
if (textFieldWord.equals(spanishWords[spanish])){
translate.setText(englishWords[spanish]);
icontwo= new ImageIcon(photos[spanish]);
imageviewer.setIcon(icontwo);
break;
}
}
}
}
}
Any help would be appreciated guys. If the top paragraph was TLDR. Im trying to make it so typing in ANY other word in the JTextField (entry) other than the 10 english and 10 spanish words will output an error msg of "That word is not in the Dictionary" in the TextArea (translate)
This is (obviously) wrong...
if (textFieldWord.!equals(englishWords[english])){
and should be...
if (!textFieldWord.equals(englishWords[english])){
Try and think of it this way, String#equals returns a boolean, you want to invert the result of this method call, it would be the same as using something like...
boolean doesEqual = textFieldWord.equals(englishWords[english]);
if (!doesEqual) {...
You need to evaluate the result of the method call, but in oder to make that call, the syntax must be [object].[method], therefore, in order to invert the value, you must complete the method call first, then apply the modifier to it ... ! ([object].[method])
Updated...
Now having said all that, let's look at the problem from a different perspective...
You need to find a matching word, in order to do that, you must, at worse case, search the entire array. Until you've search the entire array, you don't know if a match exists.
This means we could use a separate if-else statement to manage the updating of the output, for example...
String translatedWord = null;
int foundIndex = -1;
for (int english = 0; english < spanishWords.length; english++){
if (textFieldWord.equals(englishWords[english])){
translatedWord = englishWords[english];
foundIndex = english;
break;
}
}
if (translatedWord != null) {
translate.setText(translatedWord);
icon= new ImageIcon(photos[foundIndex]);
imageviewer.setIcon(icon);
} else {
translate.setText("That word is not in the Dictionary");
}
translatedWord = null;
for (int spanish = 0; spanish < englishWords.length; spanish++){
if (textFieldWord.equals(spanishWords[spanish])){
translatedWord = englishWords[english];
foundIndex = spanish;
break;
}
}
if (translatedWord != null) {
translate.setText(translatedWord);
icontwo= new ImageIcon(photos[foundIndex]);
imageviewer.setIcon(icontwo);
} else {
translate.setText("That word is not in the Dictionary");
}
Basically, all this does is sets the translatedWord to a non null value when it finds a match in either of the arrays. In this, you want to display the results, else you want to display the error message...
Equally, you could merge your current approach with the above, so when you find a work, you update the output, but also check the state of the translatedWord variable, displaying the error message if it is null...
String translatedWord = null;
for (int english = 0; english < spanishWords.length; english++){
if (textFieldWord.equals(englishWords[english])){
translatedWord = spanishWords[english];
translate.setText(translatedWord);
icon= new ImageIcon(photos[english]);
imageviewer.setIcon(icon);
break;
}
}
if (translatedWord == null) {
translate.setText("That word is not in the Dictionary");
}
translatedWord = null;
for (int spanish = 0; spanish < englishWords.length; spanish++){
if (textFieldWord.equals(spanishWords[spanish])){
translatedWord = englishWords[spanish];
translate.setText(translatedWord);
icontwo= new ImageIcon(photos[spanish]);
imageviewer.setIcon(icontwo);
break;
}
}
if (translatedWord == null) {
translate.setText("That word is not in the Dictionary");
}
Updated
Okay, you have a logic problem. You're never quite sure which direction you are translating to.
The following basically changes the follow by not translating the work from Spanish IF it was translated to English
public void actionPerformed(ActionEvent ae) {
if (ae.getSource() == getTranslation) {
textFieldWord = (entry.getText().toLowerCase());
translate.setText(null);
String translatedWord = null;
for (int english = 0; english < spanishWords.length; english++) {
if (textFieldWord.equals(englishWords[english])) {
translatedWord = spanishWords[english];
translate.append(translatedWord + "\n");
icon = new ImageIcon(photos[english]);
imageviewer.setIcon(icon);
break;
}
}
if (translatedWord == null) {
for (int spanish = 0; spanish < englishWords.length; spanish++) {
if (textFieldWord.equals(spanishWords[spanish])) {
translatedWord = englishWords[spanish];
translate.append(translatedWord + "\n");
icontwo = new ImageIcon(photos[spanish]);
imageviewer.setIcon(icontwo);
break;
}
}
}
if (translatedWord == null) {
translate.append("A Spanish-English match is not in the Dictionary\n");
}
}
}
Now, I would suggest that you replace TextArea with a JTextArea, but you will need to wrap it in a JScrollPane
translate = new JTextArea("Your translation will show here");
viewer.add("West", new JScrollPane(translate));
Avoid using null layouts, pixel perfect layouts are an illusion within modern ui design. There are too many factors which affect the individual size of components, none of which you can control. Swing was designed to work with layout managers at the core, discarding these will lead to no end of issues and problems that you will spend more and more time trying to rectify
Basically, this was really painful to try and use for this very reason...
Game class:
import java.util.Random;
public class Game {
public static void main(String args[]){
//----------Sets up GUI----------
GUI gameGUI = new GUI();
gameGUI.setVisible(true);
Player.setGUI(gameGUI);
//----------Sets initial number of marbles, computer player and human player----------
Random random = new Random();
int initialNum;
//loop makes sure initialNum of marbles is between 10 and 100
do{
initialNum = random.nextInt(100);
}while(initialNum < 10);
//*****gameGUI.manageMarbles(initialNum, true);
//end loop
Pile pile = new Pile(initialNum);
gameGUI.setPile(pile);
int compChoice = random.nextInt(2) + 1; //number index (1 or 2) representing SIMPLE_COMPUTER or SMART_COMPUTER
Player computer = new Player(Player.Type.values()[compChoice]);
Player humanPlayer = new Player(Player.Type.HUMAN);
//----------Game loop----------
//Randomly determine first player
Player currentPlayer;
int playerIndex = random.nextInt(2); //will be used to determine next player in the loop
if(playerIndex == 0){ currentPlayer = computer; }
else { currentPlayer = humanPlayer; }
//Loop
while(pile.getNumMarbles() != 0){
System.out.printf("%d marbles left.\n", pile.getNumMarbles());
int removed = currentPlayer.playTurn(pile.getNumMarbles());
pile.removeMarbles(removed);
//Determine next player
playerIndex = Math.abs(playerIndex - 1); //if playerIndex = 0, it becomes 1, and vice-versa
if(playerIndex == 0){ currentPlayer = computer; }
else { currentPlayer = humanPlayer; }
}
System.out.println(currentPlayer + " won");
}
}
Player class:
import java.util.Scanner;
import java.util.Random;
public class Player {
public enum Type{HUMAN, SIMPLE_COMPUTER, SMART_COMPUTER}
private Type type;
static private GUI gui;
public Player(Player.Type type){
this.type = type;
}
public Player.Type getType(){
return type;
}
public int playTurn(int pileSize){
Random random = new Random();
if(type == Type.HUMAN){
int marbles;
do{
marbles = gui.getMarblesToRemove();
}while(marbles < 0);
return marbles;
}
else if(type == Type.SIMPLE_COMPUTER){
if(pileSize == 1){
return 1;
}
else{
int remove = random.nextInt(pileSize/2) + 1;
if(remove == (pileSize/2) + 1){ remove -= 1; }
return remove;
}
}
else if(type == Type.SMART_COMPUTER){
if(pileSize == 1){
return 1;
}
else if(pileSize == 3 || pileSize == 7 || pileSize == 15 || pileSize== 31 || pileSize== 63 || pileSize <= 3){
int remove = random.nextInt(pileSize/2) + 1;
if(remove == (pileSize/2) + 1){ remove -= 1; }
return remove;
}
else{
for(int i=1; i<=pileSize/2; i++){
int size = pileSize - i;
if(size == 3 || size == 7 || size == 15 || size == 31 || size == 63){
return i;
}
}
}
}
return 0;
}
public String toString(){
return ""+type;
}
public static void setGUI(GUI guii){
gui = guii;
}
}
GUI class:
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JTextField;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
public class GUI extends JFrame {
private JPanel panel;
private JButton removeButton; //button to remove marbles
private JTextField marblesAmount; //amount of marbles to remove
private static final int FIELD_WIDTH = 2;
private JLabel marblesLabel;
private JLabel errorLabel;
private Pile pile;
private int marblesToRemove;
private ClickListener listener;
static final private int WIDTH = 700, HEIGHT = 600;
public GUI(){
super.setTitle("test");
super.setSize(WIDTH, HEIGHT);
super.setDefaultCloseOperation(EXIT_ON_CLOSE);
panel = new JPanel();
marblesLabel = new JLabel("How many marbles to remove?");
errorLabel = new JLabel("");
removeButton = new JButton("Remove");
listener = new ClickListener();
removeButton.addActionListener(listener);
marblesAmount = new JTextField(FIELD_WIDTH);
panel.add(removeButton);
panel.add(marblesLabel);
panel.add(marblesAmount);
panel.add(errorLabel);
super.add(panel);
marblesToRemove = 0;
}
public void setPile(Pile pile){
this.pile = pile;
}
private class ClickListener implements ActionListener{
public void actionPerformed(ActionEvent event){
marblesToRemove = Integer.parseInt(marblesAmount.getText());
}
}
public int getMarblesToRemove(){
return marblesToRemove;
}
}
Pile Class:
public class Pile {
private int initialNum;
private int currentNum;
public Pile(int initialNum){
setNumMarbles(initialNum);
currentNum = initialNum;
}
public int getNumMarbles(){
return currentNum;
}
public void removeMarbles(int numToRemove){
currentNum = currentNum - numToRemove;
}
public void setNumMarbles(int amount){
initialNum = amount;
}
public String toString(){
return "Number of marbles: " + currentNum;
}
}
What I am trying to do is to get the function playTurn(int pileSize) in the Player class to return the variable marbles(inside the if(type == Type.HUMAN) block ) only when it is not zero. The variable marblesToRemove from the gui class is assigned to marbles, by calling the function getMarblesToRemove().
marblesToRemove is initially set to 0 in the default constructor for the gui class, and that causes the functionplayTurn(int pileSize) to go in an infinite loop. But marblesToRemove is changed to another value that is input in a JTextField (marblesAmount) when a a button(removeButton) is pressed. But the the do while loop will still be an infinite loop and the function will return nothing, why? Can someone please help? Thanks.
This is probably because of at least two issues that I can see. The first is that you are modifying the variable in one thread, and reading it in the other. This should be done using either synchronization, or some other locking mechanism (Lock or AtomicInteger, etc.).
The second issue is that your reading-thread should not be doing a 'tight' loop. This is bad practices that sends one CPU to 100% usage. It should be done using some form of notification. Again, synchronization comes to mind.
Until you fix these two issues, you will always have unreliable results.
For what it's worth, in your particular case, if I were to make an educated guess, I would guess that there are two important copies of the marblesAmount (and there are alsways multiple copies). There's the copy thati's in the L1 and registers of one CPU that's doing a tight loop waiting for that register to change, and the other is in another core on your CPU setting it to a new value. Unless you use some synchronization, or somethin from the java.util.concurrent.* library you ave no way to tell one copy of the variable to refresh the other.
I got it to work finally. I just added a line of code "System.out.print("");" in the do-while loop in the Player class.
So now it looks like
do{
marbles = gui.getMarblesToRemove();
System.out.print("");
}while(marbles < 0);
I have no idea why that works, but it does lol. Now the function actually returns the value that I set in the JTextField if it is not zero.
I have created a grid that contains 10x10 buttons using 2d arrays. i tried x.getSource().getLabel() but compiler says they are not compatible. also i want to get the specific button that was clicked.
I want to get the exact button that was clicked from the grid i made and get its label. what method i need to use?
import javax.swing.JFrame; //imports JFrame library
import javax.swing.JButton; //imports JButton library
import java.awt.GridLayout; //imports GridLayout library
import javax.swing.*;
import java.awt.event.*;
import java.util.*;
public class ButtonGrid extends JFrame implements ActionListener
{
JFrame frame=new JFrame(); //creates frame
JButton[][] grid; //names the grid of buttons
public int x;
public int y;
public ButtonGrid(int width, int length)
{ //constructor
char temp;
String charput;
frame.setLayout(new GridLayout(width,length)); //set layout
grid = new JButton[width][length]; //allocate the size of grid
for(int y=0; y<length; y++)
{ //start
for(int x=0; x<width; x++)
{
temp=charRand(); //get random character
charput = ""+temp; //converts character to string
grid[x][y]=new JButton(); //creates new button
frame.add(grid[x][y]); //adds button to grid
grid[x][y].addActionListener(this);
grid[x][y].setLabel(charput); //set charput as label
}
}
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.pack(); //sets appropriate size for frame
frame.setVisible(true); //makes frame visible
}
/* generates randomiz letter for the button of the grid*/
public char charRand()
{
String consonantList = new String("BCDFGHL"); //list 1
String consonantList2 = new String("MNPRSTWY"); //list 2
String consonantList3= new String("JQXZVK"); //list 3
String vowelList = new String("AEIOU"); //list of vowels
int vowelOrConsonant; //holder of random number
int chosen; //selects the chosen random letter
Random randGen = new Random(); //generates random int value
char selected; //gets the random letter chosen by variable chosen
vowelOrConsonant = randGen.nextInt(4);
if (vowelOrConsonant == 0)
{
chosen = randGen.nextInt(5); //list of vowels
selected = vowelList.charAt(chosen); //selects a char from vowels
}
else if(vowelOrConsonant == 1)
{
chosen = randGen.nextInt(7); //list 1
selected = consonantList2.charAt(chosen); //selects a char
}
else if(vowelOrConsonant == 2)
{
chosen = randGen.nextInt(8); //list 2
selected = consonantList2.charAt(chosen); //selects a char
}
else
{
chosen = randGen.nextInt(6); //list 3
selected = consonantList.charAt(chosen);
}
return selected; //returns the random letter
}
public static void main(String[] args)
{
new ButtonGrid(10,10);//makes new ButtonGrid with 2 parameters
}
public void actionPerformed(ActionEvent x)
{
/* i get wrong output on this line.
* i want to get the exact button that was clicked and get its label.
*/
if (x.getSource()==grid[x][y])
JOptionPane.showMessageDialog(null,x.getSource().getLabel);
}
}
getSource() returns an Object, so you need to cast it to JButton, like this:
public void actionPerformed(ActionEvent x) {
JOptionPane.showMessageDialog(null, ((JButton)x.getSource()).getText());
}
Also note that getLabel() and setLabel() are deprecated and should be replaced by getText() and setText().
You can make a class that extends Jbutton. and add two fields to it of type int(X & Y ). The constructor will look like this: public MyButton(int x, y);
And when you are filling your grid, don't use directly the Jbutton class. Use your class and for X & Y supply the i & j parameters of the two for cycles that you are using. Now when you are using Action Listener for your button you can use his X & Y fields as they represent its place on the grid. Hope this helps! It tottaly worked for me and its simple as hell.
I have a working JFrame GUI with my JPanel all setup. I am trying to combine two different codes that I've got setup and working. The first code was a text converter toUpperCase in a JPanel, and the second is a Prime Factor (not prime numbers) code. I've been trying to get the JPanel to give an output of Prime Factors for any number that a user inputs. Here is what I have....
JPanel Code
public class Prime extends JPanel {
private JLabel formattedText;
public static void main(String[] args) {
JFrame frame = new JFrame();
frame.getContentPane().add(new Prime());
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.setVisible(true);
}
public Prime(){
setLayout(new BoxLayout(this,BoxLayout.Y_AXIS));
JPanel panel = new JPanel(); panel.setPreferredSize(new Dimension(640,100));
JLabel label = new JLabel("Enter a number to check for it's prime number(s).");
JTextField field = new JTextField("0");
field.addActionListener(new FieldListener());
add(label);
add(field);
add(panel);
panel = new JPanel(); panel.setPreferredSize(new Dimension(640,380));
formattedText = new JLabel();
panel.add(formattedText);
add(panel);
}
private class FieldListener implements ActionListener {
public void actionPerformed(ActionEvent event) {
JTextField field = (JTextField)event.getSource();
formattedText.setText(field.getText().toUpperCase()); // I know this is wrong... I can't figure out what to change here to get it to pull the code below.
}
}
public class PrimeFactors {
}
}
and here is the Prime Factor code
public class Temp {
static int primeCheck = 1;
public static void main(String[] args) {
System.out.println("Enter a number whose Prime factors are desired: ");
Scanner numS = new Scanner(System.in);
int numPriFac = 0;
if (numS.hasNextInt()) {
numPriFac = numS.nextInt();
}
System.out.println("All the Prime Factors of the entered number are:");
for (int tap = 1; tap <= numPriFac; tap++) {
if (numPriFac % tap == 0) {
for (int primeTest = 2; primeTest < tap; primeTest++) {
if (tap % primeTest == 0) {
primeCheck = 1;
break;
} else {
primeCheck = 0;
}
}
if (primeCheck == 0 || tap == 2) {
System.out.print(tap + " ");
}
}
}
}
}
That last PrimeFactors code in the bottom is just something left over from when I was trying to get it working on my own. Thanks so much for any help!!!
Step 1: Change the line
public static void main(String[] args) {
to something like
public static String primeFactors(int number) {
and make the method use the provided argument number instead of asking for input.
Step 2: Create a StringBuilder inprimeFactors and change all calls to System.out.print to calls to stringBuilder.append()
Step 3: Set stringBuilder.toString() as return value for primeFactors
Step 4: Change the line
formattedText.setText(field.getText().toUpperCase());
to
formattedText.setText(Temp.primeFactors(Integer.parseInt(field.getText())));
I'll leave the error handling and input safe guarding to you.