polywright은(는) 무엇을 하나요?
3D 모델 작업을 위한 허브입니다. 모델이 어떻게 만들어질지 결정하고, 모든 애셋을 매니페스트와 함께 하나의 폴더에 보관하며, 각 단계를 숫자와 그림으로 증명합니다. 하위 스킬들이 세부 사항을 담당합니다.
스크립트: 이 스킬 폴더의 scripts/pw.py (Python 3.9+, 표준 라이브러리, 명령당 하나의 JSON 객체; scripts/pw_bpy.py는 Blender 파트로, 수동으로 실행하지 않음).
세션당 한 번 python <이 폴더>/scripts/pw.py doctor를 실행하세요. Blender(모든 OS), Python 메시 라이브러리, 슬라이서 및 ComfyUI 호스트를 찾고 누락된 항목을 알려줍니다. 전체 명령 목록: references/cli.md.
1단계: 브리프 (추론할 수 없는 것만 질문)
- 무엇: 대상이나 장소, 실제 또는 상상, 그리고 얼마나 알아볼 수 있어야 하는지.
- 대상:
pw.py check --list(game-roblox, game-unity, game-unreal, web-threejs, ar-usdz, commerce-gltf, print-fdm, print-resin, video-blockout, cad-step) 중 하나 이상. 대상이 예산을 설정합니다. - 실제 크기(미터): 벤치는 1.8m, 사람은 1.7~1.8m. 잘못된 축척이 가장 흔한 무음 오류입니다.
check --real-size-m이 이를 잡아냅니다. - 입력: 프롬프트, 사진, 스케치, 측정값, 지도 위치, 기존 메시.
- 충실도 및 예산: 블록아웃, 게임 레디, 히어로; 호스팅 생성기가 소비할 시간이나 비용.
스캐폴드: pw.py new <dir> --name <Name> --kind real|imagined|hybrid --route <route> --targets a,b --real-size-m X.
폴더: refs/ (참조, 각각 소스 기록), work/ (.blend, 중간 파일), out/ (대상당 하나의 전달물), renders/ (검토 시트), brief.md, manifest.json. 다른 플러그인을 위한 계약: references/contract.md.
2단계: 경로 선택 (브리프를 충족하는 가장 저렴한 방법)
| 상황 | 경로 | 스킬 |
|---|---|---|
| 흔한 물체; 라이선스 재사용 허용 | 찾기: Poly Haven, Kenney, Quaternius (CC0), Sketchfab 및 프린트 사이트 (각 라이선스 확인) | 이 스킬, references/routes.md |
| 치수, 맞춤 부품, 날카로운 모서리 있음 (브래킷, 케이스, 건물, 가구) | 코드 (--route procedural): bpy, build123d/CadQuery/OpenSCAD | polywright-generate, polywright-blender |
| 실제 장소 (공원, 거리, 캠퍼스, 지형) | 장소: OSM + 고도 (pw.py place) | polywright-capture |
| 사진 촬영이나 스캔 가능한 실제 물체 | 캡처: 사진 측량, 스플랫, 스캐너 또는 측정값 기반 모델 | polywright-capture |
| 상상의 유기체 또는 일회성 (조각상, 생물체, 소품) | 생성: 참조 시트, 그 다음 이미지-3D | polywright-references, polywright-generate |
| 변형되는 히어로 캐릭터 | 베이스로 생성 또는 조각, 그 다음 리토폴로지 및 리깅 | polywright-generate, polywright-finish |
대부분의 좋은 결과는 경로를 혼합합니다: 생성된 히어로 소품이 있는 OSM 공원, 생성된 조각상이 있는 코드로 지은 집. 매니페스트에 각 부분의 경로를 기록하세요.
3단계: 지오메트리 전에 참조
기성품으로 찾을 수 없는 모든 것에 대해 먼저 참조를 수집하거나 생성하세요(polywright-references): 공유 지면선과 높이 막대가 있는 직교 뷰, 재질 견본, 축척 참조. 생성된 입력이 이미지-3D 결과의 대부분을 결정합니다.
4단계: 빌드 후 증명 (모든 경로)
- 먼저 블록아웃 실제 크기로: 실루엣과 비율을 위한 기본 요소. 여기서 축척을 수정하세요. 지금 수정하는 것이 저렴합니다.
- 숫자:
pw.py inspect <file>: 삼각형, 오브젝트, 크기, 재질, 텍스처, UV, 워터타이트, 부품. 각 파괴적 단계 전후에 읽으세요. - 그림:
pw.py render <file> --out renders/<step>: 여섯 개의 뷰와 하나의sheet.png. 여섯 개의 스크린샷이 아닌 시트를 읽으세요. 참조와 비교: 실루엣, 비율, 누락되거나 떠 있는 부품, 셰이딩 스파이크, 잘못된 축(옆으로 누운 경우), 잘못된 축척. - 대상:
pw.py check <file> --target <t> --real-size-m X. 실패는 전달 전에 수정을 의미하고, 경고는 인계 시 언급을 의미합니다. - 기록:
pw.py manifest <dir> --add-output out/<file> --target <t> --inspect, 모든 소스에 대해--add-source <url> --licence <l> --author <a>, 그 다음--validate.
계획, 실행 및 비평은 별도의 패스입니다: 빌드 후, 비평가처럼 시트를 보고 완료를 주장하기 전에 결함을 나열하세요. 역추적 오류를 두 번 수정하는 것은 가치가 있습니다. 그 이상은 접근 방식을 재고하세요. 마일스톤당 번호가 매겨진 .blend를 저장하세요 (work/<name>_v03.blend). 긴 작업은 디스크에서 다시 시작할 수 있습니다.
모델을 그림에 합성
이미지나 비디오 모델이 디자인된 소품을 계속 잘못 그릴 때 (스토리보드 스틸, 세트 참조, 포스터), 그림에서 구도를, 모델에서 형태를 가져오세요:
- 구도만을 위한 그림 선택: 사람이 서 있는 위치, 빛, 목적. 평범한 대체 소품도 괜찮습니다.
pw.py match model.blend --still pic.png --out work/match.png --anchor-px X,Y --anchor-local=X,Y,Z --aim-px X,Y --aim-local=X,Y,Z --depth M --horizon ROW --hide BOX --mask-add BOX: 모델의 앵커(그립)가 손에 닿고, 조준점(팁)이 정확한 픽셀에 위치하며, 사진의 렌즈와 수평선으로 RGBA 렌더링됩니다.--depth를 설정하여 픽셀 너비가 대체 소품의 너비와 일치하도록 합니다 (너비 = f_px x 직경 / 깊이;f_px는 결과에 있습니다).--hide는 손 뒤의 부품을 숨깁니다;--mask-add는 손을 마스크에 추가합니다.- 3배로 자른
match_paste.png읽기: 프레임 내 모양, 크기, 조준. 깊이와 픽셀을 수정하고 다시 실행하세요 (몇 초). - 마스크된 낮은 디노이즈 이미지 편집(FLUX.2 Klein 또는 모든 인페인트 모델: 디노이즈 0.3~0.5, 낮은 cfg)으로
match_mask.png내부를 블렌딩한 다음, 마스크를 통해 결과를 다시 붙여넣어 외부의 모든 픽셀이 그림의 고유 픽셀로 유지되도록 합니다. 전체 그림 편집은 모든 것을 다시 그립니다(HDR 색상, 더 큰 소품). - 전체 크기에서 확인; 두 개 이상의 시드를 유지하세요.
소품의 참조 시트도 모델에서 제공됩니다(polywright-references, 2b단계).
모델에서 게임 스프라이트
이미지 모델이 게임 스프라이트에서 메커니즘을 계속 잘못 그릴 때 (둥글지 않은 바퀴, 지붕 위의 칼날), 모델을 빌드하고 게임 자체 카메라를 통해 렌더링한 후 이미지 모델이 페인팅만 하도록 하세요:
pw.py spritecam <registry.json> --like <sprite> --out camera.json: 게임의 지면 다이아몬드(L-014)에서 맞춘 직교 카메라. 모델의 타일당 미터를tile_m에 설정하세요.- 씬 속성
sprite_parts에 오브젝트당 부품 접두사(wheel_,roof_...)로 모델을 빌드하고, 피벗 공간에 빌드된 피벗 빈 아래에 움직이는 부품을 배치하고, 씬 속성loop에 모션을 설정하세요. pw.py sprite model.blend --camera camera.json --out renders/L1 --scale 10.6667(96px 스프라이트에 대해 1024px): 패스와 1배율의 뷰티 시트를 게임 스프라이트 옆에서 읽으세요; 애니메이션 부품의 경우--frames N --frame-passes id,pos, 그것 없이 판의 경우--hide wheel_. 페인팅 전에 게임의 이웃 스프라이트와 크기를 확인하세요:aw.py sprite <96의 뷰티> --refs <동급 스프라이트>는 중앙값의 0.9 미만 커버리지에서 실패합니다. 다이아몬드 핏은 지면 축척을 설정하며 건물이 얼마나 크게 보이는지가 아닙니다: 먼저 매싱과 소품을 추가하고(더 높은 벽, 렌-투, 마당), 그런 다음px_per_tile을 높이고footprint_centre_px를 이동하여 경계 상자가 이웃처럼 캔버스를 채우도록 합니다(L-016). 실린더 실루엣에서 얇은 빔을 유지하세요: 경사진 레일 위의 수평 통나무는 위와 아래를 통과하는 것으로 읽힙니다(L-017).- 클레이의 Canny를 제어로 사용하여 뷰티를 페인팅하고(ControlNet이 있는 이미지 모델), 렌더의 알파로 잘라내어 프레이밍과
groundBase가 정확하게 유지되도록 한 다음,sprite.json의 ID 및 림 데이터와 페인팅을 확인하세요.
모델에서 장면 일러스트레이션
로딩 화면, 키 아트 또는 이미 존재하는 모델(건물, 기계) 주변의 표지: Blender에서 장면을 빌드하고 이미지 모델이 페인팅하도록 하여 메커니즘과 레이아웃이 올바르게 유지되도록 하세요.
- 씬 속성
scene_parts에 오브젝트당 부품 접두사로 모델 주변 장면을 빌드하고, 바퀴와 디스크는rings에, 키 포인트나 경로는scene_points에 배치하세요. 경로를 따라 있는 제방, 독, 벽은 각각 하나의sweep입니다(pw.py bpy스크립트에서scripts/pw_scene.py에서 가져옴, L-020), 일련의 상자가 아닙니다. pw.py framecam problem.json --out cameras.json: 화면 상자, UI 텍스트 밴드 밖에 유지된 포인트, 크기 측정을 최대화하는 세계 포인트; 최상의 카메라를 프리셋으로 출력합니다. 경험 법칙(L-018)이 아닌 실제 UI 파일(패딩 및 앵커)에서 밴드를 가져오세요.pw.py scene scene.blend --cameras cameras.json --camera framecam_1 --out renders/v1 --size 1280x720(페인트 워크플로우의 첫 번째 패스 크기): 클레이, 뷰티, 뎁스, 노멀, ID, 라인 및scene.json. 먼저 클레이와 뎁스를 읽으세요; 프리셋이 고정을 요구하지 않는 한 뎁스 범위를 장면 자체 측정에 맡기세요(L-019).- 제어(뎁스 또는 라인)로 페인팅한 다음,
scene.json에 대해 페인팅을 게이트하세요: 링 림, 포인트, ID 색상.
군중 및 전투 블록아웃 (AI 비디오)
비디오 모델은 군중에서 깨집니다; Blender는 그렇지 않습니다. Blender가 군대를 배치하고 비디오 모델이 모양을 페인팅하도록 하세요:
pw.py crowd --out work/crowd --action clash --preview(또는 march, advance, charge, hold;--view,--lens,--move), 그런 다음work/crowd/sheet.png를 읽으세요.- 전체 샷을 위해
--preview를 제거하세요:depth.mp4(주 제어),pose.mp4(전열),mask.mp4,clay.mp4,camera.json; 기본적으로 832x480, 16fps에서 81프레임 (Wan). - 클레이 프레임 1을 승인된 시작 스틸로 다시 페인팅하세요; 뎁스 비디오와 그 스틸로 Wan VACE 또는 Wan 2.2 Fun Control을 구동하세요. 의상, 측면별 색상, 빛과 헤이즈를 프롬프팅하고, 인원수는 프롬프팅하지 마세요.
세부 사항 및 테스트되지 않은 내용: references/crowd-blockouts.md. 샷 계획은 cinewright의 몫입니다.
두 전투원: pw.py duel shot.json --preview는 세트의 표시에, 샷의 카메라를 통해 두 마네킹을 포즈시킵니다(examples/duel.json); sheet.png를 읽은 다음, 각 제어의 mp4에 대해 --preview를 제거하세요. 더 보기: crowd-blockouts.md, "Two fighters".
실제 인물이나 장난감의 소규모 캐스트(측면이 바뀜, 추가 인물, 표식 손실): 사진에서 각각 메시를 만들고, pw.py mark로 색상과 페인트 표식을 수정하고, 비디오 모델에 참조로 pw.py turnaround 사진과 시작으로 pw.py lineup (고정된 측면의 팀, 뎁스 및 마스크)을 제공하세요: references/figures-for-video.md.
영화 샷을 위한 세트 및 소품: references/film-and-video.md.
5단계: 마무리 및 인계
대상별 마무리(UV, LOD, 노멀 맵 규칙, 축 및 단위 변환, 압축)는 polywright-finish; 프린팅(워터타이트 솔리드, 벽, 베이스, 분할, 3MF)은 polywright-print. 폴더를 사용하는 플러그인에 전달하세요: three.js 페이지(threewright), 영화 및 비디오(cinewright), Roblox 장소(roblox-agent), Unity 프로젝트(unity-agent), 프린터별 또는 슬라이서 스킬(프린트 설정용), 이미지 스킬(더 많은 그림용). 이들은 manifest.json과 out/을 읽습니다.
인계 메시지:
모델: <name> (<route>) -> out/<file> (<target> 용): <tris> 삼각형, <size> m, <watertight/parts>
확인: <target> 통과|경고 (<rules>) 검토: renders/<step>/sheet.png
소스: <n>개 (라이선스 포함); AI 제작 부품: <which, which model> 미완료: <what is not done>
규칙
- Blender 및 glTF에서 실제 크기는 미터(+Z up in Blender, +Y up in glTF); 프린트 파일에서만 밀리미터.
- 파일 이름이나 생성기의 말만으로 메시가 괜찮다고 주장하지 마세요: 검사, 렌더링, 확인.
- 다운로드 또는 생성된 모든 입력은 라이선스와 함께 소스 라인을 받습니다. 스토어 및 프린트 사이트(Fab, Unity Asset Store, Sketchfab, MakerWorld, Printables, Steam)는 AI 제작 콘텐츠의 공개를 요구합니다; 매니페스트가 이를 기록합니다.
- MCP를 통한 Blender 브릿지는 임의의 Python을 실행합니다: 복사본에서
pw.py bpy를 선호하세요; 사용자가 지켜보고 있을 때만 실시간 MCP 세션을 사용하세요(polywright-blender). - Google Photorealistic 3D Tiles는 볼 수 있지만 내보내기, 캐싱 또는 추적할 수 없습니다(해당 약관).
유지 보수
Evergreen 유닛, 티어 fast (생성기와 Blender는 매월 변경됨). 동반 파일: RESEARCH.md, CHANGELOG.md, LEARNINGS.md, TESTS.md (evals/evals.json 포함), MAINTENANCE.md, 상태는 evergreen.json. 사용할 때마다 evergreen.json을 읽으세요; 작업이 예정된 경우 먼저 작업을 수행한 다음 새로 고치세요(evergreen-refresh). 교훈을 LEARNINGS.md에 기록하세요.