ifmapper 1.0.8 → 1.0.9

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,528 @@
1
+
2
+ require 'tmpdir'
3
+
4
+ begin
5
+ require 'prawn'
6
+ rescue LoadError => e
7
+ err = "Prawn PDF library not found. Please install it.\n"
8
+ if $rubygems
9
+ err += "You can usually do so if you do 'gem install prawn'."
10
+ else
11
+ err += "You can download it from www.rubyforge.net."
12
+ end
13
+ raise LoadError, err
14
+ end
15
+
16
+ require 'IFMapper/MapPrinting'
17
+
18
+ PDF_ZOOM = 0.5
19
+ PDF_ROOM_WIDTH = W * PDF_ZOOM
20
+ PDF_ROOM_HEIGHT = H * PDF_ZOOM
21
+ PDF_ROOM_WS = WS * PDF_ZOOM
22
+ PDF_ROOM_HS = HS * PDF_ZOOM
23
+ PDF_MARGIN = 20.0
24
+
25
+ #
26
+ # Open all the map class and add all pdf methods there
27
+ # Gotta love Ruby's flexibility to just inject in new methods.
28
+ #
29
+ class FXConnection
30
+ def _cvt_pt(p, opts)
31
+ x = (p[0] - WW / 2.0) / WW.to_f
32
+ y = (p[1] - HH / 2.0) / HH.to_f
33
+ x = x * opts['ww'] + opts['ws_2'] + opts['margin_2'] + opts['w'] / 2.0
34
+ y = (opts['height'] - y) * opts['hh'] + opts['hs_2'] + opts['margin_2'] + opts['hs']
35
+ return [x, y]
36
+ end
37
+
38
+ def pdf_draw_arrow(pdf, opts, x1, y1, x2, y2)
39
+ return if @dir == BOTH
40
+
41
+ pt1, d = _arrow_info( x1, y1, x2, y2, 0.5 )
42
+
43
+ pdf.stroke_color '000000'
44
+ pdf.fill_color '000000'
45
+ pdf.fill_polygon( [ pt1[0], pt1[1] ],
46
+ [ pt1[0] + d[0], pt1[1] - d[1] ],
47
+ [ pt1[0] + d[0], pt1[1] + d[1] ] )
48
+ end
49
+
50
+ def pdf_draw_complex_as_bspline( pdf, opts )
51
+ p = []
52
+ p << _cvt_pt(@pts[0], opts)
53
+ p << p[0]
54
+ p << p[0]
55
+ @pts.each { |pt|
56
+ p << _cvt_pt(pt, opts)
57
+ }
58
+ p << p[-1]
59
+ p << p[-1]
60
+ p << p[-1]
61
+ return FXSpline::bspline(p)
62
+ end
63
+
64
+ # PRE: If it's a loop exit that comes back to the same place, let's move
65
+ # it up and right
66
+ def pdf_draw_complex_as_lines( pdf, opts )
67
+ p = []
68
+ maxy = opts['height'] * opts['hh'] + opts['hs_2'] + opts['margin_2']
69
+ @pts.each { |pt|
70
+ if loop? == true
71
+ p << [ pt[0] * PDF_ZOOM + 10, maxy - pt[1] * PDF_ZOOM + 48 ]
72
+ else
73
+ p << [ pt[0] * PDF_ZOOM, maxy - pt[1] * PDF_ZOOM ]
74
+ end
75
+ }
76
+ return p
77
+ end
78
+
79
+ def pdf_draw_door( pdf, x1, y1, x2, y2 )
80
+ v = [ (x2-x1), (y2-y1) ]
81
+ t = 10 / Math.sqrt(v[0]*v[0]+v[1]*v[1])
82
+ v = [ v[0]*t, v[1]*t ]
83
+ m = [ (x2+x1)/2, (y2+y1)/2 ]
84
+ x1, y1 = [m[0] + v[1], m[1] - v[0]]
85
+ x2, y2 = [m[0] - v[1], m[1] + v[0]]
86
+ pdf.stroke_color '000000'
87
+ pdf.fill_color '000000'
88
+ if @type == LOCKED_DOOR
89
+ pdf.move_to(x1, y1)
90
+ pdf.line_to(x2, y2)
91
+ else
92
+ pdf.cap_style = :butt
93
+ pdf.join_style = :miter
94
+ pdf.undash
95
+
96
+ v = [ v[0] / 4, v[1] / 4]
97
+ pdf.move_to(x1 - v[0], y1 - v[1])
98
+ pdf.line_to(x1 + v[0], y1 + v[1])
99
+ pdf.line_to(x2 + v[0], y2 + v[1])
100
+ pdf.line_to(x2 - v[0], y2 - v[1])
101
+ pdf.line_to(x1 - v[0], y1 - v[1])
102
+
103
+ pdf.cap_style = :butt
104
+ pdf.join_style = :miter
105
+ pdf.undash
106
+ end
107
+ end
108
+
109
+ def pdf_draw_complex( pdf, opts )
110
+ pdf.stroke_color '000000'
111
+ pdf.fill_color '000000'
112
+ if opts['Paths as Curves']
113
+ if @room[0] == @room[1]
114
+ dirA, dirB = dirs
115
+ if dirA == dirB
116
+ p = pdf_draw_complex_as_lines( pdf, opts )
117
+ else
118
+ p = pdf_draw_complex_as_bspline( pdf, opts )
119
+ end
120
+ else
121
+ p = pdf_draw_complex_as_bspline( pdf, opts )
122
+ end
123
+ else
124
+ p = pdf_draw_complex_as_lines( pdf, opts )
125
+ end
126
+
127
+ pdf.stroke_color '000000'
128
+ pdf.fill_color '000000'
129
+ pdf.move_to( p[0][0], p[0][1] )
130
+ p.each { |pt| pdf.line_to( pt[0], pt[1] ) }
131
+
132
+ x1, y1 = [p[0][0], p[0][1]]
133
+ x2, y2 = [p[-1][0], p[-1][1]]
134
+ pdf_draw_arrow(pdf, opts, x1, y1, x2, y2)
135
+
136
+ if @type == LOCKED_DOOR or @type == CLOSED_DOOR
137
+ t = p.size / 2
138
+ x1, y1 = [ p[t][0], p[t][1] ]
139
+ x2, y2 = [ p[t-2][0], p[t-2][1] ]
140
+ pdf_draw_door(pdf, x1, y1, x2, y2)
141
+ end
142
+ end
143
+
144
+ def pdf_draw_simple(pdf, opts)
145
+ return if not @room[1] # PDF does not print unfinished complex connections
146
+
147
+ dir = @room[0].exits.index(self)
148
+ x1, y1 = @room[0].pdf_corner(opts, self, dir)
149
+ x2, y2 = @room[1].pdf_corner(opts, self)
150
+ pdf.stroke_color '000000'
151
+ pdf.fill_color '000000'
152
+ pdf.move_to(x1, y1)
153
+ pdf.line_to(x2, y2)
154
+ pdf_draw_arrow(pdf, opts, x1, y1, x2, y2)
155
+ if @type == LOCKED_DOOR or @type == CLOSED_DOOR
156
+ pdf_draw_door(pdf, x1, y1, x2, y2)
157
+ end
158
+ end
159
+
160
+ #
161
+ # Draw the connection text next to the arrow ('I', 'O', etc)
162
+ #
163
+ def pdf_draw_text(pdf, x, y, dir, text, arrow)
164
+ if dir == 7 or dir < 6 and dir != 1
165
+ if arrow and (dir == 0 or dir == 4)
166
+ x += 5
167
+ end
168
+ x += 2.5
169
+ elsif dir == 6 or dir == 1
170
+ x -= 7.5
171
+ end
172
+
173
+ if dir > 5 or dir < 4
174
+ if arrow and (dir == 6 or dir == 2)
175
+ y += 5
176
+ end
177
+ y += 2.5
178
+ elsif dir == 4 or dir == 5
179
+ y -= 7.5
180
+ end
181
+
182
+ font_size = 8
183
+ pdf.text_box text, :at => [x, y], :size => font_size
184
+ end
185
+
186
+ def pdf_draw_exit_text(pdf, opts)
187
+
188
+ if @exitText[0] != 0
189
+ dir = @room[0].exits.index(self)
190
+ x, y = @room[0].pdf_corner(opts, self, dir)
191
+ pdf.move_to(x, y)
192
+ pdf_draw_text( pdf, x, y+4, dir,
193
+ EXIT_TEXT[@exitText[0]], @dir == BtoA)
194
+ end
195
+
196
+ if @exitText[1] != 0
197
+ dir = @room[1].exits.rindex(self)
198
+ x, y = @room[1].pdf_corner(opts, self, dir)
199
+ pdf_draw_text( pdf, x, y+4, dir,
200
+ EXIT_TEXT[@exitText[1]], @dir == AtoB)
201
+ end
202
+ end
203
+
204
+ def pdf_draw(pdf, opts)
205
+ pdf_draw_exit_text(pdf, opts)
206
+ if @type == SPECIAL
207
+ pdf.dash 4
208
+ else
209
+ pdf.cap_style = :butt
210
+ pdf.join_style = :miter
211
+ pdf.undash
212
+ end
213
+ pdf.stroke_color '000000'
214
+ pdf.fill_color '000000'
215
+ if @pts.size > 0
216
+ pdf_draw_complex(pdf, opts)
217
+ else
218
+ pdf_draw_simple(pdf, opts)
219
+ end
220
+ end
221
+ end
222
+
223
+
224
+ class FXRoom
225
+ def pdf_corner( opts, c, idx = nil )
226
+ x, y = _corner(c, idx)
227
+ y = -y
228
+
229
+ ww = opts['ww']
230
+ hh = opts['hh']
231
+ w = opts['w']
232
+ h = opts['h']
233
+
234
+ ry = opts['height'] - @y
235
+ x = @x * ww + opts['ws_2'] + opts['margin_2'] + x * w
236
+ y = ry * hh + opts['hs_2'] + h + opts['margin_2'] + y * h
237
+ return [x, y]
238
+ end
239
+
240
+
241
+ def pdf_draw_box( pdf, opts, idx, pdflocationnos )
242
+ x = @x * opts['ww'] + opts['ws_2'] + opts['margin_2']
243
+ y = (opts['height'] - @y) * opts['hh'] + opts['hs_2'] + opts['margin_2']
244
+
245
+ pdf.cap_style = :butt
246
+ pdf.join_style = :miter
247
+ pdf.line_width 1
248
+
249
+ if @darkness
250
+ pdf.fill_color '808080'
251
+ pdf.stroke_color '000000'
252
+ else
253
+ pdf.fill_color 'ffffff'
254
+ pdf.stroke_color '000000'
255
+ end
256
+
257
+ pdf.stroke_rectangle [x, y], opts['w'], -opts['h']
258
+
259
+ if pdflocationnos == 1
260
+ # PRE: Draw a rectangle for the location number
261
+ pdf.stroke_rectangle( [x+opts['w']-opts['w']/4, y],
262
+ opts['w']/4, -opts['h']/4 )
263
+
264
+ # PRE: Pad out the number so it is three chars long
265
+ locationno = (idx+1).to_s
266
+ if (idx+1) < 10
267
+ locationno = ' '+locationno
268
+ elsif (idx+1) < 100
269
+ locationno = ' '+locationno
270
+ end
271
+
272
+ # PRE: Write the location number
273
+ pdf.stroke_color '000000'
274
+ pdf.fill_color '000000'
275
+
276
+ pdf.text_box locationno,
277
+ :at => [(x+((opts['w']/4)*3)+2), y+7], :size => 8
278
+ end
279
+
280
+ end
281
+
282
+ def pdf_draw_text( pdf, opts, x, y, text, font_size, pdflocationnos )
283
+ miny = (opts['height'] - @y) * opts['hh'] + opts['hs_2'] +
284
+ opts['margin_2']
285
+ pdf.text_box text, :at => [x, y+6], :size => font_size,
286
+ :width => opts['w'], :height => opts['h'], :valign => :top,
287
+ :align => :left, :overflow => :shrink_to_fit
288
+ return [x, y]
289
+ end
290
+
291
+ def pdf_draw_objects(pdf, opts, x, y, pdflocationnos)
292
+ font_size = 6
293
+ objs = @objects.split("\n")
294
+ objs = objs.join(', ')
295
+ return pdf_draw_text( pdf, opts, x, y-font_size,
296
+ objs, font_size, pdflocationnos )
297
+ end
298
+
299
+ def pdf_draw_name(pdf, opts, pdflocationnos)
300
+ # We could also use pdf_corner(7) here
301
+ x = @x * opts['ww'] + opts['margin_2'] + opts['ws_2'] + 2
302
+ y = opts['height'] - @y
303
+ font_size = 8
304
+ y = y * opts['hh'] + opts['margin_2'] + opts['hs_2'] + opts['h'] -
305
+ (font_size + 2)
306
+ pdf.stroke_color '000000'
307
+ pdf.fill_color '000000'
308
+ return pdf_draw_text( pdf, opts, x, y, @name, font_size, pdflocationnos )
309
+ end
310
+
311
+ # PRE: Send through the index so we can print the location number
312
+ # along with boolean value indicating whether the user wants them
313
+ def pdf_draw( pdf, opts, idx, pdflocationnos )
314
+ pdf_draw_box( pdf, opts, idx, pdflocationnos )
315
+ x, y = pdf_draw_name( pdf, opts, pdflocationnos )
316
+ pdf_draw_objects(pdf, opts, x, y, pdflocationnos)
317
+ end
318
+ end
319
+
320
+
321
+
322
+ class FXSection
323
+
324
+ def pdf_draw_grid(pdf, opts, w, h )
325
+ (0...w).each { |xx|
326
+ (0...h).each { |yy|
327
+ x = xx * opts['ww'] + opts['ws_2'] + opts['margin_2']
328
+ y = yy * opts['hh'] + opts['hs_2'] + opts['margin_2']
329
+ pdf.rectangle([x, y], opts['w'], opts['h'])
330
+ }
331
+ }
332
+ end
333
+
334
+
335
+ def pdf_draw_section_name( pdf, opts, px, py )
336
+ return if not @name or @name == ''
337
+ xymin, xymax = min_max_rooms
338
+ text = @name
339
+ text += " (#{px}, #{py})" if px > 0 or py > 0
340
+ y = (opts['height']) * opts['hh'] + 16
341
+ w = xymax[0]
342
+ w = opts['width'] if w > opts['width']
343
+ x = (w + 2) * opts['ww'] / 2 - text.size / 2 * 16
344
+ x = 0 if x < 0
345
+ pdf.text_box( text, :at => [x,y], :font_size => 16 )
346
+ end
347
+
348
+
349
+ def pdf_draw(pdf, opts, mapname, pdflocationnos )
350
+
351
+
352
+ w, h = rooms_width_height
353
+ x, y = [0, 0]
354
+
355
+ loop do
356
+
357
+ pdf.save_graphics_state
358
+
359
+ if rotate
360
+ pdf.rotate 90.0
361
+ pdf.translate( 0, -pdf.margin_box.height )
362
+ end
363
+
364
+ # Move section to its position in page
365
+ tx1, ty1 = [@xoff * opts['ww'], @yoff * -opts['hh']]
366
+ pdf.translate( tx1, ty1 )
367
+
368
+ # Use times-roman as font
369
+ pdf.font 'Times-Roman'
370
+ pdf.stroke_color '000000'
371
+
372
+ pdf_draw_section_name( pdf, opts, x, y )
373
+
374
+ xymin, = min_max_rooms
375
+
376
+ # Move rooms, so that we don't print empty areas
377
+ tx2 = -(xymin[0]) * opts['ww'] - x * opts['ww']
378
+ ty2 = (xymin[1]) * opts['hh'] - 60 + (y - (y > 0? 1 : 0)) * opts['hh']
379
+ pdf.translate( tx2, ty2 )
380
+
381
+
382
+ # For testing purposes only, draw grid of boxes
383
+ # pdf_draw_grid( pdf, opts, w, h )
384
+ @connections.each { |c|
385
+ a = c.roomA
386
+ b = c.roomB
387
+ next if a.y < y and b and b.y < y
388
+ c.pdf_draw( pdf, opts )
389
+ }
390
+ @rooms.each_with_index { |r, idx|
391
+ next if r.y < y
392
+ r.pdf_draw( pdf, opts, idx, pdflocationnos)
393
+ }
394
+
395
+ # Reset axis
396
+ pdf.translate(-tx2, -ty2)
397
+ pdf.translate(-tx1, -ty1)
398
+
399
+ xi = opts['width']
400
+ yi = opts['height']
401
+ if rotate
402
+ xi = (pdf.margin_box.height / opts['ww']).to_i - 1
403
+ yi = (pdf.margin_box.width / opts['hh']).to_i - 1
404
+ end
405
+
406
+ x += xi
407
+ if x >= w
408
+ x = 0
409
+ y += yi
410
+ break if y >= h
411
+ end
412
+
413
+ if rotate
414
+ pdf.rotate(-90.0)
415
+ pdf.translate( 0, pdf.page_height )
416
+ end
417
+
418
+ pdf.restore_graphics_state
419
+
420
+ # We could not fit all rooms in page. Start new page
421
+ pdf.start_new_page
422
+ end
423
+ end
424
+ end
425
+
426
+
427
+ class FXMap
428
+
429
+ attr_accessor :pdfpapersize
430
+ # boolean value indicating whether the user wants to see location nos
431
+ attr_accessor :pdflocationnos
432
+
433
+ def pdf_draw_mapname( pdf, opts )
434
+ return if not @name or @name == ''
435
+ pdf.text( @name,
436
+ :font_size => 24,
437
+ :justification => :center
438
+ )
439
+ end
440
+
441
+ def pdf_draw_sections( pdf, opts )
442
+ old_section = @section
443
+ page = -1
444
+ @sections.each_with_index { |sect, idx|
445
+ if page != sect.page
446
+ page = sect.page
447
+ pdf.start_new_page if page > 1
448
+ pdf_draw_mapname( pdf, opts )
449
+ end
450
+ @section = idx
451
+ # For each page, we need to regenerate the pathmap so that complex
452
+ # paths will come out ok.
453
+ create_pathmap
454
+ # Now, we draw it
455
+ sect.pdf_draw(pdf, opts, @name, pdflocationnos)
456
+ }
457
+
458
+ # Restore original viewing page
459
+ @section = old_section
460
+ create_pathmap
461
+ end
462
+
463
+
464
+ def pdf_export(pdffile = Dir::tmpdir + "/ifmap.pdf", printer = nil)
465
+
466
+ # PRE: Let's set the PDF paper size to user's choice
467
+ paper = BOX_PDF_PAGE_SIZE_TEXT[pdfpapersize]
468
+ if printer
469
+ case printer.mediasize
470
+ when FXPrinter::MEDIA_LETTER
471
+ paper = 'LETTER'
472
+ when FXPrinter::MEDIA_LEGAL
473
+ paper = 'LEGAL'
474
+ when FXPrinter::MEDIA_A4
475
+ paper = 'A4'
476
+ when FXPrinter::MEDIA_ENVELOPE
477
+ paper = 'ENVELOPE'
478
+ when FXPrinter::MEDIA_CUSTOM
479
+ raise "Sorry, custom paper not supported"
480
+ end
481
+ end
482
+
483
+ # Open a new PDF writer with paper selected
484
+ # PRE: Let's also set the paper orientation based on user selection
485
+
486
+ pdf = Prawn::Document.new :page_size => paper
487
+
488
+ pdf_options = @options.dup
489
+
490
+ ww = PDF_ROOM_WIDTH + PDF_ROOM_WS
491
+ hh = PDF_ROOM_HEIGHT + PDF_ROOM_HS
492
+
493
+ pdf_options.merge!(
494
+ {
495
+ 'ww' => ww,
496
+ 'hh' => hh,
497
+ 'w' => PDF_ROOM_WIDTH,
498
+ 'h' => PDF_ROOM_HEIGHT,
499
+ 'ws' => PDF_ROOM_WS,
500
+ 'hs' => PDF_ROOM_HS,
501
+ 'ws_2' => PDF_ROOM_WS / 2.0,
502
+ 'hs_2' => PDF_ROOM_HS / 2.0,
503
+ 'margin' => PDF_MARGIN,
504
+ 'margin_2' => PDF_MARGIN / 2.0,
505
+ 'width' => (pdf.margin_box.width / ww).to_i - 1,
506
+ 'height' => (pdf.margin_box.height / hh).to_i - 1,
507
+ }
508
+ )
509
+
510
+
511
+ begin
512
+ # See if it is possible to pack several map sections (sections) into
513
+ # a single print page.
514
+ num = pack_sections( pdf_options['width'] + 2,
515
+ pdf_options['height'] + 2 )
516
+ pdf_draw_sections(pdf, pdf_options)
517
+ if pdffile !~ /\.pdf$/
518
+ pdffile << ".pdf"
519
+ end
520
+ status "Exporting PDF file '#{pdffile}'"
521
+ pdf.render_file pdffile
522
+ rescue => e
523
+ p e
524
+ p e.backtrace
525
+ raise e
526
+ end
527
+ end
528
+ end
data/lib/IFMapper/Room.rb CHANGED
@@ -150,6 +150,7 @@ class Room
150
150
  @desc = nil
