newick-ruby 1.0.1 → 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (4) hide show
  1. data/README +2 -0
  2. data/bin/newickDist +22 -5
  3. data/lib/Newick.rb +332 -326
  4. metadata +4 -4
data/README CHANGED
@@ -14,6 +14,8 @@ Jonathan Badger
14
14
  J. Craig Venter Institute
15
15
  jhbadger@gmail.com
16
16
 
17
+ UPDATES:
18
+ 1.0.2 -- faster distance matrix calculation
17
19
 
18
20
  License
19
21
  (The MIT License)
data/bin/newickDist CHANGED
@@ -1,16 +1,33 @@
1
1
  #!/usr/bin/env ruby
2
2
 
3
3
  require 'Newick'
4
+ require 'optparse'
5
+ require 'ostruct'
6
+
7
+ opt = OpenStruct.new
8
+ opt.verbose = false
9
+
10
+ ARGV.options {|opts|
11
+ opts.banner << " tree-file"
12
+ opts.on("-v", "--verbose", "show progress") {|t| opt.verbose = t}
13
+ begin
14
+ opts.parse!
15
+ rescue
16
+ STDERR.puts $!.message
17
+ STDERR.puts opts
18
+ exit(1)
19
+ end
20
+ if (ARGV.size < 1)
21
+ STDERR.puts opts
22
+ exit(1)
23
+ end
24
+ }
4
25
 
5
- if (ARGV.size != 1)
6
- STDERR.printf("usage: %s tree-file\n", $0)
7
- exit(1)
8
- end
9
26
 
10
27
  file = ARGV.pop
11
28
 
12
29
  tree = NewickTree.fromFile(file)
13
- dMatrix = tree.distanceMatrix
30
+ dMatrix = tree.distanceMatrix(opt.verbose)
14
31
 
15
32
  printf(" %d\n", dMatrix.keys.size)
