¿Cómo encontrar un color de fuente atractivo si se conoce el color de fondo? [cerrado]


86

Parece que hay tantas aplicaciones web de rueda de color, selector de color y coincidencia de color, en las que le das un color y encontrarán un par de otros colores que crearán un diseño armónico cuando se usen en combinación. Sin embargo, la mayoría de ellos se enfocan solo en colores de fondo y cualquier texto impreso en cada color de fondo (si el texto se imprime en la vista previa) es blanco o negro.

Mi problema es diferente. Sé el color de fondo que quiero usar para un área de texto. Necesito ayuda para elegir un par de colores (cuantos más, mejor) que puedo usar como colores de fuente en este fondo. Lo más importante es que el color asegurará que la fuente sea legible (el contraste no sea demasiado bajo, y quizás tampoco demasiado alto para evitar que los ojos se estresen) y, por supuesto, que la combinación de primer plano y fondo se vea bien.

¿Alguien está al tanto de tal aplicación? Preferiría una aplicación web a cualquier cosa que tenga que descargar. Gracias.

Respuestas:


39

Si necesita un algoritmo, intente esto: Convierta el color del espacio RGB al espacio HSV (Tono, Saturación, Valor). Si su marco de interfaz de usuario no puede hacerlo, consulte este artículo: http://en.wikipedia.org/wiki/HSL_and_HSV#Conversion_from_RGB_to_HSL_or_HSV

El tono está en [0,360). Para encontrar el color "opuesto" (piense en la rueda de colores), simplemente agregue 180 grados:

h = (h + 180) % 360;

Para saturación y valor, inviértelos:

l = 1.0 - l;
v = 1.0 - v;

Convierta de nuevo a RGB. Esto siempre debería brindarle un alto contraste, aunque la mayoría de las combinaciones se verán feas.

Si quieres evitar la parte "fea", construye una tabla con varias combinaciones "buenas", encuentra la que tenga la menor diferencia

def q(x):
    return x*x
def diff(col1, col2):
    return math.sqrt(q(col1.r-col2.r) + q(col1.g-col2.g) + q(col1.b-col2.b))

y usa eso.


4

De acuerdo, esta todavía no es la mejor solución posible, pero es un buen punto para comenzar. Escribí una pequeña aplicación Java que calcula la relación de contraste de dos colores y solo procesa colores con una relación de 5: 1 o mejor; esta relación y la fórmula que uso ha sido publicada por el W3C y probablemente reemplazará la recomendación actual (que Lo considero muy limitado). Crea un archivo en el directorio de trabajo actual llamado "selected-font-colors.html", con el color de fondo de su elección y una línea de texto en cada color que pasó esta prueba W3C. Espera un solo argumento, siendo el color de fondo.

Por ejemplo, puedes llamarlo así

java FontColorChooser 33FFB4

luego, simplemente abra el archivo HTML generado en un navegador de su elección y elija un color de la lista. Todos los colores dados pasaron la prueba W3C para este color de fondo. Puede cambiar el corte reemplazando 5 con un número de su elección (los números más bajos permiten contrastes más débiles, por ejemplo, 3 solo asegurará que el contraste sea 3: 1, 10 garantizará que sea al menos 10: 1) y también puede cortar para evitar contrastes demasiado altos (asegurándose de que sea menor que un cierto número), por ejemplo, agregando

|| cDiff > 18.0

a la cláusula if asegurará que el contraste no sea demasiado extremo, ya que los contrastes demasiado extremos pueden estresar sus ojos. Aquí está el código y diviértete jugando un poco con él :-)

import java.io.*;

/* For text being readable, it must have a good contrast difference. Why?
 * Your eye has receptors for brightness and receptors for each of the colors
 * red, green and blue. However, it has much more receptors for brightness
 * than for color. If you only change the color, but both colors have the
 * same contrast, your eye must distinguish fore- and background by the
 * color only and this stresses the brain a lot over the time, because it
 * can only use the very small amount of signals it gets from the color
 * receptors, since the breightness receptors won't note a difference.
 * Actually contrast is so much more important than color that you don't
 * have to change the color at all. E.g. light red on dark red reads nicely
 * even though both are the same color, red.
 */


public class FontColorChooser {
    int bred;
    int bgreen;
    int bblue;

    public FontColorChooser(String hexColor) throws NumberFormatException {
        int i;

        i = Integer.parseInt(hexColor, 16);
        bred = (i >> 16);
        bgreen = (i >> 8) & 0xFF;
        bblue = i & 0xFF;
    }

    public static void main(String[] args) {
        FontColorChooser fcc;

        if (args.length == 0) {
            System.out.println("Missing argument!");
            System.out.println(
                "The first argument must be the background" +
                "color in hex notation."
            );
            System.out.println(
                "E.g. \"FFFFFF\" for white or \"000000\" for black."
            );
            return;
        }
        try {
            fcc = new FontColorChooser(args[0]);
        } catch (Exception e) {
            System.out.println(
                args[0] + " is no valid hex color!"
            );
            return;
        }
        try {
            fcc.start();
        } catch (IOException e) {
            System.out.println("Failed to write output file!");
        }
    }

