diakonos 0.8.4 → 0.8.5

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,7 +1,7 @@
1
1
  module Diakonos
2
2
 
3
3
  class Buffer
4
- attr_reader :name, :modified, :original_language, :changing_selection, :read_only,
4
+ attr_reader :name, :key, :modified, :original_language, :changing_selection, :read_only,
5
5
  :last_col, :last_row, :tab_size, :last_screen_x, :last_screen_y, :last_screen_col
6
6
  attr_writer :desired_column, :read_only
7
7
 
@@ -29,9 +29,10 @@ class Buffer
29
29
  DONT_STRIP_LINE = false
30
30
 
31
31
  # Set name to nil to create a buffer that is not associated with a file.
32
- def initialize( diakonos, name, read_only = false )
32
+ def initialize( diakonos, name, key, read_only = false )
33
33
  @diakonos = diakonos
34
34
  @name = name
35
+ @key = key
35
36
  @modified = false
36
37
  @last_modification_check = Time.now
37
38
 
@@ -126,7 +127,8 @@ class Buffer
126
127
  @closers = @diakonos.closers[ @language ] || Hash.new
127
128
  @auto_indent = @settings[ "lang.#{@language}.indent.auto" ]
128
129
  @indent_size = ( @settings[ "lang.#{@language}.indent.size" ] or 4 )
129
- @indent_roundup = ( @settings[ "lang.#{@language}.indent.roundup" ] or true )
130
+ @indent_roundup = @settings[ "lang.#{@language}.indent.roundup" ].nil? ? true : @settings[ "lang.#{@language}.indent.roundup" ]
131
+ @indent_closers = @settings[ "lang.#{@language}.indent.closers" ].nil? ? true : @settings[ "lang.#{@language}.indent.closers" ]
130
132
  @default_formatting = ( @settings[ "lang.#{@language}.format.default" ] or Curses::A_NORMAL )
131
133
  @selection_formatting = ( @settings[ "lang.#{@language}.format.selection" ] or Curses::A_REVERSE )
132
134
  @indent_ignore_charset = ( @settings[ "lang.#{@language}.indent.ignore.charset" ] or "" )
@@ -139,8 +141,8 @@ class Buffer
139
141
  end
140
142
 
141
143
  def == (other)
142
- return false if other == nil
143
- return ( name == other.name )
144
+ return false if other.nil?
145
+ key == other.key
144
146
  end
145
147
 
146
148
  def length
@@ -709,16 +711,22 @@ class Buffer
709
711
  end
710
712
 
711
713
  def close_code
712
- line = @lines[ @last_row ]
713
- @closers.each_value do |h|
714
- h[ :regexp ] =~ line
715
- lm = Regexp.last_match
716
- if lm
717
- insertString h[ :closer ].call( lm ).to_s
718
- else
719
- @diakonos.log h[ :regexp ].inspect + " does not match '#{line}'"
720
- end
714
+ line = @lines[ @last_row ]
715
+ @closers.each_value do |h|
716
+ h[ :regexp ] =~ line
717
+ lm = Regexp.last_match
718
+ if lm
719
+ str = h[ :closer ].call( lm ).to_s
720
+ r, c = @last_row, @last_col
721
+ paste str, @indent_closers
722
+ cursorTo r, c
723
+ if /%_/ === str
724
+ find( [ /%_/ ], :down, '', CHOICE_YES_AND_STOP )
725
+ end
726
+ else
727
+ @diakonos.log h[ :regexp ].inspect + " does not match '#{line}'"
721
728
  end
729
+ end
722
730
  end
723
731
 
724
732
  def collapseWhitespace
@@ -1053,6 +1061,31 @@ class Buffer
1053
1061
  end
1054
1062
  cursorTo( row, col, DO_DISPLAY )
1055
1063
  end
