-1

For my project i am trying to, get the RFID scanner to run all the time by pressing a button and reasing it when stop button is pressed, however i have tried to in a while loop but the problem seems like, when i press the button code everything works perfectly and it does go in a loop however after the button is pressed it doesnt let me press anything else because it stuck in the while loop, is there a way to keep it in a loop but in same time able to stop it with stop button.

  @Override
public void start() {

    while (this.flag) {
        try {
            TerminalFactory factory = TerminalFactory.getDefault();
            List<CardTerminal> terminals = factory.terminals().list();
            System.out.println("Terminals: " + terminals);

            CardTerminal terminal = terminals.get(0);

            System.out.println("Waiting for a card..");
            if (terminal == null) {
                return;
            }
            terminal.waitForCardPresent(0);

            Card card = terminal.connect("T=1");
            System.out.println("Card: " + card);
            System.out.println("Protocol: " + card.getProtocol());
            CardChannel channel = card.getBasicChannel();

            ResponseAPDU response = channel.transmit(new CommandAPDU(new byte[]{(byte) 0xFF, (byte) 0xCA, (byte) 0x00, (byte) 0x00, (byte) 0x00}));
            System.out.println("Response: " + response.toString());
            if (response.getSW1() == 0x63 && response.getSW2() == 0x00) {
                System.out.println("Failed");
            }
            System.out.println("UID: " + bin2hex(response.getData()));

            getUid = bin2hex(response.getData());

            Thread.sleep(1000);
        } catch (CardException e) {
            System.out.println();
            JOptionPane.showMessageDialog(null, "Device Not Connected  " + e.getMessage());
        } catch (InterruptedException ex) {
            Logger.getLogger(CardId.class.getName()).log(Level.SEVERE, null, ex);
        }
}
}

and for my start button

 t = new CardId();
    t.start();

and this is my stop button

 t.flag = false;
  • I'm guessing `CardId` extends `Thread` – Rogue Feb 24 '19 at 17:13
  • yes it is class CardId extends Thread – melih anik Feb 24 '19 at 17:16
  • 1
    on a tangential note, extending `Thread` is a somewhat "deprecated" way of concurrency, you should be using Runnables and passing to the constructor of `Thread` at the very least. – Rogue Feb 24 '19 at 17:17
  • If @Rogue's answer doesn't help solve your problem, then you'll probably want to create a valid [mcve], and then post this code in your question. For this to work, you'd need to replace all non-core library calls with mock calls, such as `Thread.sleep` to replace long-running code sections. This would take quite a bit of effort on your part to do well, but if the need is great, then the effort expended would probably be worth it. Much luck. – Hovercraft Full Of Eels Feb 24 '19 at 17:23

2 Answers2

0

Rather than having your Thread loop while the button is pressed, and stop when it isn't, have the loop run constantly. When a Thread reaches the end of its required code body, it does not execute a second time, even after an invocation of Thread#start.

In short, you'll simply check the value of t.flag in your loop, and if it is false, then you can just sleep the thread until the next iteration of your loop.

Rogue
  • 11,105
  • 5
  • 45
  • 71
  • if (flag = true) { try { this.sleep(1000); } catch (InterruptedException ex) { Logger.getLogger(CardId.class.getName()).log(Level.SEVERE, null, ex); } } else if (flag = false) { this.stop(); } would it be like this? @Rogue – melih anik Feb 24 '19 at 17:35
  • Well not quite, you would sleep for `false` on the `flag` variable as well. Exiting the program should be a completely separate control in this design case imo – Rogue Feb 24 '19 at 17:37
0

First thing is, if you are using a Thread, you should override the "run()" method. NOT the "start()" method. You need to use the "start()" method only to execute the thread. Otherwise, it will use the main thread. No multithreading.

Second thing is, if the "this.flag" is an instance variable in your thread, and its value is dynamically changed by button actions, that variable should be volatile. Otherwise it is normally cached within the loop. (more)

Suggestion: Please follow a good design pattern. (Observer)

Amila
  • 168
  • 1
  • 11