Cool & Heat Air Conditioning · Florida
💨

Ductwork Repair & Sealing

Leaky or damaged ducts waste up to 30% of your cooling. We inspect, seal, repair, and replace ductwork across all of Florida.

💨 Inspection & Sealing · Repair & Replacement · All Florida
Stop Wasting Money
💨
Leaky Ducts Cost
You Every Month
Most homeowners don't realize their ductwork is the hidden culprit behind high electric bills, uneven cooling, and poor air quality. Studies show leaky ducts waste up to 30% of conditioned air. Our duct specialists find the leaks, seal them, and restore your system's efficiency — often dramatically lowering your bill.
30%
Energy Lost to Leaks
FREE
Duct Inspection
Signs You Need Duct Work
Does This
Sound Familiar?
  • Some rooms are always hotter or colder than others
  • Your electric bill keeps going up despite no changes
  • Dusty air or musty smell coming from vents
  • AC runs constantly but never quite cools the house
  • Visible duct damage, tears, or disconnected sections
  • New construction or renovation disrupted your ducts
Our Duct Services
🔧
Full Ductwork
Solutions
  • Full duct system inspection and leak testing
  • Duct sealing — mastic sealant and metal tape
  • Partial duct repair and section replacement
  • Full duct system replacement and redesign
  • Flexible duct installation and reconnection
  • Insulation repair on attic ductwork
  • Air balancing after repairs
🥰
Better Air
Quality
Sealed ducts stop attic dust, insulation fibers, and allergens from entering your home's airstream.
Lower Your
Electric Bill
Proper duct sealing is one of the highest-ROI home improvements you can make. Results are immediate.
🏠
Residential &
Commercial
We handle ductwork in single-family homes, multi-unit buildings, offices, warehouses, and retail spaces.
Gallery
Ductwork Jobs — Before & After
📷 Add Photo Click to upload a photo from Alan's gallery
📷 Add Photo Click to upload a photo from Alan's gallery
How It Works
Our Process
🔍
Free Duct Inspection

We inspect your full duct system — visually and with pressure testing — to map every leak and weak point.

📋
Detailed Report & Quote

You get a full written report of findings and a flat-rate quote before any work begins. No surprises.

🔧
Seal, Repair or Replace

Our techs seal leaks, repair damaged sections, or replace entire runs — whichever is the most cost-effective solution.

🌬
Air Balance & Test

After repairs we test airflow at every vent, balance the system, and verify your rooms all reach the set temperature.

Losing Air? Let's Fix It.

A free duct inspection can reveal exactly why your AC isn't performing — and exactly what to do about it.

