Module: ListScrollable

Included in:
RubyCurses::List, RubyCurses::TabularWidget, RubyCurses::TextArea, RubyCurses::TextView, RubyCurses::Tree
Defined in:
lib/rbcurse/core/include/listscrollable.rb

Overview

Provides the ability to scroll content, typically an array widget that includes may override on_enter_row and on_leave_row Caller should have

row_count()
scrollatrow() typically @height - 2 (unless a header row, then -3)
@current_index (row of current index, starting with 0 usually)
@toprow : set to 0 for starters, top row to be displayed
@pcol (used for horiz scrolling, starts at 0)

Instance Attribute Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#find_offsetObject (readonly)

Returns the value of attribute find_offset.



11
12
13
# File 'lib/rbcurse/core/include/listscrollable.rb', line 11

def find_offset
  @find_offset
end

#find_offset1Object (readonly)

Returns the value of attribute find_offset1.



11
12
13
# File 'lib/rbcurse/core/include/listscrollable.rb', line 11

def find_offset1
  @find_offset1
end

#search_found_ixObject (readonly)

Returns the value of attribute search_found_ix.



11
12
13
# File 'lib/rbcurse/core/include/listscrollable.rb', line 11

def search_found_ix
  @search_found_ix
end

#show_caretObject

2010-01-23 23:06 our own fake insertion point



12
13
14
# File 'lib/rbcurse/core/include/listscrollable.rb', line 12

def show_caret
  @show_caret
end

Instance Method Details

#_convert_index_to_printable_row(index = @current_index) ⇒ Object

actual position to write on window NOTE can return nil, if user scrolls forward or backward



585
586
587
588
589
590
591
# File 'lib/rbcurse/core/include/listscrollable.rb', line 585

def _convert_index_to_printable_row index=@current_index
  r,c = rowcol
  pos = _convert_index_to_visible_row(index)
  return nil unless pos
  pos = r + pos
  return pos
end

#_convert_index_to_visible_row(index = @current_index) ⇒ Object

offset in widget like 0..scrollatrow NOTE can return nil, if user scrolls forward or backward



578
579
580
581
582
# File 'lib/rbcurse/core/include/listscrollable.rb', line 578

def _convert_index_to_visible_row index=@current_index
  pos = index - @toprow
  return nil if pos < 0 || pos > scrollatrow()
  return pos
end

#_find_next(regex = @last_regex, start = @search_found_ix, first_time = false) ⇒ Object

find forwards Using this to start a search or continue search



332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
# File 'lib/rbcurse/core/include/listscrollable.rb', line 332

def _find_next regex=@last_regex, start = @search_found_ix, first_time = false
  #raise "No previous search" if regex.nil?
  warn "No previous search" and return if regex.nil?
  #$log.debug " _find_next #{@search_found_ix} : #{@current_index}"
  extra = 1 # first time search on current line, next time skip current line or else we get stuck.
  extra = 0 if first_time
  start ||= 0
  fend = @list.size-1
  if start != fend
    start += extra unless start == fend # used to be +=1 so we don't get stuck in same row
    @last_regex = regex
    @search_start_ix = start
    regex = Regexp.new(regex, Regexp::IGNORECASE) if @search_case
    start.upto(fend) do |ix| 
      row1 = @list[ix].to_s

      # 2011-09-29 crashing on a character F3 in log file
      # 2013-03-20 - 18:25 187compat
      if row1.respond_to? :encode
        row = row1.encode("ASCII-8BIT", :invalid => :replace, :undef => :replace, :replace => "?")
      else
        row = row1
      end

      m=row.match(regex)
      if !m.nil?
        @find_offset = m.offset(0)[0]
        @find_offset1 = m.offset(0)[1]
        ix += (@_header_adjustment || 0)
        @search_found_ix = ix
        return ix 
      end
    end
  end
  fend = start-1
  start = 0
  if @search_wrap
    start.upto(fend) do |ix| 
      row = @list[ix].to_s
      m=row.match(regex)
      if !m.nil?
        @find_offset = m.offset(0)[0]
        @find_offset1 = m.offset(0)[1]
        ix += (@_header_adjustment || 0)
        @search_found_ix = ix
        return ix 
      end
    end
  end
  return nil
end

#_find_prev(regex = @last_regex, start = @search_found_ix, first_time = false) ⇒ Object

find backwards Using this to start a search or continue search



416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
# File 'lib/rbcurse/core/include/listscrollable.rb', line 416