1064
+
1065
+ def cursorToEOL
1066
+ y = @win_main.cury
1067
+ end_col = lineAt( y ).length
1068
+ last_char_col = lineAt( y ).rstrip.length
1069
+ case @settings[ 'eol_behaviour' ]
1070
+ when EOL_END
1071
+ col = end_col
1072
+ when EOL_LAST_CHAR
1073
+ col = last_char_col
1074
+ when EOL_ALT_LAST_CHAR
1075
+ if @last_col == last_char_col
1076
+ col = end_col
1077
+ else
1078
+ col = last_char_col
1079
+ end
1080
+ else
1081
+ if @last_col == end_col
1082
+ col = last_char_col
1083
+ else
1084
+ col = end_col
1085
+ end
1086
+ end
1087
+ cursorTo( @last_row, col, DO_DISPLAY )
1088
+ end
1056
1089
 
1057
1090
  # Top of view
1058
1091
  def cursorToTOV
@@ -1193,29 +1226,27 @@ class Buffer
1193
1226
  end
1194
1227
 
1195
1228
  def copySelection
1196
- return selected_text
1229
+ selected_text
1197
1230
  end
1198
1231
  def selected_text
1199
- selection = selection_mark
1200
- if selection == nil
1201
- text = nil
1202
- elsif selection.start_row == selection.end_row
1203
- text = [ @lines[ selection.start_row ][ selection.start_col...selection.end_col ] ]
1204
- else
1205
- text = [ @lines[ selection.start_row ][ selection.start_col..-1 ] ] +
1206
- ( @lines[ (selection.start_row + 1) .. (selection.end_row - 1) ] or [] ) +
1207
- [ @lines[ selection.end_row ][ 0...selection.end_col ] ]
1208
- end
1209
-
1210
- return text
1232
+ selection = selection_mark
1233
+ if selection.nil?
1234
+ nil
1235
+ elsif selection.start_row == selection.end_row
1236
+ [ @lines[ selection.start_row ][ selection.start_col...selection.end_col ] ]
1237
+ else
1238
+ [ @lines[ selection.start_row ][ selection.start_col..-1 ] ] +
1239
+ ( @lines[ (selection.start_row + 1) .. (selection.end_row - 1) ] or [] ) +
1240
+ [ @lines[ selection.end_row ][ 0...selection.end_col ] ]
1241
+ end
1211
1242
  end
1212
1243
  def selected_string
1213
- lines = selected_text
1214
- if lines
1215
- lines.join( "\n" )
1216
- else
1217
- nil
1218
- end
1244
+ lines = selected_text
1245
+ if lines
1246
+ lines.join( "\n" )
1247
+ else
1248
+ nil
1249
+ end
1219
1250
  end
1220
1251
 
1221
1252
  def deleteSelection( do_display = DO_DISPLAY )
@@ -1241,44 +1272,53 @@ class Buffer
1241
1272
  setModified( do_display )
1242
1273
  end
1243
1274
 
1244
- # text is an array of Strings
1245
- def paste( text )
1246
- return if text == nil
1247
-
1248
- if not text.kind_of? Array
1249
- s = text.to_s
1250
- if s.include?( "\n" )
1251
- text = s.split( "\n", -1 )
1252
- else
1253
- text = [ s ]
1254
- end
1275
+ # text is an array of Strings, or a String with zero or more newlines ("\n")
1276
+ def paste( text, do_parsed_indent = false )
1277
+ return if text == nil
1278
+
1279
+ if not text.kind_of? Array
1280
+ s = text.to_s
1281
+ if s.include?( "\n" )
1282
+ text = s.split( "\n", -1 )
1283
+ else
1284
+ text = [ s ]
1255
1285
  end
