@@ -851,14 +851,23 @@ func (e *Engine) loopSpecial() {
851851 if result .Success {
852852 fmt .Printf ("✅ 강화 완료! [%s] +%d\n " , itemName , result .FinalLevel )
853853 overlay .UpdateStatus ("⭐ 특수 강화 완료!\n [%s] +%d" , itemName , result .FinalLevel )
854+ e .telem .TrySend ()
855+ return // 목표 달성 → 종료
854856 } else {
855- fmt .Printf ("💥 강화 중 파괴됨 (최종 레벨: +%d)\n " , result .FinalLevel )
856- overlay .UpdateStatus ("💥 특수 파괴됨\n [%s] +%d" , itemName , result .FinalLevel )
857+ // 파괴됨 → 다시 특수 아이템 찾기
858+ fmt .Printf ("💥 강화 중 파괴됨 (최종 레벨: +%d) → 다시 특수 아이템 찾기\n " , result .FinalLevel )
859+ overlay .UpdateStatus ("💥 특수 파괴됨\n 다시 특수 찾는 중..." )
860+ e .telem .TrySend ()
861+ time .Sleep (time .Duration (e .cfg .TrashDelay * float64 (time .Second )))
862+ continue // 루프 계속 → 특수 아이템 다시 찾기
857863 }
864+ } else {
865+ // 강화 목표 없으면 (보관만) 바로 종료
866+ fmt .Printf ("✅ 특수 아이템 보관 완료! [%s]\n " , itemName )
867+ overlay .UpdateStatus ("⭐ 특수 보관 완료!\n [%s]" , itemName )
868+ e .telem .TrySend ()
869+ return
858870 }
859-
860- e .telem .TrySend ()
861- return
862871 }
863872
864873 // 4. 쓰레기/일반/미판별이면 /판매로 새 아이템 받기 (v3 변경점)
@@ -875,6 +884,8 @@ func (e *Engine) loopSpecial() {
875884
876885 // /판매로 새 아이템 받기
877886 e .sendCommand ("/판매" )
887+ // 판매 응답 대기 (응답 없이 다음 /강화 보내면 꼬임)
888+ e .readChatTextWaitForChange (5 * time .Second )
878889 time .Sleep (time .Duration (e .cfg .TrashDelay * float64 (time .Second )))
879890 continue
880891 }
@@ -883,6 +894,8 @@ func (e *Engine) loopSpecial() {
883894 fmt .Printf (" ❓ 예상치 못한 아이템 타입: [%s] - 판매 처리\n " , state .ItemType )
884895 overlay .UpdateStatus ("⭐ 특수 아이템 뽑기\n ❓ 타입 불명 → 판매" )
885896 e .sendCommand ("/판매" )
897+ // 판매 응답 대기
898+ e .readChatTextWaitForChange (5 * time .Second )
886899 time .Sleep (time .Duration (e .cfg .TrashDelay * float64 (time .Second )))
887900 }
888901}
@@ -1156,7 +1169,9 @@ func (e *Engine) loopBattle() {
11561169
11571170 if len (usernames ) == 0 {
11581171 fmt .Println ("⏳ 랭킹에서 유저를 찾을 수 없음, 30초 후 재시도..." )
1159- time .Sleep (30 * time .Second )
1172+ if e .sleepWithHotkeyCheck (30 * time .Second ) {
1173+ return
1174+ }
11601175 continue
11611176 }
11621177
@@ -1198,7 +1213,9 @@ func (e *Engine) loopBattle() {
11981213
11991214 if len (candidates ) == 0 {
12001215 fmt .Println ("⏳ 적합한 타겟 없음, 30초 후 재시도..." )
1201- time .Sleep (30 * time .Second )
1216+ if e .sleepWithHotkeyCheck (30 * time .Second ) {
1217+ return
1218+ }
12021219 continue
12031220 }
12041221
@@ -1950,6 +1967,25 @@ func (e *Engine) checkStop() bool {
19501967 return ! e .running
19511968}
19521969
1970+ // sleepWithHotkeyCheck 대기 중에도 핫키 체크 (200ms 간격)
1971+ // 긴 Sleep 중에도 F9로 즉시 종료 가능
1972+ func (e * Engine ) sleepWithHotkeyCheck (duration time.Duration ) bool {
1973+ const checkInterval = 200 * time .Millisecond
1974+ elapsed := time .Duration (0 )
1975+ for elapsed < duration {
1976+ if e .checkStop () {
1977+ return true // 종료 요청됨
1978+ }
1979+ sleepTime := checkInterval
1980+ if duration - elapsed < checkInterval {
1981+ sleepTime = duration - elapsed
1982+ }
1983+ time .Sleep (sleepTime )
1984+ elapsed += sleepTime
1985+ }
1986+ return false // 정상 완료
1987+ }
1988+
19531989func (e * Engine ) stop () {
19541990 e .mu .Lock ()
19551991 defer e .mu .Unlock ()
0 commit comments