Implementare un DocumentFilter in una JTextField

Mattepuffo's logo
Implementare un DocumentFilter in una JTextField

Implementare un DocumentFilter in una JTextField

Quello che vogliamo ottenere è questo: una porzione di testo non modificabile in una JTextField, che però si va ad aggiungere al testo finale.

Con Java, fare questo, è abbastanza semplice usando un DocumentFilter.

Oggi vediamo un esempio basico.

Creeremo un JFrame, con una JTextField e un JButton.

Quando premeremo il tasto stamperemo la stringa.

Questa la classe:

public class MyDocumentFilter {

    private static final String DEFAULT_TEXT = "Test di default che non puoi toccare!";

    public void createGui() {
        JFrame frame = new JFrame(MyDocumentFilter.class.getSimpleName());
        frame.setLayout(new FlowLayout());
        final JTextField txt = new JTextField(50);
        final JButton btn = new JButton("Clicca");
        btn.addActionListener((ActionEvent ae) -> {
            System.out.println(txt.getText());
        });
        frame.add(btn);
        txt.setText(DEFAULT_TEXT);
        ((AbstractDocument) txt.getDocument()).setDocumentFilter(new DocumentFilter() {
            @Override
            public void insertString(FilterBypass fb, int offset, String string, AttributeSet attr) throws BadLocationException {
                if (offset < DEFAULT_TEXT.length()) {
                    return;
                }
                super.insertString(fb, offset, string, attr);
            }

            @Override
            public void replace(FilterBypass fb, int offset, int length, String text, AttributeSet attrs) throws BadLocationException {
                if (offset < DEFAULT_TEXT.length()) {
                    length = Math.max(0, length - DEFAULT_TEXT.length());
                    offset = DEFAULT_TEXT.length();
                }
                super.replace(fb, offset, length, text, attrs);
            }

            @Override
            public void remove(FilterBypass fb, int offset, int length) throws BadLocationException {
                if (offset < DEFAULT_TEXT.length()) {
                    length = Math.max(0, length + offset - DEFAULT_TEXT.length());
                    offset = DEFAULT_TEXT.length();
                }
                if (length > 0) {
                    super.remove(fb, offset, length);
                }
            }
        });
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(txt);
        frame.pack();
        frame.setLocationRelativeTo(null);
        frame.setVisible(true);
    }

}

Il lavoro viene fatto nei tre metodi di DocumentFilter:

  • insertString
  • replace
  • remove

A questo puntoci basta avviare il JFrame:

public class Main {

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new MyDocumentFilter()::createGui);
    }

}

Fate qualche prova!

Enjoy!


Condividi

Commentami!