def _find_prev regex=@last_regex, start = @search_found_ix, first_time = false
  #TODO the firsttime part, see find_next
  #raise "No previous search" if regex.nil?
  warn "No previous search" and return if regex.nil?
  #$log.debug " _find_prev #{@search_found_ix} : #{@current_index}"
  if start != 0
  start -= 1 unless start == 0
  @last_regex = regex
  @search_start_ix = start
  regex = Regexp.new(regex, Regexp::IGNORECASE) if @search_case
  start.downto(0) do |ix| 
    row = @list[ix].to_s
    m=row.match(regex)
    if !m.nil?
      @find_offset = m.offset(0)[0]
      @find_offset1 = m.offset(0)[1]
      ix += (@_header_adjustment || 0)
      @search_found_ix = ix
      return ix 
    end
  end
  end
  fend = start-1
  start = @list.size-1
  if @search_wrap
    start.downto(fend) do |ix| 
      row = @list[ix].to_s
      m=row.match(regex)
      if !m.nil?
        @find_offset = m.offset(0)[0]
        @find_offset1 = m.offset(0)[1]
        ix += (@_header_adjustment || 0)
        @search_found_ix = ix
        return ix 
      end
    end
  end
  return nil
end

#ask_searchObject



278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
# File 'lib/rbcurse/core/include/listscrollable.rb', line 278

def ask_search
  options = ["Search backwards", "case insensitive", "Wrap around"]
  defaults = [@search_direction_prev, @search_case, @search_wrap]
  regex = @last_regex || ""
  # persist search history so one can popup and see
  # How does user know that there is some history here.
  $list_search_history ||= []
  $list_search_history << @last_regex if @last_regex && !$list_search_history.include?(@last_regex)

  mb = MessageBox.new :title => "Search" , :width => 70 do
    fld =  Field.new :label => 'Enter regex to search', :name => "patt", :display_length => 30, 
      :bgcolor => :cyan #, :text => regex
    require 'rbcurse/core/include/rhistory'
    fld.extend(FieldHistory)
    fld.history($list_search_history)
    add fld
    add CheckBox.new :text => options[0], :value => defaults[0], :name => "0"
    add CheckBox.new :text => options[1], :value => defaults[1], :name => "1"
    add CheckBox.new :text => options[2], :value => defaults[2], :name => "2"

    button_type :ok_cancel
  end
  index = mb.run
  return if index != 0
  regex = mb.widget("patt").text || regex # if user enters nothing use existing regex
  regex = @last_regex if regex == ""
  return if regex.nil? || regex == ""
  #$list_search_history << @last_regex if @last_regex
  @search_direction_prev =  mb.widget("0").value
  @search_case = mb.widget("1").value
  @search_wrap = mb.widget("2").value
  if @search_direction_prev == true
    ix = _find_prev regex, @current_index - (@_header_adjustment || 0), true
  else
    ix = _find_next regex, @current_index - (@_header_adjustment || 0), true
  end
  if ix.nil?
    alert("No matching data for: #{regex}")
  else
    set_focus_on(ix)
    set_form_col @find_offset1
    @cell_editor.component.curpos = (@find_offset||0) if @cell_editing_allowed
  end
  @last_regex = regex
end

#bounds_checkObject

please set oldrow before calling this. Store current_index as oldrow before changing. NOTE



82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
# File 'lib/rbcurse/core/include/listscrollable.rb', line 82

def bounds_check
  h = scrollatrow()
  rc = row_count
  @old_toprow = @toprow

  @_header_adjustment ||= 0
  @current_index = 0 if @current_index < 0  # not lt 0
  @current_index = rc-1 if @current_index >= rc && rc>0 # not gt rowcount
  @toprow = rc-h-1 if rc > h && @toprow > rc - h - 1 # toprow shows full page if possible
  # curr has gone below table,  move toprow forward
  if @current_index - @toprow > h
    @toprow = @current_index - h
  elsif @current_index < @toprow
    # curr has gone above table,  move toprow up
    # sometimes current row gets hidden below header line
    @toprow = @current_index - (@_header_adjustment ||0)
    # prev line can make top row -1, however, if we are going back, lets 
    # put it at start of page, so first or second row is not hidden
    @toprow = 0 if @toprow < h
  end
 
  @row_changed = false
  if @oldrow != @current_index
    on_leave_row @oldrow if respond_to? :on_leave_row     # to be defined by widget that has included this
    on_enter_row @current_index   if respond_to? :on_enter_row  # to be defined by widget that has included this
    set_form_row
    @row_changed = true
  end
  #set_form_row # 2011-10-13 

  if @old_toprow != @toprow # only if scrolling has happened should we repaint
    @repaint_required = true #if @old_toprow != @toprow # only if scrolling has happened should we repaint
    @widget_scrolled = true
  end
