File Coverage

lib/Kephra/App/EditPanel/Margin.pm
Criterion Covered Total %
statement 6 164 3.6
branch 0 52 0.0
condition 0 27 0.0
subroutine 2 43 4.6
pod 0 34 0.0
total 8 320 2.5


line stmt bran cond sub pod time code
1             package Kephra::App::EditPanel::Margin;
2             our $VERSION = '0.13';
3            
4 1     1   1223 use strict;
  1         3  
  1         37  
5 1     1   7 use warnings;
  1         3  
  1         2631  
6            
7             my $mouse_y_pos;
8             sub _ep_ref {
9 0 0   0     Kephra::App::EditPanel::is($_[0]) ? $_[0] : Kephra::App::EditPanel::_ref()
10             }
11 0     0     sub _all_ref { Kephra::Document::Data::get_all_ep() }
12 0     0     sub _edit_config { Kephra::App::EditPanel::_config() }
13 0     0     sub _config { _edit_config()->{margin}}
14 0     0     sub _line_config { _config()->{linenumber}}
15 0     0     sub _fold_config { _config()->{fold} }
16 0     0     sub _marker_config { _config()->{marker} }
17             sub width {
18 0     0 0   my $ep = _ep_ref(shift);
19 0           my $width;
20 0           $width += $ep->GetMarginWidth($_) for 0..2;
21 0           $width
22             }
23             sub in_nr {
24 0     0 0   my $x = shift;
25 0           my $ep = _ep_ref(shift);
26 0           my $border;
27 0           for my $margin (0..2){
28 0           $border += $ep->GetMarginWidth($margin);
29 0 0         return $margin if $x <= $border;
30             }
31 0           return -1;
32             }
33            
34             sub apply_settings_here {# eval view settings for the margin of this edit panel obj
35 0     0 0   my $ep = _ep_ref(shift);
36             # defining the 3 margins
37 0           $ep->SetMarginType( 0, &Wx::wxSTC_MARGIN_SYMBOL );
38 0           $ep->SetMarginType( 1, &Wx::wxSTC_MARGIN_NUMBER );
39 0           $ep->SetMarginType( 2, &Wx::wxSTC_MARGIN_SYMBOL );
40 0           $ep->SetMarginMask( 0, 0x01FFFFFF );
41 0           $ep->SetMarginMask( 1, 0 );
42 0           $ep->SetMarginMask( 2, &Wx::wxSTC_MASK_FOLDERS );
43 0           $ep->SetMarginSensitive( 0, 1 );
44 0           $ep->SetMarginSensitive( 1, 1 );
45 0           $ep->SetMarginSensitive( 2, 1 );
46            
47             # setting folding markers
48 0           my $color = \&Kephra::Config::color;
49 0           my $f = &$color( _fold_config()->{fore_color} );
50 0           my $b = &$color( _fold_config()->{back_color} );
51 0 0         if (_fold_config()->{style} eq 'arrows') {
52 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDER, &Wx::wxSTC_MARK_ARROW, $b,$f);
53 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEREND, &Wx::wxSTC_MARK_ARROW, $b,$f);
54 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEROPEN, &Wx::wxSTC_MARK_ARROWDOWN,$b,$f);
55 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEROPENMID,&Wx::wxSTC_MARK_ARROWDOWN,$b,$f);
56 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERMIDTAIL,&Wx::wxSTC_MARK_EMPTY, $b,$f);
57 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERTAIL, &Wx::wxSTC_MARK_EMPTY, $b,$f);
58 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERSUB, &Wx::wxSTC_MARK_EMPTY, $b,$f);
59             }
60             else {
61 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDER, &Wx::wxSTC_MARK_BOXPLUS, $b,$f);
62 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEREND, &Wx::wxSTC_MARK_BOXPLUSCONNECTED,$b,$f);
63 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEROPEN, &Wx::wxSTC_MARK_BOXMINUS, $b,$f);
64 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDEROPENMID,&Wx::wxSTC_MARK_BOXMINUSCONNECTED,$b,$f);
65 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERMIDTAIL,&Wx::wxSTC_MARK_TCORNER, $b,$f);
66 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERTAIL, &Wx::wxSTC_MARK_LCORNER, $b,$f);
67 0           $ep->MarkerDefine(&Wx::wxSTC_MARKNUM_FOLDERSUB, &Wx::wxSTC_MARK_VLINE, $b,$f);
68             }
69 0 0         $ep->SetFoldFlags(16) if _fold_config()->{flag_line};
70            
71 0           show_marker_here($ep);
72 0           Kephra::Document::Data::set_attribute('margin_linemax', 0);
73             #apply_line_number_width_here($ep);
74 0           apply_line_number_color_here($ep);
75 0           show_fold_here($ep);
76 0           apply_text_width_here($ep);
77             }
78             sub refresh_changeable_settings {
79 0     0 0   my $ep = _ep_ref(shift);
80 0           apply_line_number_color_here($ep);
81 0           apply_fold_flag_color_here($ep);
82             }
83 0     0 0   sub get_contextmenu_visibility { _edit_config()->{contextmenu}{margin} }
84 0     0 0   sub switch_contextmenu_visibility { _edit_config()->{contextmenu}{margin} ^= 1 }
85             #
86             # deciding what to do when clicked on edit panel margin
87             #
88             sub on_left_click {
89 0     0 0   my ($ep, $event, $nr) = @_;
90 0 0         if ($nr < 2) {Kephra::Edit::Marker::toggle_marker_here(@_) }
  0 0          
  0            
91             elsif ($nr == 2) {Kephra::App::EditPanel::Fold::toggle_here(@_) }
92             }
93             sub on_middle_click {
94 0     0 0   my ($ep, $event, $nr) = @_;
95 0 0         Kephra::Edit::Marker::toggle_bookmark_here(@_) if $nr < 2;
96 0 0         Kephra::App::EditPanel::Fold::toggle_recursively($ep, $event) if $nr == 2;
97             }
98             sub on_right_click {
99 0     0 0   my ($ep, $event, $nr) = @_;
100 0           my ($x, $y) = ($event->GetX, $event->GetY);
101 0 0 0       if ($nr > -1 and $nr < 2 and get_contextmenu_visibility() ){
    0 0        
102 0           $mouse_y_pos = $event->GetY;
103 0           $ep->PopupMenu(
104             Kephra::App::ContextMenu::get
105             (_edit_config()->{contextmenu}{ID_margin} ), $x, $y);
106 0           undef $mouse_y_pos;
107             }
108             elsif ($nr == 2) {
109 0 0         $event->LeftIsDown
110             ? Kephra::App::EditPanel::Fold::toggle_all()
111             : Kephra::App::EditPanel::Fold::toggle_level($ep, $event);
112             }
113             }
114            
115             sub clicked_on_line {
116 0     0 0   my $event = shift;
117 0 0 0       return -1 unless defined $mouse_y_pos or ref $event eq 'Wx::MouseEvent';
118 0           my $ep = _ep_ref();
119 0           my $x = width($ep) + 5;
120             # $mouse_y_pos is saved position where context menu poped so we can fold there
121 0 0         my $y = defined $mouse_y_pos ? $mouse_y_pos : $event->GetY;
122 0           my $max_y = $ep->GetSize->GetHeight;
123 0           my $pos = $ep->PositionFromPointClose($x, $y);
124 0   0       while ($pos < 0 and $y+10 < $max_y) {
125 0           $pos = $ep->PositionFromPointClose($x, $y += 10);
126             }
127 0           return $ep->LineFromPosition($pos);
128             }
129             #
130             # line number margin
131             #
132 0     0 0   sub line_number_visible{ _line_config->{visible} }
133             sub switch_line_number {
134 0     0 0   _line_config->{visible} ^= 1;
135 0           apply_line_number_width()
136             }
137 0     0 0   sub apply_line_number_width { apply_line_number_width_here($_) for @{_all_ref()} }
  0            
