From ecc4c69a8b974c2fd18408be9cd93e818281061d Mon Sep 17 00:00:00 2001 From: Towsty Date: Sat, 26 Sep 2026 12:42:00 -0500 Subject: [PATCH] Wire Qwen Turbo toggle through Studio 2 and the runner. Force 6/1 when Turbo is on, skip negatives, keep PE in front, and fail closed if the r128 LoRA is missing. Co-authored-by: Cursor --- components/studio2/Bench.vue | 27 +++++++++-- components/studio2/Details.vue | 3 ++ components/studio2/Mobile.vue | 2 + docs/qwen21.md | 5 +- server/utils/studio2/runner.ts | 83 ++++++++++++++++++++++++---------- shared/studio2/contracts.mjs | 8 +++- shared/studio2/input.mjs | 1 + tests/studio2-bench.test.mjs | 12 ++++- 8 files changed, 110 insertions(+), 31 deletions(-) diff --git a/components/studio2/Bench.vue b/components/studio2/Bench.vue index 04ded40..9588e55 100644 --- a/components/studio2/Bench.vue +++ b/components/studio2/Bench.vue @@ -119,6 +119,12 @@ +
+ +

6-step Viggle distill. CFG stays 1. Enhance prompt recommended.

+
Negative prompt @@ -379,6 +385,7 @@ import {LOAD_GENERATION_PAYLOAD_KEY} from '~/utils/queuedJob' const NEG_STORAGE_KEY='studio2-negative-chips' const ENHANCE_STORAGE_KEY='studio2-qwen21-enhance-prompt' +const TURBO_STORAGE_KEY='studio2-qwen21-turbo' function readStoredNegatives(){ if(!import.meta.client)return [...defaultNegatives] try{ @@ -400,6 +407,14 @@ function writeStoredEnhancePrompt(on:boolean){ if(!import.meta.client)return try{localStorage.setItem(ENHANCE_STORAGE_KEY,on?'1':'0')}catch{/* ignore */} } +function readStoredTurbo(){ + if(!import.meta.client)return false + try{return localStorage.getItem(TURBO_STORAGE_KEY)==='1'}catch{return false} +} +function writeStoredTurbo(on:boolean){ + if(!import.meta.client)return + try{localStorage.setItem(TURBO_STORAGE_KEY,on?'1':'0')}catch{/* ignore */} +} const xaigen=isXaigenStudio(useRuntimeConfig().public) const instanceName=String(useRuntimeConfig().public.instanceName || 'AIGen') @@ -419,7 +434,7 @@ const liveMusic=ref>({}) const negativeDraft=ref('') const filmstripEl=ref(null) const tileRefs=new Map() -const form=reactive({mode:'generate',engine:'flux',enhancePrompt:readStoredEnhancePrompt(),imageStyles:{positive:[],negative:readStoredNegatives()},lockFace:true,lockOutfit:true,hideInput:xaigen,folderId:'',identityStillId:'',imageAId:'',imageBId:'',maskId:'',startClipId:'',endStillId:'',guides:[],promptSections:sectionsFrom({}),settings:{aspect:'auto',fps:24,steps:24,cfg:4,seed:null,seedMode:'random',duration:5,turbo:true,loraStack:[]}}) +const form=reactive({mode:'generate',engine:'flux',enhancePrompt:readStoredEnhancePrompt(),turbo:readStoredTurbo(),imageStyles:{positive:[],negative:readStoredNegatives()},lockFace:true,lockOutfit:true,hideInput:xaigen,folderId:'',identityStillId:'',imageAId:'',imageBId:'',maskId:'',startClipId:'',endStillId:'',guides:[],promptSections:sectionsFrom({}),settings:{aspect:'auto',fps:24,steps:24,cfg:4,seed:null,seedMode:'random',duration:5,turbo:true,loraStack:[]}}) const music=reactive({tags:DEFAULT_MUSIC_TAGS,lyrics:DEFAULT_MUSIC_LYRICS,duration:60,seed:'',name:''}) const tagsPlaceholder=DEFAULT_MUSIC_TAGS,lyricsPlaceholder=DEFAULT_MUSIC_LYRICS let loraMemory=createLoraMemory(xaigen) @@ -456,7 +471,7 @@ watch(engineOptions,opts=>{ }) watch(()=>form.engine,(engine,prev)=>{ if(engine==='qwen21' && prev!=='qwen21'){ - form.settings.steps=25 + form.settings.steps=form.turbo?6:25 form.settings.cfg=1 form.lockFace=false form.lockOutfit=false @@ -464,9 +479,15 @@ watch(()=>form.engine,(engine,prev)=>{ } }) watch(()=>form.enhancePrompt,on=>writeStoredEnhancePrompt(!!on)) +watch(()=>form.turbo,on=>{ + writeStoredTurbo(!!on) + if(form.engine!=='qwen21')return + form.settings.steps=on?6:25 + form.settings.cfg=1 +}) watch(()=>[form.mode,form.engine],([mode,engine])=>{ if(engine==='qwen21' && mode==='edit'){ - form.settings.steps=25 + form.settings.steps=form.turbo?6:25 form.settings.cfg=1 form.lockFace=false form.lockOutfit=false diff --git a/components/studio2/Details.vue b/components/studio2/Details.vue index f9c3c49..2bfc95d 100644 --- a/components/studio2/Details.vue +++ b/components/studio2/Details.vue @@ -22,6 +22,9 @@ const rows=computed(()=>{const m=props.metadata||{},s=m.settings||{};const time= {label:'Compiled prompt',value:m.compiledPrompt}, {label:'Prompt (raw)',value:m.promptRaw || null}, {label:'Enhance prompt',value:m.enhancePrompt==null?null:m.enhancePrompt?'On':'Off'}, + {label:'Turbo',value:m.turbo==null?null:m.turbo?'On':'Off'}, + {label:'Turbo LoRA',value:m.lora || null}, + {label:'Turbo sigmas',value:m.sigmas || null}, {label:'Enhance wh_ratio',value:m.enhance?.wh_ratio || null}, {label:'Enhance ratio_follow',value:m.enhance?.ratio_follow || null}, {label:'Enhance parse_ok',value:m.enhance?.parse_ok==null?null:m.enhance.parse_ok?'Yes':'No'}, diff --git a/components/studio2/Mobile.vue b/components/studio2/Mobile.vue index 3b50904..a22d5bf 100644 --- a/components/studio2/Mobile.vue +++ b/components/studio2/Mobile.vue @@ -159,6 +159,8 @@