...

Source file src/github.com/Azure/go-ansiterm/winterm/scroll_helper.go

Documentation: github.com/Azure/go-ansiterm/winterm

     1  // +build windows
     2  
     3  package winterm
     4  
     5  // effectiveSr gets the current effective scroll region in buffer coordinates
     6  func (h *windowsAnsiEventHandler) effectiveSr(window SMALL_RECT) scrollRegion {
     7  	top := addInRange(window.Top, h.sr.top, window.Top, window.Bottom)
     8  	bottom := addInRange(window.Top, h.sr.bottom, window.Top, window.Bottom)
     9  	if top >= bottom {
    10  		top = window.Top
    11  		bottom = window.Bottom
    12  	}
    13  	return scrollRegion{top: top, bottom: bottom}
    14  }
    15  
    16  func (h *windowsAnsiEventHandler) scrollUp(param int) error {
    17  	info, err := GetConsoleScreenBufferInfo(h.fd)
    18  	if err != nil {
    19  		return err
    20  	}
    21  
    22  	sr := h.effectiveSr(info.Window)
    23  	return h.scroll(param, sr, info)
    24  }
    25  
    26  func (h *windowsAnsiEventHandler) scrollDown(param int) error {
    27  	return h.scrollUp(-param)
    28  }
    29  
    30  func (h *windowsAnsiEventHandler) deleteLines(param int) error {
    31  	info, err := GetConsoleScreenBufferInfo(h.fd)
    32  	if err != nil {
    33  		return err
    34  	}
    35  
    36  	start := info.CursorPosition.Y
    37  	sr := h.effectiveSr(info.Window)
    38  	// Lines cannot be inserted or deleted outside the scrolling region.
    39  	if start >= sr.top && start <= sr.bottom {
    40  		sr.top = start
    41  		return h.scroll(param, sr, info)
    42  	} else {
    43  		return nil
    44  	}
    45  }
    46  
    47  func (h *windowsAnsiEventHandler) insertLines(param int) error {
    48  	return h.deleteLines(-param)
    49  }
    50  
    51  // scroll scrolls the provided scroll region by param lines. The scroll region is in buffer coordinates.
    52  func (h *windowsAnsiEventHandler) scroll(param int, sr scrollRegion, info *CONSOLE_SCREEN_BUFFER_INFO) error {
    53  	h.logf("scroll: scrollTop: %d, scrollBottom: %d", sr.top, sr.bottom)
    54  	h.logf("scroll: windowTop: %d, windowBottom: %d", info.Window.Top, info.Window.Bottom)
    55  
    56  	// Copy from and clip to the scroll region (full buffer width)
    57  	scrollRect := SMALL_RECT{
    58  		Top:    sr.top,
    59  		Bottom: sr.bottom,
    60  		Left:   0,
    61  		Right:  info.Size.X - 1,
    62  	}
    63  
    64  	// Origin to which area should be copied
    65  	destOrigin := COORD{
    66  		X: 0,
    67  		Y: sr.top - int16(param),
    68  	}
    69  
    70  	char := CHAR_INFO{
    71  		UnicodeChar: ' ',
    72  		Attributes:  h.attributes,
    73  	}
    74  
    75  	if err := ScrollConsoleScreenBuffer(h.fd, scrollRect, scrollRect, destOrigin, char); err != nil {
    76  		return err
    77  	}
    78  	return nil
    79  }
    80  
    81  func (h *windowsAnsiEventHandler) deleteCharacters(param int) error {
    82  	info, err := GetConsoleScreenBufferInfo(h.fd)
    83  	if err != nil {
    84  		return err
    85  	}
    86  	return h.scrollLine(param, info.CursorPosition, info)
    87  }
    88  
    89  func (h *windowsAnsiEventHandler) insertCharacters(param int) error {
    90  	return h.deleteCharacters(-param)
    91  }
    92  
    93  // scrollLine scrolls a line horizontally starting at the provided position by a number of columns.
    94  func (h *windowsAnsiEventHandler) scrollLine(columns int, position COORD, info *CONSOLE_SCREEN_BUFFER_INFO) error {
    95  	// Copy from and clip to the scroll region (full buffer width)
    96  	scrollRect := SMALL_RECT{
    97  		Top:    position.Y,
    98  		Bottom: position.Y,
    99  		Left:   position.X,
   100  		Right:  info.Size.X - 1,
   101  	}
   102  
   103  	// Origin to which area should be copied
   104  	destOrigin := COORD{
   105  		X: position.X - int16(columns),
   106  		Y: position.Y,
   107  	}
   108  
   109  	char := CHAR_INFO{
   110  		UnicodeChar: ' ',
   111  		Attributes:  h.attributes,
   112  	}
   113  
   114  	if err := ScrollConsoleScreenBuffer(h.fd, scrollRect, scrollRect, destOrigin, char); err != nil {
   115  		return err
   116  	}
   117  	return nil
   118  }
   119  

View as plain text