From b0bc7c3d996d25c9fefdfbcba3ca19fa46ad199f Mon Sep 17 00:00:00 2001
From: Jacob Richman <jacob314@gmail.com>
Date: Thu, 19 Jun 2025 20:17:23 +0000
Subject: Fix flicker issues by ensuring all actively changing content fits in
 the viewport (#1217)

---
 .../src/ui/components/DetailedMessagesDisplay.tsx  | 75 ++++++++++++----------
 1 file changed, 41 insertions(+), 34 deletions(-)

(limited to 'packages/cli/src/ui/components/DetailedMessagesDisplay.tsx')

diff --git a/packages/cli/src/ui/components/DetailedMessagesDisplay.tsx b/packages/cli/src/ui/components/DetailedMessagesDisplay.tsx
index c2ecb803..0c5366cd 100644
--- a/packages/cli/src/ui/components/DetailedMessagesDisplay.tsx
+++ b/packages/cli/src/ui/components/DetailedMessagesDisplay.tsx
@@ -8,20 +8,24 @@ import React from 'react';
 import { Box, Text } from 'ink';
 import { Colors } from '../colors.js';
 import { ConsoleMessageItem } from '../types.js';
+import { MaxSizedBox } from './shared/MaxSizedBox.js';
 
 interface DetailedMessagesDisplayProps {
   messages: ConsoleMessageItem[];
+  maxHeight: number | undefined;
+  width: number;
   // debugMode is not needed here if App.tsx filters debug messages before passing them.
   // If DetailedMessagesDisplay should handle filtering, add debugMode prop.
 }
 
 export const DetailedMessagesDisplay: React.FC<
   DetailedMessagesDisplayProps
-> = ({ messages }) => {
+> = ({ messages, maxHeight, width }) => {
   if (messages.length === 0) {
     return null; // Don't render anything if there are no messages
   }
 
+  const borderAndPadding = 4;
   return (
     <Box
       flexDirection="column"
@@ -29,47 +33,50 @@ export const DetailedMessagesDisplay: React.FC<
       borderStyle="round"
       borderColor={Colors.Gray}
       paddingX={1}
+      width={width}
     >
       <Box marginBottom={1}>
         <Text bold color={Colors.Foreground}>
           Debug Console <Text color={Colors.Gray}>(ctrl+O to close)</Text>
         </Text>
       </Box>
-      {messages.map((msg, index) => {
-        let textColor = Colors.Foreground;
-        let icon = '\u2139'; // Information source (ℹ)
+      <MaxSizedBox maxHeight={maxHeight} maxWidth={width - borderAndPadding}>
+        {messages.map((msg, index) => {
+          let textColor = Colors.Foreground;
+          let icon = '\u2139'; // Information source (ℹ)
 
-        switch (msg.type) {
-          case 'warn':
-            textColor = Colors.AccentYellow;
-            icon = '\u26A0'; // Warning sign (⚠)
-            break;
-          case 'error':
-            textColor = Colors.AccentRed;
-            icon = '\u2716'; // Heavy multiplication x (✖)
-            break;
-          case 'debug':
-            textColor = Colors.Gray; // Or Colors.Gray
-            icon = '\u1F50D'; // Left-pointing magnifying glass (????)
-            break;
-          case 'log':
-          default:
-            // Default textColor and icon are already set
-            break;
-        }
+          switch (msg.type) {
+            case 'warn':
+              textColor = Colors.AccentYellow;
+              icon = '\u26A0'; // Warning sign (⚠)
+              break;
+            case 'error':
+              textColor = Colors.AccentRed;
+              icon = '\u2716'; // Heavy multiplication x (✖)
+              break;
+            case 'debug':
+              textColor = Colors.Gray; // Or Colors.Gray
+              icon = '\u1F50D'; // Left-pointing magnifying glass (????)
+              break;
+            case 'log':
+            default:
+              // Default textColor and icon are already set
+              break;
+          }
 
-        return (
-          <Box key={index} flexDirection="row">
-            <Text color={textColor}>{icon} </Text>
-            <Text color={textColor} wrap="wrap">
-              {msg.content}
-              {msg.count && msg.count > 1 && (
-                <Text color={Colors.Gray}> (x{msg.count})</Text>
-              )}
-            </Text>
-          </Box>
-        );
-      })}
+          return (
+            <Box key={index} flexDirection="row">
+              <Text color={textColor}>{icon} </Text>
+              <Text color={textColor} wrap="wrap">
+                {msg.content}
+                {msg.count && msg.count > 1 && (
+                  <Text color={Colors.Gray}> (x{msg.count})</Text>
+                )}
+              </Text>
+            </Box>
+          );
+        })}
+      </MaxSizedBox>
     </Box>
   );
 };
-- 
cgit v1.2.3

