33 Commits

Author SHA1 Message Date
8eaf99c8be fix: Zoom 버튼 툴팁 문구 정정 및 Scanner Calib 오타 수정 (ISSUE-260908-01)
- MainPage.Designer.cs: 돋보기 버튼 툴팁을 실제 동작에 맞게 '화면 축소(Zoom Out)' / '화면 확대(Zoom In)' 으로 정정. Click 핸들러·Text·아이콘 리소스는 무수정(현장 티칭 습관 유지 협의).

- UCScannerCalibration.xaml: 'Run Sacanner Calib' -> 'Run Scanner Calib' 오타 수정.
2026-09-15 15:40:34 +09:00
f873e066e4 feat: 수동출사 레시피/페이지 정합성 인터락 (ISSUE-260904-03)
AutoRun 중 수동출사(Run Welding) 시 화면 띠의 PLC 지시와 실제 활성·로드 상태가 어긋난 채 출사되는 것을 차단. 검증 4종 - 활성==선택 / 활성==실제 로드파일(SelectedRecipeFile) / PLC지시 RECIPE==활성번호 / PLC지시 PAGE==현재 페이지. PLC 지시 2종은 bit15 구간에만 채워지므로 null 이면 생략. 검증 예외 시 fail-closed. 시퀀스는 무수정.
2026-09-04 16:13:37 +09:00
bd6a7cd21f fix: 레시피 저장 교차오염 트리거 차단 (ISSUE-260904-02)
OnActivatedRecipe 의 무조건 SaveRecipe 를 활성==선택 조건부로 변경하고 불일치 시 스킵 로그. PreSaved/OnSaved 에 활성!=선택 저장 차단과 안내 모달 추가. ISSUE-260826-04 의 트리거 차단이며 근본 해결은 아님. 현장에서 차단 동작 확인 완료.
2026-09-04 14:13:44 +09:00
3b8e64b9be feat: 레이저 출사중 표시 및 출사조건 로그 (ISSUE-260904-01)
메뉴얼/레시피 화면에 DI Laser_EMISSION_ON(10) 기반 출사중 램프 추가. 260904 현장 실측으로 DI 10 이 DO 9 의 에코가 아닌 실제 발진 피드백임을 확증하여 LaserIOControl 주석도 정정. 출사조건 스냅샷은 [LaserCond] 로그로 4개 시점(ShotOn/Heartbeat/ShotOff/DoorForceOff)에 기록. 표시·기록 전용이며 출사 차단 로직은 변경 없음.
2026-09-04 14:13:13 +09:00
7c974628d7 fix: 메뉴얼 모드 Door Open 시 레이저 출사 차단 (ISSUE-260902-01)
## 배경 (현장 사고 2026-09-02)
파워측정 / 파워캘 / 롱텀(1시간 연속출사) 작업 중 Door Open 상태에서 레이저가
출사되었다. 현장 요청: "메뉴얼에서도 Door open 상태에서 레이저 출사 안 되도록
Interlock 필요".

## 원인 (수정 전)

1) SeqComponentTeachingRun.CheckCondition_Interlock()
   Door 차단 코드가 '#warning to KSJ > 지워도 무방해보임' 과 함께 전체 주석 처리
   되어 있었다. 남은 검사는 HasAlarmLevelHigh() 뿐이라 Door Open 이어도 통과한다.
   이 함수가 Manual 경로(Teaching Run / Laser Shot On / Scanner Calibration)의
   유일한 출사 게이트였다.

2) UCScannerLaserControlViewModel.PerformCmdLaserShotOnPercent / ...OnWatt
   IsUseLaserAutoOffChecked == false 분기(= 파워측정 직접 출사)는 시퀀스를 아예
   타지 않고 _Scanner.LaserSignalOn() 을 직접 호출한다. 이 분기에는 Door / EMO /
   Busy / LaserReady 어떤 인터락도 없었다. LaserSignalOn 은 자동 오프가 없어
   Shot Off 를 누를 때까지 계속 출사되며, 이것이 롱텀 1시간 연속출사의 구현
   경로다. 이번 사고의 실제 경로.

