sequence_logo 1.0.3 → 1.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,114 +1,114 @@
1
- require_relative 'ytilib'
2
- require 'RMagick'
3
-
4
- module SequenceLogo
5
- def self.draw_threshold_lines(i_logo, ppm)
6
- x_size = i_logo.columns
7
- y_size = i_logo.rows
8
-
9
- line2of4 = y_size - ppm.get_line(ppm.icd2of4) * y_size
10
- lineThc = y_size - ppm.get_line(ppm.icdThc) * y_size
11
- lineTlc = y_size - ppm.get_line(ppm.icdTlc) * y_size
12
-
13
- dr = Magick::Draw.new
14
- dr.fill('transparent')
15
-
16
- dr.stroke_width(y_size / 200.0)
17
- dr.stroke_dasharray(7,7)
18
-
19
- dr.stroke('silver')
20
- dr.line(0, line2of4, x_size, line2of4)
21
- dr.line(0, lineThc, x_size, lineThc)
22
- dr.line(0, lineTlc, x_size, lineTlc)
23
-
24
- dr.draw(i_logo)
25
- end
26
-
27
- def self.create_canvas(ppm, options)
28
- x_size = options[:x_unit] * ppm.length
29
- y_size = options[:y_unit]
30
-
31
- i_logo = Magick::ImageList.new
32
- if options[:icd_mode] == :discrete
33
- i_logo.new_image(x_size, y_size, Magick::HatchFill.new('white', 'white'))
34
- draw_threshold_lines(i_logo, ppm) if options[:threshold_lines]
35
- else
36
- i_logo.new_image(x_size, y_size, Magick::HatchFill.new('white', 'bisque'))
37
- end
38
-
39
- i_logo
40
- end
41
-
42
- def self.letter_images(scheme_dir)
43
- if File.exist?(File.join(scheme_dir,'a.png'))
44
- extension = 'png'
45
- elsif File.exist?(File.join(scheme_dir,'a.gif'))
46
- extension = 'gif'
47
- else
48
- raise "Scheme not exists in folder #{scheme_dir}"
49
- end
50
-
51
- letter_files = %w[a c g t].collect{|letter| File.join(scheme_dir, "#{letter}.#{extension}") }
52
- Magick::ImageList.new(*letter_files)
53
- end
54
-
55
- def self.draw_letters_on_canvas(i_logo, i_letters, ppm, options)
56
- y_unit = options[:y_unit]
57
- x_unit = options[:x_unit]
58
- matrix = ppm.get_logo(options[:icd_mode])
59
- matrix['A'].each_index { |i|
60
- y_pos = 0
61
- sorted_letters = ['A', 'C', 'G', 'T'].collect { |letter| {:score => matrix[letter][i], :letter => letter} }.sort_by { |pair| pair[:score] }.collect { |pair| pair[:letter] }.reverse
62
- sorted_letters.each { |letter|
63
- next if y_unit * matrix[letter][i] <= 1
64
- letter_index = {'A' => 0, 'C' => 1, 'G' => 2, 'T' => 3}[letter]
65
- y_block = (y_unit * matrix[letter][i]).round
66
- i_logo << i_letters[letter_index].dup.resize(x_unit, y_block)
67
- y_pos += y_block
68
- i_logo.cur_image.page = Magick::Rectangle.new(0, 0, i * x_unit, y_unit - y_pos )
69
- }
70
- }
71
- end
72
-
73
- def self.draw_logo(ppm, options = {})
74
- ppm.words_count = options[:words_count] if options[:words_count]
75
- unless ppm.words_count
76
- report "words count for PPM is undefined, assuming weblogo mode"
77
- options[:icd_mode] = :weblogo
78
- end
79
- i_logo = create_canvas(ppm, options)
80
- scheme_dir = File.join(AssetsPath, options[:scheme])
81
- draw_letters_on_canvas(i_logo, letter_images(scheme_dir), ppm, options)
82
- i_logo = i_logo.flatten_images
83
- end
84
-
85
- # logos = { filename => {shift: ..., length: ..., name: ...} }
86
- def self.glue_files(logos, output_file, options)
87
- logo_shift = options[:logo_shift] || 300
88
- x_unit = options[:x_unit] || 30
89
- y_unit = options[:y_unit] || 60
90
- text_size = options[:text_size] || 24
91
-
92
- leftmost_shift = logos.map{|file,infos| infos[:shift] }.min
93
- logos.each{|file, infos| infos[:shift] -= leftmost_shift}
94
- full_alignment_size = logos.map{|file,infos| infos[:length] + infos[:shift] }.max
95
-
96
- x_size = logo_shift + full_alignment_size * x_unit
97
- y_size = logos.size * y_unit
98
- command_string = "convert -size #{ x_size }x#{ y_size } -pointsize #{text_size} xc:white "
99
- logos.each_with_index do |(logo_filename,infos), idx|
100
- logo_x_start = logo_shift + infos[:shift] * x_unit
101
- logo_y_start = y_unit * idx
102
- command_string << "\"#{ logo_filename }\" -geometry +#{ logo_x_start }+#{ logo_y_start } -composite "
103
- end
104
-
105
- command_draw_names = ""
106
- logos.each_with_index do |(logo_filename,infos), idx|
107
- text_x_start = 10
108
- text_y_start = y_unit * (idx + 0.5)
109
- command_draw_names << "-draw \"text #{ text_x_start },#{ text_y_start } '#{infos[:name]}'\" "
110
- end
111
-
112
- system(command_string + command_draw_names + "\"#{output_file}\"")
113
- end
1
+ require_relative 'ytilib'
2
+ require 'RMagick'
3
+
4
+ module SequenceLogo
5
+ def self.draw_threshold_lines(i_logo, ppm)
6
+ x_size = i_logo.columns
7
+ y_size = i_logo.rows
8
+
9
+ line2of4 = y_size - ppm.get_line(ppm.icd2of4) * y_size
10
+ lineThc = y_size - ppm.get_line(ppm.icdThc) * y_size
11
+ lineTlc = y_size - ppm.get_line(ppm.icdTlc) * y_size
12
+
13
+ dr = Magick::Draw.new
14
+ dr.fill('transparent')
15
+
16
+ dr.stroke_width(y_size / 200.0)
17
+ dr.stroke_dasharray(7,7)
18
+
19
+ dr.stroke('silver')
20
+ dr.line(0, line2of4, x_size, line2of4)
21
+ dr.line(0, lineThc, x_size, lineThc)
22
+ dr.line(0, lineTlc, x_size, lineTlc)
23
+
24
+ dr.draw(i_logo)
25
+ end
26
+
27
+ def self.create_canvas(ppm, options)
28
+ x_size = options[:x_unit] * ppm.length
29
+ y_size = options[:y_unit]
30
+
31
+ i_logo = Magick::ImageList.new
32
+ if options[:icd_mode] == :discrete
33
+ i_logo.new_image(x_size, y_size, Magick::HatchFill.new('white', 'white'))
34
+ draw_threshold_lines(i_logo, ppm) if options[:threshold_lines]
35
+ else
36
+ i_logo.new_image(x_size, y_size, Magick::HatchFill.new('white', 'bisque'))
37
+ end
38
+
39
+ i_logo
40
+ end
41
+
42
+ def self.letter_images(scheme_dir)
43
+ if File.exist?(File.join(scheme_dir,'a.png'))
44
+ extension = 'png'
45
+ elsif File.exist?(File.join(scheme_dir,'a.gif'))
46
+ extension = 'gif'
47
+ else
48
+ raise "Scheme not exists in folder #{scheme_dir}"
49
+ end
50
+
51
+ letter_files = %w[a c g t].collect{|letter| File.join(scheme_dir, "#{letter}.#{extension}") }
52
+ Magick::ImageList.new(*letter_files)
53
+ end
54
+
55
+ def self.draw_letters_on_canvas(i_logo, i_letters, ppm, options)
56
+ y_unit = options[:y_unit]
57
+ x_unit = options[:x_unit]
58
+ matrix = ppm.get_logo(options[:icd_mode])
59
+ matrix['A'].each_index { |i|
60
+ y_pos = 0
61
+ sorted_letters = ['A', 'C', 'G', 'T'].collect { |letter| {:score => matrix[letter][i], :letter => letter} }.sort_by { |pair| pair[:score] }.collect { |pair| pair[:letter] }.reverse
62
+ sorted_letters.each { |letter|
63
+ next if y_unit * matrix[letter][i] <= 1
64
+ letter_index = {'A' => 0, 'C' => 1, 'G' => 2, 'T' => 3}[letter]
65
+ y_block = (y_unit * matrix[letter][i]).round
66
+ i_logo << i_letters[letter_index].dup.resize(x_unit, y_block)
67
+ y_pos += y_block
68
+ i_logo.cur_image.page = Magick::Rectangle.new(0, 0, i * x_unit, y_unit - y_pos )
69
+ }
70
+ }
71
+ end
72
+
73
+ def self.draw_logo(ppm, options = {})
74
+ ppm.words_count = options[:words_count] if options[:words_count]
75
+ unless ppm.words_count
76
+ report "words count for PPM is undefined, assuming weblogo mode"
77
+ options[:icd_mode] = :weblogo
78
+ end
79
+ i_logo = create_canvas(ppm, options)
80
+ scheme_dir = File.join(AssetsPath, options[:scheme])
81
+ draw_letters_on_canvas(i_logo, letter_images(scheme_dir), ppm, options)
82
+ i_logo = i_logo.flatten_images
83
+ end
84
+
85
+ # logos = { filename => {shift: ..., length: ..., name: ...} }
86
+ def self.glue_files(logos, output_file, options)
87
+ logo_shift = options[:logo_shift] || 300
88
+ x_unit = options[:x_unit] || 30
89
+ y_unit = options[:y_unit] || 60
90
+ text_size = options[:text_size] || 24
91
+
92
+ leftmost_shift = logos.map{|file,infos| infos[:shift] }.min
93
+ logos.each{|file, infos| infos[:shift] -= leftmost_shift}
94
+ full_alignment_size = logos.map{|file,infos| infos[:length] + infos[:shift] }.max
95
+
96
+ x_size = logo_shift + full_alignment_size * x_unit
97
+ y_size = logos.size * y_unit
98
+ command_string = "convert -size #{ x_size }x#{ y_size } -pointsize #{text_size} xc:white "
99
+ logos.each_with_index do |(logo_filename,infos), idx|
100
+ logo_x_start = logo_shift + infos[:shift] * x_unit
101
+ logo_y_start = y_unit * idx
102
+ command_string << "\"#{ logo_filename }\" -geometry +#{ logo_x_start }+#{ logo_y_start } -composite "
103
+ end
104
+
105
+ command_draw_names = ""
106
+ logos.each_with_index do |(logo_filename,infos), idx|
107
+ text_x_start = 10
108
+ text_y_start = y_unit * (idx + 0.5)
109
+ command_draw_names << "-draw \"text #{ text_x_start },#{ text_y_start } '#{infos[:name]}'\" "
110
+ end
111
+
112
+ system(command_string + command_draw_names + "\"#{output_file}\"")
113
+ end
114
114
  end
@@ -1,3 +1,3 @@
1
- module SequenceLogo
2
- VERSION = "1.0.3"
3
- end
1
+ module SequenceLogo
2
+ VERSION = "1.0.4"
3
+ end