surshar / claude-code
Claude Code is an agentic coding tool that lives in your terminal, understands your codebase, and helps you code faster by executing routine tasks, explaining complex code, and handling git workflows - all through natural language commands.
Built by Anthropic · github.com/anthropics
| 1 | /* @jsxRuntime classic */ |
| 2 | /* @jsx h */ |
| 3 | /* @jsxFrag Fragment */ |
| 4 | import type { RenderElement } from 'claude-code' |
| 5 | |
| 6 | import Limits from '../../limits' |
| 7 | import Detail from '../detail' |
| 8 | import type { Kit } from '../kit' |
| 9 | import Layout from '../layout' |
| 10 | import Sections from '../sections' |
| 11 | import Plan from './plan' |
| 12 | import type { BodyLayout, HunkSegment, Segment, WindowCut } from './types' |
| 13 | |
| 14 | /** |
| 15 | * The rows of the docked body its window shows from a row down: each |
| 16 | * segment drawn from the row the window cuts it at, until the window fills. |
| 17 | * |
| 18 | * A hunk draws only its lines in view, and past MAX_BODY_CHARS of hunk |
| 19 | * text the rest waits for a scroll (the tree's cap); rows past the foot |
| 20 | * are the pane's to clip, so SCROLL_MARGIN_ROWS more are drawn than fit. |
| 21 | * |
| 22 | * @param kit the elements, the handlers, the width |
| 23 | * @param layout the body laid out |
| 24 | * @param top the body row wanted at the window's top; clamped to the body |
| 25 | * @returns the elements, top to bottom |
| 26 | */ |
| 27 | export function drawWindow( |
| 28 | kit: Kit, |
| 29 | layout: BodyLayout, |
| 30 | top: number, |
| 31 | ): RenderElement[] { |
| 32 | const { Box, Text, Code } = kit.ui |
| 33 | const drawn: RenderElement[] = [] |
| 34 | const wanted = layout.visibleRows + Limits.SCROLL_MARGIN_ROWS |
| 35 | const at = Math.max(0, Math.min(top, layout.maxTop)) |
| 36 | const onPress = kit.actions.togglePreSession |
| 37 | |
| 38 | let start = 0 |
| 39 | let filled = 0 |
| 40 | let chars = 0 |
| 41 | |
| 42 | function codeOf(segment: HunkSegment, cut: WindowCut): RenderElement { |
| 43 | const source = Detail.hunkSourceOf(Plan.hunkWindowOf(segment, cut)) |
| 44 | const path = Layout.sanitizeName(segment.path) |
| 45 | chars += source.length |
| 46 | |
| 47 | const isOver = chars > Detail.MAX_BODY_CHARS |
| 48 | |
| 49 | return isOver ? ( |
| 50 | <Text dimColor italic> |
| 51 | … |
| 52 | </Text> |
| 53 | ) : ( |
| 54 | <Code source={source} format="diff" path={path} /> |
| 55 | ) |
| 56 | } |
| 57 | |
| 58 | function elementOf(segment: Segment, cut: WindowCut): RenderElement { |
| 59 | switch (segment.kind) { |
| 60 | case 'rule': |
| 61 | return Sections.divider(kit) |
| 62 | case 'blank': |
| 63 | return <Box height={1} /> |
| 64 | case 'name': |
| 65 | return Sections.nameRow(kit, segment.name) |
| 66 | case 'hunk': |
| 67 | return codeOf(segment, cut) |
| 68 | case 'note': |
| 69 | return ( |
| 70 | <Text dimColor italic wrap="wrap"> |
| 71 | {segment.text} |
| 72 | </Text> |
| 73 | ) |
| 74 | case 'footer': |
| 75 | return ( |
| 76 | <Text dimColor italic> |
| 77 | … diff truncated (exceeded 400 line limit) |
| 78 | </Text> |
| 79 | ) |
| 80 | case 'text': |
| 81 | return Sections.dimNote(kit, segment.text) |
| 82 | case 'toggle': |
| 83 | return Sections.toggleRow(kit, 'presession', { ...segment, onPress }) |
| 84 | case 'legend': |
| 85 | return Sections.legendRow(kit, segment.entry) |
| 86 | } |
| 87 | } |
| 88 | |
| 89 | for (const segment of layout.segments) { |
| 90 | const rows = Plan.segmentRowsOf(segment) |
| 91 | const isShown = start + rows > at && filled < wanted |
| 92 | |
| 93 | if (isShown) { |
| 94 | const skip = Math.max(0, at - start) |
| 95 | |
| 96 | drawn.push(elementOf(segment, { skip, take: wanted - filled })) |
| 97 | filled += rows - skip |
| 98 | } |
| 99 | |
| 100 | start += rows |
| 101 | } |
| 102 | |
| 103 | return drawn |
| 104 | } |