Así que aquí está el escenario: me encargaron reemplazar varias docenas de botones redondeados generados por Photoshop para un sitio más grande con un equivalente de HTML / CSS / JS. Antes, cada vez que alguien quería cambiar el texto de un botón (y parecía que ocurría con frecuencia), un diseñador gráfico tenía que iniciar Photoshop, modificar un archivo, ajustar el tamaño, generar una imagen y pasar ese archivo a la persona construyendo la página. Fue un proceso involucrado para algo que debería haber sido simple.
Así que vamos a hacerlo simple!
De inmediato supe que quería presentar una solución tan simple para el desarrollador como pudiera. No quería forzarlos a usar toneladas de marcado adicional en su HTML para llevar a cabo este truco. Esto fue un pedazo de pastel en los navegadores modernos, como verá en un momento. Desafortunadamente, este sitio también tiene una gran base de usuarios de IE, por lo que también necesitaba tener en cuenta los navegadores menos modernos.

Radio de frontera para aquellos que pueden

Decidí que quería usar el radio del borde para los botones redondeados para cualquier navegador que pudiera admitirlo. También decidí que quería crear una sola clase, "botón", para cualquier botón, y debería funcionar más o menos igual en etiquetas de anclaje, etiquetas de botón y "etiquetas de entrada de tipo de envío".
En resumen, mi HTML debería ser tan simple como esto:
<a href="link.html" class="button"> ¡Un botón! </a>
<button class = "button"> También un botón </button>
<input type = "submit" class = "button" value = "Das Button" />
Las etiquetas de entrada y botón son ciertamente difíciles, como he mencionado en otra parte. Para este ejercicio ignoraremos la mayor parte de eso y no nos preocuparemos por los resultados de píxeles perfectos. Realmente, lo suficientemente cerca es lo suficientemente bueno para mí en este caso.
Mi CSS para esos felices navegadores modernos se ve así:
botón {
 pantalla: bloque en línea;
 línea de altura: 1;
 relleno: 7px 10px;
 texto-decoración: ninguno;
 font-weight: negrita;
 color: #fff;
 color de fondo: # 39c;
 -moz-border-radius: 5px;
 -webkit-border-radius: 5px;
 -khtml-border-radius: 5px;
 radio del borde: 5px;
}
input.button, button.button {
 borde: 0px ninguno;
}
La pantalla: inline-block hace que nuestro botón se comporte como un elemento a nivel de bloque (ancho, altura, relleno y el resto), mientras permanece "en línea". Nuestro radio de borde se establece en la parte inferior: 5px, todo alrededor. Primero utilizamos las reglas prefijadas por el proveedor, para los navegadores Mozilla, Webkit y Khtml. Luego terminamos con la regla "estándar" de radio de borde, que actualmente es compatible con Opera 10.5. También tenemos una regla separada para eliminar el borde predeterminado en las etiquetas de entrada y botón. El resto es solo texto y estilo de color.
Y así, tenemos buenos botones redondeados que funcionan en Safari, Chrome, Firefox e incluso la última versión de Opera. Entonces, ¿quién perdió el autobús de la fiesta? Nuestro viejo amigo Internet Explorer, por supuesto (y también los navegadores Opera de más de dos meses). El cliente no se sentía cómodo al darles a los usuarios botones cuadrados, así que tuve que hacer algo, y el primer paso es poder decir qué navegadores no pueden manejar el radio del borde.

Oler el Diff

Aquí es donde la prueba de compatibilidad con radio de borde que construí la semana pasada de repente resulta útil. Simplemente incluyo una pequeña función jQuery, ejecuto la prueba, y ahora puedo decir si el navegador es compatible con el radio del borde (prefijo del proveedor o no). Si te perdiste mi artículo la semana pasada, me aseguraré de revisarlo antes de continuar.
Con la ayuda de mi objeto $ .support.borderRadius, ahora puedo escribir algunos jQuery para tratar los navegadores que no admiten el radio de borde de manera diferente.

Modificar el DOM

No hay una buena manera de falsificar esquinas redondeadas en Internet Explorer sin tener que recurrir a las imágenes. Sin embargo, eso no significa que estemos atascados con la creación de una imagen de botón de talla única y con la inflexibilidad. Realmente, la única parte del botón que nos preocupa cambiar son las fronteras. Así que vamos a preocuparnos por ellos!
Vamos a usar jQuery para crear una estructura que se vea así:
<div class = "buttonwrap">
 <div class = "tl"> </div>
 <div class = "tr"> </div>
 <a href="link.html" class="button"> Nuestro botón </a>
 <div class = "bl"> </div>
 <div class = "br"> </div>
</div>
Buttonwrap div actúa como un contenedor para el resto de nuestros elementos, y estará en posición relativa (pero no se moverá ) para convertirlo en un padre posicionado, lo que nos permitirá mover objetos dentro de él. Las cuatro divs de esquina se colocan absolutamente encima de nuestro botón y se mueven a las cuatro esquinas ("tl" para la parte superior izquierda y así sucesivamente).
Aquí está el jQuery que lo hace:
jQuery (function () {
 jQuery.support.borderRadius = falso;
 jQuery.each (['BorderRadius', 'MozBorderRadius', 'WebkitBorderRadius', 'OBorderRadius', 'KhtmlBorderRadius'], function () {
  if (document.body.style [this]! == undefined) jQuery.support.borderRadius = true;
  return (! jQuery.support.borderRadius);
 });
});
$ (function () {
 if (! $. support.borderRadius) {
  $ ('. botón'). cada (función () {
   $ (this) .wrap ('<div class = "buttonwrap"> </div>')
   .before ('<div class = "corner tl"> </div> <div class = "corner tr"> </div>')
   .after ('<div class = "corner bl"> </div> <div class = "corner br"> </div>');
  });
 }
});
Si el navegador no es compatible con el radio de borde, envolvemos nuestros botones en el div divisor de botones, luego insertamos nuestros cuatro divs de esquina. Es cierto que podríamos haber puesto todos los rincones seguidos, pero me gusta la idea de ponerlos en el mismo orden en que aparecerán visualmente. Y seguro, son cinco divs adicionales en nuestro DOM ... pero no están en nuestro HTML. Me siento cómodo con esa compensación en esta situación.
Ahora solo necesitamos dos piezas más: el CSS para posicionar todo correctamente, y la imagen que nos permitirá falsificar nuestras esquinas. Vamos a tratar con la imagen primero.

Una imagen para redondearlos a todos.

Te sorprenderás de lo simple que resultó ser (al menos, ¡lo era!). Solo necesitamos una pequeña imagen para redondear los cuatro rincones.
En mi situación, estaba tratando con docenas de botones, algunos de colores diferentes, pero todos sobre un fondo blanco. Debido a eso, me di cuenta de que lo que necesitaba era un PNG transparente: blanco en el área de "fondo" exterior y transparente en el interior para dejar que el color de fondo del botón de mi CSS se muestre. Y como mis esquinas estaban redondeadas en la misma cantidad, lo que realmente necesitaba en cada esquina era un cuarto de círculo.
Entonces, lo que hice fue abrir Photoshop y crear una imagen de 10px por 10px. Luego le di un fondo blanco, usé la herramienta de marco elíptica para dibujar un círculo en el centro, y luego eliminé el centro (sin suavizar, pero con suavizado).
Si solo tuvieras un solo botón de color pero múltiples colores de fondo, todavía lo abordaría de la misma manera básica. Simplemente, "seleccionaría inverso" después de crear mi círculo, eliminar el exterior en lugar del interior y proceder de la misma manera.
Una vez que guardé la imagen como PNG de 24 bits, el tamaño total de mi archivo fue de 182 bytes. Si estuviera usando un programa de imágenes más sofisticado como Fireworks, probablemente podría haber reducido el tamaño de la imagen aún más. Y hay que admitir que si quieres que el PNG transparente funcione en IE6, necesitarás usar una solución PNG de algún tipo. Pero eso está fuera del alcance de este artículo en particular. Google ayudará en este caso.
Ahora, usando el poder del posicionamiento de fondo CSS, puedo mostrar solo un cuarto de esa imagen en cada uno de mis rincones. Aquí está mi CSS final compatible con IE:
.buttonwrap {
 pantalla: bloque en línea;
 posición: relativa;
 zoom: 1;
 * pantalla: en línea;
}
.corner {
 posición: absoluta;
 ancho: 5px;
 altura: 5px;
 fondo: url transparente (images / corner.png) no-repeat 0 0;
}
.tl {arriba: 0; izquierda: 0; posición de fondo: arriba a la izquierda; }
.tr {arriba: 0; derecha: 0; posición de fondo: arriba a la derecha; }
.bl {inferior: 0; izquierda: 0; posición de fondo: parte inferior izquierda; }
.br {abajo: 0; derecha: 0; posición de fondo: parte inferior derecha; }
Nota: Las reglas de "zoom" y "* pantalla" anteriores son un truco necesario que hace que IE7 imite la propiedad de bloque en línea (que no se implementa correctamente).