¿Cómo oscurecer un componente Swing?

Hola, tengo un requisito en el que, bajo alguna condición, tengo que oscurecer el componente oscilante (campo de texto) conservando su valor de cadena. es decir, el componente no debería mostrar qué valor de cadena contiene.

preguntado el 22 de mayo de 12 a las 14:05

no encontrado todavía, traté de hacerlo invisible pero quiero que el archivo esté presente pero no debería mostrar los datos. -

6 Respuestas

No hay JPasswordField, que es un campo de texto que se puede alternar para mostrar ** (o algún otro carácter de eco) en lugar del contenido real. Esa es probablemente la forma más fácil.

Si eso no es lo suficientemente bueno, puede extraer el contenido y almacenarlo externamente, en blanco o borrado o en cualquier campo, y setEnabled(false) en eso. Cuando vuelva a habilitar el campo, vuelva a colocar el contenido. Si es necesario usar getText() mientras tanto, tendrá que anular eso para poder sustituir el contenido almacenado cuando corresponda.

contestado el 22 de mayo de 12 a las 14:05

Podrías usar el Componente JLayer:

Un ejemplo de degradado frente a JPanel

contestado el 22 de mayo de 12 a las 14:05

Para hacer una llamada negra de texto completo

textfield.setForeground(new Color(0,0,0,0))
textfield.setBackground(Color.BLACK)
textfield.setOpaque(true)

para evitar que seleccionen la llamada de texto

textfield.setFocusable(false)

contestado el 22 de mayo de 12 a las 21:05

Aunque es una buena sugerencia, pero ¿por qué no usamos esto? textField.setForeground(textField.getBackground());, esto se hará sin dolores de cabeza :-) - cOw nIcE

@GuruKulki y Garrett: Considere también establecer la propiedad enfocable del campo de texto en false al hacer esto también. De lo contrario, el texto se mostrará cuando el campo tenga el foco y el texto esté seleccionado. 1+ voto por tu buena respuesta. - Aerodeslizador lleno de anguilas

Debes ocultar el campo de texto usando .setVisible(false), y reemplácelo por un componente diferente que sea negro (por ejemplo, un JLabel con fondo negro). Esto se puede hacer poniendo ambos componentes (La etiqueta y el campo de texto) en un espacio dedicado. JPanel, apilándolos unos sobre otros. Opcionalmente, puede simplemente ocultar el campo de texto, si no necesita tener un área negra allí.

Hay otros métodos para hacer esto que involucran solo el campo de texto, pero ninguno de ellos es infalible, porque diferentes sistemas operativos renderizarán los componentes de Swing de manera diferente (especialmente Mac OS X), por lo que anular el campo de texto paint() El método o cambiar el color del texto (como lo describe @GarrettHall) no siempre funcionaría, por ejemplo.

contestado el 22 de mayo de 12 a las 14:05

Probablemente, la forma más fácil de hacer esto sería sacar el componente de su contenedor y reemplazarlo con un componente ficticio del mismo tipo. Esto podría encapsularse muy bien creando su propio componente que encapsule el intercambio de componentes (esqueleto):

public class BlackOutTextField extends JPanel {

    private final JTextField realField = new JTextField();
    private final JTextField dummyField = new JTextField();
    private boolean isBlackedOut;

    {
        dummyField.setEditable(false);
        setLayout(new BorderLayout());
        add(realField, BorderLayout.CENTER);
    }

    public String getText() {
        return isBlackedOut ? "" : realField.getText();
    }

    public void setText(final String text) {
        if (!isBlackedOut)
            realField.setText(text);
    }

    public void setBlackedOut(final boolean blackedOut) {
         if (this.isBlackedOut != blackedOut) {
             this.isBlackedOut = blackedOut;
             removeAll();
             add(this.isBlackedOut ? dummyField : realField, BorderLayout.CENTER);
             revalidate();
         }
    }
}

Entiendes la idea.

contestado el 22 de mayo de 12 a las 14:05

He hecho un pequeño ejemplo que solo hace que los caracteres sean negros y el cuadro de texto también negro, usando Solo JTextField, como lo pediste.

import java.awt.Color;
import java.awt.Dimension;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JTextField;

public class RunnableTest{    
    public static void main(String args[]){

        JFrame frame = new JFrame("frame");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        JPanel panel = new JPanel();
        JTextField textfield = new JTextField();
        textfield.setPreferredSize(new Dimension(400,30));
        textfield.setForeground(Color.black);
        textfield.setBackground(Color.black);
        textfield.setSelectedTextColor(Color.black);
        textfield.setSelectionColor(Color.black);

        frame.getContentPane().add(panel);
        panel.add(textfield);
        frame.pack();

         frame.setVisible(true);    
    } 
}

este método textfield.setForeground(Color.black); establece la fuente en negro, y textfield.setBackground(Color.black); este otro método establece el fondo en negro. y

textfield.setSelectedTextColor(Color.black);
textfield.setSelectionColor(Color.black);

establece la selección en negro para que no pueda ver lo que se seleccionó.

Por supuesto, puede utilizar el campo de contraseña como alternativa, si no desea utilizar JTextField, y evitar que el usuario copie el texto.

EDITAR: si no desea que el usuario copie el texto usando CTRL+C, agregue un adaptador de tecla al campo de texto para que sepa cuándo el usuario presionó ambas teclas al mismo tiempo. por supuesto, hay muchas otras combinaciones en otros sistemas, pero esa no es la cuestión.

contestado el 22 de mayo de 12 a las 17:05

Todavía puedes CTRL-C el texto :) - Durandal

Por supuesto que puedes, es un JTextField. y el usuario no especificó que no tenías que hacerlo. no muestra el valor. - Basilio alemán

Ahha, esto es increíble, casi me olvido de la configuración, SelectionColours mientras comentaba, +1, por esta buena adición :-), aunque lo que dice @Durandal, eso da solo una opción, la JPasswordField :-)- cOw nIcE

sí, no lo había agregado pero luego vi que podía ver el texto seleccionado, gracias. - Basilio alemán

Muchos sistemas operativos no usan [Ctrl]+[C] para copiar texto. Algunas alternativas son [Ctrl]+[Alt]+[C] (Unix), [Comando]+[C] (Mac OS X), [Ctrl]+[Insert] (sistemas compatibles con Windows y CUA) o haciendo clic en el texto (X-windows). - dflemstr

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.