1256
-
1257
- takeSnapshot
1258
-
1259
- deleteSelection( DONT_DISPLAY )
1260
-
1261
- row = @last_row
1262
- col = @last_col
1263
- line = @lines[ row ]
1264
- if text.length == 1
1265
- @lines[ row ] = line[ 0...col ] + text[ 0 ] + line[ col..-1 ]
1266
- cursorTo( @last_row, @last_col + text[ 0 ].length )
1267
- elsif text.length > 1
1268
- @lines[ row ] = line[ 0...col ] + text[ 0 ]
1269
- @lines[ row + 1, 0 ] = text[ -1 ] + line[ col..-1 ]
1270
- @lines[ row + 1, 0 ] = text[ 1..-2 ]
1271
- cursorTo( @last_row + text.length - 1, columnOf( text[ -1 ].length ) )
1286
+ end
1287
+
1288
+ takeSnapshot
1289
+
1290
+ deleteSelection( DONT_DISPLAY )
1291
+
1292
+ row = @last_row
1293
+ col = @last_col
1294
+ line = @lines[ row ]
1295
+ if text.length == 1
1296
+ @lines[ row ] = line[ 0...col ] + text[ 0 ] + line[ col..-1 ]
1297
+ if do_parsed_indent
1298
+ parsedIndent row, DONT_DISPLAY
1299
+ end
1300
+ cursorTo( @last_row, @last_col + text[ 0 ].length )
1301
+ elsif text.length > 1
1302
+ @lines[ row ] = line[ 0...col ] + text[ 0 ]
1303
+ @lines[ row + 1, 0 ] = text[ -1 ] + line[ col..-1 ]
1304
+ @lines[ row + 1, 0 ] = text[ 1..-2 ]
1305
+ new_row = @last_row + text.length - 1
1306
+ if do_parsed_indent
1307
+ ( row..new_row ).each do |r|
1308
+ parsedIndent r, DONT_DISPLAY
1309
+ end
1272
1310
  end
1273
-
1274
- setModified
1311
+ cursorTo( new_row, columnOf( text[ -1 ].length ) )
1312
+ end
1313
+
1314
+ setModified
1275
1315
  end
1276
1316
 
1277
1317
  # Takes an array of Regexps, which represents a user-provided regexp,
1278
1318
  # split across newline characters. Once the first element is found,
1279
1319
  # each successive element must match against lines following the first
1280
1320
  # element.
1281
- def find( regexps, direction = :down, replacement = nil )
1321
+ def find( regexps, direction = :down, replacement = nil, auto_choice = nil )
1282
1322
  return if regexps.nil?
1283
1323
  regexp = regexps[ 0 ]
1284
1324
  return if regexp == nil or regexp == //
@@ -1296,6 +1336,7 @@ class Buffer
1296
1336
 
1297
1337
  finding = nil
1298
1338
  wrapped = false
1339
+ match = nil
1299
1340
 
1300
1341
  catch :found do
1301
1342
 
@@ -1303,26 +1344,28 @@ class Buffer
1303
1344
  # Check the current row first.
1304
1345
 
1305
1346
  if index = @lines[ @last_row ].index( regexp, ( @last_finding ? @last_finding.start_col : @last_col ) + 1 )
1306
- found_text = Regexp.last_match[ 0 ]
1307
- finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1308
- if finding.match( regexps, @lines )
1309
- throw :found
1310
- else
1311
- finding = nil
1312
- end
1347
+ match = Regexp.last_match
1348
+ found_text = match[ 0 ]
1349
+ finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1350
+ if finding.match( regexps, @lines )
1351
+ throw :found
1352
+ else
1353
+ finding = nil
1354
+ end
1313
1355
  end
1314
1356
 
1315
1357
  # Check below the cursor.
1316
1358
 
1317
1359
  ( (@last_row + 1)...@lines.length ).each do |i|
1318
1360
  if index = @lines[ i ].index( regexp )
1319
- found_text = Regexp.last_match[ 0 ]
1320
- finding = Finding.new( i, index, i, index + found_text.length )
1321
- if finding.match( regexps, @lines )
1322
- throw :found
1323
- else
1324
- finding = nil
1325
- end
1361
+ match = Regexp.last_match
1362
+ found_text = match[ 0 ]
1363
+ finding = Finding.new( i, index, i, index + found_text.length )
1364
+ if finding.match( regexps, @lines )
1365
+ throw :found
1366
+ else
1367
+ finding = nil
1368
+ end
1326
1369
  end
