[Phase L5-5] 배치 파일 이름변경 (batchren) 구현

BatchRenameHandler.cs (신규, ~55줄):
- prefix="batchren" 핸들러, batchren [glob패턴] 으로 파일 미리 로드
- ExecuteAsync: BatchRenameWindow 열기 + 초기 경로 패턴 지정 지원

BatchRenameWindow.xaml (신규, ~380줄):
- 타이틀바(파일 수 배지) + 패턴 입력 영역 + DataGrid 미리보기 + 하단 버튼 바
- 변수 힌트 팝업: {name}/{n}/{n:3}/{date}/{date:format}/{ext}/정규식 설명
- 빈 상태 안내 패널, 드래그 앤 드롭 오버레이
- DataGrid 3열: 원본 파일명 / 새 파일명 / 상태(✓·⚠ 충돌·─)
- 충돌 행: 붉은 배경(#18EF5350) 강조

BatchRenameWindow.xaml.cs (신규, ~280줄):
- RenameEntry (INotifyPropertyChanged): OriginalPath/Name/NewName/HasConflict/StatusText
- ApplyPattern(): {n:자릿수} 패딩, {date:format}, {name}/{ext} 치환, 정규식 /rx/repl/ 모드
- UpdatePreviews(): 전체 패턴 재계산 + 충돌 감지(중복 새 이름 & 기존 파일 존재)
- AddFiles(), BtnAddFolder/Files/RemoveSelected/ClearAll 이벤트
- ExtToggle: 확장자 유지 슬라이드 토글
- BtnModeVar/Regex: 변수 ↔ 정규식 모드 전환 (UI 색상 갱신)
- StartNumberBox: 시작 번호 지정
- 드래그 앤 드롭: 파일/폴더 모두 처리
- BtnApply: File.Move 적용 후 엔트리 경로 갱신, 성공/실패 알림

App.xaml.cs (수정):
- Phase L5 섹션에 BatchRenameHandler 등록

docs/LAUNCHER_ROADMAP.md (수정):
- L5-5 항목  완료 표시 + 구현 상세 기록

빌드: 경고 0, 오류 0

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-04-04 12:42:24 +09:00
parent 3bfa82c06d
commit 375ea0566d
5 changed files with 1061 additions and 1 deletions

View File

@@ -0,0 +1,86 @@
using System.IO;
using AxCopilot.SDK;
using AxCopilot.Services;
using AxCopilot.Themes;
namespace AxCopilot.Handlers;
/// <summary>
/// L5-5: 배치 파일 이름변경 핸들러. "batchren" 프리픽스로 사용합니다.
/// 예: batchren → 기능 소개 + 창 열기
/// batchren C:\work\*.xlsx → 해당 패턴 파일을 창에 미리 로드
/// </summary>
public class BatchRenameHandler : IActionHandler
{
public string? Prefix => "batchren";
public PluginMetadata Metadata => new(
"BatchRename",
"배치 파일 이름변경 — batchren",
"1.0",
"AX");
public Task<IEnumerable<LauncherItem>> GetItemsAsync(string query, CancellationToken ct)
{
var q = query.Trim();
var items = new List<LauncherItem>
{
new LauncherItem(
"배치 파일 이름변경 창 열기",
"변수 패턴 또는 정규식으로 여러 파일을 한 번에 이름변경합니다",
null,
string.IsNullOrWhiteSpace(q) ? "__open__" : q,
Symbol: Symbols.Rename),
new LauncherItem(
"변수: {name} 원본명 · {n} 순번 · {n:3} 세 자리 · {date} 날짜",
"예: 보고서_{n:3}_{date} → 보고서_001_2026-04-04.xlsx",
null, null,
Symbol: Symbols.Info),
new LauncherItem(
"변수: {ext} 확장자 · {date:yyyyMMdd} 날짜 형식 지정",
"정규식 모드: /old_pattern/new_text/ → 패턴 일치 부분 치환",
null, null,
Symbol: Symbols.Info),
};
return Task.FromResult<IEnumerable<LauncherItem>>(items);
}
public Task ExecuteAsync(LauncherItem item, CancellationToken ct)
{
var dataStr = item.Data as string;
if (dataStr == null) return Task.CompletedTask;
System.Windows.Application.Current.Dispatcher.Invoke(() =>
{
var win = new Views.BatchRenameWindow();
// 초기 경로 패턴이 지정된 경우 파일 미리 로드
if (dataStr != "__open__" && !string.IsNullOrWhiteSpace(dataStr))
{
try
{
var dir = Path.GetDirectoryName(dataStr);
var glob = Path.GetFileName(dataStr);
if (!string.IsNullOrWhiteSpace(dir) && Directory.Exists(dir))
{
var files = Directory.GetFiles(dir, glob ?? "*");
Array.Sort(files);
win.AddFiles(files);
}
}
catch (Exception ex)
{
LogService.Warn($"BatchRenameHandler: 초기 로드 실패 — {ex.Message}");
}
}
win.Show();
});
return Task.CompletedTask;
}
}