Editor de Croquis Fusión 3D
Fase 0 · prototipo Fusión 3D

Alta de edificio por croquis

Sube la foto de un croquis a mano, un DXF de AutoCAD o un SVG y deja que se reconozcan las estancias; o dibújalas sobre la retícula. Ponles uso, acabados y puntos domóticos, y el 3D se levanta solo. Lo que exportas abajo es exactamente el modelo de datos que consume el resto de la plataforma.

Vista
Plantas en 3D
Planta
Muro visible 1,3 m
Croquis · planta Arrastra para dibujar una estancia rectangular 0,00 · 0,00 m
Modelo 3D · en vivo Arrastra para orbitar · rueda para acercar · clic en un elemento para abrirlo
01

Qué demuestra este prototipo y qué falta

Lo de arriba es funcional: dibuja, mide, extruye, ancla y exporta. Es deliberadamente el recorrido más corto que ya cuenta la historia completa al cliente —del papel al gemelo operativo en un par de minutos— y sirve como banco de pruebas de la única métrica que decide si el negocio funciona: minutos por punto anclado.

Lo que hace el prototipo y el producto tendrá que hacer mejor:

CapacidadEn el prototipoEn el MVP
TrazadoContornos que mezclan tramos rectos y curvos (bulge como el DXF), retícula de 0,25 m e imán a vérticeMuros como polilíneas con detección automática de recintos (grafo planar), arcos incluidos
VisualizaciónDos modos: la planta activa con todo el detalle, o el edificio entero por código de color con balizas de alarmaSecciones verticales, filtro por servicio y encuadre guardado por usuario
ImportaciónFoto o escaneado, DXF de AutoCAD y SVGAñade PDF vectorial acotado; el DWG se resuelve pidiendo exportación a DXF
AcabadosSeis suelos y cinco muros generados por código, con color por estanciaSubir la foto del material real del cliente y biblioteca compartida entre edificios
Plano de fondoFoto del croquis reconocida y usada como calco; escala por ancho totalPDF multipágina, calibrado por cota y corrección de perspectiva
MurosEspesor único de 20 cm generado del contornoTipos de muro, medianeras compartidas, huecos de puerta y ventana
AnclajeAl centroide de la estanciaPosición libre, importación del .knxproj y emparejamiento por nombre
DatosSimulación local en el navegadorWebSocket contra el gateway del edificio
PersistenciaNinguna: vive en memoriaPostgreSQL + PostGIS con versionado de modelo
02

Los tres algoritmos que hay que resolver bien

1 · Imán y retícula

Todo el resto depende de que dos muros que deberían tocarse se toquen exactamente. El orden importa: primero se busca vértice existente dentro del radio de imán, y solo si no hay se redondea a retícula. Al revés se producen huecos de un cuarto de metro que luego rompen la detección de recintos.

function snap(p, vertices, opts = { grid: 0.25, magnet: 0.45 }) {
  let best = null, bestD = opts.magnet;
  for (const v of vertices) {
    const d = Math.hypot(v.x - p.x, v.y - p.y);
    if (d < bestD) { bestD = d; best = v; }
  }
  if (best) return { x: best.x, y: best.y, snapped: 'vertex' };
  const g = opts.grid;
  return { x: Math.round(p.x / g) * g, y: Math.round(p.y / g) * g, snapped: 'grid' };
}

2 · De polilíneas de muro a recintos

Es la pieza que convierte un dibujo en un edificio, y la que el prototipo esquiva. La solución es de libro de geometría computacional y se implementa en dos o tres días: construir un grafo planar con los segmentos, partirlos en cada intersección, y recorrer las caras internas con el giro más a la izquierda en cada nodo.

  • Partición: calcular todas las intersecciones segmento-segmento y trocear. Sin esto, dos muros en cruz no generan cuatro estancias.
  • Semiaristas: cada segmento produce dos aristas dirigidas; en cada nodo se ordenan por ángulo.
  • Recorrido de caras: desde una semiarista no visitada, tomar siempre la siguiente en sentido horario alrededor del nodo destino. Cada ciclo cerrado es una cara.
  • Descartar la exterior: la cara con área con signo negativo (o la de mayor área absoluta) es el exterior del edificio.
  • Persistencia de identidad: al recalcular, cada recinto nuevo hereda el space_id del anterior cuyo centroide esté más cerca y cuya área difiera menos de un 20 %. Sin esta regla, mover un muro borraría los anclajes de la estancia.

