File Coverage

blib/lib/Term/Choose/LineFold/PP.pm
Criterion Covered Total %
statement 52 62 83.8
branch 21 28 75.0
condition 11 12 91.6
subroutine 9 9 100.0
pod 0 4 0.0
total 93 115 80.8


line stmt bran cond sub pod time code
1             package Term::Choose::LineFold::PP;
2              
3 5     5   235508 use warnings;
  5         9  
  5         477  
4 5     5   28 use strict;
  5         10  
  5         154  
5 5     5   126 use 5.10.1;
  5         20  
6              
7             our $VERSION = '1.780';
8              
9 5     5   33 use Exporter qw( import );
  5         35  
  5         1014  
10              
11             our @EXPORT_OK = qw( char_width print_columns cut_to_printwidth adjust_to_printwidth );
12              
13             BEGIN {
14 5 50   5   41 if ( exists $ENV{TC_AMBIGUOUS_WIDTH_IS_WIDE} ) { # 24.03.2025
15 0 0       0 if ( $ENV{TC_AMBIGUOUS_WIDTH_IS_WIDE} ) {
16 0         0 require Term::Choose::LineFold::PP::CharWidthAmbiguousWide;
17 0         0 Term::Choose::LineFold::PP::CharWidthAmbiguousWide->import( 'table_char_width' );
18             }
19             else {
20 0         0 require Term::Choose::LineFold::PP::CharWidthDefault;
21 0         0 Term::Choose::LineFold::PP::CharWidthDefault->import( 'table_char_width' );
22             }
23             } #
24             else { #
25 5 50       138 if ( $ENV{TC_AMBIGUOUS_WIDE} ) { #
26 0         0 require Term::Choose::LineFold::PP::CharWidthAmbiguousWide; #
27 0         0 Term::Choose::LineFold::PP::CharWidthAmbiguousWide->import( 'table_char_width' ); #
28             } #
29             else { #
30 5         3279 require Term::Choose::LineFold::PP::CharWidthDefault; #
31 5         3884 Term::Choose::LineFold::PP::CharWidthDefault->import( 'table_char_width' ); #
32             } #
33             } #
34             }
35              
36              
37             my $table = table_char_width();
38              
39             my $cache = {};
40              
41              
42             sub char_width {
43             #my $c = $_[0];
44 80     80 0 214268 my $min = 0;
45 80         120 my $mid;
46 80         102 my $max = $#$table;
47 80 100 66     259 if ( $_[0] < $table->[0][0] || $_[0] > $table->[$max][1] ) {
48 30         84 return 1;
49             }
50 50         81 while ( $max >= $min ) {
51 449         563 $mid = int( ( $min + $max ) / 2 );
52 449 100       770 if ( $_[0] > $table->[$mid][1] ) {
    100          
53 205         295 $min = $mid + 1;
54             }
55             elsif ( $_[0] < $table->[$mid][0] ) {
56 194         273 $max = $mid - 1;
57             }
58             else {
59 50         129 return $table->[$mid][2];
60             }
61             }
62 0         0 return 1;
63             }
64              
65              
66             sub print_columns {
67             #my $str = $_[0];
68 12     12 0 2859 my $width = 0;
69 12         16 my $c;
70 12         36 for my $i ( 0 .. ( length( $_[0] ) - 1 ) ) {
71 68         99 $c = ord substr $_[0], $i, 1;
72 68   100     159 $width += ( $cache->{$c} //= char_width( $c ) );
73             }
74 12         21 return $width;
75             }
76              
77              
78             sub cut_to_printwidth {
79             #my ( $str, $avail_width ) = @_;
80 20     20 0 224030 my $str_w = 0;
81 20         39 my $c;
82 20         82 for my $i ( 0 .. ( length( $_[0] ) - 1 ) ) {
83 66         158 $c = ord substr $_[0], $i, 1;
84 66 100 100     1187 if ( ( $str_w += ( $cache->{$c} //= char_width( $c ) ) ) > $_[1] ) {
85 20 100       64 if ( ( $str_w - $cache->{$c} ) < $_[1] ) {
86 6 100       30 return substr( $_[0], 0, $i ) . ' ', substr( $_[0], $i ) if wantarray;
87 3         15 return substr( $_[0], 0, $i ) . ' ';
88             }
89 14 100       60 return substr( $_[0], 0, $i ), substr( $_[0], $i ) if wantarray;
90 7         29 return substr( $_[0], 0, $i );
91             }
92             }
93 0 0       0 return $_[0], '' if wantarray;
94 0         0 return $_[0];
95             }
96              
97              
98             sub adjust_to_printwidth {
99             # my ( $str, $width ) = @_;
100 17     17 0 18962 my $str_w = 0;
101 17         50 my $c;
102 17         79 for my $i ( 0 .. ( length( $_[0] ) - 1 ) ) {
103 63         145 $c = ord substr $_[0], $i, 1;
104 63 100 100     268 if ( ( $str_w += ( $cache->{$c} //= char_width( $c ) ) ) > $_[1] ) {
105 10 100       32 if ( ( $str_w - $cache->{$c} ) < $_[1] ) {
106 3         17 return substr( $_[0], 0, $i ) . ' ';
107             }
108 7         31 return substr( $_[0], 0, $i );
109             }
110             }
111 7 50       86 return $_[0] if $str_w == $_[1];
112 7         41 return $_[0] . ' ' x ( $_[1] - $str_w );
113             }
114              
115              
116              
117             1;
118              
119             __END__