(function () {
// FireTail portfolio — Hero (name-led landing)
const {
  Button,
  StatBlock,
  Badge
} = window.FireTailDesignSystem_df7a18;

// Readability treatment for the text column against the busy pixel-art
// backdrop. Only fades in once HeroGame signals it's actually loaded
// (gameReady below), so it's never visible with nothing behind it to read
// against.
//
// PANEL — a frosted-glass scrim behind the text column: backdrop-filter
// blur (same technique as ProjectGrid's sticky filter panel) genuinely
// blurs the live game canvas behind it, layered with a translucent
// var(--surface-overlay) tint. No edge-fade mask — a radial-gradient mask
// was tried (PANEL_MASK_INNER), but its default farthest-corner sizing
// only ever faded the corners in practice (a flat edge's midpoint sits
// well inside the "still opaque" zone of a gradient calibrated to reach
// the much-farther corner), and getting an even fade on all four sides
// needs two intersecting linear gradients instead — more than this is
// worth right now. Crisp rounded-rect edges (PANEL_BOTTOM_RADIUS) instead.
//
// backdropFilter only applies once gameReady is true (see the panel's style
// below, `gameReady ? blur(...) : "none"`) — before that the panel is
// already invisible (opacity: 0), so there's nothing to gain from paying
// the ongoing compositing cost of blurring an animating canvas for a panel
// nobody can see yet.
//
// Contrast is handled with plain color, not a text-shadow halo — the halo
// read as fog instead of crisp separation. `mode` (passed down from
// App.jsx, the same prop Nav already takes) picks a brighter literal color
// for the eyebrow/paragraph specifically in dark mode; light mode keeps
// the existing --accent/--text-muted tokens unchanged since those already
// read fine there. (Tried plain var(--accent) for the eyebrow in both
// modes — read as unreadably dark against the panel in dark mode once the
// game canvas started sitting behind it full-bleed, see HeroGame.jsx;
// reverted back to the flame-300 override below.)
//
// Fixed px, not vw — vw is relative to the raw viewport, and the text
// column it backs is capped/centered at var(--container) (1240px,
// tokens/spacing.css), not the viewport itself.
//
// Anchored to the content's actual left edge, not the section's center —
// centering on the section drifted apart from the (differently-offset,
// differently-capped) text column as viewport width changed, sometimes
// undershooting it (text spilling past the panel's left edge) and
// sometimes wildly overshooting it. Nested inside the same text wrapper
// the content lives in, and its left offset reuses that wrapper's own
// CONTENT_LEFT_PADDING formula verbatim (not an approximation of it) minus
// one constant pixel pad — so the panel's edge is mathematically locked to
// the text's edge at every viewport width, and the gap between them
// (PANEL_LEFT_PAD) is genuinely constant.
const CONTENT_LEFT_PADDING = "0px"; // "calc(1vw + 24px)"; // desktop-only nav-balance offset — shared by the text wrapper below and the panel so they can never drift apart
const PANEL_WIDTH = "880px";
const PANEL_HEIGHT = "625px";
const PANEL_BOTTOM_RADIUS = "80px 80px"; // horizontal / vertical radius — applied to all four corners, not just the bottom
const PANEL_FROST_BLUR = "14px"; // backdrop-filter blur radius, applied once gameReady (see the PANEL comment up top)
const PANEL_TINT_STRENGTH = "55%"; // how much var(--surface-overlay) shows through vs. transparent — lower = more see-through
const PANEL_TOP_OFFSET = "-60px"; // vertical nudge from the wrapper's own top edge — kept small so the panel stays inside the section's own top padding and never reaches up into Nav's sticky bar
const PANEL_LEFT_PAD = "60px"; // constant gap between the panel's left edge and where the text content actually starts

// PANEL_LEFT_PAD is a constant pullback, but the wrapper's own left offset
// shrinks with viewport (CONTENT_LEFT_PADDING/the section's clamp() padding
// don't scale down together with it) — below roughly 1200px viewport width
// the panel's true left edge goes negative, i.e. past the actual browser
// viewport edge, stranding its rounded corner against/over that edge. Below
// squares off just the left corners once that's measured to be happening
// (see the edgeFlush effect in Hero()), so the panel reads as an
// intentional flush edge instead of a corner getting clipped mid-curve.
const PANEL_EDGE_FLUSH_BUFFER_PX = 32; // headroom before the panel's measured left edge actually reaches the viewport edge — squares the corner off a little early rather than exactly at 0, so the radius never gets caught half-clipped
const PANEL_EDGE_FLUSH_TRANSITION_MS = 300; // corner-radius/left animation duration when crossing the flush threshold
const PANEL_EDGE_OVERFLOW_PX = 12; // once flush, how far past the true viewport edge to push the panel's left edge — deliberately overflowing (not just flush) so the gap can't reappear from subpixel rounding; the overflow itself is invisible, off-canvas

// GLOW — disabled for now (see PANEL above), kept for reference. Radius is
// explicit vw/vh (not a keyword like farthest-side, not percentages) —
// keyword/percentage sizing here was computing an enormous radius and
// diluting the gradient into invisibility near the edges.
// const GLOW_CENTER = "46% 0%";
// const GLOW_RADIUS = "42vw 90vh"; // horizontal / vertical — wide and shallow, not circular

function Hero({
  mode
}) {
  const [narrow, setNarrow] = React.useState(() => window.innerWidth < 768);
  const [gameReady, setGameReady] = React.useState(false);
  React.useEffect(() => {
    const mq = window.matchMedia("(max-width: 767px)");
    const fn = e => setNarrow(e.matches);
    mq.addEventListener("change", fn);
    return () => mq.removeEventListener("change", fn);
  }, []);

  // Edge-flush detection for the panel's left corners — see
  // PANEL_EDGE_FLUSH_BUFFER_PX above for why this is needed at all. Measures
  // the panel's actual rendered position rather than re-deriving the
  // crossover viewport width algebraically, so this stays correct even if
  // PANEL_WIDTH/PANEL_LEFT_PAD/the section's padding formula change later.
  // Recomputes on window resize AND visualViewport resize — the former
  // covers standard browser zoom (which changes window.innerWidth), the
  // latter covers trackpad/pinch zoom, which can change the visual viewport
  // scale without firing a window resize event on some platforms.
  //
  // edgeShiftPx pulls the panel the rest of the way left once flush, closing
  // whatever gap remains inside the buffer zone (squaring the corners alone
  // doesn't move the panel). edgeShiftRef tracks the shift last applied so
  // each recompute can add it back out of the freshly measured rect first —
  // the shift is subtracted INTO the rendered `left` (see the calc() below),
  // so the measured rect already reads naturalPosition - shift; adding shift
  // back is what recovers naturalPosition. Get this backwards (subtracting
  // again instead of adding) and every recompute after the first flush
  // double-counts the shift, making the panel look far more "still
  // overflowing" than it truly is — the detach threshold effectively moves
  // way out from PANEL_EDGE_FLUSH_BUFFER_PX instead of matching it.
  const panelRef = React.useRef(null);
  const edgeShiftRef = React.useRef(0);
  const [edgeFlush, setEdgeFlush] = React.useState(false);
  const [edgeShiftPx, setEdgeShiftPx] = React.useState(0);
  React.useEffect(() => {
    if (narrow) return; // panel isn't rendered on mobile — nothing to measure
    const recompute = () => {
      if (!panelRef.current) return;
      const naturalLeft = panelRef.current.getBoundingClientRect().left + edgeShiftRef.current;
      const flush = naturalLeft <= PANEL_EDGE_FLUSH_BUFFER_PX;
      const shift = flush ? Math.max(0, naturalLeft) + PANEL_EDGE_OVERFLOW_PX : 0;
      edgeShiftRef.current = shift;
      setEdgeFlush(flush);
      setEdgeShiftPx(shift);
    };
    recompute();
    window.addEventListener("resize", recompute);
    window.visualViewport?.addEventListener("resize", recompute);
    return () => {
      window.removeEventListener("resize", recompute);
      window.visualViewport?.removeEventListener("resize", recompute);
    };
  }, [narrow]);
  return /*#__PURE__*/React.createElement("section", {
    id: "top",
    style: {
      position: "relative",
      minHeight: "94vh",
      boxSizing: "border-box",
      padding: "clamp(10px,min(10vh,13vw),160px) clamp(10px,5vw,48px) clamp(48px,6.3vh,86px)"
    }
  }, !narrow && /*#__PURE__*/React.createElement(HeroGame, {
    mode: mode,
    onReady: () => setGameReady(true)
  }), /*#__PURE__*/React.createElement("div", {
    style: {
      position: "relative",
      zIndex: 1,
      maxWidth: "var(--container)",
      margin: "0 auto",
      paddingLeft: narrow ? 0 : CONTENT_LEFT_PADDING
    }
  }, !narrow && /*#__PURE__*/React.createElement("div", {
    ref: panelRef,
    id: "ft-anchor-hero-card",
    "aria-hidden": "true",
    style: {
      position: "absolute",
      zIndex: -1,
      top: PANEL_TOP_OFFSET,
      left: `calc(${CONTENT_LEFT_PADDING} - ${PANEL_LEFT_PAD} - ${edgeShiftPx}px)`,
      pointerEvents: "none",
      width: PANEL_WIDTH,
      height: PANEL_HEIGHT,
      borderTopLeftRadius: edgeFlush ? 0 : PANEL_BOTTOM_RADIUS,
      borderTopRightRadius: PANEL_BOTTOM_RADIUS,
      borderBottomLeftRadius: edgeFlush ? 0 : PANEL_BOTTOM_RADIUS,
      borderBottomRightRadius: PANEL_BOTTOM_RADIUS,
      background: `color-mix(in srgb, var(--surface-overlay) ${PANEL_TINT_STRENGTH}, transparent)`,
      backdropFilter: gameReady ? `blur(${PANEL_FROST_BLUR})` : "none",
      WebkitBackdropFilter: gameReady ? `blur(${PANEL_FROST_BLUR})` : "none",
      opacity: gameReady ? 1 : 0,
      // opacity matches HeroGame's CANVAS_FADE_IN_MS; border-radius/left animate the edgeFlush toggle together
      transition: `opacity 2000ms ease, border-radius ${PANEL_EDGE_FLUSH_TRANSITION_MS}ms ease, left ${PANEL_EDGE_FLUSH_TRANSITION_MS}ms ease`
    }
  }), /*#__PURE__*/React.createElement("div", {
    "data-reveal": true,
    style: {
      display: "inline-flex",
      alignItems: "center",
      gap: 12,
      marginBottom: "26px",
      flexWrap: "wrap"
    }
  }, /*#__PURE__*/React.createElement("span", {
    style: {
      fontFamily: "var(--font-mono)",
      fontSize: 14,
      letterSpacing: "0.16em",
      textTransform: "uppercase",
      // Brighter literal color in dark mode only — see the PANEL
      // comment up top. var(--accent) itself is left untouched for
      // light mode, where it already reads fine against the panel.
      // (Tried plain var(--accent) in both modes — read as unreadably
      // dark against the panel in practice, reverted.)
      color: mode === "dark" ? "var(--flame-300)" : "var(--accent)"
    }
  }, "Senior Unity Gameplay Engineer \xB7 C#"), /*#__PURE__*/React.createElement(Badge, {
    status: "live"
  }, "Open to work")), /*#__PURE__*/React.createElement("h1", {
    id: "ft-hero-name",
    "data-reveal": true,
    style: {
      margin: 0,
      fontFamily: "var(--font-display)",
      fontWeight: 500,
      fontSize: "clamp(57px, 11vw, 128px)",
      lineHeight: 0.98,
      letterSpacing: "-0.03em",
      color: "var(--text-strong)",
      textWrap: "balance"
    }
  }, "Smit Waghela"), /*#__PURE__*/React.createElement("p", {
    "data-reveal": true,
    style: {
      margin: "28px 0 0",
      fontFamily: "var(--font-sans)",
      fontSize: "clamp(16px,1.8vw,20px)",
      lineHeight: 1.6,
      color: mode === "dark" ? "var(--paper-100)" : "var(--text-muted)",
      maxWidth: 600
    }
  }, "Six years shipping mobile, PC, and WebGL games in Unity \u2014 vehicle physics, multiplayer shooters, and live-ops systems that keep players coming back."), /*#__PURE__*/React.createElement("div", {
    "data-reveal": true,
    style: {
      display: "flex",
      gap: 14,
      marginTop: "38px",
      flexWrap: "wrap"
    }
  }, /*#__PURE__*/React.createElement(Button, {
    size: "lg",
    as: "a",
    href: "#work",
    iconRight: /*#__PURE__*/React.createElement("span", {
      style: {
        fontFamily: "var(--font-mono)"
      }
    }, "\u2192")
  }, "See the work"), /*#__PURE__*/React.createElement(Button, {
    size: "lg",
    variant: "secondary",
    as: "a",
    href: "#contact"
  }, "Get in touch")), /*#__PURE__*/React.createElement("div", {
    id: "ft-hero-stats",
    "data-reveal": true,
    style: {
      display: "flex",
      gap: "clamp(28px,5vw,64px)",
      marginTop: "40px",
      flexWrap: "wrap",
      ...(mode === "dark" ? {
        "--text-muted": "var(--paper-300)"
      } : null)
    }
  }, /*#__PURE__*/React.createElement(StatBlock, {
    value: "6+",
    label: "Years in Unity"
  }), /*#__PURE__*/React.createElement(StatBlock, {
    value: "50%",
    label: "Perf. gains delivered"
  }), /*#__PURE__*/React.createElement(StatBlock, {
    value: "600k+",
    label: "Player downloads"
  })), narrow && /*#__PURE__*/React.createElement("div", {
    "data-reveal": true,
    className: "ft-hero-mobile-socials"
  }, SOCIALS.map(s => /*#__PURE__*/React.createElement("a", {
    key: s.key,
    className: "ft-sdock-item",
    href: s.href,
    target: s.mail ? undefined : "_blank",
    rel: "noreferrer",
    title: s.label,
    "aria-label": s.label
  }, /*#__PURE__*/React.createElement("span", {
    className: "ft-sdock-ic"
  }, /*#__PURE__*/React.createElement(SocialIcon, {
    s: s,
    size: 20,
    color: "currentColor"
  })))))));
}
window.Hero = Hero;
})();