Bibliotecas que evitan escribir lo peor: polygon-clipping para uniones y offsets, martinez-polygon-clipping como alternativa, y earcut para triangular el resultado.

3 · Calibrado del plano de fondo

El usuario sube un PDF o una foto del plano, hace clic en los dos extremos de una cota conocida y teclea su medida real. Con eso se resuelve la escala y todo lo que dibuje encima está en metros. Es una funcionalidad de media jornada y es la que convierte el editor en algo usable para un edificio existente sin documentación digital.

// px → metros a partir de dos puntos y una distancia conocida
const pxDist = Math.hypot(b.x - a.x, b.y - a.y);
const metersPerPixel = knownMeters / pxDist;
// el PDF se rasteriza en cliente con pdf.js y se pinta como capa de fondo
// la rotación se corrige alineando la cota con el eje X
const angle = Math.atan2(b.y - a.y, b.x - a.x);
03

Vías de entrada del plano

Tres formatos entran ya por el mismo botón, y los tres desembocan en el mismo sitio: dos familias de líneas —horizontales y verticales— que alimentan un único detector de recintos. Eso es lo que hace barato añadir formatos: el reconocimiento se escribe una vez.

FormatoEstadoEscalaQué hace falta
Foto o escaneado
JPG · PNG
FuncionaAncho real que teclea el usuarioVisión: umbral adaptativo y detección de líneas. Es el caso del croquis a mano y del plano en papel
DXF de AutoCAD
LINE · LWPOLYLINE · POLYLINE
FuncionaReal: viene en el ficheroParser de códigos de grupo y detección de unidades. Precisión milimétrica, sin calibrar nada
SVG vectorial
line · rect · polyline · path
FuncionaAncho real que teclea el usuarioEl puente universal: cualquier CAD, Illustrator o Inkscape exporta a SVG
PDF vectorial acotadoMVPReal si se lee la cotapdf.js y su lista de operadores de dibujo: las líneas salen ya vectoriales, entran por la misma tubería. Un PDF escaneado, en cambio, es una imagen y va por la primera vía
DWGNo—Formato cerrado. Se pide al cliente que exporte a DXF, que es un clic en AutoCAD y no cuesta licencia
IFCFase 2RealOtra tubería distinta: trae espacios y GUID, no hace falta detectar nada. Ver el documento de arquitectura

La diferencia práctica entre foto y CAD

En un DXF cada muro son dos líneas paralelas, no una. Si no se funden, entre ellas queda una celda de veinte centímetros que el detector leería como una habitación estrechísima. Por eso el panel tiene un «espesor máximo de muro»: agrupa los dos ejes en uno antes de construir la rejilla. Es un parámetro, no un algoritmo nuevo, y es la única concesión que ha hecho falta para que el mismo código sirva para una foto y para AutoCAD.

El reconocimiento sobre imagen, paso a paso

Corre entero en el navegador, sin servidor ni librerías externas. Son cinco pasos encadenados.

  1. Umbral adaptativo con imagen integral, no un umbral global. Es lo que hace que una foto con sombra en una esquina siga funcionando.
  2. Dilatación direccional de ±3 px en vertical antes de buscar muros horizontales, y al revés para los verticales. Aquí es donde se absorbe el pulso: una línea a mano que se desvía tres píxeles sigue leyéndose como recta.
  3. Detección de muros por tiras contiguas de tinta más largas que un umbral, con puenteo de huecos, y fusión de las tiras de filas contiguas en una sola línea.
  4. Rejilla irregular: las coordenadas de los muros se agrupan en ejes X e Y. Cada celda tiene muro en un lado si una línea cubre al menos el 60 % de ese lado.
  5. Union-find y contorno: las celdas sin muro entre ellas se fusionan, y el contorno rectilíneo de cada grupo es la estancia —incluidas las de planta en L. La región que da al exterior se descarta sola.

Esta ruta por rejilla evita el grafo planar completo de la sección anterior y, para croquis ortogonales —que es como dibuja a mano todo el mundo—, da el mismo resultado con una décima parte del código.

Visión clásica o modelo de visión

