github.com/inspektor-gadget/inspektor-gadget@v0.28.1/pkg/columns/ellipsis/ellipsis.go (about)

     1  // Copyright 2022 The Inspektor Gadget authors
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package ellipsis
    16  
    17  type EllipsisType int
    18  
    19  const (
    20  	None   EllipsisType = iota // None simply cuts the text if it is too long
    21  	End                        // End cuts an overflowing string one character before reaching the maximum width and adds an ellipsis ("…").
    22  	Start                      // Start lets the overflowing string start with an ellipsis ("…") followed by the last X characters, where X is the maximum length - 1.
    23  	Middle                     // Middle uses the first and last characters of an overflowing string, merging them in the middle with an ellipsis ("…").
    24  )
    25  
    26  const ellipsisRune = rune('…')
    27  
    28  func (et EllipsisType) String() string {
    29  	switch et {
    30  	default:
    31  		fallthrough
    32  	case None:
    33  		return "None"
    34  	case End:
    35  		return "End"
    36  	case Start:
    37  		return "Start"
    38  	case Middle:
    39  		return "Middle"
    40  	}
    41  }
    42  
    43  func ShortenString(str string, maxLength int, ellipsisType EllipsisType) string {
    44  	return string(Shorten([]rune(str), maxLength, ellipsisType))
    45  }
    46  
    47  func Shorten(rs []rune, maxLength int, ellipsisType EllipsisType) []rune {
    48  	if maxLength <= 0 {
    49  		return []rune{}
    50  	}
    51  
    52  	slen := len(rs)
    53  
    54  	if slen <= maxLength {
    55  		return rs
    56  	}
    57  
    58  	if maxLength <= 1 && ellipsisType != None {
    59  		return []rune{ellipsisRune}
    60  	}
    61  
    62  	switch ellipsisType {
    63  	default:
    64  		fallthrough
    65  	case None:
    66  		return rs[:maxLength]
    67  	case Start:
    68  		return append([]rune{ellipsisRune}, rs[slen-maxLength+1:]...)
    69  	case End:
    70  		return append(rs[:maxLength-1], ellipsisRune)
    71  	case Middle:
    72  		mid := maxLength / 2
    73  		end := mid
    74  		if maxLength%2 == 0 {
    75  			end -= 1
    76  		}
    77  		return append(append(rs[:mid], ellipsisRune), rs[slen-end:]...)
    78  	}
    79  }