Commit Graph
11 Commits
Author SHA1 Message Date
Claude 80830beae2 Fix scale-selection 500 error (missing BytesIO import) and compact GPU badge
ai_tools.py: add 'from io import BytesIO' — scale_selection and paste
endpoints used BytesIO directly but it was only imported locally in one
unrelated function, causing NameError on every scale call.

provider-badge.js: redesign badge to fit the narrow (~40px) left toolbar.
Was rendering 'GPU · sdxl_offload · Quadro RTX 3000' inline which wrapped
into multiple lines covering tool icons. Now shows a status dot + short
label (SDXL / OAI / Rep…) with all details moved to the hover tooltip.

https://claude.ai/code/session_01WVDg7amsy1TTtxvpku7bcM
2026-06-13 23:33:07 +00:00
Claude 372ab48991 Real per-step progress bars for local GPU inference
Backend:
- local_diffusion.py: add _make_step_cb() that writes step/total_steps/
  progress into _states on every diffusers callback_on_step_end; wired into
  txt2img, inpaint, img2img with TypeError fallback for older diffusers
- ai_tools.py: GET /api/generate/progress SSE endpoint — streams _states
  as JSON array every 200ms so clients get live denoising step counts

Frontend:
- progress_overlay.js: add connectProgressSSE(pipeType, baseUrl) /
  disconnectProgressSSE() — opens EventSource, maps step/total_steps
  to bar percentage (0→85% during denoising, 85→100 for decode/place)
- text_to_image.js: connect SSE before POST, disconnect on done/error
- selection_actions.js: connect SSE for AI edit / asymmetry operations

Result: for local GPU, progress bar shows "Step 12 / 30" with exact fill;
for remote providers and upscale (no step callbacks), shimmer animates.

https://claude.ai/code/session_01WVDg7amsy1TTtxvpku7bcM
2026-06-13 16:48:55 +00:00
Claude a97834fda3 feat: real-world selection actions — scale %, AI edit, clipboard paste
Backend (3 new endpoints under /api/image/):
- POST /api/image/scale-selection  — scale selected object by any % in-place;
  LaMa/OpenCV fills the exposed gap so the scene looks natural
- POST /api/image/ai-edit-region   — AI redraws the masked region via the
  configured inpaint provider (local_gpu / InvokeAI / ComfyUI / OpenAI)
- POST /api/image/paste-into-selection — scales clipboard image to fit the
  selection bounding box, masks it to the selection shape, composites result

Frontend (selection_actions.js + tool integration):
- New SelectionActions panel: fixed bottom-center HUD that appears
  automatically after every SAM selection (click or paint)
- Panel actions: Scale by % (default 3%), Make less symmetrical (AI),
  custom AI Edit prompt, Replace with clipboard, Copy/Cut to layer, Erase
- Both smart_select.js and brush_select.js updated to show the panel,
  add updateLayerWithResult(), and hide panel on clearSelection/on_leave
- brush_select: offerFloatSelection() replaced with richer action panel

Real-world workflows now supported in one click after painting over object:
  "Make this 3% bigger" → scale-selection (LaMa fills gap)
  "Make this less symmetrical" → ai-edit-region with asymmetry prompt
  "Replace this with what I copied" → paste-into-selection

https://claude.ai/code/session_01WVDg7amsy1TTtxvpku7bcM
2026-06-13 16:10:32 +00:00
Claude fe4d911a00 Dynamic GPU capability detection: probe CC, VRAM, feature flags, pick best model
Replaces fixed tier table with real hardware probing and dynamic model selection.

gpu_detect.py — complete rewrite:
- Reads torch.cuda.get_device_properties + mem_get_info for actual free VRAM
- Detects: fp16 (CC≥6.0), bf16 (CC≥8.0), fp8 (CC≥8.9 Ada/Hopper),
           int8 (CC≥7.0), tensor_cores (CC≥7.0), xformers presence