Visión clásica en el navegadorModelo de visión (VLM)
Coste por fotoCeroCéntimos, y recurrente
LatenciaMenos de un segundo3 a 10 segundos
Funciona sin conexiónSíNo
DeterministaSí: mismos parámetros, mismo resultadoNo: dos llamadas iguales pueden diferir
Croquis torcido, curvo o sucioFallaRobusto
Lee lo escrito a manoNoSí: nombres de estancia y cotas
Deduce el uso de cada estanciaNoSí

La recomendación: híbrido, y en este orden

Primero el clásico, porque resuelve gratis y al instante el croquis ortogonal sobre papel blanco, que es la mayoría. El VLM entra como segunda pasada, solo cuando el clásico no cierra ningún recinto o cuando el usuario pulsa «no es esto» —y ahí aporta lo que el otro no puede: leer «salón», «cocina» y «3,20» escritos a mano, y devolver nombres, usos y la cota de calibrado. Así el coste variable solo aparece en los croquis difíciles.

Con una condición: la geometría del VLM se regulariza siempre en local —ortogonalizar, cerrar polígonos, imantar a la retícula de 0,25 m— porque un modelo de lenguaje da coordenadas aproximadas, nunca exactas.

// Segunda pasada: contrato estricto de salida del VLM
{
  "spaces": [
    { "name": "salón", "use": "living", "confidence": 0.86,
      "polygon": [[0.06,0.09],[0.36,0.09],[0.36,0.58],[0.06,0.58]] }   // normalizado 0-1
  ],
  "dimensions": [
    { "text": "12,50 m", "value_m": 12.5, "spans": "ancho total" }      // calibra la escala
  ],
  "notes": "croquis ortogonal, 5 recintos, cota en el borde superior"
}

Límites que hay que decir en la demo comercial

  • Croquis ortogonales sobre fondo claro. Las diagonales y las curvas no se reconocen —el detector trabaja sobre rejilla—, y no merece la pena forzarlas: el tramo curvo del editor las dibuja a mano en treinta segundos.
  • Foto tomada de frente. Con perspectiva marcada hay que rectificar antes detectando las cuatro esquinas del papel —es el siguiente incremento natural, media jornada.
  • Alguien tiene que decir cuánto mide algo. El VLM lee la cota escrita si la hay; si no, el editor la pide. No hay forma de deducir la escala de un dibujo sin referencia.
  • Entra siempre como borrador. El objetivo no es acertar el 100 %: es ahorrar el 80 % del trazado y que el repaso humano cueste dos minutos.

En el plan, la vía clásica cae en el sprint 3 —ya está validada aquí arriba— y la segunda pasada con VLM en fase 2, cuando haya croquis reales de clientes con los que medir cuántos la necesitan de verdad.

04

Contrato de datos

El editor no habla con la base de datos: publica un documento de modelo y el servidor lo valida, lo versiona y deriva de él la geometría 3D. Que el editor sea sustituible es intencionado —mañana el mismo documento puede venir de un IFC o de un escaneo.

POST /v1/buildings/:id/model-versions
{
  "source": "sketch",
  "editor_version": "0.4.1",
  "storeys": [{
    "ref": "p00", "name": "Planta baja", "level": 0, "height": 3.0,
    "spaces": [{
      "ref": "spc_recepcion", "name": "Recepción", "use": "reception",
      "footprint": [[0,0],[7,0],[7,4],[0,4]],      // metros, sentido antihorario
      "wall_thickness": 0.2
    }]
  }],
  "anchors": [
    { "point_ref": "knx:1/1/3", "space_ref": "spc_recepcion", "role": "actuator",
      "representation": "luminaire", "position": [3.5, 2.7, 2.0] }
  ]
}

201 → { "model_version_id": "mv_01J8...", "status": "processing",
        "spaces_created": 8, "anchors_bound": 6, "anchors_orphaned": 0 }

El worker responde por webhook cuando la geometría está teselada:
{ "event": "model.ready", "assets": [
    { "storey_ref": "p00", "lod": 0, "uri": "s3://.../p00_lod0.glb", "bytes": 184320 } ] }

La regla que no se negocia

El anclaje se guarda contra space_ref, y la posición [x,y,z] es opcional y local a la estancia. Si en la versión siguiente del modelo la estancia cambia de forma, el anclaje sobrevive; si desaparece, el anclaje pasa a una bandeja de huérfanos y el alta no se pierde. Esto es lo que permite que el croquis sea tosco y rehacible sin coste.

05

Materiales y realismo

El botón Texturas está activo desde el arranque: cada estancia tiene un suelo y un acabado de muro, con valores por defecto según su uso —parquet y yeso en despachos, gres en pasillos, hidráulica y alicatado en aseos, hormigón visto en la sala técnica— y se cambian en el panel derecho, material y color, con un botón para aplicar a toda la planta.

Las texturas se dibujan por código en un canvas de 256 píxeles: vetas de mármol, juntas de gres, hiladas de ladrillo, fibra de moqueta. Ninguna se descarga.

  • Peso: una biblioteca de texturas fotográficas decente son decenas de megabytes. Aquí son cero bytes de red y unos milisegundos de CPU.
  • Licencias: no hay que auditar la procedencia de ninguna imagen antes de venderle el producto a un cliente.
  • Tintado: el color es un parámetro, no un filtro. El gestor prueba cinco tonos de pintura en la sala y el material se regenera al instante.
  • Escala real: cada material declara su tamaño de repetición en metros —1,4 m el parquet, 0,6 m el gres— y las UV del modelo van en metros, así que una baldosa mide lo que mide independientemente del tamaño de la sala.

Cuando esto llegue a producción, el siguiente escalón es permitir subir una foto del material real —el gres concreto que va a poner el cliente— y usarla como textura. Es lo mismo, con una imagen en vez de un canvas.

Textura y dato no se mezclan

Al activar Estado en vivo las texturas se apagan solas y el suelo pasa a colorearse por temperatura o consumo. Es deliberado: un mapa de calor sobre un parquet no se lee, y un gemelo que intenta ser bonito y analítico a la vez falla en las dos cosas. Son dos vistas del mismo modelo —la de enseñar y la de operar— y el usuario alterna entre ellas con un clic.

06

Curvas y vista de edificio

Un contorno, dos tipos de tramo

Una estancia ha dejado de ser una lista de puntos: es una lista de nodos, y cada nodo lleva un bulge —la tangente de un cuarto del ángulo abarcado, exactamente la convención del DXF—. Cero es un tramo recto; cualquier otro valor es un arco. El polígono que consume el resto del editor —área, extrusión, muros, anclaje, JSON— se tesela de ese contorno, así que nada del código existente ha tenido que enterarse de que ahora hay curvas.

  • Al dibujar: con la herramienta Polígono, A pone en curvo el siguiente tramo. Clic en el final del arco, mueve el ratón para darle la flecha y clic para fijarla. Rectas y curvas se alternan en el mismo contorno sin cambiar de herramienta.
  • Al editar: cualquier estancia ya dibujada —incluida una rectangular o una importada de un croquis— muestra un tirador redondo en el centro de cada lado. Arrastrarlo curva ese lado; devolverlo al centro lo endereza.
  • Al exportar: el documento lleva las dos cosas, outline con los bulges y footprint ya teselado. El servidor no necesita trigonometría y el editor no pierde la curva al recargar el modelo.

La teselación es adaptativa —paso máximo de 12° y cuerda de 35 cm—, de modo que un muro curvo de tres metros son ocho cajas en el 3D y un ábside completo, veinticuatro. Sale más barato que una geometría de revolución y se lleva bien con el muro de espesor constante.

// del arrastre del tirador al bulge, que es lo que se guarda
const h = (p.x - mid.x)*n.x + (p.y - mid.y)*n.y;   // n = normal izquierda del tramo
const bulge = 2*h / chord;                          // 0 = recto · 1 = semicírculo
// y de vuelta, para teselar
const R = (chord*chord/4 + h*h) / (2*Math.abs(h));
const steps = Math.ceil(Math.max(Math.abs(sweep)/0.21, R*Math.abs(sweep)/0.35));

Una planta o el edificio entero

Las plantas semitransparentes apiladas no se leen: el ojo no sabe decir si una mancha roja está en la tercera o en la quinta. Por eso el visor tiene ahora dos modos, y ninguno de los dos es un compromiso entre los otros.

  • Activa: sólo la planta del selector, a ras de suelo, con texturas, elementos anclados y widgets. Es la vista de trabajo —dar de alta, anclar, comprobar— y es la que estaba emborronando el apilado anterior.
  • Todas: el edificio completo, con separación regulable entre plantas, sin texturas y sin elementos. Sólo losas por código de color, muros bajos para ver dentro y una baliza pulsante sobre cada estancia en alarma. La pregunta que responde es «¿dónde está el problema?», no «¿qué hay en esta sala?».