3) Door 신호 2계통이 모두 출사를 막지 않고 있었다
   - PLC 비트: AlarmManager.IsPlcDoorOpen() 을 호출하는 살아있는 코드가 0곳
     (SeqComponentTeachingRun 주석, UCMainAutoRunViewModel 블록 주석)
   - IO DI 접점: IODevice.MonitorIOInterfaceMap 이 DoorLockOpen1~4 를 읽지만
     타워램프 점등과 EVENT_DOOR_INTERLOCK 발행만 하고, 그 이벤트의 구독자가 없다

## 변경 (수정 후)

[WeldingCommon/Alarm/AlarmManager.cs]
- IsDoorOpen(caller) 신규: PLC 비트(PLC_DOOR_INTERLOCK)와 IO DI 접점
  (DoorLockOpen1~4)을 OR 판정. 한쪽 배선/맵이 틀려도 다른 쪽이 잡도록 했다.
- IsIoDoorOpen(), GetDoorStateText() 신규.
- PAIXIO.ReadDiBit 은 비트 1개마다 DI 배열 전체를 읽으므로(PAIXIO.cs:305~307)
  80ms TTL 캐시를 두어 100ms 감시 1틱당 실제 읽기 1회로 제한했다.
- IsPlcDoorOpen(): _Plc 지연 조회 보완. 기존에는 AlarmManager 생성 시점에 PLC
  등록이 안 끝났으면 _Plc 가 null 로 남아 영구히 false 를 반환 → Door 인터락이
  조용히 무력화될 수 있었다.
- PLC/IO 미연결 계통은 판정에서 제외(의도적 fail-open). Door 맵이 없는 타 설비가
  이 변경으로 갑자기 출사 불가가 되는 것을 막기 위함. PTOP 는 둘 다 연결되어 있다.

[WeldingCommon/Views/Manual/Scanner/UCScannerLaserControlViewModel.cs]
- PerformCmdLaserShotOnPercent / ...OnWatt 진입부에 Door 게이트 추가
  -> 시퀀스 분기와 직접 출사 분기를 모두 커버한다.
- OnMonitoring(100ms)에 MonitorDoorInterlock() 추가: 출사 중 Door 가 열리면
  StopExecution + LaserSignalOff + SetStandby 로 강제 차단한다. 시작 게이트만으로는
  롱텀 도중 문이 열리는 이번 사고 상황을 막을 수 없어 추가했다.
- VisibleChanged: 직접 출사 중에는 화면을 벗어나도 감시 타이머를 유지한다.
  기존처럼 Stop 하면 롱텀 출사 중 Door 감시가 통째로 사라진다.
- 롱텀 추적용 10초 주기 하트비트 로그(Door 상태 + DA1/DA2 전압) 추가.

[ILSOS_PrismaticRD_PTOP/Sequences/Manual/SeqComponentTeachingRun.cs]
- CheckCondition_Interlock(): 주석 처리돼 있던 Door 차단을 IsDoorOpen() 으로 복구.
- DoComponentWelding(): ExecuteList 직전 최종 게이트 추가. 시작 게이트는 시퀀스
  진입 시 1회만 돌아, 객체가 여러 개일 때 매 출사 직전 재확인이 필요하다.

## 영향 범위
- SeqAutoRunPTOP 은 자체 ExecuteWelding(SeqAutoRunPTOP.cs:1314)을 사용하며
  SeqComponentTeachingRun 을 서브시퀀스로 타지 않는다 -> Auto 생산 동작 변경 없음.
- WeldingCommon 공용 파일을 수정했으나, Door 맵이 없는 설비는 fail-open 으로
  기존 동작이 유지된다.