📅 Get a Free Estimate 📞 (954) 278-4004
* * No requiere frameworks. Vanilla JS. Preferencias guardadas en localStorage. */ (function () { "use strict"; const STORAGE_KEY = "aaj-web-prefs"; /** * Configuración por sitio. Cada cliente define esto ANTES de cargar * aaj-widget.js, por ejemplo: * * * * * Si no se define simplifyEndpoint, el botón "Simplificar" se oculta. */ const config = Object.assign( { siteId: null, simplifyEndpoint: null }, window.AAJ_CONFIG || {} ); const defaultPrefs = { fontScale: 1, // 1 = 100% lineSpacing: 1, // 1 = normal, 1.5 / 2 = aumentado dyslexiaFont: false, highContrast: false, mode: "default", // "default" | "zen" | "gamer" }; let prefs = loadPrefs(); // ---------- Persistencia ---------- function loadPrefs() { try { const raw = localStorage.getItem(STORAGE_KEY); if (!raw) return { ...defaultPrefs }; return { ...defaultPrefs, ...JSON.parse(raw) }; } catch (e) { return { ...defaultPrefs }; } } function savePrefs() { try { localStorage.setItem(STORAGE_KEY, JSON.stringify(prefs)); } catch (e) { /* almacenamiento no disponible, continuar sin persistencia */ } } // ---------- Estilos ---------- function injectStyles() { const style = document.createElement("style"); style.id = "aaj-web-styles"; style.textContent = ` #aaj-toggle { position: fixed; bottom: 20px; right: 20px; width: 56px; height: 56px; border-radius: 50%; background: linear-gradient(135deg, #8aff5e, #5ec6ff); border: none; box-shadow: 0 4px 14px rgba(0,0,0,0.25); cursor: pointer; z-index: 2147483000; display: flex; align-items: center; justify-content: center; font-size: 26px; line-height: 1; transition: transform 0.2s ease; } #aaj-toggle:hover { transform: scale(1.08); } #aaj-toggle:focus-visible { outline: 3px solid #222; outline-offset: 2px; } #aaj-panel { position: fixed; bottom: 86px; right: 20px; width: 300px; max-width: calc(100vw - 40px); max-height: 70vh; overflow-y: auto; background: #14171c; color: #f2f2f2; border-radius: 14px; box-shadow: 0 8px 30px rgba(0,0,0,0.35); font-family: Arial, Helvetica, sans-serif; font-size: 15px; padding: 16px; z-index: 2147483000; display: none; } #aaj-panel.aaj-open { display: block; } #aaj-panel h2 { font-size: 16px; margin: 0 0 12px 0; display: flex; align-items: center; gap: 8px; } #aaj-panel .aaj-section { margin-bottom: 14px; padding-bottom: 14px; border-bottom: 1px solid rgba(255,255,255,0.08); } #aaj-panel .aaj-section:last-child { border-bottom: none; margin-bottom: 0; padding-bottom: 0; } #aaj-panel label { display: block; margin-bottom: 6px; font-weight: bold; } #aaj-panel .aaj-row { display: flex; gap: 8px; flex-wrap: wrap; } #aaj-panel button.aaj-btn { flex: 1; min-width: 60px; padding: 8px 10px; border-radius: 8px; border: 1px solid rgba(255,255,255,0.15); background: #20252d; color: #f2f2f2; cursor: pointer; font-size: 14px; } #aaj-panel button.aaj-btn:hover { background: #2c333d; } #aaj-panel button.aaj-btn.aaj-active { background: #5ec6ff; color: #0a0a0a; border-color: #5ec6ff; font-weight: bold; } #aaj-panel .aaj-toggle-row { display: flex; align-items: center; justify-content: space-between; margin-bottom: 6px; } #aaj-panel .aaj-footer { font-size: 11px; opacity: 0.6; text-align: center; margin-top: 4px; } /* ---- Estados aplicados al sitio ---- */ html.aaj-dyslexia-font, html.aaj-dyslexia-font * { font-family: "OpenDyslexic", "Comic Sans MS", Arial, sans-serif !important; } html.aaj-high-contrast, html.aaj-high-contrast body { background: #000 !important; color: #fff !important; } html.aaj-high-contrast a { color: #ffd400 !important; } html.aaj-high-contrast img { filter: grayscale(40%) contrast(1.1); } /* Modo Zen (filtro Franz): tonos suaves, baja saturación */ html.aaj-mode-zen { filter: saturate(0.75) brightness(0.97); } html.aaj-mode-zen, html.aaj-mode-zen body { background-color: #f4f1ec !important; } /* Modo Gamer (filtro Kalman): contraste y saturación elevados */ html.aaj-mode-gamer { filter: saturate(1.25) contrast(1.05); } #aaj-reading-highlight { outline: 2px solid #5ec6ff; outline-offset: 2px; border-radius: 3px; } `; document.head.appendChild(style); } // ---------- UI ---------- function buildUI() { // Botón flotante const toggle = document.createElement("button"); toggle.id = "aaj-toggle"; toggle.type = "button"; toggle.setAttribute("aria-label", "Abrir opciones de accesibilidad AimAndJoy"); toggle.setAttribute("aria-expanded", "false"); toggle.innerHTML = "♿"; // Panel const panel = document.createElement("div"); panel.id = "aaj-panel"; panel.setAttribute("role", "dialog"); panel.setAttribute("aria-label", "Opciones de accesibilidad AimAndJoy"); panel.innerHTML = `

♿ Accesibilidad · AAJ

`; document.body.appendChild(toggle); document.body.appendChild(panel); toggle.addEventListener("click", () => { const isOpen = panel.classList.toggle("aaj-open"); toggle.setAttribute("aria-expanded", String(isOpen)); }); panel.addEventListener("click", handlePanelClick); return { toggle, panel }; } // ---------- Lógica de acciones ---------- function handlePanelClick(e) { const btn = e.target.closest("button[data-action]"); if (!btn) return; const action = btn.dataset.action; switch (action) { case "font-inc": prefs.fontScale = Math.min(2, +(prefs.fontScale + 0.1).toFixed(2)); break; case "font-dec": prefs.fontScale = Math.max(0.8, +(prefs.fontScale - 0.1).toFixed(2)); break; case "font-reset": prefs.fontScale = 1; break; case "spacing-normal": prefs.lineSpacing = 1; break; case "spacing-comfortable": prefs.lineSpacing = 1.5; break; case "spacing-wide": prefs.lineSpacing = 2; break; case "toggle-dyslexia": prefs.dyslexiaFont = !prefs.dyslexiaFont; break; case "toggle-contrast": prefs.highContrast = !prefs.highContrast; break; case "mode-default": prefs.mode = "default"; break; case "mode-zen": prefs.mode = "zen"; break; case "mode-gamer": prefs.mode = "gamer"; break; case "read-page": readPageAloud(); return; // no necesita re-render del panel case "stop-read": stopReadingAloud(); return; case "simplify": simplifyPage(btn); return; } savePrefs(); applyPrefs(); syncPanelState(); } function applyPrefs() { const html = document.documentElement; // Tamaño de texto html.style.fontSize = (prefs.fontScale * 100) + "%"; // Espaciado de línea if (prefs.lineSpacing === 1) { html.style.removeProperty("--aaj-line-height"); document.body.style.removeProperty("line-height"); } else { document.body.style.lineHeight = String(prefs.lineSpacing); } // Fuente para dislexia html.classList.toggle("aaj-dyslexia-font", !!prefs.dyslexiaFont); // Alto contraste html.classList.toggle("aaj-high-contrast", !!prefs.highContrast); // Modo visual (Zen / Gamer / Original) html.classList.remove("aaj-mode-zen", "aaj-mode-gamer"); if (prefs.mode === "zen") html.classList.add("aaj-mode-zen"); if (prefs.mode === "gamer") html.classList.add("aaj-mode-gamer"); } function syncPanelState() { const panel = document.getElementById("aaj-panel"); if (!panel) return; const dyslexiaBtn = panel.querySelector("#aaj-dyslexia"); dyslexiaBtn.classList.toggle("aaj-active", !!prefs.dyslexiaFont); dyslexiaBtn.textContent = prefs.dyslexiaFont ? "Desactivar" : "Activar"; const contrastBtn = panel.querySelector("#aaj-contrast"); contrastBtn.classList.toggle("aaj-active", !!prefs.highContrast); contrastBtn.textContent = prefs.highContrast ? "Desactivar" : "Activar"; const spacingMap = { 1: "spacing-normal", 1.5: "spacing-comfortable", 2: "spacing-wide" }; highlightGroup(panel, ["spacing-normal", "spacing-comfortable", "spacing-wide"], spacingMap[prefs.lineSpacing]); const modeMap = { default: "mode-default", zen: "mode-zen", gamer: "mode-gamer" }; highlightGroup(panel, ["mode-default", "mode-zen", "mode-gamer"], modeMap[prefs.mode]); } function highlightGroup(panel, actions, activeAction) { actions.forEach((action) => { const btn = panel.querySelector(`[data-action="${action}"]`); if (btn) btn.classList.toggle("aaj-active", action === activeAction); }); } // ---------- Lectura en voz alta ---------- function readPageAloud() { if (!("speechSynthesis" in window)) { alert("Tu navegador no soporta lectura en voz alta."); return; } stopReadingAloud(); const text = getReadableText(); if (!text.trim()) return; const utterance = new SpeechSynthesisUtterance(text); utterance.lang = document.documentElement.lang || "es-ES"; window.speechSynthesis.speak(utterance); } function stopReadingAloud() { if ("speechSynthesis" in window) { window.speechSynthesis.cancel(); } } function getReadableText() { // Extrae texto visible del
si existe, o del completo, // excluyendo el propio panel de AAJ. const root = document.querySelector("main") || document.body; const clone = root.cloneNode(true); clone.querySelectorAll("#aaj-panel, #aaj-toggle, script, style, noscript").forEach((el) => el.remove()); return clone.textContent.replace(/\s+/g, " ").trim().slice(0, 4000); } // ---------- Simplificación con IA ---------- async function simplifyPage(button) { const resultBox = document.getElementById("aaj-simplify-result"); if (!config.simplifyEndpoint || !config.siteId) return; const originalLabel = button.textContent; button.disabled = true; button.textContent = "Procesando…"; resultBox.style.display = "block"; resultBox.textContent = "Analizando el contenido de la página…"; try { const text = getReadableText(); const response = await fetch(config.simplifyEndpoint, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ siteId: config.siteId, text }), }); if (!response.ok) { throw new Error("Respuesta no válida del servidor."); } const data = await response.json(); resultBox.textContent = data.result || "No se obtuvo resultado."; } catch (err) { resultBox.textContent = "No se pudo simplificar el contenido en este momento. Inténtalo de nuevo más tarde."; } finally { button.disabled = false; button.textContent = originalLabel; } } // ---------- Inicialización ---------- function init() { injectStyles(); buildUI(); applyPrefs(); syncPanelState(); if (config.simplifyEndpoint && config.siteId) { const section = document.getElementById("aaj-simplify-section"); if (section) section.style.display = "block"; } } if (document.readyState === "loading") { document.addEventListener("DOMContentLoaded", init); } else { init(); } })();