138             sub apply_line_number_width_here {
139 0     0 0   my $ep = _ep_ref(shift);
140 0           my $doc_nr = shift;
141 0 0         $doc_nr = Kephra::Document::Data::nr_from_ep($ep) unless defined $doc_nr;
142 0           my $config = _line_config();
143 0           my $char_width = Kephra::Document::Data::get_attribute('line_nr_margin_width', $doc_nr);
144 0 0 0       if (not defined $char_width or not $char_width) {
145 0           $char_width = needed_line_number_width($ep);
146 0           Kephra::Document::Data::set_attribute
147             ('line_nr_margin_width', $char_width, $doc_nr);
148             }
149 0 0         my $px_width = $config->{visible}
150             ? $char_width * _edit_config()->{font}{size}
151             : 0;
152 0           $ep->SetMarginWidth( 1, $px_width );
153 0 0 0       if ($config->{autosize} and $config->{visible}) {
154 0           Kephra::EventTable::add_call ('document.text.change',
155             'autosize_line_number', \&line_number_autosize_update);
156             } else {
157 0           Kephra::EventTable::del_call
158             ('document.text.change', 'autosize_line_number');
159             }
160             }
161             sub set_line_number_width_here {
162 0     0 0   my $width = shift;
163 0 0         my $doc_nr = shift or Kephra::Document::Data::current_nr();
164 0           my $config = _line_config();
165 0           Kephra::Document::Data::set_attribute('line_nr_margin_width', $width, $doc_nr);
166 0           Kephra::Document::Data::set_attribute('margin_linemax', 10 ** $width - 1, $doc_nr);
167 0           apply_line_number_width_here( Kephra::Document::Data::_ep($doc_nr) );
168             }
169             sub needed_line_number_width {
170 0     0 0   my $width = length _ep_ref(shift)->GetLineCount;
171 0           my $min = _line_config()->{min_width};
172 0 0 0       $width = $min if defined $min and $min and $min > $width;
      0        
173 0           return $width;
174             }
175             sub autosize_line_number {
176 0     0 0   my $ep = _ep_ref(shift);
177 0           my $doc_nr = shift;
178 0 0         $doc_nr = Kephra::Document::Data::nr_from_ep($ep) unless defined $doc_nr;
179 0           my $config = _line_config();
180 0 0         return unless _line_config()->{autosize};
181 0           my $need = needed_line_number_width($ep);
182 0           my $is = Kephra::Document::Data::get_attribute('line_nr_margin_width', $doc_nr);
183 0 0 0       set_line_number_width_here($need, $doc_nr) if not defined $is or $need > $is;
184             }
185            
186             sub line_number_autosize_update {
187 0     0 0   my $line_max = Kephra::Document::Data::get_attribute('margin_linemax');
188 0           my $ep = _ep_ref();
189 0 0         autosize_line_number($ep) if $ep->GetLineCount > $line_max;
190             }
191            
192 0     0 0   sub apply_line_number_color { apply_line_number_color_here($_) for @{_all_ref()} }
  0            