151
151
  @objects = ''
152
152
  @tasks = ''
153
+ @comment = nil
153
154
  end
154
155
 
155
156
  def to_s
@@ -140,6 +140,7 @@ class TranscriptReader
140
140
  SHORTNAME_MOONMIST = 2
141
141
  SHORTNAME_WITNESS = 3
142
142
  SHORTNAME_ADRIFT = 4
143
+ SHORTNAME_ALL_CAPS = 5
143
144
 
144
145
  attr_reader :shortName
145
146
  attr_accessor :identify, :map
@@ -843,6 +844,8 @@ class TranscriptReader
843
844
 
844
845
  def room_name(line)
845
846
  case @shortName
847
+ when SHORTNAME_ALL_CAPS
848
+ return room_name_all_caps(line)
846
849
  when SHORTNAME_CAPITALIZED
847
850
  return room_name_classic(line, false)
848
851
  when SHORTNAME_MOONMIST
@@ -952,6 +955,64 @@ class TranscriptReader
952
955
  return line
953
956
  end
954
957
 
958
+ #
959
+ # Determine if line corresponds to a room name
960
+ #
961
+ def room_name_all_caps(line)
962
+ # Check if user/game has created a room with that name already
963
+ return line if find_room(line, nil)
964
+
965
+ # We have a room if we match darkness
966
+ return line if line =~ DARKNESS
967
+
968
+ # Remove unwanted stuff line (on the bed)
969
+ line.sub!(NAME_REMOVE, '')
970
+
971
+ # Check if user/game has created a room with that name already
972
+ return line if find_room(line, nil)
973
+
974
+ # Remove periods from salutations
975
+ line.sub!(SALUTATIONS, '\1')
976
+
977
+ # quick check for invalid format
978
+ return false if line =~ NAME_INVALID
979
+
980
+ # Qucik check for word characters
981
+ return false unless line =~ /\w/
982
+
983
+ # Check if we start line with uncapitalized words or symbols
984
+ return false if line =~ /^[ a-z\/\\\-\(\)']/
985
+
986
+ # Check if line holds only capitalized words or several spaces together
987
+ # or a quote or a 1) line. If so, not a room.
988
+ return false if line =~ /^[a-z\d,\.\/\-"'\s]+$/ or line =~ /\s\s/ or
989
+ line =~ /^".*"$/ or line =~ /^"[^"]+$/ or line =~ /^\d+\)/
990
+
991
+ # Check word count (if too many, not a room)
992
+ words = line.split(' ')
993
+ return false if words.size > NAME_MAXWORDS
994
+
995
+
996
+ # If not, check all words of 4 chars or more are capitalized
997
+ # and that there are no 3 or more short letter words together
998
+ # (which means a diagram)
999
+ num = 0
1000
+ words.each { |w|
1001
+ if w.size <= 2
1002
+ num += 1
1003
+ return false if num > 2
1004
+ else
1005
+ num = 0
1006
+ end
1007
+ }
1008
+
1009
+ # Restore period to salutations
1010
+ line.sub!(/\b#{SALUT}\b/, '\1.')
1011
+
1012
+ # Okay, it is a room.
1013
+ return line
1014
+ end
1015
+
955
1016
  #
956
1017
  # Create a new room
957
1018
  #
@@ -133,6 +133,8 @@ Commands always begin with a > prompt.",
133
133
  names where all words of 5 or more characters are capitalized).