end

#find_moreObject



323
324
325
326
327
328
329
# File 'lib/rbcurse/core/include/listscrollable.rb', line 323

def find_more
  if @search_direction_prev 
    find_prev
  else
    find_next
  end
end

#find_nextObject



383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
# File 'lib/rbcurse/core/include/listscrollable.rb', line 383

def find_next
  unless @last_regex
    alert("No previous search. Search first.")
    return
  end
    ix = _find_next
    regex = @last_regex 
    if ix.nil?
      alert("No more matching data for: #{regex}")
    else
      set_focus_on(ix) 
      set_form_col @find_offset1
    @cell_editor.component.curpos = (@find_offset||0) if @cell_editing_allowed
    end
end

#find_prevObject



398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
# File 'lib/rbcurse/core/include/listscrollable.rb', line 398

def find_prev
  unless @last_regex
    alert("No previous search. Search first.")
    return
  end
    ix = _find_prev
    regex = @last_regex 
    if ix.nil?
      alert("No previous matching data for: #{regex}")
    else
      set_focus_on(ix)
      set_form_col @find_offset
      @cell_editor.component.curpos = (@find_offset||0) if @cell_editing_allowed
    end
end

#focussed_indexObject Also known as: selected_index

not that saving content_rows is buggy since we add rows.

caution, this now uses winrow not prow for user to know which row is being focussed on



207
208
209
# File 'lib/rbcurse/core/include/listscrollable.rb', line 207

def focussed_index
  @current_index # 2009-01-07 14:35 
end

#forward_char(char = nil) ⇒ Object

goes to next occurence of <char> (or nth occurence) Actually, we can club this with forward_word so no duplication Or call one from the other



498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
# File 'lib/rbcurse/core/include/listscrollable.rb', line 498

def forward_char char=nil
  if char.nil?
    $log.debug " XXX acceptng char"
    ch = @graphic.getchar
    return -1 if ch < 0 or ch > 255 # or 127 ???
    char = ch.chr
  end
  $log.debug " forward_char char:#{char}:"
  $multiplier = 1 if !$multiplier or $multiplier == 0
  line = @current_index
  buff = @list[line].to_s
  pos = @curpos
  $multiplier.times {
    found = false
    while !found
      found = buff.index(char, pos)
      if !found
        line += 1 # unless eof
        buff = @list[line].to_s
        pos = 0
      else
        pos = found + 1
      end
      break if line >= @list.size
      $log.debug " #{found} forward_word: pos #{pos} line #{line} buff: #{buff}"
    end
  }
  @current_index = line
  @curpos = pos
  @buffer = @list[@current_index].to_s
  set_form_row
  set_form_col pos
  @repaint_required = true
end

#forward_wordObject

goes to start of next word (or n words) - vi’s w NOTE: will not work if the list has different data from what is displayed Nothing i can do about it. Also does not work as expected if consecutive spaces FIXME Will not scroll list, if reaches end, jist goes on and vanshes FIXME



462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
# File 'lib/rbcurse/core/include/listscrollable.rb', line 462

def forward_word
  $multiplier = 1 if !$multiplier || $multiplier == 0
  line = @current_index
  buff = @list[line].to_s
  return unless buff
  pos = @curpos || 0 # list does not have curpos
  $multiplier.times {
    #found = buff.index(/[[:punct:][:space:]]+/, pos)
    # 2013-03-04 - 17:35 modified so it skips spaces and puncts
    found = buff.index(/[[:punct:][:space:]]\w/, pos)
    if !found
      # if not found, we've lost a counter
      if line+1 < @list.length
        line += 1
      else
        return
      end
      buff = @list[line].to_s
      pos = 0
    else
      pos = found + 1
    end
    $log.debug " forward_word: pos #{pos} line #{line} buff: #{buff}"
  }
  @current_index = line
  @curpos = pos
  @buffer = @list[@current_index].to_s
  set_form_row
  set_form_col pos
  @repaint_required = true
end

#goto_bottomObject Also known as: goto_end



39
40
41
42
43
44
# File 'lib/rbcurse/core/include/listscrollable.rb', line 39

def goto_bottom
  @oldrow = @current_index
  rc = row_count
  @current_index = rc -1
  bounds_check
end

#goto_last_positionObject

returns cursor to last row (if moving columns in same row, won’t work) Useful after a large move such as 12j, 20 C-n etc, Mapped to ” in textview



198
199
200
201
202
# File 'lib/rbcurse/core/include/listscrollable.rb', line 198

def goto_last_position
  return unless @oldrow
  @current_index = @oldrow
  bounds_check
end

#goto_topObject Also known as: goto_start



46
47
48
49
50
# File 'lib/rbcurse/core/include/listscrollable.rb', line 46

def goto_top
  @oldrow = @current_index
  @current_index = 0
  bounds_check
end

#highlight_focussed_row(type, r = nil, c = nil, acolor = nil) ⇒ Object

highlights the focussed (current) and unfocussed (oldrow)

NOTE: when multiselecting ... it will remove selection
so be careful when calling.


596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
# File 'lib/rbcurse/core/include/listscrollable.rb', line 596

def highlight_focussed_row type, r=nil, c=nil, acolor=nil
  return unless @should_show_focus
  case type
  when :FOCUSSED
    ix = @current_index
    return if is_row_selected ix
    r = _convert_index_to_printable_row() unless r
    attrib = @focussed_attrib || 'bold'

  when :UNFOCUSSED
    return if @oldrow.nil? || @oldrow == @current_index
    ix = @oldrow
    return if is_row_selected ix
    r = _convert_index_to_printable_row(@oldrow) unless r
    return unless r # row is not longer visible
    attrib = @attr
  end
  unless c
    _r, c = rowcol
  end
  # this optimization now overrides any coloring that listbox may have done per row XXX
  acolor ||= get_color $datacolor
  att = get_attrib(attrib) #if @focussed_attrib
  @graphic.mvchgat(y=r, x=c, @width-@internal_width, att , acolor , nil)
end

#install_keysObject



268
269
270
271
272
273
274
275
276
277
# File 'lib/rbcurse/core/include/listscrollable.rb', line 268

def install_keys
=begin
  @KEY_ASK_FIND_FORWARD ||= ?\M-f.getbyte(0)
  @KEY_ASK_FIND_BACKWARD ||= ?\M-F.getbyte(0)
  @KEY_FIND_NEXT ||= ?\M-g.getbyte(0)
  @KEY_FIND_PREV ||= ?\M-G.getbyte(0)
=end
  @KEY_ASK_FIND ||= ?\M-f.getbyte(0)
  @KEY_FIND_MORE ||= ?\M-g.getbyte(0)
end

#is_visible?(index) ⇒ Boolean

Is the given index in the visible area UNTESTED XXX

Returns:

  • (Boolean)


570
571
572
573
574
# File 'lib/rbcurse/core/include/listscrollable.rb', line 570

def is_visible? index
  #(0..scrollatrow()).include? index - @toprow
  j = index - @toprow
  j >= 0 && j <= scrollatrow()
end

#next_match(char) ⇒ Object

finds the next match for the char pressed returning the index If we are only checking first char, then why chomp ? Please note that this is used now by tree, and list can have non-strings, so use to_s



222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
# File 'lib/rbcurse/core/include/listscrollable.rb', line 222

def next_match char
  data = get_content
  row = focussed_index + 1
  row.upto(data.length-1) do |ix|
    #val = data[ix].chomp rescue return  # 2010-01-05 15:28 crashed on trueclass
    val = data[ix].to_s rescue return  # 2010-01-05 15:28 crashed on trueclass
    #if val[0,1] == char #and val != currval
    if val[0,1].casecmp(char) == 0 #AND VAL != CURRval
      return ix
    end
  end
  row = focussed_index - 1
  0.upto(row) do |ix|
    #val = data[ix].chomp
    val = data[ix].to_s
    #if val[0,1] == char #and val != currval
    if val[0,1].casecmp(char) == 0 #and val != currval
      return ix
    end
  end
  return -1
end

#next_row(num = (($multiplier.nil? or $multiplier == 0) ? 1 : $multiplier)) ⇒ Object Also known as: down



26
27
28
29
30
31
32
33
34
35
36
37
# File 'lib/rbcurse/core/include/listscrollable.rb', line 26

def next_row num=(($multiplier.nil? or $multiplier == 0) ? 1 : $multiplier)
  rc = row_count
  # returning unhandled was clever .. when user hits down arrow on last row the focus goes to
  # next field. however, in long lists when user scrolls the sudden jumping to next is very annoying.
  # In combos, if focus was on last row, the combo closed which is not accceptable.
  #return :UNHANDLED if @current_index == rc-1 # EVIL !!!
  return :NO_NEXT_ROW if @current_index == rc-1  # changed 2011-10-5 so process can do something
  @oldrow = @current_index
  @current_index += 1*num if @current_index < rc
  bounds_check
  $multiplier = 0
end

#previous_row(num = (($multiplier.nil? or $multiplier == 0) ? 1 : $multiplier)) ⇒ Object Also known as: up



13
14
15
16
17
18
19
20
21
22
23
24
# File 'lib/rbcurse/core/include/listscrollable.rb', line 13

def previous_row num=(($multiplier.nil? or $multiplier == 0) ? 1 : $multiplier)
  #return :UNHANDLED if @current_index == 0 # EVIL
  return :NO_PREVIOUS_ROW if @current_index == 0 
  @oldrow = @current_index
  # NOTE that putting a multiplier inside, prevents an event from being triggered for each row's
  # on leave and on enter
  num.times { 
    @current_index -= 1 if @current_index > 0
  }
  bounds_check
  $multiplier = 0
end

#sanitize(content) ⇒ Object

takes a block, this way anyone extending this class can just pass a block to do his job This modifies the string



534
535
536
537
538
539
540
541
542
543
544
545
546
547
# File 'lib/rbcurse/core/include/listscrollable.rb', line 534

def sanitize content  #:nodoc:
  if content.is_a? String
    content.chomp!
    # 2013-03-20 - 18:29 187compat
    if content.respond_to? :encode
      content.replace(content.encode("ASCII-8BIT", :invalid => :replace, :undef => :replace, :replace => "?"))
    end
    content.gsub!(/[\t\r\n]/, '  ') # don't display tab, newline
    content.gsub!(/\n/, '  ') # don't display tab, newline
    content.gsub!(/[^[:print:]]/, '')  # don't display non print characters
  else
    content
  end
end

#scroll_backwardObject



52
53
54
55
56
57
58
59
# File 'lib/rbcurse/core/include/listscrollable.rb', line 52

def scroll_backward
  @oldrow = @current_index
  h = scrollatrow()
  m = $multiplier == 0? 1 : $multiplier
  @current_index -= h * m
  bounds_check
  $multiplier = 0
end

#scroll_forwardObject



60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
# File 'lib/rbcurse/core/include/listscrollable.rb', line 60

def scroll_forward
  @oldrow = @current_index
  h = scrollatrow()
  rc = row_count
  m = $multiplier == 0? 1 : $multiplier
  # more rows than box
  if h * m < rc
    # next 2 lines were preventing widget_scrolled from being set to true,
    # so i've modified it slightly as per scroll_down 2011-11-1 
    #@toprow += h+1 #if @current_index+h < rc
    #@current_index = @toprow
    @current_index += h+1
  else
    # fewer rows than box
    @current_index = rc -1
  end
  #@current_index += h+1 #if @current_index+h < rc
  bounds_check
end

#scroll_leftObject



190
191
192
193
194
195
# File 'lib/rbcurse/core/include/listscrollable.rb', line 190

def scroll_left
  hscrollcols = $multiplier > 0 ? $multiplier : @width/2
  @pcol -= hscrollcols if @pcol > 0
  @pcol = 0 if @pcol < 0
  @repaint_required = true
end

#scroll_rightObject



174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
# File 'lib/rbcurse/core/include/listscrollable.rb', line 174

def scroll_right
  $log.debug " inside scroll_right "
  hscrollcols = $multiplier > 0 ? $multiplier : @width/2
  #hscrollcols = $multiplier > 0 ? $multiplier : 1 # for testing out 
  $log.debug " scroll_right  mult:#{$multiplier} , hscrollcols  #{hscrollcols}, pcol #{@pcol} w: #{@width} ll:#{@longest_line} "
  #blen = @buffer.rstrip.length
  blen = @longest_line
  if @pcol + @width < blen 
    @pcol += hscrollcols if @pcol + @width < blen 
  else
    # due to some change somewhere, sometimes width = longest which is not true
    hscrollcols = $multiplier > 0 ? $multiplier : 1
    @pcol += hscrollcols
  end
  @repaint_required = true
end

#selected_itemObject

only to be used in single selection cases as focussed item FIXME. best not to use, as can be implementation dep, use current_index



212
213
214
# File 'lib/rbcurse/core/include/listscrollable.rb', line 212

def selected_item
  get_content()[focussed_index()]
end

#set_focus_on(arow) ⇒ Object

ensures that the given row is focussed new version of older one that was not perfect. 2009-01-17 13:25



260
261
262
263
264
265
266
# File 'lib/rbcurse/core/include/listscrollable.rb', line 260

def set_focus_on arow
  @oldrow = @current_index
  # the next line fixed cursor positioning, but when wraparound then it messed up
  # matching line would get hidden
  @current_index = arow
  bounds_check if @oldrow != @current_index
end

#set_form_rowObject

the cursor should be appropriately positioned



118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
# File 'lib/rbcurse/core/include/listscrollable.rb', line 118

def set_form_row
  r,c = rowcol
  @rows_panned ||= 0
  
  win_row = 0 # 2010-02-07 21:44 now ext offset added by widget

  # when the toprow is set externally then cursor can be mispositioned since 
  # bounds_check has not been called
  if @current_index < @toprow
    # cursor is outside table
    @current_index = @toprow # ??? only if toprow 2010-10-19 12:56 
  end

  row = win_row + r + (@current_index-@toprow) + @rows_panned 
  #$log.debug " #{@name} set_form_row #{row} = ci #{@current_index} + r #{r} + winrow: #{win_row} - tr:#{@toprow} #{@toprow} + rowsp #{@rows_panned} "
  # row should not be < r or greater than r+height TODO FIXME

 
  
  setrowcol row, nil
  #show_caret_func
end

#set_selection_for_char(char) ⇒ Object

2008-12-18 18:03 sets the selection to the next row starting with char



246
247
248
249
250
251
252
253
254
# File 'lib/rbcurse/core/include/listscrollable.rb', line 246

def set_selection_for_char char
  @oldrow = @current_index
  @last_regex = "^#{char}"
  ix = next_match char
  @current_index = ix if ix && ix != -1
  @search_found_ix = @current_index
  bounds_check
  return ix
end

#show_caret_funcObject

paint the cursor ourselves on the widget, rather than rely on getting to the top window with the correct coordinates. I do need to erase cursor too. Can be dicey, but is worth the attempt. This works perfectly, except for when placed in a Tabbedpane since that prints the form with a row offset + of 2 and the widget does not know of the offset. cursor gets it correct since the form has an add_row.



150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
# File 'lib/rbcurse/core/include/listscrollable.rb', line 150

def show_caret_func
    return unless @show_caret
    # trying highlighting cursor 2010-01-23 19:07 TABBEDPANE TRYING
    # TODO take into account rows_panned etc ? I don't think so.
    @rows_panned ||= 0
    r,c = rowcol
    yy = r + @current_index - @toprow - @win_top
    #xx = @form.col # how do we know what value has been set earlier ?
    yy = r + @current_index - @toprow #- @win_top
    yy = @row_offset + @current_index - @toprow #- @win_top
    xx = @col_offset + @curpos || 0
    #yy = @row_offset if yy < @row_offset # sometimes r is 0, we are missing something in tabbedpane+scroll
    #xx = @col_offset if xx < @col_offset
    #xx = 0 if xx < 0

    $log.debug " #{@name} printing CARET at #{yy},#{xx}: fwt:- #{@win_top} r:#{@row} tr:-#{@toprow}+ci:#{@current_index},+r #{r}  "
    if !@oldcursorrow.nil?
        @graphic.mvchgat(y=@oldcursorrow, x=@oldcursorcol, 1, Ncurses::A_NORMAL, $datacolor, NIL)
    end
    @oldcursorrow = yy
    @oldcursorcol = xx
    @graphic.mvchgat(y=yy, x=xx, 1, Ncurses::A_NORMAL, $reversecolor, nil)
    @buffer_modified = true
end

#truncate(content) ⇒ Object

returns only the visible portion of string taking into account display length and horizontal scrolling. MODIFIES STRING NOTE truncate does not take into account left_margin that some widgets might use



551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
# File 'lib/rbcurse/core/include/listscrollable.rb', line 551

def truncate content  #:nodoc:
  #maxlen = @maxlen || @width-2
  _maxlen = @maxlen || @width-@internal_width
  _maxlen = @width-@internal_width if _maxlen > @width-@internal_width
  if !content.nil? 
    if content.length > _maxlen # only show maxlen
      @longest_line = content.length if content.length > @longest_line
      #content = content[@pcol..@pcol+_maxlen-1] 
      content.replace content[@pcol..@pcol+_maxlen-1] 
    else
      # can this be avoided if pcol is 0 XXX
      content.replace content[@pcol..-1] if @pcol > 0
    end
  end
  content
end