요약에서 환자를 두 번 적지 않고, 흐린 글씨를 표면 단위로 잡는다

## ① 요약이 환자를 두 번 적고 있었다

아래 버튼이 이미 "환자 해제 — 강한(0001381872) · 외래 2019-03-28 09:22 · 기준 …" 을
그대로 보여 주는데 요약도 같은 것을 다시 적었다. 두 줄로 늘어 결과 표를 밀어내고,
화면에 환자 이름이 필요 이상으로 여러 번 남았다.

환자가 있을 때는 침묵한다 — 버튼이 이미 말한다.
없을 때만 "변수 NULL — 구문만 검사" 를 남긴다(그 결과는 값이 아니라는 뜻이고,
그건 버튼 글자로는 알 수 없다). 빈 조각은 걸러 낸다 — 안 걸러 내면
"성공 · · 경고" 처럼 가운뎃점이 떠 있는다.

## ② 앞 수정이 부족했다 — 표면마다 경계가 따로 있다

카드 DockPanel 에만 힌트를 걸어 두고 고쳤다고 했는데 정작 SQL 글자는 계속 뭉개졌다.
본문은 SqlHighlightLayer 가 그리고 그 사이에 또 다른 중간 서피스가 있으며,
치환 변수 목록은 ListBox 템플릿 안에 ScrollViewer 를 품고 있다 —
카드에 건 힌트는 그 <b>바깥</b>이라 듣지 않는다(진단 표본 I 가 정확히 그 경우다).

- SQL 편집 영역: 불투명 B.Surface 를 가진 안쪽 Border 에 힌트
- 검증 결과 창(TrialPane): 배경 + 힌트
- 치환 변수 목록: ItemsPanel 을 불투명하게 만들어 ScrollViewer <b>안쪽</b>에 힌트(표본 J).
  VirtualizingStackPanel 을 쓴다 — StackPanel 로 바꾸면 변수 120개가 전부 실체화된다.

## 게이트가 초록불인데 화면만 틀린 것을 또 만들지 않기 위해

앞 커밋에서 실제 창 표본을 넣었지만 <b>카드 제목만</b> 쟀다.
제목은 켜졌고(150) 본문은 꺼져 있었는데 게이트는 통과했다 — 같은 함정을 한 번 더 밟았다.
사람이 실제로 들여다보는 표면을 다 재도록 바꿨다:

  G 카드 제목        색번짐    150
  H SQL 본문         색번짐  8,114
  I 치환 변수 목록   색번짐 22,047

대조군(B Effect·C1 힌트를 Effect 요소에·I 힌트 바깥 ScrollViewer)은 모두 0 이므로
이 숫자들은 뜻이 있다.

## 게이트

- dotnet test 323/323
- --cleartype 실패 0 (실제 창 표본 1개 → 3개)
- --query-popup 실패 0 · --edit-smoke 실패 0 · --dialog-shots FAIL 0
  (변수 목록 그룹 표시 유지 확인 — ItemsPanel 교체가 그룹을 깨지 않았다)