193             sub apply_line_number_color_here {
194 0     0 0   my $ep = _ep_ref(shift);
195 0           my $config = _line_config();
196 0           my $color = \&Kephra::Config::color;
197 0           $ep->StyleSetForeground(&Wx::wxSTC_STYLE_LINENUMBER,&$color($config->{fore_color}));
198 0           $ep->StyleSetBackground(&Wx::wxSTC_STYLE_LINENUMBER,&$color($config->{back_color}));
199             }
200            
201            
202             #
203             # marker margin
204             #
205 0     0 0   sub marker_visible { _marker_config->{visible} }
206 0     0 0   sub show_marker { show_marker_here($_) for @{_all_ref()} }
  0            
207             sub show_marker_here {
208 0     0 0   my $ep = _ep_ref(shift);
209 0 0         marker_visible()
210             ? $ep->SetMarginWidth(0, 16)
211             : $ep->SetMarginWidth(0, 0);
212             }
213             sub switch_marker {
214 0     0 0   _marker_config->{visible} ^= 1;
215 0           show_marker();
216             }
217            
218            
219             #
220             # fold margin
221             #
222 0     0 0   sub fold_visible { _fold_config()->{visible} }
223 0     0 0   sub show_fold { show_fold_here($_) for @{_all_ref()} }
  0            
224             sub show_fold_here {
225 0     0 0   my $ep = _ep_ref(shift);
226 0           my $visible = fold_visible();
227 0 0         my $width = $visible ? 16 : 0;
228 0           $ep->SetProperty('fold' => $visible);
229 0           $ep->SetMarginWidth( 2, $width );
230 0 0         Kephra::App::EditPanel::Fold::unfold_all() unless $visible;
231             }
232             sub switch_fold {
233 0     0 0   _fold_config()->{visible} ^= 1;
234 0           show_fold();
235             }
236 0     0 0   sub apply_fold_flag_color { apply_text_width_here($_) for @{_all_ref()}; }
  0            
237             sub apply_fold_flag_color_here {
238 0     0 0   my $ep = _ep_ref(shift);
239 0           my $color = Kephra::Config::color( _fold_config()->{fore_color} );
240 0           $ep->StyleSetForeground(&Wx::wxSTC_STYLE_DEFAULT, $color);
241             }
242            
243             #
244             # extra text margin
245             #
246 0     0 0   sub get_text_width { _config->{text} }
247             sub set_text_width {
248 0     0 0   _config->{text} = shift;
249 0           apply_text_width();
250             }
251 0     0 0   sub apply_text_width { apply_text_width_here($_) for @{_all_ref()} }
  0            
252             sub apply_text_width_here {
253 0     0 0   my $ep = _ep_ref(shift);
254 0           my $width = get_text_width();
255 0           $ep->SetMargins( $width, $width );
256             }
257            
258             1;
259             #wxSTC_MARK_MINUS wxSTC_MARK_PLUS wxSTC_MARK_CIRCLE wxSTC_MARK_SHORTARROW
260             #wxSTC_FOLDFLAG_LINEBEFORE_CONTRACTED
261            
262             =head1 NAME
263            
264             Kephra::App::EditPanel::Margin - managing margin visuals for marker, linenumber, folding & extra space
265            
266             =head1 DESCRIPTION
267            
268             =cut