134
134
  However, commands do not begin with any type of prompt but start
135
135
  with a lowercase word without any margin.",
136
+ "ALL CAPS mode is like Classic Mode but expects locations to be
137
+ spelled all in caps."
136
138
  ]
137
139
 
138
140
 
@@ -171,6 +173,12 @@ Front of Mall
171
173
  spot of pavement is too narrow a place for them to stall. It is just
172
174
  right for bicycles and motorbikes such as yours.
173
175
  ",
176
+ "
177
+ > look
178
+ WEST OF HOUSE
179
+ You are standing in an open field west of a white house, with a boarded
180
+ front door.
181
+ "
174
182
  ]
175
183
 
176
184
  TRANSCRIPT_LOCATION2_TEXT = [
@@ -189,6 +197,9 @@ Women's change room
189
197
  "
190
198
  Front of Mall
191
199
  ",
200
+ "
201
+ WEST OF HALL
202
+ "
192
203
  ]
193
204
 
194
205
 
@@ -203,6 +214,7 @@ TRANSCRIPT_SHORTNAME_TYPE = [
203
214
  'Moonmist',
204
215
  'Witness',
205
216
  'ADRIFT',
217
+ 'ALL CAPS'
206
218
  ]
207
219
 
208
220
  ############ Window Titles