- Pre-Pascal (CC<6.0): effective_vram halved (fp32 weights are 2× larger)
- Subtracts 400MB driver overhead from free VRAM before model selection
- _select_txt2img / _select_inpaint / _select_img2img / _select_upscale:
    eff≥20GB  → FLUX.1-schnell (no offload)
    eff≥10GB  → FLUX.1-schnell (model_cpu_offload)
    eff≥7.5GB → SDXL
    eff≥5.5GB → SDXL + attention_slicing
    eff≥3.5GB → SD 2.1
    eff≥2.5GB → SD 2.1-base + attention_slicing
    eff≥1.7GB → SD 1.5
    else      → SD 1.5 + sequential_cpu_offload
- ModelSpec carries: model_id, family, memory_opt, native_res, vram_fp16_gb
- Warnings: old CC, pre-Pascal fp32, fp8 upgrade hint, xformers install tip
- Compatibility shim get_model_ids() retained for existing callers
- infer_spec_from_model_id() auto-detects family from HF_MODEL_* overrides

local_diffusion.py — refactored to use ModelSpec:
- Reads spec from GpuCapabilities.recommended[op] instead of tier table
- FLUX.1-schnell: FluxPipeline / FluxImg2ImgPipeline, 4 steps, guidance=0.0
- SD families: family-aware pipeline class selection (sd15/sd2x/sdxl)
- Memory opts applied per ModelSpec.memory_opt field
- xformers attention enabled automatically when xformers detected

gpu_status.py — richer response:
- Exposes all feature flags (fp16/bf16/fp8/int8/tensor_cores/xformers)
- Returns full ModelSpec per operation (model_id, family, memory_opt, native_res)

ai_tools.py — /api/config exposes:
- gpu_vram_total, gpu_vram_free, gpu_cc, gpu_fp16, gpu_bf16, gpu_fp8,
  gpu_tensor_cores, gpu_eff_vram, local_gpu_warnings

requirements.gpu.txt:
- diffusers bumped to >=0.29.0 (FLUX pipeline added in 0.29)
- transformers bumped to >=4.40.0
- sentencepiece added (FLUX T5 tokenizer)

scripts/gpu_setup.py:
- Prints full model table at startup (op → model_id, family, memory_opt, res)
- Shows all feature flags in one line

https://claude.ai/code/session_01WVDg7amsy1TTtxvpku7bcM
2026-06-13 15:35:37 +00:00
Claude 8fe8498df2 Add local GPU inference: auto-detect GPU, auto-download best diffusion models
Adds AI_PROVIDER=local_gpu — a fully self-contained GPU inference engine
using HuggingFace Diffusers that requires zero InvokeAI/ComfyUI setup.
All existing providers (InvokeAI, ComfyUI, OpenAI, Replicate) remain intact
and can be mixed with local GPU via per-operation overrides.

New features:
- GPU auto-detection (CUDA/NVIDIA, MPS/Apple Silicon, CPU fallback)
- VRAM-tiered model selection:
    ultra ≥16 GB → SDXL inpaint + SDXL base
    high  8-16 GB → SDXL inpaint + SDXL base
    medium 4-8 GB → SD 2.x inpaint + SD 2.1
    low  <4 GB   → SD 2.x (small)
- Auto-download model weights to HuggingFace disk cache at startup
  (background task; first request loads from local disk, not internet)
- LRU pipeline cache evicts oldest GPU pipeline when VRAM limit reached
- Per-operation model overrides via HF_MODEL_INPAINT / HF_MODEL_TXT2IMG etc.
- Optional HF_TOKEN for gated/private HuggingFace models

New files:
- backend/app/services/gpu_detect.py   — GPU detection + tier/model mapping
- backend/app/services/local_diffusion.py — Diffusers provider + LRU cache
- backend/app/routers/gpu_status.py    — GET /api/gpu/status, POST /api/gpu/prefetch
- backend/requirements.gpu.txt         — Diffusers ecosystem deps (GPU only)
- docker-compose.gpu.yml               — NVIDIA GPU compose (one-command startup)
- Dockerfile.gpu                       — pytorch/pytorch:2.1.0-cuda12.1 base image
- scripts/gpu_setup.py                 — Startup GPU info logger

Modified:
- backend/app/config.py                — local_gpu settings added
- backend/app/services/remote_provider.py — local_gpu registered as provider
- backend/app/routers/ai_tools.py      — /api/config exposes GPU tier + caps
- backend/app/main.py                  — GPU router + background prefetch task
- backend/entrypoint.sh                — runs gpu_setup.py at container start
- .env.example                         — local_gpu documented as first option

Quick start with GPU:
  docker compose -f docker-compose.gpu.yml up --build

https://claude.ai/code/session_01WVDg7amsy1TTtxvpku7bcM
2026-06-13 15:08:41 +00:00
Claude 065495e665 Fix startup crash: replace sklearn k-means with pure numpy implementation
sklearn was not installed in the container, causing ModuleNotFoundError on
import of ai_tools.py and preventing the server from starting.

Replaced with a self-contained numpy k-means++ implementation:
- k-means++ seeding for better initial centers
- 20-iteration Lloyd's algorithm
- Same output: hex colors sorted by cluster frequency

No new dependencies required.

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-11 23:24:00 +00:00
Claude d2273017fd Add Auto-Enhance, Color Palette, History Panel, Align, Text Presets
Auto-Enhance (Image menu):
  POST /api/enhance — gray-world white balance, CLAHE contrast on L channel,
  saturation boost ×1.15 in HSV, unsharp mask; all blended by strength slider
  Frontend: strength selector (25/50/75/100%), keep-original option

Extract Color Palette (Image menu):
  POST /api/extract-colors — k-means on 150×150 thumbnail, returns N dominant
  colors sorted by cluster size. Frontend: floating swatch panel, click=copy
  hex, shift+click=set as active color, toggle on/off.

History Panel (Edit menu, Ctrl+H):
  Pure frontend — reads app.State.action_history and action_history_index,
  renders clickable list of past actions (newest first), click any step to
  undo/redo to that point. Auto-refreshes every 800ms while open.

Align to Canvas (Layer menu):
  Floating toolbar with 7 alignment buttons: center H, center V, center both,
  align left/right/top/bottom edges. Uses Update_layer_action for undo support.

Add Text (Generate menu):
  6 styled presets (Heading, Subheading, Body, Caption, Quote, Bold Label)
  shown as live-rendered previews in the dialog. Click a preset to insert a
  text layer with the correct font/size/weight/color pre-applied.

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-11 01:41:20 +00:00
Claude 3746c02d44 Add SAM click-to-select with brush refinement in AI Edit tool
Backend:
- sam_service.py: auto-downloads SAM ViT-B (~375 MB) on first use with
  progress tracking; loads model to CUDA/MPS/CPU; predict_points() takes
  multi-point prompts (include/exclude labels) and returns best mask
- POST /api/segment/point: SAM point-prompt endpoint; returns mask PNG
- GET  /api/segment/install-status: poll download progress
- POST /api/segment/install: explicit trigger (also auto on first click)
- main.py: pre-download SAM on startup alongside NCNN

Frontend (ai_edit.js):
- Click mode (default): click object → SAM generates mask instantly
  Alt+click → subtract (deselect over-selected area)
  Multiple clicks accumulate for multi-object or refinement
- Brush + / Brush − modes: paint to add or erase from SAM mask by hand
- If SAM model is still downloading on first click: inline progress bar,
  user retries the click when done
- Unified action bar: Erase | Replace (inline prompt) | Upscale | Expand | Clear
- All modes share the same mask canvas; SAM and brush are fully composited

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-10 18:18:33 +00:00
Claude d01c11f948 Add per-operation AI provider routing
Each operation (inpaint, txt2img, img2img, outpaint) can now use a different
provider. Resolution order: per-op override → global AI_PROVIDER default.

Example: txt2img→openai, inpaint→invokeai, everything else→invokeai default.

Backend:
- config.py: add AI_PROVIDER_INPAINT / TXT2IMG / IMG2IMG / OUTPAINT settings
- remote_provider.py: get_remote_provider(operation) resolves override then default;
  _build_provider() extracted as shared factory; _OP_FIELD maps op→setting name
- ai_tools.py: each endpoint passes its operation to _require_remote();
  GET /api/config runs per-op health checks concurrently, returns operations map
  and overrides; POST /api/config accepts and applies per-op override fields

Frontend:
- ai_provider_settings.js: four new selects (inpaint/txt2img/img2img/outpaint);
  persists to localStorage and sends per-op fields to POST /api/config
- provider-badge.js: shows override summary (e.g. "invokeai · txt2img→openai")
  and per-op health in tooltip
- .env.example: document per-op override env vars with examples

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-09 18:14:12 +00:00
Claude b2a12c356f Add generative panels, provider settings UI, and credits
Frontend:
- tools/ai_replace_selection.js: use any selection → remote inpaint with prompt
- modules/generate/text_to_image.js: Text → Image dialog (new layer or replace canvas)
- modules/generate/outpaint.js: Expand Canvas in any direction via remote provider
- modules/tools/ai_provider_settings.js: in-app provider config (OpenAI / InvokeAI /
  ComfyUI / Replicate); persists to localStorage, pushes to POST /api/config at runtime
- config.js: register ai_replace_selection tool
- config-menu.js: add Generate menu (Text→Image, Outpaint); AI Provider Settings under Tools
- modules/help/about.js: updated credits (LaMa, rembg, SAM, InvokeAI, ComfyUI, OpenAI)
- api/capabilities.js: add refreshCapabilities() for post-save cache invalidation

Backend:
- routers/ai_tools.py: POST /api/config — apply provider settings at runtime
  without restart (session-scoped, non-persistent; .env for permanence)

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-09 17:54:44 +00:00
Claude 27261c4ef4 Add LaMa magic eraser, remote provider abstraction, and AI tool infrastructure
Backend:
- requirements.txt: add simple-lama-inpainting, rembg[gpu]; upgrade opencv to 4.10+
- app/config.py: add InvokeAI (url, model) and ComfyUI (url, model) settings; OPENAI_MODEL
- app/services/local_inpaint.py: LaMa, OpenCV, rembg wrappers (auto GPU/CPU)
- app/services/remote_provider.py: abstract RemoteAIProvider + OpenAI, InvokeAI, ComfyUI drivers
- app/routers/ai_tools.py: new /api/* endpoints — /erase, /inpaint/lama, /inpaint/fast,
  /background/remove, /inpaint/remote, /generate/txt2img, /generate/img2img,
  /generate/outpaint, GET /config (capability flags)
- app/main.py: register ai_tools router

Frontend:
- services/api.js: add erase(), textToImage(), imageToImage(), remoteInpaint(), getConfig()
- api/capabilities.js: lazy-fetch /api/config singleton; hasRemote() helper
- tools/ai_lama_erase.js: brush-paint mask → LaMa erase → apply to layer
- tools/ai_smart_inpaint.js: brush mask + dialog (Fast/Quality mode + prompt) → inpaint
- core/components/provider-badge.js: shows active provider + health in toolbar
- config.js: register ai_lama_erase and ai_smart_inpaint tools
- main.js: mount provider badge on load
- .env.example: document InvokeAI, ComfyUI, OpenAI provider settings

https://claude.ai/code/session_01B58MaJCU1R6KwBDJCp8AfN
2026-06-09 17:42:48 +00:00