icodi 0.1.1 → 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (4) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +41 -12
  3. data/lib/icodi.rb +72 -39
  4. metadata +2 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c658ed87b6473e55b975104c7578b27ee558df59623a710d89637fd168acb528
4
- data.tar.gz: e5c37860c467df8b4daa3046352812ee036cf3f5197530aa8c83f4d8ae76d972
3
+ metadata.gz: 9d272a6dc8d9e595006ce36f72421892a2381cb0d51285e2390143d257c9f119
4
+ data.tar.gz: e7fc61dfee1364269ffe07d4100b14fa7b48ec100680ed5094b6e40b673ea6c3
5
5
  SHA512:
6
- metadata.gz: c8f9a6b9bee3066dffa76ca91def8f199aed7fc15b0c21828b5f6add814e464a02e4138eac8dffb1b64dca07dc17870e8d23765c481db5112103c8caf1c67813
7
- data.tar.gz: 1da2da19a46676aa49a7b4dd01eb90ba5d7f86703aaf8946febbb5777c709128dc0d04b6c4da431e560ffbdc00c1ac242feca8bc6fe685761807349f374a2cac
6
+ metadata.gz: 86b7e257b95b0ead2d4ec44ee27edb3187cafa18ba519f99776831520502294b6a47c80732cc71abbf5f3e544a17307f449d66153391b8d806c7df03298a6b86
7
+ data.tar.gz: 68fa6d9f3ed793c99f3cdce6437781026e2bd44c8192bae60e8925988ec8b496840083bbf4a5c2314b1a6fa33f4069e0d150413928e91054fe6d35f71d54bdd4
data/README.md CHANGED
@@ -5,6 +5,7 @@ Icodi - Deterministic Random SVG Icon Generator
5
5
 