@@ -227,7 +239,7 @@ MSG_COMPLEX_CONNECTION_STOPPED = 'Complex connection interrupted.'
227
239
  MSG_COMPLEX_CONNECTION_DONE = 'Complex connection done.'
228
240
 
229
241
  MSG_CLICK_TO_SELECT_AND_MOVE = 'Click to select and move. Double click to edit.'
230
- MSG_CLICK_CHANGE_DIR = 'Click to change direction of connection.'
242
+ MSG_CLICK_TOGGLE_ONE_WAY_CONNECTION = 'Click to toggle one way connection.'
231
243
  MSG_CLICK_CREATE_ROOM = 'Click to create new room.'
232
244
  MSG_CLICK_CREATE_LINK = 'Click to create new connection.'
233
245
 
@@ -142,6 +142,8 @@ Los comandos siempre comienzan tras un >.",
142
142
  "Modo ADRIFT espera las localidades como en el modo Clásico
143
143
  (encabezados de palabras de 5 o más letras en mayúsculas).
144
144
  Los comandos comienzan sólo con una palabra en minúscula sin margen.",
145
+ "Modo TODO MAYUSCULAS es como el modo Classic pero espera que los encabezados
146
+ de la localidad esten todo en mayusculas."
145
147
  ]
146
148
 