Un clic sobre cualquier planta de la vista de edificio la convierte en la activa, así que el recorrido natural —ver la alarma arriba, bajar al detalle— cuesta un clic. Con el estado en vivo apagado, el color es el uso de la estancia; encendido, es la temperatura o el consumo, y las balizas marcan lo que se sale de rango o el sensor de humos o fuga que ha saltado.

Por qué la vista de edificio no lleva detalles

Un edificio de ocho plantas con cuarenta puntos por planta son trescientos marcadores en pantalla: a esa densidad no se distingue ninguno. La vista de vigilancia renuncia a propósito a los elementos, a las texturas y a los rótulos, y se queda con lo único que hay que reconocer de un vistazo y desde lejos: qué planta, qué estancia y de qué color. El detalle está a un clic, que es exactamente donde tiene que estar.

07

Stack del módulo

PiezaElecciónPor qué esta y no otra
Lienzo 2DCanvas 2D nativoUn editor de plantas es dibujo vectorial simple; ni SVG ni una librería de diagramas aportan nada y ambas estorban al llegar a mil segmentos
Motor 3Dthree.jsMIT, el mismo motor del visor de explotación: una sola escena que mantener
Geometría de polígonospolygon-clippingUniones, diferencias y offsets robustos con coordenadas en punto flotante
TriangulaciónearcutLosas y techos; es lo que usa three.js por dentro, sin dependencia nueva real
Croquis desde fotoCódigo propio, sin dependenciasUmbral adaptativo, rejilla y union-find: 300 líneas de JavaScript, cero coste por uso y determinista. Segunda pasada con VLM solo para los croquis que fallen
DXF y SVGParsers propiosEl DXF son pares código-valor: se lee sin librería. El SVG, con DOMParser del navegador. Ambos alimentan el mismo detector de recintos
MaterialesCanvas 2D → CanvasTextureTexturas generadas por código: cero peso de red, cero licencias que auditar y tintado por parámetro
PDF vectorialpdf.jsSu lista de operadores da las líneas ya vectoriales; el PDF escaneado va por la vía de imagen
Estado del editorZustand + patch inmutableDeshacer y rehacer salen gratis si cada acción es un parche; imprescindible en un editor
Teselado servidorNode + gltf-transformCompresión Draco y Meshopt, generación de LOD y miniatura de planta
PersistenciaPostgreSQL + PostGISfootprint como POLYGON permite consultas espaciales reales: qué hay dentro, qué toca con qué
08

Plan de ocho semanas

Un desarrollador con dedicación completa, más medio perfil de producto para las pruebas con usuario. Cada sprint termina con algo que se puede enseñar a un gestor de fincas.

Sprint 1 · sem 1-2

Lienzo y trazado

  • Retícula, zoom, paneo, escala métrica
  • Muros como polilíneas con imán
  • Deshacer y rehacer
  • Persistencia local del borrador
Salida: se dibuja una planta y se recupera al recargar
Sprint 2 · sem 3-4

Recintos y 3D

  • Grafo planar y detección de caras
  • Identidad estable de estancia
  • Extrusión y vista 3D sincronizada
  • Uso, altura y nombre por estancia
Salida: planta dibujada = edificio navegable
Sprint 3 · sem 5-6

Plano de fondo y plantas

  • Reconocimiento de foto de croquis (ya prototipado)
  • Carga de PDF y calibrado por cota
  • Varias plantas, duplicado y calco
  • Guardado en servidor con versionado
  • Teselado y LOD en el worker
Salida: un edificio real de 4 plantas dado de alta en menos de una hora
Sprint 4 · sem 7-8

Anclaje y estado

  • Importación del .knxproj y descubrimiento Modbus
  • Emparejamiento asistido por nombre
  • Anclaje masivo y bandeja de huérfanos
  • Estado en vivo desde el gateway
Salida: el KPI de minutos por punto medido sobre instalación real

El criterio de salida del MVP

No es una lista de funcionalidades: es que un técnico vuestro, sin acompañamiento, dé de alta un edificio de cuatro plantas con cuarenta puntos en menos de tres horas, y que un gestor que nunca ha visto el producto encuentre la sala más caliente del edificio en menos de treinta segundos. Si eso se cumple, hay producto; si no, ninguna funcionalidad adicional lo arregla.