## 남은 사항 (별건)
- 본 변경은 SW 방어이지 안전 인터락이 아니다. Door 감시가 UI 스레드
  DispatcherTimer 기반이라 UI 정지 시 함께 멈춘다. Class 4 레이저 기준 최종
  차단은 PLC/하드와이어 안전회로로 별도 협의가 필요하다.
- SeqComponentTeachingRun 의 EMO 차단(IsPlcEmoAlarm)도 함께 주석 처리되어 있다.
  이번 범위에서 제외했으며, PLC_EMO_STATUS 맵 확인 후 복구 여부를 결정한다.
- UCMainAutoRunViewModel.ApproveAutorunByUserOrAuto() 전체가 블록 주석
  (399~431행)이다. Auto 시작 게이트 복구는 Vision Recipe 검사까지 함께 살아나므로
  별건으로 검토한다.
2026-09-02 22:34:17 +09:00
2ef276e093 fix: Laser Ready 버튼을 DO 되읽기 토글로 전환 (ISSUE-260826-03)
증상: 버튼을 한 번 눌러도 반응이 없고 두 번 눌러야 Laser_REMOTE 가 켜진다(현장 확인).

원인: toggleIO 가 "다음에 쓸 값"을 VM 이 기억하는 방식이라 실제 DO 와 어긋난다.
SeqAutoRunPTOP 가 같은 DO 를 쓰면서 toggleIO 를 갱신하지 않기 때문 —
  :1220 용접시작 true / :1243 용접종료 false / :1701 정지 false
어긋나면 버튼이 같은 값을 다시 써서 아무 변화가 없다.

조치: 현재 DO 를 읽어 반전한다(바로 위 PerformCmdLaserGuideBeam :607-608 과 동일 패턴).
- 버튼 1회 입력에 TRUE/FALSE 가 정확히 기록된다
- 누가 중간에 DO 를 건드려도 항상 현재 상태 기준으로 동작한다
- 표시(OnMonitoring 의 IsLaserReady = ReadDO(Laser_REMOTE))와 1:1 로 맞는다
- AC_KEY(DO 8)는 전원 투입 계층이라 건드리지 않는다

toggleIO 필드는 원복 대비로 남겨둔다(주석 블록 2개가 참조). 외부 참조·XAML 바인딩 없음.
원복: "260826 이전 원본" region 을 살리고 아래 2줄을 제거.

부수 확인: "뷰 전환 시 REMOTE 꺼짐" 은 VisibleChanged(:251-260)에 DO 쓰기가 없고
시퀀스가 끄는 정상 동작이라 별도 조치하지 않는다.
2026-08-27 09:27:25 +09:00
5be34e612e feat: 본 레이저 단일 발진기 전환 - IO 채널 재정의 및 enum 단일화
레이저 발진기 교체(임시 Core/Ring 2대 -> 본 레이저 Max MFMC-2000/2000M 1대)에
따른 IO 재정의. 현장 적용 후 정상 동작 확인.

- ePrismaticDIAddress / ePrismaticDOAddress 를 본 레이저 38핀 커넥터 매뉴얼 기준으로
  재정의. 상태 신호 8개 -> 4개. 도면(엑셀) 라벨 오기도 함께 정정
  (Laser_FIRE -> Laser_MAIN_PWR_STATE)
- PAIX_PTOP / SeqAutoRunPTOP 의 중복 enum 정의 제거.
  WeldingCommon 의 PAIX_PrismaticScanner 를 IO 채널 번호의 단일 소스로 통일
- 발진 게이트를 Core/Ring_Control 2발 -> Laser_REMOTE 1발로 변경
  (ExecuteWelding ON/OFF, 정지 시 해제)
- DO 8 충돌 제거: Auto 시작 시 PCLBADReadyStatus(=8) write 삭제.
  본 레이저 배선에서 DO 8 = Laser_AC_KEY 라 그대로 두면 Auto 시작이
  레이저 AC KEY 릴레이를 켠다. LBAD 는 미등록 디바이스라 무의미