1327
1370
  end
1328
1371
 
@@ -1332,13 +1375,14 @@ class Buffer
1332
1375
 
1333
1376
  ( 0...@last_row ).each do |i|
1334
1377
  if index = @lines[ i ].index( regexp )
1335
- found_text = Regexp.last_match[ 0 ]
1336
- finding = Finding.new( i, index, i, index + found_text.length )
1337
- if finding.match( regexps, @lines )
1338
- throw :found
1339
- else
1340
- finding = nil
1341
- end
1378
+ match = Regexp.last_match
1379
+ found_text = match[ 0 ]
1380
+ finding = Finding.new( i, index, i, index + found_text.length )
1381
+ if finding.match( regexps, @lines )
1382
+ throw :found
1383
+ else
1384
+ finding = nil
1385
+ end
1342
1386
  end
1343
1387
  end
1344
1388
 
@@ -1347,13 +1391,14 @@ class Buffer
1347
1391
  #if index = @lines[ @last_row ].index( regexp, ( @last_finding ? @last_finding.start_col : @last_col ) - 1 )
1348
1392
  if index = @lines[ @last_row ].index( regexp )
1349
1393
  if index <= ( @last_finding ? @last_finding.start_col : @last_col )
1350
- found_text = Regexp.last_match[ 0 ]
1351
- finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1352
- if finding.match( regexps, @lines )
1353
- throw :found
1354
- else
1355
- finding = nil
1356
- end
1394
+ match = Regexp.last_match
1395
+ found_text = match[ 0 ]
1396
+ finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1397
+ if finding.match( regexps, @lines )
1398
+ throw :found
1399
+ else
1400
+ finding = nil
1401
+ end
1357
1402
  end
1358
1403
  end
1359
1404
 
@@ -1362,26 +1407,28 @@ class Buffer
1362
1407
 
1363
1408
  col_to_check = ( @last_finding ? @last_finding.end_col : @last_col ) - 1
1364
1409
  if ( col_to_check >= 0 ) and ( index = @lines[ @last_row ][ 0...col_to_check ].rindex( regexp ) )
1365
- found_text = Regexp.last_match[ 0 ]
1366
- finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1367
- if finding.match( regexps, @lines )
1368
- throw :found
1369
- else
1370
- finding = nil
1371
- end
1410
+ match = Regexp.last_match
1411
+ found_text = match[ 0 ]
1412
+ finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1413
+ if finding.match( regexps, @lines )
1414
+ throw :found
1415
+ else
1416
+ finding = nil
1417
+ end
1372
1418
  end
1373
1419
 
1374
1420
  # Check above the cursor.
1375
1421
 
1376
1422
  (@last_row - 1).downto( 0 ) do |i|
1377
1423
  if index = @lines[ i ].rindex( regexp )
1378
- found_text = Regexp.last_match[ 0 ]
1379
- finding = Finding.new( i, index, i, index + found_text.length )
1380
- if finding.match( regexps, @lines )
1381
- throw :found
1382
- else
1383
- finding = nil
1384
- end
1424
+ match = Regexp.last_match
1425
+ found_text = match[ 0 ]
1426
+ finding = Finding.new( i, index, i, index + found_text.length )
1427
+ if finding.match( regexps, @lines )
1428
+ throw :found
1429
+ else
1430
+ finding = nil
1431
+ end
1385
1432
  end
1386
1433
  end
1387
1434
 
@@ -1391,13 +1438,14 @@ class Buffer
1391
1438
 
1392
1439
  (@lines.length - 1).downto(@last_row + 1) do |i|
1393
1440
  if index = @lines[ i ].rindex( regexp )