147
149
 
@@ -180,6 +182,11 @@ Entrada del Shopping
180
182
  del pavimento es demasiado angosto para que estacionen. Es apenas
181
183
  apropiado para bicicletas y motocicletas como la tuya.
182
184
  ",
185
+ "> mira
186
+ AL OESTE DE LA CASA
187
+ Estás parado en un campo abierto al oeste de una casa blanca, con una
188
+ puerta clausurada.
189
+ "
183
190
  ]
184
191
 
185
192
  TRANSCRIPT_LOCATION2_TEXT = [
@@ -198,6 +205,9 @@ Vestidor de mujeres
198
205
  "
199
206
  Entrada del Shopping
200
207
  ",
208
+ "
209
+ AL OESTE DE LA CASA
210
+ "
201
211
  ]
202
212
 
203
213
 
@@ -212,6 +222,7 @@ TRANSCRIPT_SHORTNAME_TYPE = [
212
222
  'Moonmist',
213
223
  'Witness',
214
224
  'ADRIFT',
225
+ 'Todo Mayúsculas'
215
226
  ]
216
227
 
217
228
  ############ Títulos de Ventanas
@@ -233,7 +244,7 @@ MSG_COMPLEX_CONNECTION_STOPPED = 'Creación de la conexión compleja interrumpid
233
244
  MSG_COMPLEX_CONNECTION_DONE = 'Conexión compleja completada.'
234
245
 
235
246
  MSG_CLICK_TO_SELECT_AND_MOVE = 'Cliquée para seleccionar y mover. Cliquée dos veces para editar.'
236
- MSG_CLICK_CHANGE_DIR = 'Cliquée para cambiar dirección de la conexión.'
247
+ MSG_CLICK_TOGGLE_ONE_WAY_CONNECTION = 'Cliquée para intercambiar conexión de un solo lado.'
237
248
  MSG_CLICK_CREATE_ROOM = 'Cliquée para crear una nueva localidad.'
238
249
  MSG_CLICK_CREATE_LINK = 'Cliquée para crear una nueva conexión.'
239
250
 
@@ -354,7 +365,7 @@ BOX_OBJECTS = 'Objetos: '
354
365
  BOX_DARKNESS = 'Oscuridad'
355
366
  BOX_TASKS = 'Tareas: '
356
367
  BOX_DESCRIPTION = 'Descripción: '
357
- BOX_COMMENTS = 'Comments: '
368
+ BOX_COMMENTS = 'Comentarios: '
358
369
 
359
370
  BOX_CONNECTION_TYPE = 'Tipo de Conexión: '
360
371
  BOX_CONNECTION_TYPE_TEXT = [