- GetLaserReady() 를 Laser_READY 단독 판정으로 변경
- 가이드빔 DO 를 EX_Red_Control -> Laser_GUIDE_BEAM_CONTROL 로 전환
- IO Board 에 설정 화면(UCIOInterfaceView) 연결
- IsLaserReady 표시를 DO Laser_REMOTE 되읽기로 확정 (260826 협의, 현장 미검증)

원복: 각 파일의 "260824 이전 원본" region 을 살리고 아래 블록을 제거하면 된다.
2026-08-26 11:45:40 +09:00
c054439c19 feat: Recipe 작업 화면 상단에 PLC 지시 Recipe/Page 표시
bit15(M70515) 팝업은 상승엣지 1회라 닫으면 값이 사라져, 현장에서 작업자가
레시피/페이지를 잊는 문제가 있었다. 팝업과 같은 기준·같은 워드를 화면 상단
전폭 띠로 ON 구간 내내 표시한다(Collapsed 시 높이 0이라 평소 화면 영향 없음).

공용(WeldingCommon)은 Status만 읽고 PTOP을 참조하지 않는다 —
값을 넣지 않는 타 설비는 분기문 없이 자동 미표시.
2026-08-21 00:06:30 +09:00
b7437a00f7 feat: 수동 Scout 이미지 파일명에 레시피/페이지 번호 태그 추가
레시피 티칭 화면 Scout 출사 시 SaveTag를 normal_{recipeId}_{pageNo}로 주입해 1_HHmmss_normal_23_5.PNG 형태로 저장. 공통 시퀀스 SeqScoutNormal은 무수정(기존 SaveTag 확장점 사용). 페이지 번호는 1-base로 AutoRun의 auto_{recipe}_{page}_pre/post와 숫자 정합. 원복 마커: #region 260807. 현장 검증 완료.
2026-08-07 10:39:42 +09:00
b3cb159491 fix: MoveScanner SelectedIndex 범위 가드 추가
그리드 빈 영역/헤더 더블클릭, Apply 전, Esc 선택해제 등으로 SelectedIndex가 -1이거나 VisionCorrectionList 범위를 벗어난 상태에서 MoveScanner가 호출되면 인덱스 예외가 발생했다. 진입부에서 범위를 검사해 무시하도록 처리.
2026-07-28 17:09:41 +09:00
to3796zw
9c1daaee1d fix: Busy bit 위치 변경 및 Scanner Cam 팝업 모션 수정
- Laser On Display 타이밍을 맞추기 위해 PC_WELD_BUSY bit
  기록 위치 변경 (SeqAutoRunPTOP)
- 레시피 Scanner Cam 팝업(WDScannerCamMotion)을 직접 실행
  모드(publishMode:false)로 변경하고, 창 표시 시 모니터
  타이머/Limit 초기화를 호출해 모션 미동작·좌표 0 고정 해소
- 작업일지 2026-06-26 추가, Laser Interface 문서 갱신

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 15:02:21 +09:00
to3796zw
041c15550c feat: 레시피별 Front/Down 레이저 인터락 추가
Use Interlock ON 시 ① 안전구역 게이트(기존) 유지 + ② 레시피별 방향 차단(신규). Recipe 폴더의 Recipe_Laser_Interlock.json(Front/Down 0/1)에 저장하고, 경로는 FieldHelper.json과 동일 소스(DB.Dao.SystemRecipe.WorkRecipeFile) 사용. Auto/Manual 양쪽 적용(Manual은 ①+② 신규), VM 체크박스는 레시피 전환 시 Background 우선순위 재로드로 stale 방지.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-25 22:30:57 +09:00
a64dd12519 fix: 레시피 Field 버튼 아이콘을 Select Field 아이콘(slash.jpg)으로 교체
빔 아이콘(guide.png)이 아니라 매뉴얼 화면 Select Field 버튼과 동일한
slash.jpg 아이콘 사용 (20x20).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-23 18:45:34 +09:00
d272d6e7e9 style: 레시피 Field 버튼을 기존 Scanner Cam 버튼 디자인으로 통일
StButtonAccentBlue + guide.png 아이콘 + 텍스트 StackPanel 형태로 변경
(기존 Scanner Cam 버튼과 동일한 디자인).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-23 18:34:18 +09:00
357702399c feat: 레시피 Scout Normal 줄에 Field 버튼 추가 (3열 [Field]-[Run]-[Stop])
- UCScannerObjectTeachingControlBox.xaml: Scout Normal 실행 줄을 2열에서 3열로
  재구성, 너비 1*/1.3*/1*로 Run 강조. Run Scout Normal 버튼을 Run으로 변경,
  1열에 Field 버튼 신규 추가.