- --db-render P062 md5 8d683835f5d81e7bb41c79071d6bf954 불변

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Msystech
2026-08-19 10:36:38 +09:00
co-authored by Claude Opus 5
parent 52f1e30437
commit bbbc7f5a08
3 changed files with 61 additions and 19 deletions
@@ -317,7 +317,9 @@
</DockPanel>
</Border>
<DockPanel x:Name="TrialPane" Visibility="Collapsed" Margin="12,10,12,10">
<DockPanel x:Name="TrialPane" Visibility="Collapsed" Margin="12,10,12,10"
Background="{DynamicResource B.Surface}"
RenderOptions.ClearTypeHint="Enabled">
<DockPanel DockPanel.Dock="Top" Margin="0,0,0,8">
<Button DockPanel.Dock="Right" Content="닫기"
Style="{StaticResource LinkBtn}" Click="OnCloseTrial"/>
@@ -338,8 +340,13 @@
본문 사이 구분선까지 함께 휘어 보인다. -->
<!-- 본문 면은 B.Surface 다. B.Input 을 쓰면 다크에서 홈통(B.Chip)과 같은 #262626 이라
홈통이 통째로 사라진다(양 토큰이 같은 값이다). -->
<!-- ClearTypeHint 를 여기에 건다. 카드 DockPanel 에만 걸어 봤더니 SQL 글자는
계속 뭉개졌다 — 본문은 이 아래 SqlHighlightLayer 가 그리고, 그 사이에
또 다른 중간 서피스가 있다(진단 cleartype 표본 I·J — ScrollViewer 도 경계다).
이 Border 는 불투명 B.Surface 를 갖고 Effect 경계 안쪽이라 조건이 맞는다. -->
<Border BorderThickness="1" CornerRadius="0"
BorderBrush="{DynamicResource B.Line2}" Background="{DynamicResource B.Surface}">
BorderBrush="{DynamicResource B.Line2}" Background="{DynamicResource B.Surface}"
RenderOptions.ClearTypeHint="Enabled">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
@@ -455,6 +462,19 @@
HorizontalContentAlignment="Stretch"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
AutomationProperties.Name="치환 변수 목록">
<!--
ListBox 는 템플릿 안에 ScrollViewer 를 품고 있고 그것이 중간 서피스다 —
카드에 건 힌트는 <b>바깥</b>이라 목록 글자에는 듣지 않는다(표본 I).
항목 패널을 불투명하게 만들어 힌트를 ScrollViewer <b>안쪽</b>에 둔다(표본 J).
StackPanel 이 아니라 VirtualizingStackPanel 이어야 한다 —
바꾸면 변수 120개가 전부 실체화된다.
-->
<ListBox.ItemsPanel>
<ItemsPanelTemplate>
<VirtualizingStackPanel Background="{DynamicResource B.Surface}"
RenderOptions.ClearTypeHint="Enabled"/>
</ItemsPanelTemplate>
</ListBox.ItemsPanel>
<ListBox.ItemTemplate>
<DataTemplate>
<DockPanel Margin="0,3" ToolTip="{Binding Token}">
@@ -560,11 +560,12 @@ public partial class QueryEditorWindow : Window
}
TrialPane.Visibility = Visibility.Visible;
// 무엇으로 돌렸는지 먼저 말한다 — 실제 값인지 자리표시인지에 따라 결과의 의미가 완전히 다르다.
// 이 한 줄이 없으면 0행을 보고 "이 환자에게 자료가 없다"로 잘못 읽는다.
var basis = variables is not null
? $"환자 {Services.PatientSession.Label} 의 실제 값으로 실행"
: "환자를 고르지 않아 변수를 NULL 로 두고 구문만 검사";
// 무엇으로 돌렸는지는 말해야 하지만 <b>환자를 두 번 적지 않는다</b> —
// 아래 버튼이 이미 "환자 해제 — 강한(0001381872) · 외래 …" 를 그대로 보여 준다.
// 같은 정보를 두 군데 적으면 요약이 두 줄로 늘어 결과 표를 밀어내고,
// 화면에 환자 이름이 필요 이상으로 여러 번 남는다.
// 환자가 있을 때 필요한 말은 이미 버튼이 하고 있으므로 여기서는 침묵한다.
var basis = variables is not null ? string.Empty : "변수 NULL — 구문만 검사";
var notes = new List<string>();
// 환자를 안 골랐으면 <b>모든</b> 변수가 Unknown 이다 — 그것을 "아직 옮기지 않았다"고 적으면
// 거짓이 된다(ChtNum 은 옮겨져 있다). 그 사유는 위 basis 줄이 이미 말한다.
@@ -597,7 +598,9 @@ public partial class QueryEditorWindow : Window
? " — 구문은 정상입니다(변수가 NULL 이라 조건에 걸리는 행이 없습니다)."
: " — 구문은 정상이고, 이 환자에게 해당하는 행이 없습니다.")
: result.Summary;
TrialSummary.Text = string.Join(" · ", new[] { head, basis }.Concat(notes));
// 빈 조각은 버린다 — 안 버리면 "성공 · · 경고" 처럼 가운뎃점이 떠 있는다
TrialSummary.Text = string.Join(" · ",
new[] { head, basis }.Concat(notes).Where(s => s.Length > 0));
TrialGrid.ItemsSource = ToGridRows(result);
TrialGrid.Visibility = result.Rows.Count > 0 ? Visibility.Visible : Visibility.Collapsed;
}
@@ -605,7 +608,7 @@ public partial class QueryEditorWindow : Window
{
TrialSummary.Foreground = (System.Windows.Media.Brush)FindResource("B.Danger");
TrialSummary.Text = string.Join(" · ",
new[] { "실패 — " + result.Error, basis }.Concat(notes));
new[] { "실패 — " + result.Error, basis }.Concat(notes).Where(s => s.Length > 0));
TrialGrid.ItemsSource = null;
TrialGrid.Visibility = Visibility.Collapsed;
}