16
33
  dMatrix.keys.each {|key1|
data/lib/Newick.rb CHANGED
@@ -8,7 +8,7 @@ class NewickToken
8
8
  attr_reader :type
9
9
  # string value of token
10
10
  attr_reader :value
11
-
11
+
12
12
  def initialize(type, value)
13
13
  @type = type
14
14
  @value = value
@@ -19,7 +19,7 @@ end
19
19
 
20
20
  # Splits a Newick tree string into tokens that NewickTree uses
21
21
  class NewickTokenizer
22
-
22
+
23
23
  def initialize(str)
24
24
  @str = str
25
25
  @pos = 0
@@ -45,17 +45,17 @@ class NewickTokenizer
45
45
  return NewickToken.new("SYMBOL", c)
46
46
  elsif (c == ":")
47
47
  if (@str.index((/([0-9|\.|\-|e|E]+)/), @pos) == @pos)
48
- @pos += $1.length
49
- return NewickToken.new("WEIGHT", $1)
48
+ @pos += $1.length
49
+ return NewickToken.new("WEIGHT", $1)
50
50
  else
51
- raise NewickParseError, "Illegal weight at pos #{@pos} of #{@str}"
51
+ raise NewickParseError, "Illegal weight at pos #{@pos} of #{@str}"
52
52
  end
53
53
  elsif (c == "'")
54
54
  if (@str.index(/(\'[^\']*\')/, @pos - 1) == @pos - 1)
55
- @pos += $1.length - 1
56
- return NewickToken.new("LABEL", $1)
55
+ @pos += $1.length - 1
56
+ return NewickToken.new("LABEL", $1)
57
57
  else
58
- raise NewickParseError, "Illegal label at pos #{@pos} of #{@str}"
58
+ raise NewickParseError, "Illegal label at pos #{@pos} of #{@str}"
59
59
  end
60
60
  elsif (@str.index(/([^,():]+)/, @pos - 1) == @pos - 1)
61
61
  @pos += $1.length - 1
@@ -112,10 +112,10 @@ class NewickNode
112
112
  s = ""
113
113
  if (!leaf?)
114
114
  s += "("
115
- @children.each {|child|
116
- s += child.to_s(showLen, bootStrap)
117
- s += "," if (child != @children.last)
118
- }
115
+ @children.each do |child|
116
+ s += child.to_s(showLen, bootStrap)
117
+ s += "," if (child != @children.last)
118
+ end
119
119
  s += ")"
120
120
  end
121
121
  if (leaf? || bootStrap == "node")
@@ -133,32 +133,32 @@ class NewickNode
133
133
  taxa = []
134
134
  if (!leaf?)
135
135
  taxa.push(@name) if (bootstrap)
136
- @children.each {|child|
137
- child.taxa.each {|taxon|
138
- taxa.push(taxon)
139
- }
140
- }
136
+ @children.each do |child|
137
+ child.taxa.each do |taxon|
138
+ taxa.push(taxon)
139
+ end
140
+ end
141
141
  else
142
142
  taxa.push(name)
143
143
  end
144
144
  return taxa.sort
145
145
  end
146
-
146
+
147
147
  # returns array of leaves (taxa) are contained in the node
148
148
  def leaves
149
149
  nodes = []
150
- descendants.each {|node|
150
+ descendants.each do |node|
151
151
  nodes.push(node) if (node.leaf?)
152
- }
152
+ end
153
153
  return nodes
154
154
  end
155
155
 
156
156
  # returns array of non leaves (taxa) that are contained in the node
157
157
  def intNodes
158
158
  nodes = []
159
- descendants.each {|child|
159
+ descendants.each do |child|
160
160
  nodes.push(child) if (!child.leaf?)
161
- }
161
+ end
162
162
  return nodes
163
163
  end
164
164
 
@@ -168,10 +168,10 @@ class NewickNode
168
168
  if (@name =~/#{name}/)
169
169
  found = self
170
170
  else
171
- @children.each {|child|
172
- found = child.findNode(name)
173
- break if found
174
- }
171
+ @children.each do |child|
172
+ found = child.findNode(name)
173
+ break if found
174
+ end
175
175
  end
176
176
  return found
177
177
  end
@@ -188,7 +188,7 @@ class NewickNode
188
188
  oldParent.edgeLen = @edgeLen
189
189
  @edgeLen = 0
190
190
  end
191
-
191
+
192
192
  # True if given node is child (or grandchild, etc.) of self. False otherwise
193
193
  def include?(node)
194
194
  while(node.parent != nil)
@@ -210,12 +210,12 @@ class NewickNode
210
210
  # returns array of all descendant nodes
211
211
  def descendants
212
212
  descendants = []
213
- @children.each {|child|
213
+ @children.each do |child|
214
214
  descendants.push(child)
215
- child.descendants.each {|grandchild|
216
- descendants.push(grandchild)
217
- }
218
- }
215
+ child.descendants.each do |grandchild|
216
+ descendants.push(grandchild)
217
+ end
218
+ end
219
219
  return descendants
220
220
  end
221
221
 
@@ -225,24 +225,24 @@ class NewickNode
225
225
  if (parent.nil?)
226
226
  return siblings
227
227
  else
228
- @parent.children.each {|child|
228
+ @parent.children.each do |child|
229
229
  siblings.push(child) if (child!=self)
230
- }
230
+ end
231
231
  return siblings
232
232
  end
233
233
  end
234
234
 
235
- # reorders descendant nodes alphabetically and by size
235
+ # reorders descendant nodes alphabetically and by size
236
236
  def reorder
237
237
  return if (@children.empty?)
238
238
  @children.sort! {|x, y| x.name <=> y.name}
239
- @children.each {|child|
239
+ @children.each do |child|
240
240
  child.reorder
241
- }
241
+ end
242
242
  return self
243
243
  end
244
244
 
245
-
245
+
246
246
 
247
247
  # returns the last common ancestor node of self and given node
248
248
  def lca(node)
@@ -265,7 +265,7 @@ class NewickNode
265
265
  end
266
266
  return dist
267
267
  end
268
-
268
+
269
269
 
270
270
  # returns number of nodes to the ancestor node
271
271
  def nodesToAncestor(ancestor)
@@ -280,7 +280,7 @@ class NewickNode
280
280
  end
281
281
  end
282
282
 
283
-
283
+
284
284
  # returns number of nodes to other node
285
285
  def nodesToNode(node)
286
286
  lca = lca(node)
@@ -296,9 +296,9 @@ class NewickNode
296
296
  # calculates node Y positions
297
297
  def calcYPos
298
298
  ySum = 0
299
- @children.each {|child|
299
+ @children.each do |child|
300
300
  ySum += child.y
301
- }
301
+ end
302
302
  @y = ySum / @children.size
303
303
  end
304
304
 
@@ -311,36 +311,36 @@ class NewickNode
311
311
  @x = parent.x + @edgeLen
312
312
  end
313
313
  if (!leaf?)
314
- @children.each {|child|
314
+ @children.each do |child|
315
315
  child.calcXPos
316
- }
316
+ end
317
317
  end
318
318
  end
319
319
 
320
320
  # returns the maximum X value in node
321
321
  def xMax
322
322
  xMax = 0
323
- children.each {|child|
323
+ children.each do |child|
324
324
  xMax = child.edgeLen if (child.x > xMax)
325
- }
325
+ end
326
326
  return xMax
327
327
  end
328
328
 
329
329
  # returns the maximum Y value in node
330
330
  def yMax
331
331
  yMax = 0
332
- children.each {|child|
332
+ children.each do |child|
333
333
  yMax = child.y if (child.y > yMax)
334
- }
334
+ end
335
335
  return yMax
336
336
  end
337
337
 
338
338
  # returns the minimum Y value in node
339
339
  def yMin
340
340
  yMin = 1e6
341
- children.each {|child|
341
+ children.each do |child|
342
342
  yMin = child.y if (child.y < yMin)
343
- }
343
+ end
344
344
  return yMin
345
345
  end
346
346
 
@@ -357,9 +357,9 @@ class NewickTree
357
357
  def NewickTree.fromFile(fileName)
358
358
  treeString = ""
359
359
  inFile = File.new(fileName)
360
- inFile.each {|line|
360
+ inFile.each do |line|
361
361
  treeString += line.chomp
362
- }
362
+ end
363
363
  inFile.close
364
364
  treeString.gsub!(/\[[^\]]*\]/,"") # remove comments before parsing
365
365
  return NewickTree.new(treeString)
@@ -369,43 +369,43 @@ class NewickTree
369
369
  def buildTree(parent, tokenizer)
370
370
  while (!(token = tokenizer.nextToken).nil?)
371
371
  if (token.type == "LABEL")
372
- name = token.value
373
- edgeLen = 0
374
- if (tokenizer.peekToken.type == "WEIGHT")
375
- edgeLen = tokenizer.nextToken.value.to_f
376
- end
377
- node = NewickNode.new(name, edgeLen)
378
- return node
372
+ name = token.value
373
+ edgeLen = 0
374
+ if (tokenizer.peekToken.type == "WEIGHT")
375
+ edgeLen = tokenizer.nextToken.value.to_f
376
+ end
377
+ node = NewickNode.new(name, edgeLen)
378
+ return node
379
379
  elsif (token.value == "(")
380
- node = NewickNode.new("", 0)
381
- forever = true
382
- while (forever)
383
- child = buildTree(node, tokenizer)
384
- node.addChild(child)
385
- break if tokenizer.peekToken.value != ","
386
- tokenizer.nextToken
387
- end
388
- if (tokenizer.nextToken.value != ")")
389
- raise NewickParseError, "Expected ')' but found: #{token.value}"
390
- else
391
- peek = tokenizer.peekToken
392
- if (peek.value == ")" || peek.value == "," || peek.value == ";")
393
- return node
394
- elsif (peek.type == "WEIGHT")
395
- node.edgeLen = tokenizer.nextToken.value.to_f
396
- return node
397
- elsif (peek.type == "LABEL")
398
- token = tokenizer.nextToken
399
- node.name = token.value
400
- if (tokenizer.peekToken.type == "WEIGHT")
401
- node.edgeLen = tokenizer.nextToken.value.to_f
402
- end
403
- return node
404
- end
405
- end
380
+ node = NewickNode.new("", 0)
381
+ forever = true
382
+ while (forever)
383
+ child = buildTree(node, tokenizer)
384
+ node.addChild(child)
385
+ break if tokenizer.peekToken.value != ","
386
+ tokenizer.nextToken
387
+ end
388
+ if (tokenizer.nextToken.value != ")")
389
+ raise NewickParseError, "Expected ')' but found: #{token.value}"
390
+ else
391
+ peek = tokenizer.peekToken
392
+ if (peek.value == ")" || peek.value == "," || peek.value == ";")
393
+ return node
394
+ elsif (peek.type == "WEIGHT")
395
+ node.edgeLen = tokenizer.nextToken.value.to_f
396
+ return node
397
+ elsif (peek.type == "LABEL")
398
+ token = tokenizer.nextToken
399
+ node.name = token.value
400
+ if (tokenizer.peekToken.type == "WEIGHT")
401
+ node.edgeLen = tokenizer.nextToken.value.to_f
402
+ end
403
+ return node
404
+ end
405
+ end
406
406
  else
407
- raise NewickParseError,
408
- "Expected '(' or label but found: #{token.value}"
407
+ raise NewickParseError,
408
+ "Expected '(' or label but found: #{token.value}"
409
409
  end
410
410
  end
411
411
  end
@@ -437,33 +437,33 @@ class NewickTree
437
437
  else
438
438
  taxon = "SEQ0000001"
439
439
  end
440
- @root.descendants.each {|node|
440
+ @root.descendants.each do |node|
441
441
  if (node.name != "" && node.name.to_i == 0)
442
- ali[taxon] = node.name
443
- aliF.printf("%s\t%s\n", taxon, node.name) if (!aliasFile.nil?)
444
- node.name = taxon.dup
445
- taxon.succ!
442
+ ali[taxon] = node.name
443
+ aliF.printf("%s\t%s\n", taxon, node.name) if (!aliasFile.nil?)
444
+ node.name = taxon.dup
445
+ taxon.succ!
446
446
  end
447
- }
447
+ end
448
448
  aliF.close if (!aliasFile.nil?)
449
449
  return self, ali
450
450
  end
451
451
 
452
452
  # renames nodes according to alias hash
453
453
  def unAlias(aliasNames)
454
- @root.descendants.each {|node|
454
+ @root.descendants.each do |node|
455
455
  node.name = aliasNames[node.name] if (!aliasNames[node.name].nil?)
456
- }
456
+ end
457
457
  return self
458
458
  end
459
459
 
460
460
  # renames nodes according to inverse alias hash
461
461
  def reAlias(aliasNames)
462
- @root.descendants.each {|node|
463
- aliasNames.keys.each {|key|
462
+ @root.descendants.each do |node|
463
+ aliasNames.keys.each do |key|
464
464
  node.name = key if (aliasNames[key] == node.name)
465
- }
466
- }
465
+ end
466
+ end
467
467
  return self
468
468
  end
469
469
 
@@ -473,22 +473,28 @@ class NewickTree
473
473
  end
474
474
 
475
475
  # returns a 2D hash of pairwise distances on tree
476
- def distanceMatrix
476
+ def distanceMatrix(verbose = nil)
477
477
  dMatrix = Hash.new
478
- @root.taxa.each {|taxon1|
479
- dMatrix[taxon1] = Hash.new
480
- taxon1Node = @root.findNode(taxon1)
481
- @root.taxa.each {|taxon2|
482
- if (taxon1 == taxon2)
483
- dMatrix[taxon1][taxon2] = 0.0
484
- else
485
- taxon2Node = @root.findNode(taxon2)
486
- lca = taxon1Node.lca(taxon2Node)
487
- dMatrix[taxon1][taxon2] = taxon1Node.distToAncestor(lca) +
488
- taxon2Node.distToAncestor(lca)
489
- end
490
- }
491
- }
478
+ leaves = root.leaves
479
+ num = (leaves.size)**2
480
+ numpercent = num/100
481
+ count = 0
482
+
483
+ leaves.each do |leaf1|
484
+ dMatrix[leaf1.name] = Hash.new
485
+ leaves.each do |leaf2|
486
+ count += 1
487
+ if (verbose && count % numpercent == 0)
488
+ STDERR.printf("Processing %s %s (%d of %d)\n", leaf1.name, leaf2.name, count, num)
489
+ end
490
+ if (leaf1 == leaf2)
491
+ dMatrix[leaf1.name][leaf2.name] = 0.0
492
+ else
493
+ lca = leaf1.lca(leaf2)
494
+ dMatrix[leaf1.name][leaf2.name] = leaf1.distToAncestor(lca) + leaf2.distToAncestor(lca)
495
+ end
496
+ end
497
+ end
492
498
  return dMatrix
493
499
  end
494
500
 
@@ -496,22 +502,22 @@ class NewickTree
496
502
  def compare(tree)
497
503
  tree1 = self.dup.unroot
498
504
  tree2 = tree.dup.unroot
499
-
505
+
500
506
  diff1 = []
501
507
  diff2 = []
502
508
  if (tree1.taxa == tree2.taxa)
503
509
  clades1 = tree1.clades
504
510
  clades2 = tree2.clades
505
- clades1.each {|clade|
506
- if (!clades2.include?(clade))
507
- diff1.push(clade)
508
- end
509
- }
510
- clades2.each {|clade|
511
- if (!clades1.include?(clade))
512
- diff2.push(clade)
513
- end
514
- }
511
+ clades1.each do |clade|
512
+ if (!clades2.include?(clade))
513
+ diff1.push(clade)
514
+ end
515
+ end
516
+ clades2.each do |clade|
517
+ if (!clades1.include?(clade))
518
+ diff2.push(clade)
519
+ end
520
+ end
515
521
  else
516
522
  raise NewickParseError, "The trees have different taxa!"
517
523
  end
@@ -531,9 +537,9 @@ class NewickTree
531
537
  left, right = @root.children
532
538
  left, right = right, left if (right.leaf?) # don't uproot leaf side
533
539
  left.edgeLen += right.edgeLen
534
- right.children.each {|child|
540
+ right.children.each do |child|
535
541
  @root.addChild(child)
536
- }
542
+ end
537
543
  @root.removeChild(right)
538
544
  return self
539
545
  end
@@ -560,37 +566,37 @@ class NewickTree
560
566
  greatestDist = 0
561
567
  dist = Hash.new
562
568
  org1, org2 = nil, nil
563
- @root.leaves.each {|node1|
564
- @root.leaves.each {|node2|
569
+ @root.leaves.each do |node1|
570
+ @root.leaves.each do |node2|
565
571
  dist[node1] = Hash.new if dist[node1].nil?
566
572
  dist[node2] = Hash.new if dist[node2].nil?
567
573
  next if (!dist[node1][node2].nil?)
568
574
  lca = node1.lca(node2)
569
575
  dist[node1][node2] = node1.distToAncestor(lca) +
570
- node2.distToAncestor(lca)
576
+ node2.distToAncestor(lca)
571
577
  dist[node2][node1] = dist[node1][node2]
572
578
  if (dist[node1][node2] > greatestDist)
573
579
  org1 = node1
574
580
  org2 = node2
575
581
  greatestDist = dist[node1][node2]
576
- end
577
- }
578
- }
582
+ end
583
+ end
584
+ end
579
585
  return org1, org2, greatestDist
580
586
  end
581
587
 
582
588
  # add EC numbers from alignment
583
589
  def addECnums(alignFile)
584
590
  ec = Hash.new
585
- File.new(alignFile).each {|line|
591
+ File.new(alignFile).each do |line|
586
592
  if (line =~ /^>/)
587
- definition = line.chomp[1..line.length]
588
- name = definition.split(" ").first
589
- if (definition =~ /\[EC:([0-9|\.]*)/)
590
- ec[name] = name + "_" + $1
591
- end
593
+ definition = line.chomp[1..line.length]
594
+ name = definition.split(" ").first
595
+ if (definition =~ /\[EC:([0-9|\.]*)/)
596
+ ec[name] = name + "_" + $1
597
+ end
592
598
  end
593
- }
599
+ end
594
600
  unAlias(ec)
595
601
  end
596
602
 
@@ -626,23 +632,23 @@ class NewickTree
626
632
  # returns array of arrays representing the tree clades
627
633
  def clades(bootstrap = false)
628
634
  clades = []
629
- @root.descendants.each {|clade|
635
+ @root.descendants.each do |clade|
630
636
  clades.push(clade.taxa(bootstrap)) if (!clade.children.empty?)
631
- }
637
+ end
632
638
  return clades
633
639
  end
634
640
 
635
641
  # add bootstrap values (given in clade arrays) to a tree
636
642
  def addBootStrap(bootClades)
637
- @root.descendants.each {|clade|
643
+ @root.descendants.each do |clade|
638
644
  next if clade.leaf?
639
- bootClades.each {|bClade|
640
- boot, rest = bClade.first, bClade[1..bClade.size - 1]
641
- if (rest == clade.taxa ) # same clade found
642
- clade.name = boot
643
- end
644
- }
645
- }
645
+ bootClades.each do |bClade|
646
+ boot, rest = bClade.first, bClade[1..bClade.size - 1]
647
+ if (rest == clade.taxa ) # same clade found
648
+ clade.name = boot
649
+ end
650
+ end
651
+ end
646
652
  end
647
653
 
648
654
  # return array of arrays of taxa representing relatives at each level
@@ -653,23 +659,23 @@ class NewickTree
653
659
  else
654
660
  relatives = []
655
661
  while(!node.parent.nil?)
656
- relatives.push(node.parent.taxa - node.taxa)
657
- node = node.parent
662
+ relatives.push(node.parent.taxa - node.taxa)
663
+ node = node.parent
658
664
  end
659
665
  return relatives
660
666
  end
661
667
  end
662
668
 
663
-
669
+
664
670
  # Fixes PHYLIP's mistake of using branch lengths and not node values
665
671
  def fixPhylip
666
- @root.descendants.each {|child|
672
+ @root.descendants.each do |child|
667
673
  br = child.edgeLen.to_i
668
674
  child.edgeLen = 0
669
675
  if (br > 0 && !child.leaf?)
670
676
  child.name = br.to_s
671
677
  end
672
- }
678
+ end
673
679
  end
674
680
 
675
681
 
@@ -678,189 +684,189 @@ class NewickTree
678
684
  yPos = 0.25
679
685
  @root.reorder
680
686
  leaves = @root.leaves.sort {|x, y| x.nodesToNode(y) <=> y.nodesToNode(x)}
681
- leaves.each {|leaf|
687
+ leaves.each do |leaf|
682
688
  leaf.y = yPos
683
689
  yPos += yUnit
684
- }
685
- nodes = @root.intNodes.sort{|x, y| y.nodesToAncestor(@root) <=>
686
- x.nodesToAncestor(@root)}
687
- nodes.each {|node|
688
- node.calcYPos
689
- }
690
- @root.calcYPos
691
- @root.calcXPos
692
- nodes = @root.intNodes.sort{|x, y| x.nodesToAncestor(@root) <=>
693
- y.nodesToAncestor(@root)}
694
- nodes.each {|node|
695
- @root.calcXPos # (forwards from root)
696
- }
697
- end
698
-
699
- # function to generate gi link to ncbi for draw, below
700
- def giLink(entry)
701
- ncbiLink = "http://www.ncbi.nlm.nih.gov/entrez/"
702
- protLink = "viewer.fcgi?db=protein&val="
703
- if (entry =~ /^gi[\_]*([0-9]*)/ || entry =~ /(^[A-Z|0-9]*)\|/)
704
- return ncbiLink + protLink + $1
705
- else
706
- return nil
707
690
  end
708
- end
709
-
710
- # returns PDF representation of branching structure of tree
711
- def draw(pdfFile, boot="width", linker = :giLink, labelName = false,
712
- highlights = Hash.new, brackets = nil, rawNames = false)
713
- colors = {"goldenrod4"=>[139, 105, 20], "lightcyan"=>[224, 255, 255], "rosybrown1"=>[255, 193, 193], "sienna1"=>[255, 130, 71], "lavender"=>[230, 230, 250], "rosybrown2"=>[238, 180, 180], "wheat1"=>[255, 231, 186], "linen"=>[250, 240, 230], "beige"=>[245, 245, 220], "sienna2"=>[238, 121, 66], "paleturquoise1"=>[187, 255, 255], "pink1"=>[255, 181, 197], "wheat2"=>[238, 216, 174], "violetred"=>[208, 32, 144], "palegreen"=>[152, 251, 152], "gray50"=>[127, 127, 127], "rosybrown3"=>[205, 155, 155], "sienna3"=>[205, 104, 57], "paleturquoise2"=>[174, 238, 238], "green1"=>[0, 255, 0], "pink2"=>[238, 169, 184], "wheat3"=>[205, 186, 150], "lightskyblue1"=>[176, 226, 255], "gray51"=>[130, 130, 130], "rosybrown4"=>[139, 105, 105], "sienna4"=>[139, 71, 38], "paleturquoise3"=>[150, 205, 205], "green2"=>[0, 238, 0], "pink3"=>[205, 145, 158], "wheat4"=>[139, 126, 102], "lightskyblue2"=>[164, 211, 238], "yellow1"=>[255, 255, 0], "sgilightgray"=>[170, 170, 170], "paleturquoise4"=>[102, 139, 139], "green3"=>[0, 205, 0], "pink4"=>[139, 99, 108], "lightskyblue3"=>[141, 182, 205], "yellow2"=>[238, 238, 0], "gray52"=>[133, 133, 133], "mediumorchid"=>[186, 85, 211], "green4"=>[0, 139, 0], "lightskyblue4"=>[96, 123, 139], "ivory1"=>[255, 255, 240], "yellow3"=>[205, 205, 0], "plum1"=>[255, 187, 255], "lightblue1"=>[191, 239, 255], "seashell1"=>[255, 245, 238], "gray53"=>[135, 135, 135], "ivory2"=>[238, 238, 224], "violetred1"=>[255, 62, 150], "plum2"=>[238, 174, 238], "lightblue2"=>[178, 223, 238], "seashell2"=>[238, 229, 222], "gray54"=>[138, 138, 138], "white"=>[255, 255, 255], "mediumslateblue"=>[123, 104, 238], "ivory3"=>[205, 205, 193], "yellow4"=>[139, 139, 0], "lightcyan1"=>[224, 255, 255], "plum3"=>[205, 150, 205], "lightslateblue"=>[132, 112, 255], "lightblue3"=>[154, 192, 205], "seashell3"=>[205, 197, 191], "gray55"=>[140, 140, 140], "ivory4"=>[139, 139, 131], "lightcyan2"=>[209, 238, 238], "violetred2"=>[238, 58, 140], "peru"=>[205, 133, 63], "lightblue4"=>[104, 131, 139], "seashell4"=>[139, 134, 130], "gray56"=>[143, 143, 143], "flesh"=>[255, 125, 64], "lightcyan3"=>[180, 205, 205], "violetred3"=>[205, 50, 120], "plum4"=>[139, 102, 139], "lightblue"=>[173, 216, 230], "gray57"=>[145, 145, 145], "coral"=>[255, 127, 80], "cadmiumorange"=>[255, 97, 3], "khaki1"=>[255, 246, 143], "lightcyan4"=>[122, 139, 139], "violetred4"=>[139, 34, 82], "lightslategray"=>[119, 136, 153], "gray58"=>[148, 148, 148], "sgigray32"=>[81, 81, 81], "khaki2"=>[238, 230, 133], "dodgerblue1"=>[30, 144, 255], "lavenderblush1"=>[255, 240, 245], "gray59"=>[150, 150, 150], "khaki3"=>[205, 198, 115], "dodgerblue2"=>[28, 134, 238], "lavenderblush2"=>[238, 224, 229], "banana"=>[227, 207, 87], "khaki4"=>[139, 134, 78], "dodgerblue3"=>[24, 116, 205], "lavenderblush3"=>[205, 193, 197], "cyan2"=>[0, 238, 238], "cadetblue"=>[95, 158, 160], "cadmiumyellow"=>[255, 153, 18], "mediumpurple"=>[147, 112, 219], "dodgerblue4"=>[16, 78, 139], "lavenderblush4"=>[139, 131, 134], "cyan3"=>[0, 205, 205], "silver"=>[192, 192, 192], "sgigray36"=>[91, 91, 91], "cyan4"=>[0, 139, 139], "deeppink1"=>[255, 20, 147], "burntumber"=>[138, 51, 36], "deeppink2"=>[238, 18, 137], "aliceblue"=>[240, 248, 255], "rosybrown"=>[188, 143, 143], "aquamarine"=>[127, 255, 212], "plum"=>[221, 160, 221], "deeppink3"=>[205, 16, 118], "darkgoldenrod"=>[184, 134, 11], "darkslategray1"=>[151, 255, 255], "chartreuse1"=>[127, 255, 0], "deeppink4"=>[139, 10, 80], "antiquewhite"=>[250, 235, 215], "darkslategray2"=>[141, 238, 238], "chartreuse2"=>[118, 238, 0], "darkslategray3"=>[121, 205, 205], "raspberry"=>[135, 38, 87], "chartreuse3"=>[102, 205, 0], "darkslategray4"=>[82, 139, 139], "chartreuse4"=>[69, 139, 0], "lightsalmon"=>[255, 160, 122], "warmgrey"=>[128, 128, 105], "cobalt"=>[61, 89, 171], "pink"=>[255, 192, 203], "orangered"=>[255, 69, 0], "indianred"=>[205, 92, 92], "palegreen1"=>[154, 255, 154], "red1"=>[255, 0, 0], "darkorange1"=>[255, 127, 0], "palegreen2"=>[144, 238, 144], "darkorchid"=>[153, 50, 204], "red2"=>[238, 0, 0], "darkorange2"=>[238, 118, 0], "palegreen3"=>[124, 205, 124], "goldenrod"=>[218, 165, 32], "red3"=>[205, 0, 0], "tomato1"=>[255, 99, 71], "yellowgreen"=>[154, 205, 50], "darkorange3"=>[205, 102, 0], "palegreen4"=>[84, 139, 84], "gray30"=>[77, 77, 77], "red4"=>[139, 0, 0], "tomato2"=>[238, 92, 66], "darkorange4"=>[139, 69, 0], "antiquewhite1"=>[255, 239, 219], "gray31"=>[79, 79, 79], "brown"=>[165, 42, 42], "tomato3"=>[205, 79, 57], "thistle1"=>[255, 225, 255], "antiquewhite2"=>[238, 223, 204], "darkolivegreen1"=>[202, 255, 112], "gray32"=>[82, 82, 82], "gray80"=>[204, 204, 204], "tomato4"=>[139, 54, 38], "sepia"=>[94, 38, 18], "thistle2"=>[238, 210, 238], "deepskyblue"=>[0, 191, 255], "antiquewhite3"=>[205, 192, 176], "darkolivegreen2"=>[188, 238, 104], "cornflowerblue"=>[100, 149, 237], "gray33"=>[84, 84, 84], "gray81"=>[207, 207, 207], "thistle3"=>[205, 181, 205], "peachpuff"=>[255, 218, 185], "steelblue1"=>[99, 184, 255], "antiquewhite4"=>[139, 131, 120], "darkolivegreen3"=>[162, 205, 90], "gray34"=>[87, 87, 87], "gray82"=>[209, 209, 209], "maroon"=>[128, 0, 0], "thistle4"=>[139, 123, 139], "springgreen1"=>[0, 238, 118], "steelblue2"=>[92, 172, 238], "darkolivegreen4"=>[110, 139, 61], "gray35"=>[89, 89, 89], "gray83"=>[212, 212, 212], "springgreen2"=>[0, 205, 102], "steelblue3"=>[79, 148, 205], "steelblue"=>[70, 130, 180], "gray36"=>[92, 92, 92], "gray84"=>[214, 214, 214], "springgreen3"=>[0, 139, 69], "steelblue4"=>[54, 100, 139], "gray37"=>[94, 94, 94], "blue2"=>[0, 0, 238], "darkturquoise"=>[0, 206, 209], "gray38"=>[97, 97, 97], "gray85"=>[217, 217, 217], "sgigray12"=>[30, 30, 30], "blanchedalmond"=>[255, 235, 205], "violet"=>[238, 130, 238], "blue3"=>[0, 0, 205], "gray39"=>[99, 99, 99], "gray86"=>[219, 219, 219], "burlywood1"=>[255, 211, 155], "navy"=>[0, 0, 128], "darkviolet"=>[148, 0, 211], "blue4"=>[0, 0, 139], "gray87"=>[222, 222, 222], "burlywood2"=>[238, 197, 145], "floralwhite"=>[255, 250, 240], "turquoise"=>[64, 224, 208], "darkorange"=>[255, 140, 0], "gray88"=>[224, 224, 224], "burlywood3"=>[205, 170, 125], "gray89"=>[227, 227, 227], "dimgray"=>[105, 105, 105], "sgigray16"=>[40, 40, 40], "snow"=>[255, 250, 250], "burlywood4"=>[139, 115, 85], "mediumvioletred"=>[199, 21, 133], "seagreen"=>[46, 139, 87], "purple1"=>[155, 48, 255], "lightsteelblue1"=>[202, 225, 255], "purple2"=>[145, 44, 238], "orangered1"=>[255, 69, 0], "lightsteelblue2"=>[188, 210, 238], "purple3"=>[125, 38, 205], "cyan/aqua"=>[0, 255, 255], "orangered2"=>[238, 64, 0], "lightsteelblue3"=>[162, 181, 205], "purple4"=>[85, 26, 139], "orangered3"=>[205, 55, 0], "fuchsia"=>[255, 0, 255], "lightsteelblue4"=>[110, 123, 139], "mistyrose1"=>[255, 228, 225], "orangered4"=>[139, 37, 0], "darkorchid1"=>[191, 62, 255], "lemonchiffon1"=>[255, 250, 205], "mistyrose2"=>[238, 213, 210], "darkorchid2"=>[178, 58, 238], "lemonchiffon2"=>[238, 233, 191], "mistyrose3"=>[205, 183, 181], "royalblue"=>[65, 105, 225], "darkorchid3"=>[154, 50, 205], "lemonchiffon3"=>[205, 201, 165], "sgiolivedrab"=>[142, 142, 56], "mistyrose4"=>[139, 125, 123], "darkorchid4"=>[104, 34, 139], "peachpuff1"=>[255, 218, 185], "mediumseagreen"=>[60, 179, 113], "lemonchiffon4"=>[139, 137, 112], "lightgreen"=>[144, 238, 144], "peachpuff2"=>[238, 203, 173], "peachpuff3"=>[205, 175, 149], "peachpuff4"=>[139, 119, 101], "lightsteelblue"=>[176, 196, 222], "skyblue"=>[135, 206, 235], "gray10"=>[26, 26, 26], "magenta"=>[255, 0, 255], "turquoise1"=>[0, 245, 255], "gray11"=>[28, 28, 28], "turquoise2"=>[0, 229, 238], "chartreuse"=>[127, 255, 0], "navajowhite"=>[255, 222, 173], "ghostwhite"=>[248, 248, 255], "gray12"=>[31, 31, 31], "gray60"=>[153, 153, 153], "melon"=>[227, 168, 105], "turquoise3"=>[0, 197, 205], "gray13"=>[33, 33, 33], "gray61"=>[156, 156, 156], "coral1"=>[255, 114, 86], "turquoise4"=>[0, 134, 139], "gray14"=>[36, 36, 36], "gray62"=>[158, 158, 158], "sgiteal"=>[56, 142, 142], "coral2"=>[238, 106, 80], "honeydew"=>[240, 255, 240], "gray1"=>[3, 3, 3], "gray15"=>[38, 38, 38], "firebrick"=>[178, 34, 34], "coral3"=>[205, 91, 69], "lightpink"=>[255, 182, 193], "gray2"=>[5, 5, 5], "gray16"=>[41, 41, 41], "gray63"=>[161, 161, 161], "coral4"=>[139, 62, 47], "mediumblue"=>[0, 0, 205], "gray3"=>[8, 8, 8], "gray17"=>[43, 43, 43], "gray64"=>[163, 163, 163], "blueviolet"=>[138, 43, 226], "darkgreen"=>[0, 100, 0], "gray4"=>[10, 10, 10], "gray18"=>[46, 46, 46], "gray65"=>[166, 166, 166], "deepskyblue1"=>[0, 191, 255], "gray5"=>[13, 13, 13], "gray19"=>[48, 48, 48], "gray66"=>[168, 168, 168], "mediumspringgreen"=>[0, 250, 154], "darkkhaki"=>[189, 183, 107], "lightgoldenrodyellow"=>[250, 250, 210], "orange"=>[255, 128, 0], "deepskyblue2"=>[0, 178, 238], "gray6"=>[15, 15, 15], "gray67"=>[171, 171, 171], "mediumturquoise"=>[72, 209, 204], "deepskyblue3"=>[0, 154, 205], "turquoiseblue"=>[0, 199, 140], "gray7"=>[18, 18, 18], "gray68"=>[173, 173, 173], "orchid"=>[218, 112, 214], "burlywood"=>[222, 184, 135], "thistle"=>[216, 191, 216], "mediumpurple1"=>[171, 130, 255], "deepskyblue4"=>[0, 104, 139], "gray8"=>[20, 20, 20], "gray69"=>[176, 176, 176], "palevioletred"=>[219, 112, 147], "sandybrown"=>[244, 164, 96], "mediumpurple2"=>[159, 121, 238], "yellow"=>[255, 255, 0], "darkgoldenrod1"=>[255, 185, 15], "gray9"=>[23, 23, 23], "darkseagreen"=>[143, 188, 143], "mediumpurple3"=>[137, 104, 205], "darkgoldenrod2"=>[238, 173, 14], "sgigray92"=>[234, 234, 234], "mediumpurple4"=>[93, 71, 139], "darkgoldenrod3"=>[205, 149, 12], "mediumaquamarine"=>[102, 205, 170], "firebrick1"=>[255, 48, 48], "tomato"=>[255, 99, 71], "darkgoldenrod4"=>[139, 101, 8], "gray"=>[128, 128, 128], "firebrick2"=>[238, 44, 44], "palegoldenrod"=>[238, 232, 170], "moccasin"=>[255, 228, 181], "firebrick3"=>[205, 38, 38], "snow1"=>[255, 250, 250], "sgigray96"=>[244, 244, 244], "firebrick4"=>[139, 26, 26], "snow2"=>[238, 233, 233], "papayawhip"=>[255, 239, 213], "snow3"=>[205, 201, 201], "eggshell"=>[252, 230, 201], "snow4"=>[139, 137, 137], "tan"=>[210, 180, 140], "peacock"=>[51, 161, 201], "gold1"=>[255, 215, 0], "slateblue1"=>[131, 111, 255], "springgreen"=>[0, 255, 127], "ivoryblack"=>[41, 36, 33], "gold2"=>[238, 201, 0], "honeydew1"=>[240, 255, 240], "greenyellow"=>[173, 255, 47], "slateblue2"=>[122, 103, 238], "gainsboro"=>[220, 220, 220], "azure"=>[240, 255, 255], "gold3"=>[205, 173, 0], "oldlace"=>[253, 245, 230], "honeydew2"=>[224, 238, 224], "gold4"=>[139, 117, 0], "honeydew3"=>[193, 205, 193], "slateblue3"=>[105, 89, 205], "green"=>[0, 128, 0], "skyblue1"=>[135, 206, 255], "honeydew4"=>[131, 139, 131], "cadetblue1"=>[152, 245, 255], "slateblue4"=>[71, 60, 139], "sienna"=>[160, 82, 45], "darksalmon"=>[233, 150, 122], "skyblue2"=>[126, 192, 238], "cadetblue2"=>[142, 229, 238], "sapgreen"=>[48, 128, 20], "gray40"=>[102, 102, 102], "skyblue3"=>[108, 166, 205], "midnightblue"=>[25, 25, 112], "blue"=>[0, 0, 255], "cadetblue3"=>[122, 197, 205], "sgichartreuse"=>[113, 198, 113], "skyblue4"=>[74, 112, 139], "cadetblue4"=>[83, 134, 139], "lime"=>[0, 255, 0], "gray90"=>[229, 229, 229], "gray42"=>[105, 105, 105], "mistyrose"=>[255, 228, 225], "burntsienna"=>[138, 54, 15], "ivory"=>[255, 255, 240], "gray43"=>[110, 110, 110], "gray91"=>[232, 232, 232], "darkcyan"=>[0, 139, 139], "gray44"=>[112, 112, 112], "gray92"=>[235, 235, 235], "lawngreen"=>[124, 252, 0], "gray45"=>[115, 115, 115], "gray93"=>[237, 237, 237], "palevioletred1"=>[255, 130, 171], "saddlebrown"=>[139, 69, 19], "lavenderblush"=>[255, 240, 245], "gray46"=>[117, 117, 117], "gray94"=>[240, 240, 240], "palevioletred2"=>[238, 121, 159], "khaki"=>[240, 230, 140], "paleturquoise"=>[174, 238, 238], "gray47"=>[120, 120, 120], "gray95"=>[242, 242, 242], "carrot"=>[237, 145, 33], "palevioletred3"=>[205, 104, 137], "lightsalmon1"=>[255, 160, 122], "olivedrab"=>[107, 142, 35], "gray48"=>[122, 122, 122], "palevioletred4"=>[139, 71, 93], "wheat"=>[245, 222, 179], "lightsalmon2"=>[238, 149, 114], "powderblue"=>[176, 224, 230], "gray49"=>[125, 125, 125], "gray96"=>[245, 245, 245], "red"=>[255, 0, 0], "brown1"=>[255, 64, 64], "lightsalmon3"=>[205, 129, 98], "manganeseblue"=>[3, 168, 158], "gray97"=>[247, 247, 247], "brown2"=>[238, 59, 59], "lightsalmon4"=>[139, 87, 66], "olive"=>[128, 128, 0], "gray98"=>[250, 250, 250], "lightgrey"=>[211, 211, 211], "sgigray72"=>[183, 183, 183], "brown3"=>[205, 51, 51], "gold"=>[255, 215, 0], "mintcream"=>[245, 255, 250], "gray99"=>[252, 252, 252], "brown4"=>[139, 35, 35], "sgidarkgray"=>[85, 85, 85], "magenta2"=>[238, 0, 238], "sgigray76"=>[193, 193, 193], "magenta3"=>[205, 0, 205], "dodgerblue"=>[30, 144, 255], "magenta4"=>[139, 0, 139], "cobaltgreen"=>[61, 145, 64], "sgisalmon"=>[198, 113, 113], "emeraldgreen"=>[0, 201, 87], "sgibrightgray"=>[197, 193, 170], "darkred"=>[139, 0, 0], "rawsienna"=>[199, 97, 20], "seagreen1"=>[84, 255, 159], "lightyellow"=>[255, 255, 224], "olivedrab1"=>[192, 255, 62], "orchid1"=>[255, 131, 250], "seashell"=>[255, 245, 238], "seagreen2"=>[78, 238, 148], "bisque1"=>[255, 228, 196], "olivedrab2"=>[179, 238, 58], "orchid2"=>[238, 122, 233], "azure1"=>[240, 255, 255], "seagreen3"=>[67, 205, 128], "bisque2"=>[238, 213, 183], "whitesmoke"=>[245, 245, 245], "olivedrab3"=>[154, 205, 50], "orchid3"=>[205, 105, 201], "azure2"=>[224, 238, 238], "lightpink1"=>[255, 174, 185], "lightgoldenrod1"=>[255, 236, 139], "bisque3"=>[205, 183, 158], "olivedrab4"=>[105, 139, 34], "orchid4"=>[139, 71, 137], "purple"=>[128, 0, 128], "lemonchiffon"=>[255, 250, 205], "azure3"=>[193, 205, 205], "lightpink2"=>[238, 162, 173], "seagreen4"=>[46, 139, 87], "forestgreen"=>[34, 139, 34], "lightgoldenrod2"=>[238, 220, 130], "bisque4"=>[139, 125, 107], "sgislateblue"=>[113, 113, 198], "azure4"=>[131, 139, 139], "lightpink3"=>[205, 140, 149], "lightgoldenrod3"=>[205, 190, 112], "gray20"=>[51, 51, 51], "sgibeet"=>[142, 56, 142], "limegreen"=>[50, 205, 50], "orange1"=>[255, 165, 0], "lightpink4"=>[139, 95, 101], "lightgoldenrod4"=>[139, 129, 76], "gray21"=>[54, 54, 54], "orange2"=>[238, 154, 0], "gray22"=>[56, 56, 56], "gray70"=>[179, 179, 179], "orange3"=>[205, 133, 0], "gray23"=>[59, 59, 59], "gray71"=>[181, 181, 181], "orange4"=>[139, 90, 0], "lightseagreen"=>[32, 178, 170], "bisque"=>[255, 228, 196], "gray24"=>[61, 61, 61], "gray72"=>[184, 184, 184], "darkslateblue"=>[72, 61, 139], "gray25"=>[64, 64, 64], "gray73"=>[186, 186, 186], "lightcoral"=>[240, 128, 128], "tan1"=>[255, 165, 79], "gray26"=>[66, 66, 66], "black"=>[0, 0, 0], "tan2"=>[238, 154, 73], "gray27"=>[69, 69, 69], "gray74"=>[189, 189, 189], "teal"=>[0, 128, 128], "tan3"=>[205, 133, 63], "aquamarine1"=>[127, 255, 212], "gray28"=>[71, 71, 71], "gray75"=>[191, 191, 191], "tan4"=>[139, 90, 43], "darkmagenta"=>[139, 0, 139], "aquamarine2"=>[118, 238, 198], "gray29"=>[74, 74, 74], "gray76"=>[194, 194, 194], "indianred1"=>[255, 106, 106], "chocolate"=>[210, 105, 30], "aquamarine3"=>[102, 205, 170], "gray77"=>[196, 196, 196], "indianred2"=>[238, 99, 99], "slategray1"=>[198, 226, 255], "chocolate1"=>[255, 127, 36], "aquamarine4"=>[69, 139, 116], "gray78"=>[199, 199, 199], "sgigray52"=>[132, 132, 132], "indianred3"=>[205, 85, 85], "salmon"=>[250, 128, 114], "darkblue"=>[0, 0, 139], "lightyellow1"=>[255, 255, 224], "slategray2"=>[185, 211, 238], "chocolate2"=>[238, 118, 33], "gray79"=>[201, 201, 201], "indianred4"=>[139, 58, 58], "hotpink"=>[255, 105, 180], "brick"=>[156, 102, 31], "lightyellow2"=>[238, 238, 209], "slategray3"=>[159, 182, 205], "chocolate3"=>[205, 102, 29], "darkgray"=>[169, 169, 169], "lightyellow3"=>[205, 205, 180], "darkolivegreen"=>[85, 107, 47], "slategray4"=>[108, 123, 139], "chocolate4"=>[139, 69, 19], "salmon1"=>[255, 140, 105], "deeppink"=>[255, 20, 147], "indigo"=>[75, 0, 130], "darkslategray"=>[47, 79, 79], "navajowhite1"=>[255, 222, 173], "lightyellow4"=>[139, 139, 122], "royalblue1"=>[72, 118, 255], "slateblue"=>[106, 90, 205], "maroon1"=>[255, 52, 179], "sgigray56"=>[142, 142, 142], "salmon2"=>[238, 130, 98], "navajowhite2"=>[238, 207, 161], "coldgrey"=>[128, 138, 135], "royalblue2"=>[67, 110, 238], "cornsilk1"=>[255, 248, 220], "maroon2"=>[238, 48, 167], "salmon3"=>[205, 112, 84], "navajowhite3"=>[205, 179, 139], "royalblue3"=>[58, 95, 205], "cornsilk2"=>[238, 232, 205], "maroon3"=>[205, 41, 144], "slategray"=>[112, 128, 144], "salmon4"=>[139, 76, 57], "navajowhite4"=>[139, 121, 94], "royalblue4"=>[39, 64, 139], "darkseagreen1"=>[193, 255, 193], "cornsilk3"=>[205, 200, 177], "maroon4"=>[139, 28, 98], "hotpink1"=>[255, 110, 180], "mediumorchid1"=>[224, 102, 255], "darkseagreen2"=>[180, 238, 180], "cornsilk4"=>[139, 136, 120], "mint"=>[189, 252, 201], "hotpink2"=>[238, 106, 167], "sgilightblue"=>[125, 158, 192], "goldenrod1"=>[255, 193, 37], "mediumorchid2"=>[209, 95, 238], "darkseagreen3"=>[155, 205, 155], "hotpink3"=>[205, 96, 144], "goldenrod2"=>[238, 180, 34], "mediumorchid3"=>[180, 82, 205], "darkseagreen4"=>[105, 139, 105], "hotpink4"=>[139, 58, 98], "crimson"=>[220, 20, 60], "lightskyblue"=>[135, 206, 250], "goldenrod3"=>[205, 155, 29], "mediumorchid4"=>[122, 55, 139], "cornsilk"=>[255, 248, 220]}
714
- pdf=FPDF.new('P', "cm")
715
- pdf.SetTitle(pdfFile)
716
- pdf.SetCreator("newickDraw")
717
- pdf.SetAuthor(ENV["USER"]) if (!ENV["USER"].nil?)
718
- pdf.AddPage
719
- yUnit = nil
720
- lineWidth = nil
721
- fontSize = nil
722
- bootScale = 0.6
723
- if (taxa.size < 30)
724
- fontSize = 10
725
- yUnit = 0.5
726
- lineWidth = 0.02
727
- elsif (taxa.size < 60)
728
- fontSize = 8
729
- yUnit = 0.25
730
- lineWidth = 0.01
731
- elsif (taxa.size < 150)
732
- fontSize = 8
733
- yUnit = 0.197
734
- lineWidth = 0.01
735
- elsif (taxa.size < 300)
736
- fontSize = 2
737
- yUnit = 0.09
738
- lineWidth = 0.005
739
- elsif (taxa.size < 400)
740
- fontSize = 2
741
- yUnit = 0.055
742
- lineWidth = 0.002
743
- elsif (taxa.size < 800)
744
- fontSize = 1
745
- yUnit = 0.030
746
- lineWidth = 0.0015
747
- else
748
- fontSize = 0.5
749
- yUnit = 0.020
750
- lineWidth = 0.0010
751
- end
752
- bootScale = 0.5 * fontSize
753
- pdf.SetFont('Times','B', fontSize)
754
- calcPos(yUnit) # calculate node pos before drawing
755
- max = 0
756
- @root.leaves.each {|leaf|
757
- d = leaf.distToAncestor(@root)
758
- max = d if (max < d)
759
- }
760
- xScale = 10.0/max
761
- xOffSet = 0.25
762
- pdf.SetLineWidth(lineWidth)
763
- pdf.SetTextColor(0, 0, 0)
764
- pdf.Line(0, @root.y, xOffSet, @root.y)
765
- pdf.Line(xOffSet, @root.yMin, xOffSet, @root.yMax)
766
- @root.descendants.each {|child|
767
- if (!child.leaf?)
768
- if (child.name.to_i > 75 && boot == "width") # good bootstrap
769
- pdf.SetLineWidth(lineWidth * 5)
770
- else
771
- pdf.SetLineWidth(lineWidth)
691
+ nodes = @root.intNodes.sort{|x, y| y.nodesToAncestor(@root) <=>
692
+ x.nodesToAncestor(@root)}
693
+ nodes.each do |node|
694
+ node.calcYPos
695
+ end
696
+ @root.calcYPos
697
+ @root.calcXPos
698
+ nodes = @root.intNodes.sort{|x, y| x.nodesToAncestor(@root) <=>
699
+ y.nodesToAncestor(@root)}
700
+ nodes.each do |node|
701
+ @root.calcXPos # (forwards from root)
772
702
  end
773
- bootX = xOffSet + child.x*xScale
774
- bootY = ((child.yMin + child.yMax) / 2.0)
775
- pdf.SetXY(bootX, bootY)
776
- pdf.SetFont('Times','B', bootScale)
777
- pdf.Write(0, child.name.to_s)
778
- pdf.SetFont('Times','B', fontSize)
779
- pdf.Line(xOffSet + child.x*xScale, child.yMin,
780
- xOffSet + child.x*xScale, child.yMax)
781
- else
782
- if (child.parent.name.to_i > 75 && boot == "width") # good bootstrap
783
- pdf.SetLineWidth(lineWidth * 5)
703
+ end
704
+
705
+ # function to generate gi link to ncbi for draw, below
706
+ def giLink(entry)
707
+ ncbiLink = "http://www.ncbi.nlm.nih.gov/entrez/"
708
+ protLink = "viewer.fcgi?db=protein&val="
709
+ if (entry =~ /^gi[\_]*([0-9]*)/ || entry =~ /(^[A-Z|0-9]*)\|/)
710
+ return ncbiLink + protLink + $1
784
711
  else
785
- pdf.SetLineWidth(lineWidth)
712
+ return nil
786
713
  end
787
- pdf.SetXY(xOffSet + child.x*xScale, child.y)
788
- efields = child.name.split("__")
789
- entry, species = efields.first, efields.last
790
- if (entry =~/\{([^\}]*)\}/)
791
- species = $1
792
- end
793
- species = entry if species.nil? && !rawNames
794
- species = child.name if rawNames
795
- hl = false
796
- highlights.keys.each{|highlight|
797
- hl = highlights[highlight] if (entry.index(highlight))
798
- }
799
- if (pdfFile.index(entry)) # name of query taxon
800
- pdf.SetTextColor(colors["red"][0], colors["red"][1], colors["red"][2])
801
- pdf.Write(0, entry)
802
- pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2])
803
- elsif (linker && link = send(linker, entry))
804
- pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
805
- pdf.Write(0, species, link)
806
- pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
807
- elsif (!species.nil?)
808
- pdf.SetTextColor(colors[hl][0], colors[hl][1], colors[hl][2]) if hl
809
- pdf.Write(0, species)
810
- pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
714
+ end
715
+
716
+ # returns PDF representation of branching structure of tree
717
+ def draw(pdfFile, boot="width", linker = :giLink, labelName = false,
718
+ highlights = Hash.new, brackets = nil, rawNames = false)
719
+ colors = {"goldenrod4"=>[139, 105, 20], "lightcyan"=>[224, 255, 255], "rosybrown1"=>[255, 193, 193], "sienna1"=>[255, 130, 71], "lavender"=>[230, 230, 250], "rosybrown2"=>[238, 180, 180], "wheat1"=>[255, 231, 186], "linen"=>[250, 240, 230], "beige"=>[245, 245, 220], "sienna2"=>[238, 121, 66], "paleturquoise1"=>[187, 255, 255], "pink1"=>[255, 181, 197], "wheat2"=>[238, 216, 174], "violetred"=>[208, 32, 144], "palegreen"=>[152, 251, 152], "gray50"=>[127, 127, 127], "rosybrown3"=>[205, 155, 155], "sienna3"=>[205, 104, 57], "paleturquoise2"=>[174, 238, 238], "green1"=>[0, 255, 0], "pink2"=>[238, 169, 184], "wheat3"=>[205, 186, 150], "lightskyblue1"=>[176, 226, 255], "gray51"=>[130, 130, 130], "rosybrown4"=>[139, 105, 105], "sienna4"=>[139, 71, 38], "paleturquoise3"=>[150, 205, 205], "green2"=>[0, 238, 0], "pink3"=>[205, 145, 158], "wheat4"=>[139, 126, 102], "lightskyblue2"=>[164, 211, 238], "yellow1"=>[255, 255, 0], "sgilightgray"=>[170, 170, 170], "paleturquoise4"=>[102, 139, 139], "green3"=>[0, 205, 0], "pink4"=>[139, 99, 108], "lightskyblue3"=>[141, 182, 205], "yellow2"=>[238, 238, 0], "gray52"=>[133, 133, 133], "mediumorchid"=>[186, 85, 211], "green4"=>[0, 139, 0], "lightskyblue4"=>[96, 123, 139], "ivory1"=>[255, 255, 240], "yellow3"=>[205, 205, 0], "plum1"=>[255, 187, 255], "lightblue1"=>[191, 239, 255], "seashell1"=>[255, 245, 238], "gray53"=>[135, 135, 135], "ivory2"=>[238, 238, 224], "violetred1"=>[255, 62, 150], "plum2"=>[238, 174, 238], "lightblue2"=>[178, 223, 238], "seashell2"=>[238, 229, 222], "gray54"=>[138, 138, 138], "white"=>[255, 255, 255], "mediumslateblue"=>[123, 104, 238], "ivory3"=>[205, 205, 193], "yellow4"=>[139, 139, 0], "lightcyan1"=>[224, 255, 255], "plum3"=>[205, 150, 205], "lightslateblue"=>[132, 112, 255], "lightblue3"=>[154, 192, 205], "seashell3"=>[205, 197, 191], "gray55"=>[140, 140, 140], "ivory4"=>[139, 139, 131], "lightcyan2"=>[209, 238, 238], "violetred2"=>[238, 58, 140], "peru"=>[205, 133, 63], "lightblue4"=>[104, 131, 139], "seashell4"=>[139, 134, 130], "gray56"=>[143, 143, 143], "flesh"=>[255, 125, 64], "lightcyan3"=>[180, 205, 205], "violetred3"=>[205, 50, 120], "plum4"=>[139, 102, 139], "lightblue"=>[173, 216, 230], "gray57"=>[145, 145, 145], "coral"=>[255, 127, 80], "cadmiumorange"=>[255, 97, 3], "khaki1"=>[255, 246, 143], "lightcyan4"=>[122, 139, 139], "violetred4"=>[139, 34, 82], "lightslategray"=>[119, 136, 153], "gray58"=>[148, 148, 148], "sgigray32"=>[81, 81, 81], "khaki2"=>[238, 230, 133], "dodgerblue1"=>[30, 144, 255], "lavenderblush1"=>[255, 240, 245], "gray59"=>[150, 150, 150], "khaki3"=>[205, 198, 115], "dodgerblue2"=>[28, 134, 238], "lavenderblush2"=>[238, 224, 229], "banana"=>[227, 207, 87], "khaki4"=>[139, 134, 78], "dodgerblue3"=>[24, 116, 205], "lavenderblush3"=>[205, 193, 197], "cyan2"=>[0, 238, 238], "cadetblue"=>[95, 158, 160], "cadmiumyellow"=>[255, 153, 18], "mediumpurple"=>[147, 112, 219], "dodgerblue4"=>[16, 78, 139], "lavenderblush4"=>[139, 131, 134], "cyan3"=>[0, 205, 205], "silver"=>[192, 192, 192], "sgigray36"=>[91, 91, 91], "cyan4"=>[0, 139, 139], "deeppink1"=>[255, 20, 147], "burntumber"=>[138, 51, 36], "deeppink2"=>[238, 18, 137], "aliceblue"=>[240, 248, 255], "rosybrown"=>[188, 143, 143], "aquamarine"=>[127, 255, 212], "plum"=>[221, 160, 221], "deeppink3"=>[205, 16, 118], "darkgoldenrod"=>[184, 134, 11], "darkslategray1"=>[151, 255, 255], "chartreuse1"=>[127, 255, 0], "deeppink4"=>[139, 10, 80], "antiquewhite"=>[250, 235, 215], "darkslategray2"=>[141, 238, 238], "chartreuse2"=>[118, 238, 0], "darkslategray3"=>[121, 205, 205], "raspberry"=>[135, 38, 87], "chartreuse3"=>[102, 205, 0], "darkslategray4"=>[82, 139, 139], "chartreuse4"=>[69, 139, 0], "lightsalmon"=>[255, 160, 122], "warmgrey"=>[128, 128, 105], "cobalt"=>[61, 89, 171], "pink"=>[255, 192, 203], "orangered"=>[255, 69, 0], "indianred"=>[205, 92, 92], "palegreen1"=>[154, 255, 154], "red1"=>[255, 0, 0], "darkorange1"=>[255, 127, 0], "palegreen2"=>[144, 238, 144], "darkorchid"=>[153, 50, 204], "red2"=>[238, 0, 0], "darkorange2"=>[238, 118, 0], "palegreen3"=>[124, 205, 124], "goldenrod"=>[218, 165, 32], "red3"=>[205, 0, 0], "tomato1"=>[255, 99, 71], "yellowgreen"=>[154, 205, 50], "darkorange3"=>[205, 102, 0], "palegreen4"=>[84, 139, 84], "gray30"=>[77, 77, 77], "red4"=>[139, 0, 0], "tomato2"=>[238, 92, 66], "darkorange4"=>[139, 69, 0], "antiquewhite1"=>[255, 239, 219], "gray31"=>[79, 79, 79], "brown"=>[165, 42, 42], "tomato3"=>[205, 79, 57], "thistle1"=>[255, 225, 255], "antiquewhite2"=>[238, 223, 204], "darkolivegreen1"=>[202, 255, 112], "gray32"=>[82, 82, 82], "gray80"=>[204, 204, 204], "tomato4"=>[139, 54, 38], "sepia"=>[94, 38, 18], "thistle2"=>[238, 210, 238], "deepskyblue"=>[0, 191, 255], "antiquewhite3"=>[205, 192, 176], "darkolivegreen2"=>[188, 238, 104], "cornflowerblue"=>[100, 149, 237], "gray33"=>[84, 84, 84], "gray81"=>[207, 207, 207], "thistle3"=>[205, 181, 205], "peachpuff"=>[255, 218, 185], "steelblue1"=>[99, 184, 255], "antiquewhite4"=>[139, 131, 120], "darkolivegreen3"=>[162, 205, 90], "gray34"=>[87, 87, 87], "gray82"=>[209, 209, 209], "maroon"=>[128, 0, 0], "thistle4"=>[139, 123, 139], "springgreen1"=>[0, 238, 118], "steelblue2"=>[92, 172, 238], "darkolivegreen4"=>[110, 139, 61], "gray35"=>[89, 89, 89], "gray83"=>[212, 212, 212], "springgreen2"=>[0, 205, 102], "steelblue3"=>[79, 148, 205], "steelblue"=>[70, 130, 180], "gray36"=>[92, 92, 92], "gray84"=>[214, 214, 214], "springgreen3"=>[0, 139, 69], "steelblue4"=>[54, 100, 139], "gray37"=>[94, 94, 94], "blue2"=>[0, 0, 238], "darkturquoise"=>[0, 206, 209], "gray38"=>[97, 97, 97], "gray85"=>[217, 217, 217], "sgigray12"=>[30, 30, 30], "blanchedalmond"=>[255, 235, 205], "violet"=>[238, 130, 238], "blue3"=>[0, 0, 205], "gray39"=>[99, 99, 99], "gray86"=>[219, 219, 219], "burlywood1"=>[255, 211, 155], "navy"=>[0, 0, 128], "darkviolet"=>[148, 0, 211], "blue4"=>[0, 0, 139], "gray87"=>[222, 222, 222], "burlywood2"=>[238, 197, 145], "floralwhite"=>[255, 250, 240], "turquoise"=>[64, 224, 208], "darkorange"=>[255, 140, 0], "gray88"=>[224, 224, 224], "burlywood3"=>[205, 170, 125], "gray89"=>[227, 227, 227], "dimgray"=>[105, 105, 105], "sgigray16"=>[40, 40, 40], "snow"=>[255, 250, 250], "burlywood4"=>[139, 115, 85], "mediumvioletred"=>[199, 21, 133], "seagreen"=>[46, 139, 87], "purple1"=>[155, 48, 255], "lightsteelblue1"=>[202, 225, 255], "purple2"=>[145, 44, 238], "orangered1"=>[255, 69, 0], "lightsteelblue2"=>[188, 210, 238], "purple3"=>[125, 38, 205], "cyan/aqua"=>[0, 255, 255], "orangered2"=>[238, 64, 0], "lightsteelblue3"=>[162, 181, 205], "purple4"=>[85, 26, 139], "orangered3"=>[205, 55, 0], "fuchsia"=>[255, 0, 255], "lightsteelblue4"=>[110, 123, 139], "mistyrose1"=>[255, 228, 225], "orangered4"=>[139, 37, 0], "darkorchid1"=>[191, 62, 255], "lemonchiffon1"=>[255, 250, 205], "mistyrose2"=>[238, 213, 210], "darkorchid2"=>[178, 58, 238], "lemonchiffon2"=>[238, 233, 191], "mistyrose3"=>[205, 183, 181], "royalblue"=>[65, 105, 225], "darkorchid3"=>[154, 50, 205], "lemonchiffon3"=>[205, 201, 165], "sgiolivedrab"=>[142, 142, 56], "mistyrose4"=>[139, 125, 123], "darkorchid4"=>[104, 34, 139], "peachpuff1"=>[255, 218, 185], "mediumseagreen"=>[60, 179, 113], "lemonchiffon4"=>[139, 137, 112], "lightgreen"=>[144, 238, 144], "peachpuff2"=>[238, 203, 173], "peachpuff3"=>[205, 175, 149], "peachpuff4"=>[139, 119, 101], "lightsteelblue"=>[176, 196, 222], "skyblue"=>[135, 206, 235], "gray10"=>[26, 26, 26], "magenta"=>[255, 0, 255], "turquoise1"=>[0, 245, 255], "gray11"=>[28, 28, 28], "turquoise2"=>[0, 229, 238], "chartreuse"=>[127, 255, 0], "navajowhite"=>[255, 222, 173], "ghostwhite"=>[248, 248, 255], "gray12"=>[31, 31, 31], "gray60"=>[153, 153, 153], "melon"=>[227, 168, 105], "turquoise3"=>[0, 197, 205], "gray13"=>[33, 33, 33], "gray61"=>[156, 156, 156], "coral1"=>[255, 114, 86], "turquoise4"=>[0, 134, 139], "gray14"=>[36, 36, 36], "gray62"=>[158, 158, 158], "sgiteal"=>[56, 142, 142], "coral2"=>[238, 106, 80], "honeydew"=>[240, 255, 240], "gray1"=>[3, 3, 3], "gray15"=>[38, 38, 38], "firebrick"=>[178, 34, 34], "coral3"=>[205, 91, 69], "lightpink"=>[255, 182, 193], "gray2"=>[5, 5, 5], "gray16"=>[41, 41, 41], "gray63"=>[161, 161, 161], "coral4"=>[139, 62, 47], "mediumblue"=>[0, 0, 205], "gray3"=>[8, 8, 8], "gray17"=>[43, 43, 43], "gray64"=>[163, 163, 163], "blueviolet"=>[138, 43, 226], "darkgreen"=>[0, 100, 0], "gray4"=>[10, 10, 10], "gray18"=>[46, 46, 46], "gray65"=>[166, 166, 166], "deepskyblue1"=>[0, 191, 255], "gray5"=>[13, 13, 13], "gray19"=>[48, 48, 48], "gray66"=>[168, 168, 168], "mediumspringgreen"=>[0, 250, 154], "darkkhaki"=>[189, 183, 107], "lightgoldenrodyellow"=>[250, 250, 210], "orange"=>[255, 128, 0], "deepskyblue2"=>[0, 178, 238], "gray6"=>[15, 15, 15], "gray67"=>[171, 171, 171], "mediumturquoise"=>[72, 209, 204], "deepskyblue3"=>[0, 154, 205], "turquoiseblue"=>[0, 199, 140], "gray7"=>[18, 18, 18], "gray68"=>[173, 173, 173], "orchid"=>[218, 112, 214], "burlywood"=>[222, 184, 135], "thistle"=>[216, 191, 216], "mediumpurple1"=>[171, 130, 255], "deepskyblue4"=>[0, 104, 139], "gray8"=>[20, 20, 20], "gray69"=>[176, 176, 176], "palevioletred"=>[219, 112, 147], "sandybrown"=>[244, 164, 96], "mediumpurple2"=>[159, 121, 238], "yellow"=>[255, 255, 0], "darkgoldenrod1"=>[255, 185, 15], "gray9"=>[23, 23, 23], "darkseagreen"=>[143, 188, 143], "mediumpurple3"=>[137, 104, 205], "darkgoldenrod2"=>[238, 173, 14], "sgigray92"=>[234, 234, 234], "mediumpurple4"=>[93, 71, 139], "darkgoldenrod3"=>[205, 149, 12], "mediumaquamarine"=>[102, 205, 170], "firebrick1"=>[255, 48, 48], "tomato"=>[255, 99, 71], "darkgoldenrod4"=>[139, 101, 8], "gray"=>[128, 128, 128], "firebrick2"=>[238, 44, 44], "palegoldenrod"=>[238, 232, 170], "moccasin"=>[255, 228, 181], "firebrick3"=>[205, 38, 38], "snow1"=>[255, 250, 250], "sgigray96"=>[244, 244, 244], "firebrick4"=>[139, 26, 26], "snow2"=>[238, 233, 233], "papayawhip"=>[255, 239, 213], "snow3"=>[205, 201, 201], "eggshell"=>[252, 230, 201], "snow4"=>[139, 137, 137], "tan"=>[210, 180, 140], "peacock"=>[51, 161, 201], "gold1"=>[255, 215, 0], "slateblue1"=>[131, 111, 255], "springgreen"=>[0, 255, 127], "ivoryblack"=>[41, 36, 33], "gold2"=>[238, 201, 0], "honeydew1"=>[240, 255, 240], "greenyellow"=>[173, 255, 47], "slateblue2"=>[122, 103, 238], "gainsboro"=>[220, 220, 220], "azure"=>[240, 255, 255], "gold3"=>[205, 173, 0], "oldlace"=>[253, 245, 230], "honeydew2"=>[224, 238, 224], "gold4"=>[139, 117, 0], "honeydew3"=>[193, 205, 193], "slateblue3"=>[105, 89, 205], "green"=>[0, 128, 0], "skyblue1"=>[135, 206, 255], "honeydew4"=>[131, 139, 131], "cadetblue1"=>[152, 245, 255], "slateblue4"=>[71, 60, 139], "sienna"=>[160, 82, 45], "darksalmon"=>[233, 150, 122], "skyblue2"=>[126, 192, 238], "cadetblue2"=>[142, 229, 238], "sapgreen"=>[48, 128, 20], "gray40"=>[102, 102, 102], "skyblue3"=>[108, 166, 205], "midnightblue"=>[25, 25, 112], "blue"=>[0, 0, 255], "cadetblue3"=>[122, 197, 205], "sgichartreuse"=>[113, 198, 113], "skyblue4"=>[74, 112, 139], "cadetblue4"=>[83, 134, 139], "lime"=>[0, 255, 0], "gray90"=>[229, 229, 229], "gray42"=>[105, 105, 105], "mistyrose"=>[255, 228, 225], "burntsienna"=>[138, 54, 15], "ivory"=>[255, 255, 240], "gray43"=>[110, 110, 110], "gray91"=>[232, 232, 232], "darkcyan"=>[0, 139, 139], "gray44"=>[112, 112, 112], "gray92"=>[235, 235, 235], "lawngreen"=>[124, 252, 0], "gray45"=>[115, 115, 115], "gray93"=>[237, 237, 237], "palevioletred1"=>[255, 130, 171], "saddlebrown"=>[139, 69, 19], "lavenderblush"=>[255, 240, 245], "gray46"=>[117, 117, 117], "gray94"=>[240, 240, 240], "palevioletred2"=>[238, 121, 159], "khaki"=>[240, 230, 140], "paleturquoise"=>[174, 238, 238], "gray47"=>[120, 120, 120], "gray95"=>[242, 242, 242], "carrot"=>[237, 145, 33], "palevioletred3"=>[205, 104, 137], "lightsalmon1"=>[255, 160, 122], "olivedrab"=>[107, 142, 35], "gray48"=>[122, 122, 122], "palevioletred4"=>[139, 71, 93], "wheat"=>[245, 222, 179], "lightsalmon2"=>[238, 149, 114], "powderblue"=>[176, 224, 230], "gray49"=>[125, 125, 125], "gray96"=>[245, 245, 245], "red"=>[255, 0, 0], "brown1"=>[255, 64, 64], "lightsalmon3"=>[205, 129, 98], "manganeseblue"=>[3, 168, 158], "gray97"=>[247, 247, 247], "brown2"=>[238, 59, 59], "lightsalmon4"=>[139, 87, 66], "olive"=>[128, 128, 0], "gray98"=>[250, 250, 250], "lightgrey"=>[211, 211, 211], "sgigray72"=>[183, 183, 183], "brown3"=>[205, 51, 51], "gold"=>[255, 215, 0], "mintcream"=>[245, 255, 250], "gray99"=>[252, 252, 252], "brown4"=>[139, 35, 35], "sgidarkgray"=>[85, 85, 85], "magenta2"=>[238, 0, 238], "sgigray76"=>[193, 193, 193], "magenta3"=>[205, 0, 205], "dodgerblue"=>[30, 144, 255], "magenta4"=>[139, 0, 139], "cobaltgreen"=>[61, 145, 64], "sgisalmon"=>[198, 113, 113], "emeraldgreen"=>[0, 201, 87], "sgibrightgray"=>[197, 193, 170], "darkred"=>[139, 0, 0], "rawsienna"=>[199, 97, 20], "seagreen1"=>[84, 255, 159], "lightyellow"=>[255, 255, 224], "olivedrab1"=>[192, 255, 62], "orchid1"=>[255, 131, 250], "seashell"=>[255, 245, 238], "seagreen2"=>[78, 238, 148], "bisque1"=>[255, 228, 196], "olivedrab2"=>[179, 238, 58], "orchid2"=>[238, 122, 233], "azure1"=>[240, 255, 255], "seagreen3"=>[67, 205, 128], "bisque2"=>[238, 213, 183], "whitesmoke"=>[245, 245, 245], "olivedrab3"=>[154, 205, 50], "orchid3"=>[205, 105, 201], "azure2"=>[224, 238, 238], "lightpink1"=>[255, 174, 185], "lightgoldenrod1"=>[255, 236, 139], "bisque3"=>[205, 183, 158], "olivedrab4"=>[105, 139, 34], "orchid4"=>[139, 71, 137], "purple"=>[128, 0, 128], "lemonchiffon"=>[255, 250, 205], "azure3"=>[193, 205, 205], "lightpink2"=>[238, 162, 173], "seagreen4"=>[46, 139, 87], "forestgreen"=>[34, 139, 34], "lightgoldenrod2"=>[238, 220, 130], "bisque4"=>[139, 125, 107], "sgislateblue"=>[113, 113, 198], "azure4"=>[131, 139, 139], "lightpink3"=>[205, 140, 149], "lightgoldenrod3"=>[205, 190, 112], "gray20"=>[51, 51, 51], "sgibeet"=>[142, 56, 142], "limegreen"=>[50, 205, 50], "orange1"=>[255, 165, 0], "lightpink4"=>[139, 95, 101], "lightgoldenrod4"=>[139, 129, 76], "gray21"=>[54, 54, 54], "orange2"=>[238, 154, 0], "gray22"=>[56, 56, 56], "gray70"=>[179, 179, 179], "orange3"=>[205, 133, 0], "gray23"=>[59, 59, 59], "gray71"=>[181, 181, 181], "orange4"=>[139, 90, 0], "lightseagreen"=>[32, 178, 170], "bisque"=>[255, 228, 196], "gray24"=>[61, 61, 61], "gray72"=>[184, 184, 184], "darkslateblue"=>[72, 61, 139], "gray25"=>[64, 64, 64], "gray73"=>[186, 186, 186], "lightcoral"=>[240, 128, 128], "tan1"=>[255, 165, 79], "gray26"=>[66, 66, 66], "black"=>[0, 0, 0], "tan2"=>[238, 154, 73], "gray27"=>[69, 69, 69], "gray74"=>[189, 189, 189], "teal"=>[0, 128, 128], "tan3"=>[205, 133, 63], "aquamarine1"=>[127, 255, 212], "gray28"=>[71, 71, 71], "gray75"=>[191, 191, 191], "tan4"=>[139, 90, 43], "darkmagenta"=>[139, 0, 139], "aquamarine2"=>[118, 238, 198], "gray29"=>[74, 74, 74], "gray76"=>[194, 194, 194], "indianred1"=>[255, 106, 106], "chocolate"=>[210, 105, 30], "aquamarine3"=>[102, 205, 170], "gray77"=>[196, 196, 196], "indianred2"=>[238, 99, 99], "slategray1"=>[198, 226, 255], "chocolate1"=>[255, 127, 36], "aquamarine4"=>[69, 139, 116], "gray78"=>[199, 199, 199], "sgigray52"=>[132, 132, 132], "indianred3"=>[205, 85, 85], "salmon"=>[250, 128, 114], "darkblue"=>[0, 0, 139], "lightyellow1"=>[255, 255, 224], "slategray2"=>[185, 211, 238], "chocolate2"=>[238, 118, 33], "gray79"=>[201, 201, 201], "indianred4"=>[139, 58, 58], "hotpink"=>[255, 105, 180], "brick"=>[156, 102, 31], "lightyellow2"=>[238, 238, 209], "slategray3"=>[159, 182, 205], "chocolate3"=>[205, 102, 29], "darkgray"=>[169, 169, 169], "lightyellow3"=>[205, 205, 180], "darkolivegreen"=>[85, 107, 47], "slategray4"=>[108, 123, 139], "chocolate4"=>[139, 69, 19], "salmon1"=>[255, 140, 105], "deeppink"=>[255, 20, 147], "indigo"=>[75, 0, 130], "darkslategray"=>[47, 79, 79], "navajowhite1"=>[255, 222, 173], "lightyellow4"=>[139, 139, 122], "royalblue1"=>[72, 118, 255], "slateblue"=>[106, 90, 205], "maroon1"=>[255, 52, 179], "sgigray56"=>[142, 142, 142], "salmon2"=>[238, 130, 98], "navajowhite2"=>[238, 207, 161], "coldgrey"=>[128, 138, 135], "royalblue2"=>[67, 110, 238], "cornsilk1"=>[255, 248, 220], "maroon2"=>[238, 48, 167], "salmon3"=>[205, 112, 84], "navajowhite3"=>[205, 179, 139], "royalblue3"=>[58, 95, 205], "cornsilk2"=>[238, 232, 205], "maroon3"=>[205, 41, 144], "slategray"=>[112, 128, 144], "salmon4"=>[139, 76, 57], "navajowhite4"=>[139, 121, 94], "royalblue4"=>[39, 64, 139], "darkseagreen1"=>[193, 255, 193], "cornsilk3"=>[205, 200, 177], "maroon4"=>[139, 28, 98], "hotpink1"=>[255, 110, 180], "mediumorchid1"=>[224, 102, 255], "darkseagreen2"=>[180, 238, 180], "cornsilk4"=>[139, 136, 120], "mint"=>[189, 252, 201], "hotpink2"=>[238, 106, 167], "sgilightblue"=>[125, 158, 192], "goldenrod1"=>[255, 193, 37], "mediumorchid2"=>[209, 95, 238], "darkseagreen3"=>[155, 205, 155], "hotpink3"=>[205, 96, 144], "goldenrod2"=>[238, 180, 34], "mediumorchid3"=>[180, 82, 205], "darkseagreen4"=>[105, 139, 105], "hotpink4"=>[139, 58, 98], "crimson"=>[220, 20, 60], "lightskyblue"=>[135, 206, 250], "goldenrod3"=>[205, 155, 29], "mediumorchid4"=>[122, 55, 139], "cornsilk"=>[255, 248, 220]}
720
+ pdf=FPDF.new('P', "cm")
721
+ pdf.SetTitle(pdfFile)
722
+ pdf.SetCreator("newickDraw")
723
+ pdf.SetAuthor(ENV["USER"]) if (!ENV["USER"].nil?)
724
+ pdf.AddPage
725
+ yUnit = nil
726
+ lineWidth = nil
727
+ fontSize = nil
728
+ bootScale = 0.6
729
+ if (taxa.size < 30)
730
+ fontSize = 10
731
+ yUnit = 0.5
732
+ lineWidth = 0.02
733
+ elsif (taxa.size < 60)
734
+ fontSize = 8
735
+ yUnit = 0.25
736
+ lineWidth = 0.01
737
+ elsif (taxa.size < 150)
738
+ fontSize = 8
739
+ yUnit = 0.197
740
+ lineWidth = 0.01
741
+ elsif (taxa.size < 300)
742
+ fontSize = 2
743
+ yUnit = 0.09
744
+ lineWidth = 0.005
745
+ elsif (taxa.size < 400)
746
+ fontSize = 2
747
+ yUnit = 0.055
748
+ lineWidth = 0.002
749
+ elsif (taxa.size < 800)
750
+ fontSize = 1
751
+ yUnit = 0.030
752
+ lineWidth = 0.0015
811
753
  else
812
- pdf.SetTextColor(colors[hl][0], colors[hl][1], colors[hl][2]) if hl
813
- pdf.Write(0, entry)
814
- pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
754
+ fontSize = 0.5
755
+ yUnit = 0.020
756
+ lineWidth = 0.0010
815
757
  end
816
- end
817
- pdf.Line(xOffSet + child.parent.x*xScale, child.y,
818
- xOffSet + child.x*xScale, child.y)
819
- }
820
- if (labelName)
821
- pdf.SetFont('Times','B', 24)
822
- pdf.SetXY(0, pdf.GetY + 1)
823
- pdf.Write(0, labelName)
824
- end
825
- if (brackets)
826
- brackets.each {|bracket|
827
- x, y1, y2, label, r, p = bracket
828
- next if label.nil?
829
- pdf.SetLineWidth(lineWidth * 5)
830
- pdf.SetFont('Times','B', fontSize*1.5)
831
- pdf.Line(x, y1, x, y2)
832
- pdf.Line(x, y1, x - 0.3, y1)
833
- pdf.Line(x, y2, x - 0.3, y2)
834
- pdf.SetXY(x, (y1+y2)/2)
835
- pdf.Write(0, label)
836
- if (r == "r")
837
- pdf.SetTextColor(255, 0, 0)
838
- pdf.SetXY(x + 1.8, -0.65+(y1+y2)/2)
839
- pdf.SetFont('Times','B', fontSize*10)
840
- pdf.Write(0, " .")
841
- pdf.SetTextColor(0, 0, 0)
758
+ bootScale = 0.5 * fontSize
759
+ pdf.SetFont('Times','B', fontSize)
760
+ calcPos(yUnit) # calculate node pos before drawing
761
+ max = 0
762
+ @root.leaves.each do |leaf|
763
+ d = leaf.distToAncestor(@root)
764
+ max = d if (max < d)
765
+ end
766
+ xScale = 10.0/max
767
+ xOffSet = 0.25
768
+ pdf.SetLineWidth(lineWidth)
769
+ pdf.SetTextColor(0, 0, 0)
770
+ pdf.Line(0, @root.y, xOffSet, @root.y)
771
+ pdf.Line(xOffSet, @root.yMin, xOffSet, @root.yMax)
772
+ @root.descendants.each do |child|
773
+ if (!child.leaf?)
774
+ if (child.name.to_i > 75 && boot == "width") # good bootstrap
775
+ pdf.SetLineWidth(lineWidth * 5)
776
+ else
777
+ pdf.SetLineWidth(lineWidth)
778
+ end
779
+ bootX = xOffSet + child.x*xScale
780
+ bootY = ((child.yMin + child.yMax) / 2.0)
781
+ pdf.SetXY(bootX, bootY)
782
+ pdf.SetFont('Times','B', bootScale)
783
+ pdf.Write(0, child.name.to_s)
784
+ pdf.SetFont('Times','B', fontSize)
785
+ pdf.Line(xOffSet + child.x*xScale, child.yMin,
786
+ xOffSet + child.x*xScale, child.yMax)
787
+ else
788
+ if (child.parent.name.to_i > 75 && boot == "width") # good bootstrap
789
+ pdf.SetLineWidth(lineWidth * 5)
790
+ else
791
+ pdf.SetLineWidth(lineWidth)
792
+ end
793
+ pdf.SetXY(xOffSet + child.x*xScale, child.y)
794
+ efields = child.name.split("__")
795
+ entry, species = efields.first, efields.last
796
+ if (entry =~/\{([^\}]*)\}/)
797
+ species = $1
798
+ end
799
+ species = entry if species.nil? && !rawNames
800
+ species = child.name if rawNames
801
+ hl = false
802
+ highlights.keys.each do |highlight|
803
+ hl = highlights[highlight] if (entry.index(highlight))
804
+ end
805
+ if (pdfFile.index(entry)) # name of query taxon
806
+ pdf.SetTextColor(colors["red"][0], colors["red"][1], colors["red"][2])
807
+ pdf.Write(0, entry)
808
+ pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2])
809
+ elsif (linker && link = send(linker, entry))
810
+ pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
811
+ pdf.Write(0, species, link)
812
+ pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
813
+ elsif (!species.nil?)
814
+ pdf.SetTextColor(colors[hl][0], colors[hl][1], colors[hl][2]) if hl
815
+ pdf.Write(0, species)
816
+ pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
817
+ else
818
+ pdf.SetTextColor(colors[hl][0], colors[hl][1], colors[hl][2]) if hl
819
+ pdf.Write(0, entry)
820
+ pdf.SetTextColor(colors["black"][0], colors["black"][1], colors["black"][2]) if hl
821
+ end
842
822
  end
843
- if (p == "p" || r == "p")
844
- pdf.SetTextColor(255, 0, 255)
845
- pdf.SetXY(x + 2.3, -0.65+(y1+y2)/2)
846
- pdf.SetFont('Times','B', fontSize*10)
847
- pdf.Write(0, " .")
848
- pdf.SetTextColor(0, 0, 0)
823
+ pdf.Line(xOffSet + child.parent.x*xScale, child.y,
824
+ xOffSet + child.x*xScale, child.y)
825
+ end
826
+ if (labelName)
827
+ pdf.SetFont('Times','B', 24)
828
+ pdf.SetXY(0, pdf.GetY + 1)
829
+ pdf.Write(0, labelName)
830
+ end
831
+ if (brackets)
832
+ brackets.each do |bracket|
833
+ x, y1, y2, label, r, p = bracket
834
+ next if label.nil?
835
+ pdf.SetLineWidth(lineWidth * 5)
836
+ pdf.SetFont('Times','B', fontSize*1.5)
837
+ pdf.Line(x, y1, x, y2)
838
+ pdf.Line(x, y1, x - 0.3, y1)
839
+ pdf.Line(x, y2, x - 0.3, y2)
840
+ pdf.SetXY(x, (y1+y2)/2)
841
+ pdf.Write(0, label)
842
+ if (r == "r")
843
+ pdf.SetTextColor(255, 0, 0)
844
+ pdf.SetXY(x + 1.8, -0.65+(y1+y2)/2)
845
+ pdf.SetFont('Times','B', fontSize*10)
846
+ pdf.Write(0, " .")
847
+ pdf.SetTextColor(0, 0, 0)
848
+ end
849
+ if (p == "p" || r == "p")
850
+ pdf.SetTextColor(255, 0, 255)
851
+ pdf.SetXY(x + 2.3, -0.65+(y1+y2)/2)
852
+ pdf.SetFont('Times','B', fontSize*10)
853
+ pdf.Write(0, " .")
854
+ pdf.SetTextColor(0, 0, 0)
855
+ end
849
856
  end
850
- }
857
+ end
858
+ pdf.SetLineWidth(lineWidth * 5)
859
+ pdf.Line(1, pdf.GetY + 1, 1 + 0.1*xScale, pdf.GetY + 1)
860
+ pdf.SetFont('Times','B', fontSize)
861
+ pdf.SetXY(1 + 0.1*xScale, pdf.GetY + 1)
862
+ pdf.Write(0, "0.1")
863
+ if (pdfFile =~/^--/)
864
+ return pdf.Output
865
+ else
866
+ pdf.Output(pdfFile)
867
+ end
851
868
  end
852
- pdf.SetLineWidth(lineWidth * 5)
853
- pdf.Line(1, pdf.GetY + 1, 1 + 0.1*xScale, pdf.GetY + 1)
854
- pdf.SetFont('Times','B', fontSize)
855
- pdf.SetXY(1 + 0.1*xScale, pdf.GetY + 1)
856
- pdf.Write(0, "0.1")
857
- if (pdfFile =~/^--/)
858
- return pdf.Output
859
- else
860
- pdf.Output(pdfFile)
861
869
  end
862
- end
863
- end
864
870
 
865
871
 
866
872
 
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: newick-ruby
3
3
  version: !ruby/object:Gem::Version
4
- hash: 21
4
+ hash: 19
5
5
  prerelease: false
6
6
  segments:
7
7
  - 1
8
8
  - 0
9
- - 1
10
- version: 1.0.1
9
+ - 2
10
+ version: 1.0.2
11
11
  platform: ruby
12
12
  authors:
13
13
  - Jonathan Badger
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2010-08-02 00:00:00 -07:00
18
+ date: 2010-11-08 00:00:00 -08:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency