# Packshoty na białym tle w ComfyUI, bez Photoshopa

Jak lokalnie, w ComfyUI na karcie graficznej laptopa, robię packshoty produktów na białym tle: kilka sekund na zdjęcie, bez Photoshopa i bez subskrypcji.

**Canonical:** https://spoko.space/pl/blog/packshoty-na-bialym-tle-comfyui/  
**Language:** pl  
**Published:** 2026-10-11  
**Tags:** ComfyUI, packshot, BiRefNet, AI, automatyzacja, e-commerce  
**Category:** Poradnik

---
**Do produktu na czystym, białym tle nie potrzebujesz Photoshopa ani subskrypcji.** Laptop z kartą graficzną NVIDIA, ComfyUI i model AI do usuwania tła robią to w kilka sekund na zdjęcie, a krótki graf załatwia resztę: kadr, margines i proporcje.

## Dlaczego przestałem używać narzędzi online {#dlaczego-przestałem-używać-narzędzi-online}

Packshotów potrzebuję często. Produkty fotografuję tam, gdzie akurat leżą: w kartonie, na trawniku, na posadzce warsztatu. Sklep, katalog czy oferta wyglądają lepiej, gdy każda okładka to sam produkt na bieli.

Najpierw próbowałem narzędzi online do usuwania tła, między innymi [iloveimg](https://www.iloveimg.com/remove-background) i [usuwania tła w Adobe Firefly](https://www.adobe.com/products/firefly/features/remove-background.html). To drugie średnio się u mnie sprawdzało. Najlepszy wynik nadal daje ręczne zaznaczenie części w Photoshopie narzędziem Pióro (Pen Tool). To dobra metoda na profesjonalną sesję zdjęciową, a zła na setki miniatur produktów: trwa za długo.

Zrobiłem więc to lokalnie. ComfyUI okazał się dobrym wyborem, bo cała robota to graf, który buduję raz i puszczam na każde zdjęcie.

## Czym jest ComfyUI {#czym-jest-comfyui}

ComfyUI to darmowy, otwarty program do uruchamiania modeli AI do obrazu na własnym komputerze. Zamiast jednego przycisku „usuń tło" budujesz graf: łączysz węzły, z których każdy robi jedną rzecz (wczytuje zdjęcie, wycina tło, zmienia rozmiar), a cały graf jest Twoim narzędziem. Działa jako lokalny serwer z interfejsem w przeglądarce i z API przez HTTP, więc ten sam graf uruchomisz ręcznie albo ze skryptu.

## Czego potrzeba {#czego-potrzeba}

| | Czego używam |
| --- | --- |
| Laptop | Lenovo, Intel Core Ultra 9 275HX, 64 GB RAM, Windows 11 |
| Karta graficzna | NVIDIA RTX PRO 3000 Blackwell Laptop GPU, 12 GB VRAM |
| ComfyUI | 0.13.0 (Python 3.13, PyTorch 2.10 z CUDA) |
| Model | BiRefNet-General |
| Własne węzły | `ComfyUI_LayerStyle_Advance` (uruchamia BiRefNet), `ComfyUI_essentials` (`MaskBoundingBox+`) |

Nie sprawdzałem słabszego sprzętu, więc nie obiecuję dla niego żadnych czasów.

## Jak działa graf {#jak-działa-graf}

Numery poniżej zgadzają się z etykietami na zrzucie.

1. **Zdjęcie źródłowe.** Węzeł `LoadImage`. To jedyne miejsce, które zmienia się między zdjęciami.
2. **Model BiRefNet.** Wczytuje `BiRefNet-General`.
3. **Wycięcie części.** `BiRefNetUltraV2` zwraca maskę: biała tam, gdzie jest część, czarna wszędzie indziej. Do krawędzi używam `GuidedFilter`, erode 4, dilate 2, black point 0,01 i white point 0,99. Węzeł liczy wewnętrznie na obrazie co najwyżej 4 megapikseli.
4. **Białe płótno, potem część na bieli (4 i 5).** Puste białe płótno wielkości zdjęcia i oryginał wklejony na nie przez maskę, więc wszystko poza maską zostaje białe.
5. **Kadr do obrysu (6).** `MaskBoundingBox+` przycina obraz do prostokąta wokół maski. Dlatego margines jest równy, niezależnie od kadru oryginału.
6. **Wpasowanie w ostateczną ramkę (7a–7c i 8a–8c).** `ResizeAndPadImage` skaluje część do 1800×1300, a węzeł kompozycji wstawia ją w punkt x=100, y=100 na białym płótnie 2000×1500, co daje 100 px marginesu z każdej strony. Druga gałąź robi to samo dla 2000×2000.

Z jednego przebiegu robię dwa pliki: 4:3 i kwadrat. Kafelki i galerie często mają różne proporcje, u mnie 3:2 i 4:3, a obraz 4:3 mieści się w obu bez ucinania części. Kwadrat przydaje się wszędzie tam, gdzie zdjęcie ma trafić do kwadratowego pola, na przykład do miniatury. Dwa węzły `PreviewImage` mają tytuły **packshot 4:3** i **packshot 1:1**. Zostaw te tytuły, jeśli wywołujesz graf ze skryptu, bo po nich skrypt znajduje wyjścia.

Pobierz graf: [packshot-birefnet.workflow.json](https://spoko.space/downloads/packshot-birefnet.workflow.json) otwiera się w ComfyUI (przeciągnij plik na płótno), a [packshot-birefnet.api.json](https://spoko.space/downloads/packshot-birefnet.api.json) to ten sam graf w formacie API, dla skryptów.

### Przezroczyste tło zamiast białego {#przezroczyste-tło-zamiast-białego}

Z tej samej maski dostaniesz też przezroczyste tło. Odwróć ją węzłem `InvertMask`, podaj razem z oryginalnym zdjęciem do `JoinImageWithAlpha` (ten węzeł sam odwraca maskę, więc podwójne odwrócenie zostawia część nieprzezroczystą) i zapisz wynik jako PNG. Tak powstał cover tego artykułu w trybie ciemnym. Samo przycięcie i wyśrodkowanie zrobiłem poza ComfyUI, w ImageMagicku.

### Pułapki, na które wpadłem {#pułapki-na-które-wpadłem}

- **Wagi BiRefNet-General trzeba pobrać ręcznie.** Węzeł sam pobiera tylko inny model:

  ```bash
  python -c "from huggingface_hub import snapshot_download; snapshot_download(repo_id='ZhengPeng7/BiRefNet', local_dir=r'\models\BiRefNet\BiRefNet-General', ignore_patterns=['*.md', '*.txt'])"
  ```

- **Przy transformers 5 węzeł BiRefNet u mnie się wywalał** z błędem `Input type (float) and bias type (c10::Half) should be the same`. Pomogło dodanie `dtype=torch.float32` do `from_pretrained(...)` w pliku `birefnet_ultra_v2.py` tego węzła. Nowsza wersja węzła może tego nie wymagać, a aktualizacja może poprawkę cofnąć.
- **Nie kadruj przez `CropByMask V2`.** W trybie `min_bounding_rect` bierze tylko największy kontur i ucinał mi zagłówki foteli połączone z oparciem cienkimi prętami.

## Jak to wygląda w trakcie generowania {#jak-to-wygląda-w-trakcie-generowania}

Naciskasz Run i patrzysz. U góry okna rośnie pasek postępu, liczony węzeł jest obrysowany na niebiesko, a kolejka zadań po prawej wypisuje każde skończone zadanie z jego czasem. Tytuł karty pokazuje procent i nazwę bieżącego węzła, co przydaje się, gdy ComfyUI działa w tle.

Na moim laptopie zdjęcie około 2000 px, taki rozmiar zwykle trzymam, zajmuje 2–4 sekundy. Pełne zdjęcie z telefonu, 3800 px, około 5 sekund. Pierwszy przebieg po starcie ComfyUI jest wolniejszy, około 6 sekund, bo najpierw musi wczytać model.

## Przykłady {#przykłady}

Wszystko to surowy wynik grafu, bez retuszu. Zdjęcie źródłowe jest po lewej.

![Filtr paliwa leżący na szarej powierzchni i ten sam filtr na białym tle](https://spoko.space/_spoko/packshot-example-fuel-filter.BdSTJhW4.webp)

![Osłona silnika leżąca na folii bąbelkowej na wzorzystej, odbijającej światło metalowej powierzchni, z etykietami przesyłki obok, i ta sama osłona wycięta na białe tło w kwadratowej wersji 1:1](https://spoko.space/_spoko/packshot-example-engine-cover.CoX0CVev.webp)

Ta wyszła szczególnie dobrze. Osłona silnika Audi leżała na folii bąbelkowej na wzorzystej, odbijającej światło powierzchni, a obok miała etykiety przesyłki. Wycięła się sama osłona, z ostrymi kółkami i napisem TFSI. Widzisz tu kwadratowe wyjście; wersja 4:3 powstaje w tym samym przebiegu.

![Rura ciśnieniowa z czerwoną opaską na trawie i ta sama część na białym tle](https://spoko.space/_spoko/packshot-example-pressure-pipe.DYmNM8hq.webp)

![Łoże skrzyni biegów na niebieskiej macie z siatką i ta sama część na białym tle](https://spoko.space/_spoko/packshot-example-gearbox-bracket.CtWr20yX.webp)

![Dwa przednie fotele na trawie i oba fotele na białym tle](https://spoko.space/_spoko/packshot-example-front-seats.BxqCW6Qh.webp)

Modelu nie mylą też szara powierzchnia, siatka maty, cienie na trawie ani czerwona opaska. Ostatnia para pokazuje, gdzie się myli:

![Filtr paliwa stojący na swoim kartonie i ten sam filtr na białym tle, z kartonem nadal na zdjęciu](https://spoko.space/_spoko/packshot-example-fuel-filter-on-box.BqV5Ehu3.webp)

Filtr stoi na swoim kartonie i karton został w kadrze, bo model nie wie, który przedmiot jest na sprzedaż.

## Od jednego zdjęcia do kilkuset {#od-jednego-zdjęcia-do-kilkuset}

Graf wywołasz z dowolnego języka, bo ComfyUI udostępnia API przez HTTP. Skrypt musi zrobić trzy rzeczy: wysłać zdjęcie i wskazać je węzłowi `LoadImage`, zakolejkować graf i poczekać na koniec, a potem pobrać oba wyniki. Całość w Pythonie, z wersją API grafu zapisaną obok:

```python

Jeśli strona działa na serwerze bez karty graficznej, nie przenoś tam pracy. Niech komputer z GPU sam pyta serwer o czekające zlecenia, po jednym, dzięki czemu serwer nigdy nie musi się z nim łączyć. W moim kodzie w [Laravelu](https://spoko.space/pl/slownik/laravel/) pętla wygląda tak (w skrócie):

```php
$job = $api->claim(1)[0] ?? null;                       // ask production for a queued render
$packshot = $renderer->render($api->download($job['source_url'])); // run the graph in ComfyUI
$upload = $api->uploadUrl($productId);                  // presigned URL on the CDN
$api->upload($upload['upload_url'], $packshot->jpeg, $upload['content_type']);
$api->upload($upload['square_upload_url'], $packshot->squareJpeg, $upload['content_type']);
$api->complete($productId, $upload['key'], $packshot->workflowVersion->value);
```

Gdy laptop jest wyłączony, zlecenia czekają w kolejce i nic nie ginie. Plik grafu jest wersjonowany w repozytorium, a każdy packshot zapisuje, jaka wersja grafu go zrobiła, więc po zmianie wiem, które zdjęcia trzeba zrobić od nowa. System wokół tego workera opisuję w [studium przypadku systemu magazynowego](https://spoko.space/pl/magazyn-garazowy/).

## Gdzie model się myli, więc sprawdzam każdy wynik

Model usuwa wszystko, co wygląda na pierwszy plan. W praktyce kilka rodzajów zdjęć daje zły wynik:

- **Część zaznaczona ramką albo strzałką na większym zespole.** Intercooler zakreślony na pakiecie chłodnic wychodzi jako cały pakiet.
- **Część sfotografowana na aucie.** Felgi na samochodzie wychodzą jako całe auto.
- **Inne przedmioty albo napisy w kadrze.** Trafiają do wyniku razem z częścią, jak karton wyżej.
- **Otwory.** Model sam ocenia, czy to, co widać przez otwór, jest częścią przedmiotu. Osłona z przykładu ma okrągły otwór: na kopii 1200×1600 graf go wyciął, a na oryginale 3028×4038 zostawił w nim widoczną folię. Wynik zmieniał się też z rozmiarem, do jakiego zmniejszyłem zdjęcie, więc otwory trzeba sprawdzać, a ważny otwór dorysować ręcznie.
- **Przezroczyste szkła, cienkie przewody i chrom.** Model może je ocenić źle, więc żaden packshot nie jest publikowany bez mojej zgody.

Gotowy packshot czeka obok zdjęcia źródłowego i dopiero po moim zatwierdzeniu staje się okładką. Jeśli jest zły, zlecam go ponownie z innego zdjęcia, na którym część leży sama, albo go odrzucam i strona zostaje przy oryginalnym zdjęciu.

## Porównanie z narzędziami online

Żeby sprawdzić to na czymś trudnym, puściłem te same zdjęcia przez dwa narzędzia online, [iloveimg](https://www.iloveimg.com/remove-background) (darmowa wersja, bez konta) i [usuwanie tła w Adobe Firefly](https://www.adobe.com/products/firefly/features/remove-background.html) (też bez logowania), oraz przez swój graf. Oba zdjęcia poszły przez wszystkie trzy narzędzia.

### Osłona silnika na folii bąbelkowej

Pierwsze zdjęcie to osłona silnika Audi sfotografowana z góry. Leży na folii bąbelkowej na wzorzystej, odbijającej światło metalowej powierzchni, a obok ma etykiety przesyłki.

Adobe Firefly zabrał tylko skrajny brzeg sceny i zostawił 51% kadru. Folia bąbelkowa, wzorzysta powierzchnia i etykiety zostały, więc wynik to nadal zdjęcie całej sceny, w której gdzieś jest osłona. iloveimg i graf w ComfyUI wycięły samą osłonę, zostawiając ok. 15% kadru.

### Obudowa filtra powietrza na trawie

Drugie zdjęcie to obudowa filtra powietrza na trawie, w ostrym słońcu, z mocnym cieniem, cienką rurką i wtyczką z wystającymi uciętymi przewodami.

Wszystkie trzy narzędzia poradziły sobie z ogólnym kształtem, łącznie z rurką i przewodami. iloveimg i Adobe oddają wycięcie w oryginalnym kadrze, więc część zostaje w nim i trzeba ją jeszcze przyciąć i wyśrodkować. Graf robi to od razu i daje gotowy plik 4:3 z równym marginesem.

Wycięcia z iloveimg i ComfyUI pokrywają się w 99,5% pikseli, a wycięcie z Adobe z każdym z nich w ok. 98%. W powiększeniu różnice dotyczą ostrości: iloveimg ma brzegi odrobinę bardziej miękkie niż graf, a Adobe najbardziej miękkie, z kępkami trawy zostawionymi między przewodami. Adobe zwrócił też obraz 800×600, czyli o połowę mniejszy od zdjęcia, które dostał. Pod względem samego cięcia iloveimg i graf są na równi. Graf daje tu gotowy kadr i automatyzację, a nie lepsze wycięcie, a od iloveimg odróżniają go limity: serwis sam podaje, że nieograniczone przetwarzanie obrazów daje dopiero Premium. Adobe Firefly zawiódł też na pierwszym zdjęciu, ale dwa zdjęcia i po jednej próbie to obserwacja, nie ranking.

## Kiedy lepsze jest coś innego

- **Photoshop z narzędziem Pióro** nadal daje najlepszą krawędź. To dobry wybór na profesjonalną sesję zdjęciową, gdzie liczy się pojedyncze zdjęcie i jest czas na jego dopracowanie.
- **Narzędzie online** jest szybsze przy pojedynczym zdjęciu, bo nie trzeba niczego instalować. Przy dużej liczbie zdjęć trzeba za to liczyć się z limitami wersji darmowej albo z płatnym planem.
- **Własny graf w ComfyUI** opłaca się, gdy robisz to często i masz kartę NVIDIA: konfiguracja zajmuje trochę czasu jeden raz, a każde następne zdjęcie to kilka sekund.

## Podsumowanie

- ComfyUI z BiRefNet zamienia zdjęcie części w packshot na bieli w 2–4 sekundy na karcie graficznej laptopa. Jest darmowy, a obliczenia odbywają się na Twoim komputerze.
- Graf jest krótki: wycięcie, wklejenie na biel, kadr do obrysu, wpasowanie w ramkę z marginesem. Jeden przebieg daje plik 4:3 i kwadratowy.
- Krótki skrypt w Pythonie puszcza go na cały folder, a mały worker może go karmić ze sklepu lub strony na serwerze bez karty graficznej.
- Model nie wie, który przedmiot jest na sprzedaż, więc każdy wynik trzeba szybko przejrzeć, zanim zostanie opublikowany.
- Przy pojedynczym zdjęciu albo profesjonalnej sesji lepsze jest narzędzie online lub Photoshop.

Tego samego narzędzia używam też do upscale'owania zdjęć. A jak Ty robisz packshoty: ręcznie, w narzędziu online, a może lokalnie? Ciekaw jestem, co działa u Ciebie i czego brakuje w moim grafie.

## Najczęściej zadawane pytania {#faq}

### Czy potrzebuję karty graficznej NVIDIA? {#faq-czy-potrzebuję-karty-graficznej-nvidia}

Graf uruchamiam na karcie NVIDIA (węzeł BiRefNet ma ustawione <strong>cuda</strong>). Nie sprawdzałem procesora ani karty AMD, więc nie podam dla nich czasów.

### Czy to naprawdę nic nie kosztuje? {#faq-czy-to-naprawdę-nic-nie-kosztuje}

ComfyUI jest darmowy i otwarty, a wagi BiRefNet pobierasz z Hugging Face. Zanim użyjesz wyników komercyjnie, sprawdź licencję modelu, którego używasz.

### Czy poradzi sobie z setkami zdjęć? {#faq-czy-poradzi-sobie-z-setkami-zdjęć}

Tak. Skrypt poniżej wysyła jedno zdjęcie naraz, bo pojedyncza karta nic nie zyskuje na paczce: kazałaby tylko kolejnym zdjęciom czekać. Przy 3 sekundach na zdjęcie 300 zdjęć to 15 minut.

### Czy mogę zmienić margines albo rozmiar? {#faq-czy-mogę-zmienić-margines-albo-rozmiar}

Tak. Liczby są w węzłach 7a–7c i 8a–8c: płótno (2000×1500 i 2000×2000), rozmiar, do którego wpasowuję część (bok 1800 px), i położenie (margines 100 px).

### Czy wycina każdą część poprawnie? {#faq-czy-wycina-każdą-część-poprawnie}

Nie. Model usuwa wszystko, co wygląda na pierwszy plan, i nie wie, która część jest na sprzedaż, więc każdy wynik sprawdzam, zanim zostanie opublikowany. Sekcja o błędach niżej pokazuje, gdzie się myli.


## Źródła {#sources}

- [ComfyUI](https://github.com/comfyanonymous/ComfyUI) — Interfejs węzłowy i serwer, który uruchamia graf.
- [ComfyUI: trasy serwera i API](https://docs.comfy.org/development/comfyui-server/comms_routes) — Endpointy /upload/image, /prompt, /history i /view, z których korzysta skrypt.
- [BiRefNet](https://github.com/ZhengPeng7/BiRefNet) — Model segmentacji, który wycina część z tła.
- [Bilateral Reference for High-Resolution Dichotomous Image Segmentation](https://arxiv.org/abs/2401.03407) — Praca naukowa, na której opiera się BiRefNet.
- [ComfyUI_LayerStyle_Advance](https://github.com/chflame163/ComfyUI_LayerStyle_Advance) — Węzły, które wczytują i uruchamiają BiRefNet.
- [ComfyUI_essentials](https://github.com/cubiq/ComfyUI_essentials) — Węzły z MaskBoundingBox+, który przycina obraz do obrysu maski.
- [Cennik iLoveIMG](https://www.iloveimg.com/pricing) — Plany darmowy i Premium, razem ze stwierdzeniem, że Premium odblokowuje nieograniczone przetwarzanie obrazów.