- VM: 매뉴얼 화면과 동일한 WDSelectScoutField 팝업을 띄우는
  CMD_ShowSelectFieldWindow 이식. 저장은 팝업 VM에서 자체 처리하므로
  비전 이벤트 구독(SAVE_CHILD_IMAGE_SETTING)은 제외.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-23 18:23:10 +09:00
4ed35cb94a feat: 레시피 화면에서 스캐너 카메라+모션 토글 창 추가 (이벤트 구동)
- 레시피 컨트롤박스에 'Scanner Cam' 버튼 추가 → 카메라+모션 창 Show/Hide 토글
- WDScannerCamMotion: 전용 displayType(Machine_C) 카메라뷰 + 매뉴얼 UCScannerMotion 재사용
- UCScannerMotionViewModel: publish/execute 모드 분리
  - 레시피(publish): 입력값을 EVENT_SCANNER_COMMAND_MOVE 로 발행
  - 매뉴얼(execute): 이벤트 구독해 동일 메소드로 실제 스캐너 이동(인터락 그대로 재사용)
- Move/Jog/Home 메소드를 인자형으로 리팩터해 UI·이벤트 경로가 같은 본체 공유
- 분석 문서 추가(docs/분석/2026/06/23)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-23 17:03:21 +09:00
to3796zw
7fc11f2602 fix: AjinIO.IsConnected 반전 로직 정정
AxlGetBoardStatus가 SUCCESS일 때 미연결로 반환하던 반전 버그를
정정(실제 Ajin 연결 시 OnMonitoring 폴링이 스킵되던 원인).
연동해 OnMonitoring 미연결 가드를 앞으로 정리.
2026-06-20 10:14:18 +09:00
to3796zw
4a655ecefb fix: ScoutNormal 페이지별 필드 로드 정정 (PageIndex 주입)
증상: 운전화면 페이지 이동 후에도 SeqScoutNormal이 이전 페이지(보통 0)의
스카우트 필드로 동작.
원인: LoadScoutField()가 GUI 캐시 selectedIndexNo 의존 — WinForms 티칭
콤보에서만 갱신되어 운전화면/자동운전 경로에선 stale.

- SeqScoutNormal_InitParam에 PageIndex 추가, 실행 시점 라이브 페이지
  (GetCurrentPageIndex)를 호출부(Recipe/Test VM)에서 명시 주입
- MainPage: LoadScoutField(int) 오버로드 + GetCurrentPageIndex() 추가
- 폴백: 페이지 없으면 selectedIndexNo 로드, 그래도 null이면 빈 리스트(NRE 방지)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 17:44:35 +09:00
to3796zw
e263ab8a5a feat: ScoutNormal 행 전환 sleep 분리 (SameRow/RowChange)
같은 행 이동과 행 전환 이동(먼 거리)의 대기시간을 RowIdx 기준으로 분리.

- SystemParameter: ScoutSameRowSleepMs(150)/ScoutRowChangeSleepMs(300) 추가
- Recipe View > Scout Image 그룹에 입력 UI 2줄 + 즉시 저장
- SeqScoutNormal.CaptureNextPosition: prevRowIdx 추적해 행 전환 시 분기
- 공유(WeldingCommon)라 같은행은 150(기존동일), 행전환 기본 300ms

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 15:25:53 +09:00
8bfeb7377a fix: 레시피 Guide Beam DO 읽기 try/catch 이동(크래시 방지) + AjinIO.ReadDoBit 구현 활성화
- UCScannerObjectTeachingControlBoxViewModel.OnMonitoring:
  IsGuidBeam = _IODevice.ReadDO(17) 를 try 블록 안으로 이동, catch 에서 IsGuidBeam=false
  → IO 미연결(시뮬/개발PC)에서 Recipe View 진입 시 미처리 예외로 앱 종료되던 문제 해결
- AjinIO.ReadDoBit(int): 스텁(return true) → AxdoReadOutport 실제 구현 활성화

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-19 13:57:15 +09:00
3b8799aa51 feat/docs: 가이드빔·알람·PLC(MXComponent) 분석 및 현장 임시 수정
- 분석 문서 4종 추가 (docs/분석/2026/06/19):
  알람부 종합 / MX Component PLC 연결 / AjinIO.ReadDoBit / 가이드빔 TruPulse(ExtPilotOnOff 미구현)
- AjinIO.ReadDoBit(int): 스텁(return true) 유지 + 구현(ReadDiBit 패턴) 주석 보존
- SeqComponentTeachingRun: 중알람 인터락 임시 주석 (현장 PLC 미연결 우회, 추후 원복)
- 레시피 Guide Beam: DO 17 read/write + IsConnected 가드 주석 (필요시 주석 토글 운용)
- 작업일지 2026-06-19 정리

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-19 12:49:08 +09:00
a312e4ec8a fix: 레시피 화면 IO 미연결 시 null 가드 (OnMonitoring)
시뮬 모드가 아니고 IO보드가 없으면 IODevice._iOUnit이 null이라
OnMonitoring의 ReadDI(11/15)에서 NRE 발생(현장 PC에서 레시피 메뉴 진입 시).
IsConnected()로 미연결을 선검사해 폴링을 스킵, 프로그램이 꺼지지 않도록 함.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 20:32:35 +09:00
12402f81d6 feat :ReadbackAnalogOut 아날로그 Vot 값 표시 수정 2026-06-18 17:08:17 +09:00
5eebe96779 프로그램 시작 시 Manual - Laser Powe Control 부분 파라미터 Power 값 10 -> 0 300 ->0 수정 2026-06-18 15:54:50 +09:00
1fbe7fa98f feat: DA1/DA2 Voltage 표시를 No Laser 토글에 연동(조건부 표시)
DA1/DA2 Voltage UniformGrid에 Visibility 바인딩(IsNoLaser, convTrueVisible) 추가.
Time이 Use Spot Time 체크 시 표시되듯, No Laser 체크 시에만 전압 표시.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 14:20:26 +09:00
accffdd94a feat: NoLaser 옵션을 Manual(ScannerLaserControl)로 이동, Recipe NoLaser 제거
- Manual: IsNoLaser 추가, Laser On 직접 분기(Percent/Watt)의 LaserSignalOn을
  if(!IsNoLaser)로 가드 → 체크 시 발진 없이 전압만 인가
- Manual XAML: Use Spot Time과 동일 ToggleSwitch 디자인의 'No Laser(전압만)' 토글 추가
  (Timer Set: UseSpotTime → Time(체크시) → NoLaser → DA1/DA2 Voltage)
- Recipe(UCScannerObjectTeachingControlBox): NoLaser 완전 제거(원래 의도가 Manual),
  PerformCmdLaserReadyCheck를 WriteDoBit(9/13,true)로 환원. DI 11&15 변경은 유지.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 14:14:59 +09:00