    public void start() throws IOException {
        int r;
        int b;
        int g;
        OutputStreamWriter out;

        out = new OutputStreamWriter(
            new FileOutputStream("chosen-font-colors.html"),
            "UTF-8"
        );

        // simple, not W3C comform (most browsers won't care), HTML header
        out.write("<html><head><title>\n");
        out.write("</title><style type=\"text/css\">\n");
        out.write("body { background-color:#");
        out.write(rgb2hex(bred, bgreen, bblue));
        out.write("; }\n</style></head>\n<body>\n");

        // try 4096 colors
        for (r = 0; r <= 15; r++) {
            for (g = 0; g <= 15; g++) {
                for (b = 0; b <= 15; b++) {
                    int red;
                    int blue;
                    int green;
                    double cDiff;

                    // brightness increasse like this: 00, 11,22, ..., ff
                    red = (r << 4) | r;
                    blue = (b << 4) | b;
                    green = (g << 4) | g;

                    cDiff = contrastDiff(
                        red, green, blue,
                        bred, bgreen, bblue
                    );
                    if (cDiff < 5.0) continue;
                    writeDiv(red, green, blue, out);
                }
            }
        }

        // finalize HTML document
        out.write("</body></html>");

        out.close();
    }

    private void writeDiv(int r, int g, int b, OutputStreamWriter out)
        throws IOException
    {
        String hex;

        hex = rgb2hex(r, g, b);
        out.write("<div style=\"color:#" + hex + "\">");
        out.write("This is a sample text for color " + hex + "</div>\n");
    }

    private double contrastDiff(
        int r1, int g1, int b1, int r2, int g2, int b2
    ) {
        double l1;
        double l2;

        l1 = ( 
            0.2126 * Math.pow((double)r1/255.0, 2.2) +
            0.7152 * Math.pow((double)g1/255.0, 2.2) +
            0.0722 * Math.pow((double)b1/255.0, 2.2) +
            0.05
        );
        l2 = ( 
            0.2126 * Math.pow((double)r2/255.0, 2.2) +
            0.7152 * Math.pow((double)g2/255.0, 2.2) +
            0.0722 * Math.pow((double)b2/255.0, 2.2) +
            0.05
        );

        return (l1 > l2) ? (l1 / l2) : (l2 / l1);
    }

    private String rgb2hex(int r, int g, int b) {
        String rs = Integer.toHexString(r);
        String gs = Integer.toHexString(g);
        String bs = Integer.toHexString(b);
        if (rs.length() == 1) rs = "0" + rs;
        if (gs.length() == 1) gs = "0" + gs;
        if (bs.length() == 1) bs = "0" + bs;
        return (rs + gs + bs);
    }
}

Más uno, cálculo de contraste, exactamente lo que estaba buscando.
Max Kielland

2

Esta es una pregunta interesante, pero no creo que sea posible. Si dos colores "encajan" como colores de fondo y de primer plano depende de la tecnología de visualización y de las características fisiológicas de la visión humana, pero lo más importante es de los gustos personales moldeados por la experiencia. Un recorrido rápido por MySpace muestra claramente que no todos los seres humanos perciben los colores de la misma manera. No creo que este sea un problema que se pueda resolver algorítmicamente, aunque puede haber una enorme base de datos en algún lugar de colores coincidentes aceptables.


2

Implementé algo similar por una razón diferente: era un código para decirle al usuario final si los colores de primer plano y de fondo que seleccionaron resultarían en texto ilegible. Para hacer esto, en lugar de examinar los valores RGB, convertí el valor del color a HSL / HSV y luego determiné mediante experimentación cuál era mi punto de corte para la legibilidad al comparar los valores fg y bg. Esto es algo que quizás desee / deba considerar.


2

En una aplicación reciente que hice, usé los colores invertidos. Con los valores r, gy b en la mano, simplemente calcule (en este ejemplo, el rango de color varía de 0 a 255):

r = 127-(r-127) and so on.

1

Puede ser extraño responder a mi propia pregunta, pero aquí hay otro selector de color realmente genial que nunca vi antes. Tampoco resuelve mi problema: - ((((sin embargo, creo que es mucho mejor que estos que ya sé.

http://www.colorjack.com/

A la derecha, en Herramientas, seleccione "Esfera de color", una esfera muy poderosa y personalizable (vea lo que puede hacer con las ventanas emergentes en la parte superior), "Galaxia de color". Todavía no estoy seguro de cómo funciona, pero se ve genial y "Color Studio" también es agradable. Además, puede exportar a todo tipo de formatos (por ejemplo, Illustrator o Photoshop, etc.)

¿Qué tal esto, elijo mi color de fondo allí, dejo que cree un color complementario (desde la primera ventana emergente); esto debería tener el mayor contraste y, por lo tanto, ser mejor legible, ahora seleccione el color complementario como color principal y seleccione neutral? Hmmm ... tampoco demasiado bueno, pero estamos mejorando ;-)


No, no es extraño en absoluto responder tu propia pregunta, terminé haciéndolo un par de veces y obtener las respuestas solo mejora a la comunidad.
Dillie-O

0

¿Ha considerado permitir que el usuario de su aplicación seleccione su propio esquema de color? Sin falta, no podrá complacer a todos sus usuarios con su selección, pero puede permitirles encontrar lo que les agrade.


1
No hay nada de malo en dejar que el usuario decida, pero al menos debería incluir un tema de color predeterminado útil, ¿no? No puede ser que sea ilegible y feo como el infierno por defecto hasta que cada usuario lo arregle ;-)
Mecki

0

Similar a la sugerencia de @Aaron Digulla, excepto que sugeriría una herramienta de diseño gráfico, seleccione el color base, en su caso el color de fondo, luego ajuste el tono, la saturación y el valor. Con esto, puede crear muestras de color muy fácilmente. Paint.Net es gratuito y lo uso todo el tiempo para esto y también las herramientas de pago también lo harán.


0

Personalmente, no creo que podamos encontrar un algoritmo para calcular el color de texto más coincidente especificando el color de fondo.

Creo que actualmente el artista debería tener una lista de pares de colores que tenga una buena calidad de lectura, podemos agregarlos a una tabla y establecer uno de estos pares al azar como nuestro tema de lectura ...

esto es muy razonable y no obtendremos pares de colores feos ...

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.