1394
- found_text = Regexp.last_match[ 0 ]
1395
- finding = Finding.new( i, index, i, index + found_text.length )
1396
- if finding.match( regexps, @lines )
1397
- throw :found
1398
- else
1399
- finding = nil
1400
- end
1441
+ match = Regexp.last_match
1442
+ found_text = match[ 0 ]
1443
+ finding = Finding.new( i, index, i, index + found_text.length )
1444
+ if finding.match( regexps, @lines )
1445
+ throw :found
1446
+ else
1447
+ finding = nil
1448
+ end
1401
1449
  end
1402
1450
  end
1403
1451
 
@@ -1406,19 +1454,20 @@ class Buffer
1406
1454
  search_col = ( @last_finding ? @last_finding.start_col : @last_col ) + 1
1407
1455
  if index = @lines[ @last_row ].rindex( regexp )
1408
1456
  if index > search_col
1409
- found_text = Regexp.last_match[ 0 ]
1410
- finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1411
- if finding.match( regexps, @lines )
1412
- throw :found
1413
- else
1414
- finding = nil
1415
- end
1457
+ match = Regexp.last_match
1458
+ found_text = match[ 0 ]
1459
+ finding = Finding.new( @last_row, index, @last_row, index + found_text.length )
1460
+ if finding.match( regexps, @lines )
1461
+ throw :found
1462
+ else
1463
+ finding = nil
1464
+ end
1416
1465
  end
1417
1466
  end
1418
1467
  end
1419
1468
  end
1420
1469
 
1421
- if finding != nil
1470
+ if finding
1422
1471
  @diakonos.setILine( "(search wrapped around BOF/EOF)" ) if wrapped
1423
1472
 
1424
1473
  removeSelection( DONT_DISPLAY )
@@ -1441,26 +1490,37 @@ class Buffer
1441
1490
  end
1442
1491
  display
1443
1492
 
1444
- if replacement != nil
1445
- choice = @diakonos.getChoice(
1446
- "Replace?",
1447
- [ CHOICE_YES, CHOICE_NO, CHOICE_ALL, CHOICE_CANCEL, CHOICE_YES_AND_STOP ],
1448
- CHOICE_YES
1449
- )
1450
- case choice
1451
- when CHOICE_YES
1452
- paste [ replacement ]
1453
- find( regexps, direction, replacement )
1454
- when CHOICE_ALL
1455
- replaceAll( regexp, replacement )
1456
- when CHOICE_NO
1457
- find( regexps, direction, replacement )
1458
- when CHOICE_CANCEL
1459
- # Do nothing further.
1460
- when CHOICE_YES_AND_STOP
1461
- paste [ replacement ]
1462
- # Do nothing further.
1493
+ if replacement
1494
+ # Substitute placeholders (e.g. \1) in str for the group matches of the last match.
1495
+ actual_replacement = replacement.dup
1496
+ actual_replacement.gsub!( /\\(\\|\d+)/ ) { |m|
1497
+ ref = $1
1498
+ if ref == "\\"
1499
+ "\\"
1500
+ else
1501
+ match[ ref.to_i ]
1463
1502
  end
1503
+ }
1504
+
1505
+ choice = auto_choice || @diakonos.getChoice(
1506
+ "Replace?",
1507
+ [ CHOICE_YES, CHOICE_NO, CHOICE_ALL, CHOICE_CANCEL, CHOICE_YES_AND_STOP ],
1508
+ CHOICE_YES
1509
+ )
1510
+ case choice
1511
+ when CHOICE_YES
1512
+ paste [ actual_replacement ]
1513
+ find( regexps, direction, replacement )
1514
+ when CHOICE_ALL
1515
+ replaceAll( regexp, replacement )
1516
+ when CHOICE_NO
1517
+ find( regexps, direction, replacement )
1518
+ when CHOICE_CANCEL
1519
+ # Do nothing further.
1520
+ when CHOICE_YES_AND_STOP
1521
+ paste [ actual_replacement ]
1522
+ # Do nothing further.
1523
+ end
1464
1524
  end
1465
1525
  else
1466
1526
  @diakonos.setILine "/#{regexp.source}/ not found."