166d1bd2f0 feat: RTC5 AnalogOut 전압 readback - device 계층 + ViewModel + XAML 표시
ed36f8d에서 분석 문서만 들어가, 실제 구현 소스를 함께 커밋.
- ScannerObj.GetAnalogOut(abstract) + RTC5/RTC6(n_get_value, signal=portNo+32)/Simul(0) + Scanner 파사드(-1)
- UCScannerLaserControlViewModel: AnalogOut1/2Voltage + ReadbackAnalogOut(raw/4095*10 V), Laser On 직접 분기 WriteDA 직후 호출
- UCScannerLaserControl.xaml: Control Setting에 DA1/DA2 Voltage [V] 표시
- 작업일지 13:55 기록

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 13:57:14 +09:00
f0380f43f9 fix: Laser Ready 판정 DI 변경 (IO 결선 변경 12&24 → 11&15)
IO 결선 변경에 따라 Laser Ready 입력 판정을
ReadDI(12) && ReadDI(24) → ReadDI(11) && ReadDI(15)로 수정. 로직 동일.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 12:21:08 +09:00
8ec4fd0d62 feat: NoLaser 옵션 - 레이저 컨트롤러 IO(DO9/13) 안 켜고 Laser On 가능
UCScannerObjectTeachingControlBox에 IsNoLaser 추가. Laser Ready 버튼이
CoreLaser_Control(DO9)/RingLaser_Control(DO13)을 켜는 분기에서 ctrlOn=!IsNoLaser
적용 → IsNoLaser=true면 DO9/13을 false로 유지(레이저 컨트롤러 OFF)하여
발진 없이 전압만 인가한 채 Laser On 가능(Cal/전압 측정용).
XAML에 'No Laser' 체크박스 추가. 디바이스 레이어 무변경.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 12:12:48 +09:00
ad6cf68498 feat: Manual Laser Power Control의 Watt 입력 GroupBox 숨김(Collapsed)
W 입력 영역은 주로 사용하지 않아 UCScannerLaserControl.xaml의 Grid.Row=1
(Watt 기준) GroupBox를 Visibility=Collapsed 처리. Percent 영역만 노출.
ViewModel/바인딩은 변경 없음(CMD_LaserShotOnWatt 등 유지).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-18 11:32:51 +09:00
9aa1b2aa13 fix: Laser Ready 판정을 Core·Ring Control Status(DI12 & DI24) 동시 조건으로 변경
OnMonitoring의 IsLaserReady 판정을 DI(9)(CoreLaser_Laser_Ready 단독)에서
DI(12) && DI(24) (CoreLaser_Control_Status AND RingLaser_Control_Status)로 변경.
버튼이 켜는 Control(DO9/13)의 피드백을 Core·Ring 둘 다 확인.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-17 15:12:52 +09:00
354cc29f83 fix: Recipe 탭 DI 읽기 실패 해결 (ERROR CODE:3102)
PTOP 변경 과정에서 Recipe 탭 진입 시 IO Device DI 읽기 실패로 시스템 크래시 발생.

  근본 원인:
  - DI 24가 PTOP 하드웨어에 미정의됨
  - UCScannerObjectTeachingControlBoxViewModel에서 DI 9, 24를 함께 읽으려고 시도
  - 범위 초과 오류(ERROR CODE:3102) 발생

  변경사항:
  - DI 24 읽기 제거 (Scanner 레거시 코드, PTOP에 불필요)
  - DI 9 읽기만 수행하도록 변경
  - try-catch 예외 처리 추가로 안정성 개선
  - 오류 발생 시 에러 로깅

  Fixes: Recipe 탭 시스템 셧다운

  또는 더 간단하게:

  fix: Recipe 탭 DI 읽기 오류 해결

  DI 24가 PTOP에 미정의되어 OnMonitoring에서 범위 초과 에러 발생.
  DI 9만 읽도록 수정하고 try-catch 예외 처리 추가.
2026-06-16 15:00:25 +09:00
d28e76c2fe file update 2026-06-05 13:44:39 +09:00