6
6
  [![Gem Version](https://badge.fury.io/rb/icodi.svg)](https://badge.fury.io/rb/icodi)
7
7
  [![Build Status](https://travis-ci.com/DannyBen/icodi.svg?branch=master)](https://travis-ci.com/DannyBen/icodi)
8
+ [![Maintainability](https://api.codeclimate.com/v1/badges/0b74be3877413501c7a9/maintainability)](https://codeclimate.com/github/DannyBen/icodi/maintainability)
8
9
 
9
10
  ---
10
11
 
@@ -13,6 +14,16 @@ Generate repeatable random SVG icons from any string, similar to
13
14
 
14
15
  ---
15
16
 
17
+ Table of Contents
18
+ --------------------------------------------------
19
+
20
+ - [Installation](#installation)
21
+ - [Examples](#examples)
22
+ - [Usage](#usage)
23
+ - [Options](#options)
24
+ - [Using with Sinatra](#using-with-sinatra)
25
+
26
+
16
27
  Installation
17
28
  --------------------------------------------------
18
29
 
@@ -23,33 +34,41 @@ Installation
23
34
  Examples
24
35
  --------------------------------------------------
25
36
 
26
- ### Grid: 5x5, Mirror: X (default options)
37
+ ### Grid: 5x5, Mirror: X (default settings)
27
38
 
28
- ![sample](assets/sample-strip-default.svg)
39
+ ![strip1](assets/strip_default.svg)
29
40
 
30
- ### Grid: 6x6, Mirror: Y
41
+ ### Grid: 6x6, Mirror: Y, Stroke: 4
31
42
 
32
- ![sample](assets/sample-strip-6y.svg)
43
+ ![strip2](assets/strip_mirror_y.svg)
33
44
 
34
- ### Grid: 8x8, Mirror: X/Y, Density: 0.3
45
+ ### Grid: 8x8, Stroke: 7, Density: 0.3
35
46
 
36
- ![sample](assets/sample-strip-8xylow.svg)
47
+ ![strip3](assets/strip_thick_stroke.svg)
37
48
 
38
- ### Grid: 8x8, Mirror: X/Y, Density: 0.8
49
+ ### Grid: 7x7, Mirror: X/Y, Stroke: 3, Density: 0.8
39
50
 
40
- ![sample](assets/sample-strip-8xyhigh.svg)
51
+ ![strip4](assets/strip_mirror_both.svg)
52
+
53
+ ### Grid: 5x5, Jitter: 0.9, Stroke: 2
54
+
55
+ ![strip4](assets/strip_jitter.svg)
41
56
 
42
57
  ### Increasing Stroke: 0.1 - 5.0
43
58
 
44
- ![sample](assets/sample-strip-stroke.svg)
59
+ ![strip5](assets/strip_strokes.svg)
45
60
 
46
61
  ### Increasing Density: 0.3 - 0.8
47
62
 
48
- ![sample](assets/sample-strip-density.svg)
63
+ ![strip6](assets/strip_densities.svg)
64
+
65
+ ### Increasing Jitter: 0 - 1.0
66
+
67
+ ![strip6](assets/strip_jitters.svg)
49
68
 
50
69
  ### Mirror Styles: X, Y, Both, None
51
70
 
52
- ![sample](assets/sample-strip-mirrors.svg)
71
+ ![strip7](assets/strip_mirrors.svg)
53
72
 
54
73
 
55
74
  Usage
@@ -98,13 +117,23 @@ Parameter | Default | Type | Description
98
117
  ------------|------------|---------|---------------------
99
118
  `pixels` | `5` | Integer | Grid size.
100
119
  `mirror` | `:x` | Symbol | Mirroring mode: `:x`, `:y`, `:both` or `:none`.
101
- `color` | Deterministic Random | String | A color string for the pixels.
120
+ `color` | Deterministic Random | String | A color string for the pixels.
102
121
  `density` | `0.5` | Float | A value between 0 and 1 representing the chance for a pixel to be drawn. Lower values mean less pixels.
103
122
  `stroke` | `0.1` | Float | Width of the border around each pixel. Note that each pixel is a 10x10 box, so a stroke of 1 means it will take 10% of the box. Higher values generate more overlap between the pixels.
123
+ `jitter` | `0` | Float | A value between 0 and 1 representing the chance for a pixel to be dislocated by half of its size in a random direction.
104
124
  `background`| `#fff` | String | A named SVG color string (`blue`, `yellow` etc.) or RGB color (for example `#dddddd`).
105
125
  `template` | `:default` | Symbol/String | SVG template to use. Can be `:default`, `:html` or a path to a file. Read more on [Victor SVG Templates].
106
126
 
107
127
  ---
108
128
 
129
+
130
+ Using with Sinatra
131
+ --------------------------------------------------
132
+
133
+ To create a Sinatra server that serves Icodi images, see the
134
+ [server.rb](server.rb) example code.
135
+
136
+
137
+
109
138
  [GitHub identicons]: https://blog.github.com/2013-08-14-identicons/
110
139
  [Victor SVG Templates]: https://github.com/DannyBen/victor#svg-templates
data/lib/icodi.rb CHANGED
@@ -6,49 +6,50 @@ class Icodi < Victor::SVGBase
6
6
 
7
7
  def initialize(text = nil, options = {})
8
8
  text, options = nil, text if text.is_a? Hash
9
- @text, @options = text, options
10
- super template: template, viewBox: "0 0 #{size} #{size}"
9
+
10
+ @text = text
11
+ @options = default_options.merge options
11
12
 
12
- first_random_hit
13
+ super template: template, viewBox: "0 0 #{size} #{size}", clip_path: "url(#rect)"
14
+
13
15
  generate
14
16
  end
15
17
 
16
- def template
17
- options[:template] ||= :default
18
+ def method_missing(method_name, *_args, &_block)
19
+ respond_to?(method_name) ? options[method_name] : super
18
20
  end
19
21
 
20
- def pixels
21
- options[:pixels] ||= 5
22
+ def respond_to?(method_name, include_private = false)
23
+ options.has_key?(method_name) ? true : super
22
24
  end
23
25
 
24
- def density
25
- options[:density] ||= 0.5
26
- end
27
-
28
- def stroke
29
- options[:stroke] ||= 0.1
30
- end
31
-
32
- def background
33
- options[:background] ||= '#fff'
34
- end
26
+ private
35
27
 
36
- def color
37
- options[:color] ||= "#%06x" % (random.rand * 0xffffff)
28
+ def default_options
29
+ {
30
+ template: :default,
31
+ pixels: 5,
32
+ density: 0.5,
33
+ stroke: 0.1,
34
+ background: '#fff',
35
+ color: random_color,
36
+ mirror: :x,
37
+ jitter: 0,
38
+ }
38
39
  end
39
40
 
40
- def mirror
41
- options[:mirror] ||= :x
41
+ def random_color
42
+ "#%06x" % (random(:color).rand * 0xffffff)
42
43
  end
43
44
 
44
- private
45
-
46
45
  def seed(string)
47
46
  Digest::MD5.hexdigest(string).to_i(16)
48
47
  end
49
48
 
50
- def random
51
- @random ||= (text ? Random.new(seed(text)) : Random.new)
49
+ def random(set = nil)
50
+ @random_sets ||= {}
51
+ set ||= :default
52
+ @random_sets[set] ||= (text ? Random.new(seed(text)) : Random.new)
52
53
  end
53
54
 
54
55
  def size
@@ -59,29 +60,33 @@ private
59
60
  @style ||= { stroke: color, stroke_width: stroke }
60
61
  end
61
62
 
62
- def mirror_x
63
+ def mirror_x?
63
64
  [:x, :both].include? mirror
64
65
  end
65
66
 
66
- def mirror_y
67
+ def mirror_y?
67
68
  [:y, :both].include? mirror
68
69
  end
69
70
 
70
- def mirror_both
71
+ def mirror_both?
71
72
  mirror == :both
72
73
  end
73
74
 
74
- def first_random_hit
75
- options[:color] ? random.rand : color
76
- end
77
-
78
75
  def generate
79
76
  element :rect, x: 0, y: 0, width: size, height: size, fill: background
77
+ element :defs do
78
+ element :clipPath, id: :clipper do
79
+ element :rect, width: size, height: size
80
+ end
81
+ end
82
+
80
83
  half = (pixels / 2.0).round
81
- x = mirror_x ? half : pixels
82
- y = mirror_y ? half : pixels
84
+ x = mirror_x? ? half : pixels
85
+ y = mirror_y? ? half : pixels
83
86
 
84
- draw x, y
87
+ element :g, clip_path: "url(#clipper)" do
88
+ draw x, y
89
+ end
85
90
  end
86
91
 
87
92
  def draw(x_times, y_times)
@@ -93,14 +98,42 @@ private
93
98
  end
94
99
 
95
100
  def add_pixels(x, y)
101
+ x, y = add_jitter x, y
102
+
96
103
  draw_pixel x, y
97
- draw_pixel pixels-1-x, y if mirror_x and x != pixels/2
98
- draw_pixel x, pixels-1-y if mirror_y and y != pixels/2
99
- draw_pixel pixels-1-x, pixels-1-y if mirror_both and x != pixels/2 and y != pixels/2
104
+ draw_pixel mirror_value(x), y if mirror? x: x
105
+ draw_pixel x, mirror_value(y) if mirror? y: y
106
+ draw_pixel mirror_value(x), mirror_value(y) if mirror? x: x, y: y
107
+ end
108
+
109
+ def mirror?(x: nil, y: nil)
110
+ if x and y
111
+ mirror_both? and !mid?(x: x) and !mid?(y: y)
112
+ elsif x
113
+ mirror_x? and !mid? x: x
114
+ elsif y
115
+ mirror_y? and !mid? y: y
116
+ end
117
+ end
118
+
119
+ def mid?(x: nil, y: nil)
120
+ x ? x == pixels/2 : y ? y == pixels/2 : nil
121
+ end
122
+
123
+ def add_jitter(x, y)
124
+ return [x, y] unless jitter > 0 and random(:jitter).rand < jitter
125
+
126
+ x += [0, 0.5, -0.5][random(:jitter).rand(3)] unless mirror_x? and mid? x: x
127
+ y += [0, 0.5, -0.5][random(:jitter).rand(3)] unless mirror_y? and mid? y: y
128
+ [x, y]
100
129
  end
101
130
 
102
131
  def draw_pixel(x, y)
103
132
  element :rect, x: x*10, y: y*10, width: 10, height: 10, fill: color, style: style
104
133
  end
105
134
 
135
+ def mirror_value(value)
136
+ pixels - 1 - value
137
+ end
138
+
106
139
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: icodi
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Danny Ben Shitrit
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-12-17 00:00:00.000000000 Z
11
+ date: 2018-12-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: victor