📝 tec
← Volver

Temario de Oposición: Tecnologías Web


TEMA 1: SERVICIOS REST (Representational State Transfer)

1.1. Definición y Origen

REST es un estilo arquitectónico para sistemas distribuidos basado en hipermedia, definido por Roy Fielding en su tesis doctoral del año 2000 ("Architectural Styles and the Design of Network-based Software Architectures"). No es un protocolo ni un estándar, sino un conjunto de principios y restricciones arquitectónicas.

Un servicio web que sigue los principios REST se denomina RESTful.


1.2. Principios Fundamentales (Restricciones REST)

REST define 6 restricciones arquitectónicas que debe cumplir un sistema para ser considerado RESTful:

1. Cliente-Servidor (Client-Server)

2. Sin Estado (Stateless)

3. Caché (Cacheable)

4. Interfaz Uniforme (Uniform Interface)

Principio central que distingue REST de otros estilos. Se compone de cuatro subprincipios:

5. Sistema en Capas (Layered System)

6. Código en Demanda (Code on Demand) — Opcional


1.3. Recursos y URIs

Un recurso es cualquier información que pueda ser nombrada: un documento, una imagen, un servicio, una colección de otros recursos, etc.

Buenas prácticas en el diseño de URIs:

# Correcto — Sustantivos en plural
GET /usuarios
GET /usuarios/123
GET /usuarios/123/pedidos

# Incorrecto — Verbos en la URI
GET /obtenerUsuarios
POST /crearUsuario/123

1.4. Métodos HTTP en REST

Los métodos HTTP definen la acción a realizar sobre el recurso:

Método Operación CRUD Descripción Idempotente Seguro
GET Read Obtiene la representación de un recurso
POST Create Crea un nuevo recurso subordinado No No
PUT Update/Replace Reemplaza completamente un recurso No
PATCH Update/Modify Modifica parcialmente un recurso No* No
DELETE Delete Elimina un recurso No
HEAD Igual que GET pero sin cuerpo de respuesta
OPTIONS Describe las opciones de comunicación del recurso

Idempotente: Realizar la misma operación múltiples veces produce el mismo resultado que hacerla una sola vez.
Seguro: La operación no modifica el estado del servidor.


1.5. Códigos de Estado HTTP

Los códigos de estado son fundamentales en REST para comunicar el resultado de una petición:

2xx — Éxito

Código Nombre Uso típico
200 OK Respuesta exitosa a GET, PUT, PATCH, DELETE
201 Created Recurso creado exitosamente (POST)
204 No Content Exitoso sin cuerpo de respuesta (DELETE)

3xx — Redirección

Código Nombre Uso típico
301 Moved Permanently Recurso movido permanentemente
304 Not Modified Respuesta de caché válida (no se retransmite)

4xx — Error del Cliente

Código Nombre Uso típico
400 Bad Request Petición malformada
401 Unauthorized Autenticación requerida
403 Forbidden Autenticado pero sin permisos
404 Not Found Recurso no encontrado
405 Method Not Allowed Método HTTP no permitido para el recurso
409 Conflict Conflicto con el estado actual del recurso
422 Unprocessable Entity Entidad semánticamente incorrecta
429 Too Many Requests Límite de peticiones excedido

5xx — Error del Servidor

Código Nombre Uso típico
500 Internal Server Error Error genérico del servidor
502 Bad Gateway El servidor upstream devolvió una respuesta inválida
503 Service Unavailable Servidor no disponible (mantenimiento)

1.6. Cabeceras HTTP Relevantes en REST

# Petición
Content-Type: application/json       # Tipo del cuerpo enviado
Accept: application/json             # Tipo esperado en respuesta
Authorization: Bearer <token>        # Autenticación
If-None-Match: "abc123"              # Validación de caché (ETag)

# Respuesta
Content-Type: application/json       # Tipo del cuerpo devuelto
ETag: "abc123"                       # Identificador de versión del recurso
Cache-Control: max-age=3600          # Política de caché
Location: /api/v1/usuarios/456       # URI del recurso creado (201 Created)

1.7. Autenticación y Seguridad en REST

Métodos de autenticación:

Buenas prácticas de seguridad:


1.8. HATEOAS

Hypermedia As The Engine Of Application State es el nivel más alto de madurez REST (nivel 3 del modelo de Richardson).

Permite que el cliente navegue por la API dinámicamente a través de los enlaces proporcionados por el servidor, sin necesidad de conocer las URIs de antemano.

{
  "id": 123,
  "nombre": "Juan García",
  "estado": "activo",
  "_links": {
    "self": { "href": "/api/v1/usuarios/123" },
    "pedidos": { "href": "/api/v1/usuarios/123/pedidos" },
    "desactivar": { "href": "/api/v1/usuarios/123/desactivar", "method": "POST" }
  }
}

1.9. Modelo de Madurez de Richardson

Define 4 niveles de adopción de REST:

Nivel Nombre Descripción
0 The Swamp of POX Un único endpoint, todo mediante POST
1 Resources URIs individuales por recurso
2 HTTP Verbs Uso correcto de los métodos HTTP
3 Hypermedia Controls HATEOAS — la API es autodescriptiva

1.10. REST vs SOAP vs GraphQL

Característica REST SOAP GraphQL
Protocolo HTTP HTTP, SMTP, TCP... HTTP
Formato JSON, XML... XML obligatorio JSON
Contrato OpenAPI/Swagger WSDL Schema GraphQL
Flexibilidad Alta Baja Muy alta
Overfetching Posible Posible No
Caché Nativa HTTP Compleja Limitada
Curva aprendizaje Baja Alta Media


TEMA 2: FORMATO JSON (JavaScript Object Notation)

2.1. Definición y Origen

JSON (JavaScript Object Notation) es un formato ligero de intercambio de datos basado en texto, fácil de leer y escribir para humanos, y fácil de parsear y generar para máquinas.


2.2. Tipos de Datos en JSON

JSON define seis tipos de valores:

1. String (Cadena de texto)

"Hola mundo"
"Texto con \"comillas\" escapadas"
"Carácter Unicode: \u00E9"

- Siempre entre comillas dobles ".
- Caracteres que deben escaparse: ", \, /, y los de control (\n, \r, \t, \b, \f).

2. Number (Número)

42
-17
3.14159
2.5e10
-1.5E-3

- Sin distinción entre enteros y decimales.
- No admite NaN, Infinity ni -Infinity.
- No usa comillas.

3. Boolean (Booleano)

true
false

- Solo valores literales true o false (en minúscula).

4. Null

null

- Representa ausencia de valor.

5. Object (Objeto)

{
  "nombre": "María",
  "edad": 28,
  "activa": true
}

- Colección de pares clave-valor no ordenada.
- Claves siempre entre comillas dobles.
- Los pares se separan con comas ,.
- La coma final (trailing comma) no está permitida.

6. Array (Arreglo)

["rojo", "verde", "azul"]
[1, 2, 3, 4, 5]
[true, null, 42, "texto"]

- Lista ordenada de valores.
- Los elementos pueden ser de tipos distintos.


2.3. Estructura de un Documento JSON

Un documento JSON válido tiene exactamente un valor raíz (puede ser cualquier tipo, aunque habitualmente es un objeto o array):

{
  "usuario": {
    "id": 1001,
    "nombre": "Ana López",
    "email": "ana.lopez@ejemplo.es",
    "activo": true,
    "perfil": null,
    "roles": ["admin", "editor"],
    "preferencias": {
      "idioma": "es",
      "notificaciones": true,
      "tema": "oscuro"
    },
    "ultimoAcceso": "2024-03-15T10:30:00Z"
  }
}

2.4. Reglas de Sintaxis JSON


2.5. JSON Schema

JSON Schema permite definir la estructura y validación de documentos JSON. Es un vocabulario que permite anotar y validar documentos JSON.

{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "title": "Usuario",
  "type": "object",
  "required": ["id", "nombre", "email"],
  "properties": {
    "id": {
      "type": "integer",
      "minimum": 1
    },
    "nombre": {
      "type": "string",
      "minLength": 2,
      "maxLength": 100
    },
    "email": {
      "type": "string",
      "format": "email"
    },
    "edad": {
      "type": "integer",
      "minimum": 0,
      "maximum": 150
    }
  },
  "additionalProperties": false
}

2.6. JSON vs XML

Característica JSON XML
Legibilidad Alta Media (más verboso)
Tamaño Menor Mayor (etiquetas de cierre)
Tipos de datos 6 tipos nativos Solo texto (tipos via XSD)
Comentarios No soportados Soportados
Arrays Nativos Emulados con elementos repetidos
Namespaces No
Validación JSON Schema XSD, DTD, RELAX NG
Transformación jq, JSONPath XSLT, XPath
Uso principal APIs REST, configuración Documentos, SOAP, config legacy

2.7. Métodos JSON en JavaScript

// Serialización: objeto JS → string JSON
const obj = { nombre: "Juan", edad: 30 };
const json = JSON.stringify(obj);
// '{"nombre":"Juan","edad":30}'

// Con formato (indentación de 2 espacios)
const jsonFormateado = JSON.stringify(obj, null, 2);

// Con replacer (filtrar propiedades)
const jsonFiltrado = JSON.stringify(obj, ['nombre']);
// '{"nombre":"Juan"}'

// Deserialización: string JSON → objeto JS
const texto = '{"nombre":"Juan","edad":30}';
const objeto = JSON.parse(texto);
// { nombre: 'Juan', edad: 30 }

// Con reviver (transformar valores durante el parseo)
const resultado = JSON.parse(texto, (clave, valor) => {
  if (clave === 'edad') return valor + 1;
  return valor;
});

2.8. JSONPath

JSONPath es un lenguaje de consulta para JSON, análogo a XPath para XML.

$.store.book[*].author       → Todos los autores
$..author                    → Todos los autores (recursivo)
$.store.book[0].title        → Título del primer libro
$.store.book[?(@.price < 10)] → Libros con precio < 10
$.store.book[-1:]            → Último libro
$.store.book[0,1]            → Primero y segundo libro

2.9. Variantes de JSON



TEMA 3: HTML5

3.1. Definición y Evolución

HTML (HyperText Markup Language) es el lenguaje de marcado estándar para crear páginas web. HTML5 es la quinta versión principal, desarrollada conjuntamente por el W3C (World Wide Web Consortium) y el WHATWG (Web Hypertext Application Technology Working Group).


3.2. Estructura Básica de un Documento HTML5

<!DOCTYPE html>
<html lang="es">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="description" content="Descripción de la página">
    <title>Título de la Página</title>
    <link rel="stylesheet" href="estilos.css">
</head>
<body>
    <!-- Contenido de la página -->
    <script src="script.js" defer></script>
</body>
</html>

Elementos del <head>:


3.3. Elementos Semánticos de HTML5

HTML5 introdujo un conjunto de elementos semánticos que describen el significado del contenido, mejorando la accesibilidad y el SEO:

Elementos de estructura de página:

<header>    <!-- Encabezado del sitio o sección -->
<nav>       <!-- Navegación principal -->
<main>      <!-- Contenido principal (único por página) -->
<article>   <!-- Contenido independiente y reutilizable -->
<section>   <!-- Sección temática del documento -->
<aside>     <!-- Contenido tangencialmente relacionado (sidebar) -->
<footer>    <!-- Pie de página -->

Ejemplo de estructura semántica:

<body>
  <header>
    <nav>
      <ul>
        <li><a href="/inicio">Inicio</a></li>
        <li><a href="/blog">Blog</a></li>
      </ul>
    </nav>
  </header>

  <main>
    <article>
      <header>
        <h1>Título del artículo</h1>
        <time datetime="2024-03-15">15 de marzo de 2024</time>
      </header>
      <section>
        <h2>Primera sección</h2>
        <p>Contenido...</p>
      </section>
      <footer>
        <p>Autor: <address>Juan García</address></p>
      </footer>
    </article>

    <aside>
      <h2>Artículos relacionados</h2>
    </aside>
  </main>

  <footer>
    <p>&copy; 2024 Mi Sitio Web</p>
  </footer>
</body>

Otros elementos semánticos importantes:

Elemento Descripción
<figure> Contenido independiente (imagen, diagrama, código)
<figcaption> Leyenda para <figure>
<time> Fecha u hora (atributo datetime en formato ISO)
<mark> Texto resaltado/marcado
<details> Widget de divulgación (expand/collapse)
<summary> Resumen visible de <details>
<dialog> Cuadro de diálogo o ventana modal
<meter> Medida escalar dentro de un rango conocido
<progress> Progreso de una tarea
<output> Resultado de un cálculo

3.4. Formularios en HTML5

HTML5 potencia enormemente los formularios con nuevos tipos de <input> y atributos de validación:

Nuevos tipos de input:

<input type="email">       <!-- Valida formato de email -->
<input type="url">         <!-- Valida formato de URL -->
<input type="tel">         <!-- Campo para teléfono -->
<input type="number" min="0" max="100" step="5">
<input type="range" min="0" max="100">
<input type="date">        <!-- Selector de fecha -->
<input type="datetime-local"> <!-- Fecha y hora -->
<input type="month">       <!-- Mes y año -->
<input type="week">        <!-- Semana y año -->
<input type="time">        <!-- Hora -->
<input type="color">       <!-- Selector de color -->
<input type="search">      <!-- Campo de búsqueda -->

Atributos de validación:

<input required>                    <!-- Campo obligatorio -->
<input minlength="5" maxlength="20"> <!-- Longitud mínima y máxima -->
<input min="0" max="100">           <!-- Valor mínimo y máximo -->
<input pattern="[A-Za-z]{3,}">     <!-- Validación con regex -->
<input autocomplete="email">        <!-- Autocompletado -->
<input placeholder="Introduce tu email"> <!-- Texto de ayuda -->
<input autofocus>                   <!-- Foco automático -->
<input novalidate>                  <!-- Desactivar validación -->

Elementos nuevos:

<datalist id="opciones">   <!-- Lista de sugerencias para input -->
  <option value="Madrid">
  <option value="Barcelona">
</datalist>
<input list="opciones">

<fieldset>                 <!-- Agrupa controles relacionados -->
  <legend>Datos personales</legend>
</fieldset>

3.5. APIs de HTML5

HTML5 incluye numerosas APIs JavaScript que amplían las capacidades del navegador:

Canvas API

<canvas id="miCanvas" width="800" height="600"></canvas>
<script>
  const canvas = document.getElementById('miCanvas');
  const ctx = canvas.getContext('2d');
  ctx.fillStyle = '#FF0000';
  ctx.fillRect(10, 10, 150, 100);
  ctx.beginPath();
  ctx.arc(100, 100, 50, 0, 2 * Math.PI);
  ctx.stroke();
</script>

Web Storage API

// localStorage — persiste sin expiración
localStorage.setItem('clave', 'valor');
localStorage.getItem('clave');
localStorage.removeItem('clave');
localStorage.clear();

// sessionStorage — persiste solo mientras dure la sesión
sessionStorage.setItem('clave', 'valor');
sessionStorage.getItem('clave');

Diferencia con cookies: mayor capacidad (~5-10 MB), no se envían al servidor automáticamente, no tienen expires.

Geolocation API

navigator.geolocation.getCurrentPosition(
  (posicion) => {
    const lat = posicion.coords.latitude;
    const lon = posicion.coords.longitude;
  },
  (error) => console.error(error),
  { enableHighAccuracy: true, timeout: 5000 }
);

Drag and Drop API

<div draggable="true" ondragstart="drag(event)" id="elemento">Arrastra</div>
<div ondragover="allowDrop(event)" ondrop="drop(event)">Zona de destino</div>

Web Workers API

// Hilo de trabajo (worker.js)
self.onmessage = function(e) {
  const resultado = calcularAlgoComplejo(e.data);
  self.postMessage(resultado);
};

// Hilo principal
const worker = new Worker('worker.js');
worker.postMessage(datos);
worker.onmessage = (e) => console.log(e.data);

History API

history.pushState({ pagina: 1 }, 'Título', '/nueva-url');
history.replaceState({ pagina: 2 }, 'Título', '/otra-url');
history.back();
history.forward();
history.go(-2);

WebSockets

const ws = new WebSocket('wss://servidor.ejemplo.com/socket');
ws.onopen = () => ws.send('Hola servidor');
ws.onmessage = (e) => console.log('Recibido:', e.data);
ws.onerror = (e) => console.error(e);
ws.onclose = () => console.log('Conexión cerrada');

Server-Sent Events (SSE)

const eventSource = new EventSource('/api/eventos');
eventSource.onmessage = (e) => console.log(e.data);
eventSource.addEventListener('actualizacion', (e) => { /* ... */ });

3.6. Multimedia en HTML5

<!-- Audio -->
<audio controls autoplay loop muted preload="auto">
  <source src="audio.mp3" type="audio/mpeg">
  <source src="audio.ogg" type="audio/ogg">
  Tu navegador no soporta el elemento audio.
</audio>

<!-- Vídeo -->
<video controls width="800" height="450" poster="thumbnail.jpg" preload="metadata">
  <source src="video.mp4" type="video/mp4">
  <source src="video.webm" type="video/webm">
  <track kind="subtitles" src="subs_es.vtt" srclang="es" label="Español" default>
  Tu navegador no soporta el elemento video.
</video>

3.7. Accesibilidad (WAI-ARIA)

WAI-ARIA (Web Accessibility Initiative - Accessible Rich Internet Applications) es una especificación del W3C que define formas de hacer el contenido web más accesible.

<!-- Roles ARIA -->
<div role="button" tabindex="0" aria-pressed="false">Botón personalizado</div>
<nav role="navigation" aria-label="Menú principal">...</nav>

<!-- Estados y propiedades ARIA -->
<input type="text" aria-required="true" aria-invalid="false">
<div aria-live="polite" aria-atomic="true">Contenido dinámico</div>
<button aria-expanded="false" aria-controls="menu-id">Menú</button>
<ul id="menu-id" aria-hidden="true">...</ul>

<!-- Landmark roles -->
<header role="banner">
<nav role="navigation">
<main role="main">
<footer role="contentinfo">
<aside role="complementary">

3.8. Meta etiquetas importantes

<!-- SEO básico -->
<meta name="description" content="Descripción de la página (150-160 caracteres)">
<meta name="keywords" content="palabra1, palabra2, palabra3">
<meta name="robots" content="index, follow">
<meta name="author" content="Nombre del autor">

<!-- Open Graph (redes sociales) -->
<meta property="og:title" content="Título para redes sociales">
<meta property="og:description" content="Descripción para redes sociales">
<meta property="og:image" content="https://ejemplo.com/imagen.jpg">
<meta property="og:url" content="https://ejemplo.com/pagina">
<meta property="og:type" content="website">

<!-- Twitter Cards -->
<meta name="twitter:card" content="summary_large_image">
<meta name="twitter:site" content="@usuario">

<!-- Responsive -->
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=5.0">


TEMA 4: CSS3

4.1. Definición y Evolución

CSS (Cascading Style Sheets) es un lenguaje de hojas de estilo utilizado para describir la presentación de un documento HTML. CSS3 es la versión más reciente, organizada en módulos independientes, cada uno en su propia especificación, en constante evolución.


4.2. Selectores CSS3

Selectores básicos:

*           { /* Selector universal */ }
div         { /* Selector de tipo/elemento */ }
.clase      { /* Selector de clase */ }
#id         { /* Selector de ID */ }
div, p      { /* Selector de lista/agrupación */ }

Selectores de relación:

div p       { /* Descendiente (cualquier nivel) */ }
div > p     { /* Hijo directo */ }
div + p     { /* Hermano adyacente (inmediatamente después) */ }
div ~ p     { /* Hermanos generales (todos los siguientes) */ }

Pseudoclases:

a:hover          { /* Al pasar el cursor */ }
a:focus          { /* Al recibir foco */ }
a:visited        { /* Enlace visitado */ }
a:active         { /* Al hacer clic */ }
p:first-child    { /* Primer hijo de su padre */ }
p:last-child     { /* Último hijo de su padre */ }
p:nth-child(2n)  { /* Hijos pares (even) */ }
p:nth-child(2n+1){ /* Hijos impares (odd) */ }
p:not(.excluido) { /* Negación */ }
input:checked    { /* Checkbox/radio marcado */ }
input:disabled   { /* Campo deshabilitado */ }
input:valid      { /* Campo con validación correcta */ }
input:invalid    { /* Campo con validación incorrecta */ }
:root            { /* Elemento raíz (html) — para variables */ }

Pseudoelementos:

p::first-line    { /* Primera línea del párrafo */ }
p::first-letter  { /* Primera letra del párrafo */ }
div::before      { /* Inserta contenido antes del elemento */ }
div::after       { /* Inserta contenido después del elemento */ }
::selection      { /* Texto seleccionado por el usuario */ }
::placeholder    { /* Placeholder de inputs */ }

Selectores de atributo:

[href]            { /* Elementos con atributo href */ }
[type="text"]     { /* Atributo con valor exacto */ }
[class~="btn"]    { /* Atributo con valor en lista */ }
[lang|="es"]      { /* Atributo igual o con prefijo "es-" */ }
[href^="https"]   { /* Atributo comienza con */ }
[href$=".pdf"]    { /* Atributo termina con */ }
[href*="ejemplo"] { /* Atributo contiene */ }

4.3. El Modelo de Caja (Box Model)

Todo elemento HTML es representado como una caja rectangular compuesta por:

+----------------------------------+
|           MARGIN                 |
|  +----------------------------+  |
|  |         BORDER             |  |
|  |  +----------------------+  |  |
|  |  |       PADDING        |  |  |
|  |  |  +----------------+  |  |  |
|  |  |  |    CONTENT     |  |  |  |
|  |  |  +----------------+  |  |  |
|  |  +----------------------+  |  |
|  +----------------------------+  |
+----------------------------------+
/* box-sizing controla cómo se calcula el tamaño */
* {
  box-sizing: border-box; /* width/height incluyen padding y border */
}
/* vs */
* {
  box-sizing: content-box; /* Valor por defecto: width/height solo contenido */
}

4.4. Flexbox

CSS Flexible Box Layout (Flexbox) es un modelo de diseño unidimensional para distribuir espacio entre elementos en una interfaz y mejorar las capacidades de alineación.

Contenedor Flex (eje principal):

.contenedor {
  display: flex;               /* o inline-flex */
  flex-direction: row;         /* row | row-reverse | column | column-reverse */
  flex-wrap: nowrap;           /* nowrap | wrap | wrap-reverse */
  flex-flow: row nowrap;       /* shorthand de flex-direction y flex-wrap */
  justify-content: flex-start; /* Alineación en eje principal */
                               /* flex-start | flex-end | center | space-between | space-around | space-evenly */
  align-items: stretch;        /* Alineación en eje cruzado */
                               /* flex-start | flex-end | center | stretch | baseline */
  align-content: flex-start;   /* Alineación de líneas en eje cruzado */
  gap: 1rem;                   /* Espacio entre elementos (row-gap column-gap) */
}

Elementos Flex (hijos):

.elemento {
  flex-grow: 0;    /* Factor de crecimiento (por defecto 0) */
  flex-shrink: 1;  /* Factor de reducción (por defecto 1) */
  flex-basis: auto;/* Tamaño base antes de distribuir espacio */
  flex: 1;         /* Shorthand: flex-grow flex-shrink flex-basis */
                   /* flex: 1 = flex: 1 1 0% */
  align-self: auto;/* Sobreescribe align-items para este elemento */
  order: 0;        /* Orden de aparición */
}

4.5. CSS Grid

CSS Grid Layout es un sistema de diseño bidimensional que permite crear layouts de filas y columnas simultáneamente.

Contenedor Grid:

.contenedor {
  display: grid;

  /* Definir columnas */
  grid-template-columns: 200px 1fr 1fr;          /* Tamaños fijos y fraccionados */
  grid-template-columns: repeat(3, 1fr);          /* 3 columnas iguales */
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr)); /* Responsive */

  /* Definir filas */
  grid-template-rows: auto 1fr auto;

  /* Áreas nombradas */
  grid-template-areas:
    "header  header  header"
    "sidebar main    main"
    "footer  footer  footer";

  /* Espaciado */
  gap: 1rem;               /* row-gap y column-gap */
  row-gap: 1rem;
  column-gap: 2rem;

  /* Alineación del grid en su contenedor */
  justify-content: start;  /* start | end | center | stretch | space-around | space-between */
  align-content: start;

  /* Alineación de los elementos dentro de su celda */
  justify-items: stretch;  /* start | end | center | stretch */
  align-items: stretch;
}

Elementos Grid:

.elemento {
  /* Posicionamiento por líneas */
  grid-column: 1 / 3;          /* Desde línea 1 hasta línea 3 */
  grid-column: 1 / span 2;     /* Desde línea 1, ocupa 2 columnas */
  grid-row: 2 / 4;

  /* Posicionamiento por áreas nombradas */
  grid-area: header;           /* Nombre del área definida en el contenedor */

  /* Alineación individual */
  justify-self: center;
  align-self: end;
}

4.6. Variables CSS (Custom Properties)

Introducidas en CSS3, las variables CSS permiten reutilizar valores a lo largo de la hoja de estilos:

/* Declaración (en :root para acceso global) */
:root {
  --color-primario: #3498db;
  --color-secundario: #2ecc71;
  --fuente-principal: 'Georgia', serif;
  --espaciado-base: 1rem;
  --radio-borde: 8px;
  --sombra: 0 4px 6px rgba(0, 0, 0, 0.1);
}

/* Uso */
.boton {
  background-color: var(--color-primario);
  font-family: var(--fuente-principal);
  padding: var(--espaciado-base);
  border-radius: var(--radio-borde);
  box-shadow: var(--sombra);
}

/* Con valor de fallback */
.elemento {
  color: var(--color-texto, #333);
}

/* Sobreescribir en contexto local */
.tema-oscuro {
  --color-primario: #2980b9;
  --color-fondo: #1a1a2e;
}

/* Manipulación con JavaScript */
document.documentElement.style.setProperty('--color-primario', '#ff0000');
const valor = getComputedStyle(document.documentElement).getPropertyValue('--color-primario');

4.7. Transformaciones y Transiciones

Transformaciones 2D y 3D:

.elemento {
  /* 2D */
  transform: translate(50px, 100px);
  transform: rotate(45deg);
  transform: scale(1.5);
  transform: scale(1.5, 0.8);
  transform: skew(15deg, 5deg);

  /* Múltiples transformaciones (orden importa) */
  transform: rotate(45deg) scale(1.2) translate(10px, 20px);

  /* 3D */
  transform: rotateX(45deg) rotateY(30deg) translateZ(100px);
  transform: perspective(500px) rotateY(45deg);

  /* Punto de origen de la transformación */
  transform-origin: center center;
  transform-origin: top left;
  transform-origin: 50% 50%;

  /* Contexto 3D para hijos */
  transform-style: preserve-3d;
  perspective: 1000px;
}

Transiciones:

.boton {
  background-color: blue;

  /* Shorthand */
  transition: background-color 0.3s ease-in-out;

  /* Múltiples propiedades */
  transition: background-color 0.3s ease, transform 0.2s linear, opacity 0.4s;

  /* Todas las propiedades */
  transition: all 0.3s ease;

  /* Con retardo */
  transition: background-color 0.3s ease 0.1s;
}

.boton:hover {
  background-color: darkblue;
  transform: scale(1.05);
}

Funciones de temporización:


4.8. Animaciones CSS

/* Definición de keyframes */
@keyframes deslizarEntrada {
  from {
    opacity: 0;
    transform: translateX(-100px);
  }
  to {
    opacity: 1;
    transform: translateX(0);
  }
}

@keyframes latido {
  0%, 100% { transform: scale(1); }
  50%       { transform: scale(1.1); }
}

/* Aplicación de la animación */
.elemento {
  animation-name: deslizarEntrada;
  animation-duration: 0.5s;
  animation-timing-function: ease-out;
  animation-delay: 0.2s;
  animation-iteration-count: 1;    /* número o infinite */
  animation-direction: normal;     /* normal | reverse | alternate | alternate-reverse */
  animation-fill-mode: forwards;   /* none | forwards | backwards | both */
  animation-play-state: running;   /* running | paused */

  /* Shorthand */
  animation: deslizarEntrada 0.5s ease-out 0.2s 1 normal forwards;

  /* Múltiples animaciones */
  animation: deslizarEntrada 0.5s ease, latido 1s ease infinite;
}

4.9. Media Queries y Diseño Responsive

/* Mobile-first approach (recomendado) */

/* Estilos base para móvil */
.contenedor {
  width: 100%;
  padding: 1rem;
}

/* Tablet (≥ 768px) */
@media (min-width: 768px) {
  .contenedor {
    padding: 2rem;
  }
}

/* Desktop (≥ 1024px) */
@media (min-width: 1024px) {
  .contenedor {
    max-width: 1200px;
    margin: 0 auto;
    padding: 3rem;
  }
}

/* Pantallas de alta densidad */
@media (-webkit-min-device-pixel-ratio: 2), (min-resolution: 192dpi) {
  .logo {
    background-image: url('logo@2x.png');
  }
}

/* Orientación */
@media (orientation: landscape) { /* ... */ }
@media (orientation: portrait)  { /* ... */ }

/* Preferencias del sistema */
@media (prefers-color-scheme: dark) {
  :root {
    --color-fondo: #1a1a2e;
    --color-texto: #e0e0e0;
  }
}

@media (prefers-reduced-motion: reduce) {
  * {
    animation: none !important;
    transition: none !important;
  }
}

/* Impresión */
@media print {
  nav, aside, footer { display: none; }
  body { font-size: 12pt; }
}

4.10. Funciones CSS Avanzadas

Funciones de color:

color: rgb(255, 0, 0);
color: rgba(255, 0, 0, 0.5);
color: hsl(0, 100%, 50%);
color: hsla(0, 100%, 50%, 0.5);
color: oklch(0.7 0.2 30);      /* Espacio de color perceptualmente uniforme */

Funciones de cálculo:

width: calc(100% - 2rem);
width: calc(50% + 20px);
font-size: calc(1rem + 1vw);   /* Tipografía fluida */

/* Funciones min(), max(), clamp() */
width: min(100%, 600px);       /* El menor de los valores */
width: max(300px, 50%);        /* El mayor de los valores */
font-size: clamp(1rem, 2.5vw, 2rem); /* min, preferido, max */

Gradientes:

/* Gradiente lineal */
background: linear-gradient(to right, #ff6b6b, #feca57);
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);

/* Gradiente radial */
background: radial-gradient(circle at center, #ff6b6b, #feca57);
background: radial-gradient(ellipse 80% 50% at 50% 50%, #ff6b6b, transparent);

/* Gradiente cónico */
background: conic-gradient(from 0deg, red, yellow, green, blue, red);

/* Gradiente repetido */
background: repeating-linear-gradient(45deg, #fff 0, #fff 10px, #eee 10px, #eee 20px);

4.11. Cascade, Especificidad y Herencia

Cascada (orden de precedencia):

  1. Declaraciones de agente de usuario (estilos del navegador)
  2. Declaraciones del autor (archivo CSS)
  3. Declaraciones del usuario (preferencias del navegador)
  4. Declaraciones con !important del autor
  5. Declaraciones con !important del usuario

Especificidad (de menor a mayor):

Selector Especificidad
Elementos y pseudoelementos (div, ::before) (0, 0, 1)
Clases, atributos, pseudoclases (.clase, [attr], :hover) (0, 1, 0)
IDs (#id) (1, 0, 0)
Estilos en línea (style="") (1, 0, 0, 0)
!important Sobreescribe todo

Se calcula como (IDs, Clases, Elementos). Mayor número = mayor especificidad.

/* Especificidad: 0,0,1 */
p { color: blue; }

/* Especificidad: 0,1,1 */
p.destacado { color: green; }

/* Especificidad: 1,1,1 */
#main p.destacado { color: red; } /* Gana */

4.12. Unidades CSS

Absolutas:

Unidad Equivalencia
px Píxel (relativo al dispositivo)
pt Punto tipográfico (1pt = 1/72in)
cm Centímetro
mm Milímetro
in Pulgada (1in = 96px)

Relativas:

Unidad Relativo a...
em Tamaño de fuente del elemento padre
rem Tamaño de fuente del elemento raíz (html)
% Tamaño del elemento padre
vw 1% del ancho del viewport
vh 1% del alto del viewport
vmin 1% del lado menor del viewport
vmax 1% del lado mayor del viewport
ch Ancho del carácter "0" en la fuente actual
ex Altura de la letra "x" en la fuente actual
lh Altura de línea del elemento

4.13. Preprocesadores CSS

Aunque no son CSS puro, son ampliamente utilizados:

Características comunes:

// SCSS - Variables
$color-primario: #3498db;
$fuente-base: 16px;

// Anidamiento
nav {
  background: $color-primario;

  ul {
    list-style: none;

    li {
      display: inline-block;

      &:hover { /* & referencia al selector padre */
        background: darken($color-primario, 10%);
      }
    }
  }
}

// Mixin
@mixin flex-centro {
  display: flex;
  justify-content: center;
  align-items: center;
}

.contenedor {
  @include flex-centro;
}


4.14. Metodologías CSS

BEM (Block Element Modifier)

/* Bloque: componente independiente */
.card { }

/* Elemento: parte del bloque */
.card__title { }
.card__image { }
.card__body { }

/* Modificador: variación del bloque o elemento */
.card--destacado { }
.card__title--grande { }

OOCSS (Object Oriented CSS)

Separar estructura de apariencia, y contenedor de contenido.

SMACSS (Scalable and Modular Architecture for CSS)

Categorías: Base, Layout, Module, State, Theme.

Atomic CSS / Utility-first (Tailwind CSS)

Clases de utilidad de propósito único: flex, mt-4, text-center, bg-blue-500.


Documento generado para preparación de oposiciones. Última actualización: 2024.