punks 0.1.1 → 0.2.2
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.
- checksums.yaml +4 -4
- data/Manifest.txt +9 -0
- data/README.md +2 -2
- data/Rakefile +1 -1
- data/config/philip-24x24.png +0 -0
- data/config/punks-24x24.csv +822 -0
- data/config/punks-24x24.png +0 -0
- data/lib/punks/generator.rb +330 -0
- data/lib/punks/marilyns.rb +20 -0
- data/lib/punks/philips.rb +24 -0
- data/lib/punks/phunks.rb +14 -0
- data/lib/punks/punks.rb +123 -0
- data/lib/punks/punks_xl.rb +36 -0
- data/lib/punks/version.rb +2 -2
- data/lib/punks.rb +23 -31
- metadata +17 -8
Binary file
|
@@ -0,0 +1,330 @@
|
|
1
|
+
|
2
|
+
module Punk
|
3
|
+
|
4
|
+
class Metadata
|
5
|
+
### todo/fix:
|
6
|
+
## move into Punks::Metadata or such
|
7
|
+
class Sprite
|
8
|
+
attr_reader :id, :name, :type, :gender, :size, :more_names
|
9
|
+
|
10
|
+
|
11
|
+
def initialize( id:,
|
12
|
+
name:,
|
13
|
+
type:,
|
14
|
+
gender:,
|
15
|
+
size:,
|
16
|
+
more_names: [] )
|
17
|
+
@id = id # zero-based index eg. 0,1,2,3, etc.
|
18
|
+
@name = name
|
19
|
+
@type = type
|
20
|
+
@gender = gender
|
21
|
+
@size = size
|
22
|
+
@more_names = more_names
|
23
|
+
end
|
24
|
+
|
25
|
+
## todo/check - find better names for type attribute/archetypes?
|
26
|
+
## use (alternate name/alias) base or face for archetypes? any others?
|
27
|
+
def attribute?() @type.downcase.start_with?( 'attribute' ); end
|
28
|
+
def archetype?() @type.downcase.start_with?( 'archetype' ); end
|
29
|
+
|
30
|
+
def small?() @size == 's'; end
|
31
|
+
def large?() @size == 'l'; end
|
32
|
+
def universal?() @size == 'u'; end
|
33
|
+
alias_method :unisize?, :universal? ## add unisize or allsizes or such - why? why not?
|
34
|
+
|
35
|
+
def male?() @gender == 'm'; end
|
36
|
+
def female?() @gender == 'f'; end
|
37
|
+
def unisex?() @gender == 'u'; end
|
38
|
+
end # class Metadata::Sprite
|
39
|
+
end # class Metadata
|
40
|
+
|
41
|
+
|
42
|
+
|
43
|
+
|
44
|
+
class Generator
|
45
|
+
|
46
|
+
######
|
47
|
+
# static helpers - (turn into "true" static self.class methods - why? why not?)
|
48
|
+
#
|
49
|
+
def self.normalize_key( str )
|
50
|
+
## add & e.g. B&W
|
51
|
+
str.downcase.gsub(/[ ()&°_-]/, '').strip
|
52
|
+
end
|
53
|
+
|
54
|
+
def self.normalize_gender( str )
|
55
|
+
## e.g. Female => f
|
56
|
+
## F => f
|
57
|
+
## always return f/m
|
58
|
+
str.downcase[0]
|
59
|
+
end
|
60
|
+
|
61
|
+
def self.normalize_size( str )
|
62
|
+
## e.g. U or Unisize or Univeral => u
|
63
|
+
## S or Small => s
|
64
|
+
## L or Large => l
|
65
|
+
## always return u/l/s
|
66
|
+
str.downcase[0]
|
67
|
+
end
|
68
|
+
|
69
|
+
def self.normalize_name( str )
|
70
|
+
## normalize spaces in more names
|
71
|
+
str.strip.gsub( /[ ]{2,}/, ' ' )
|
72
|
+
end
|
73
|
+
|
74
|
+
def normalize_key( str ) self.class.normalize_key( str ); end
|
75
|
+
def normalize_gender( str ) self.class.normalize_gender( str ); end
|
76
|
+
def normalize_size( str ) self.class.normalize_size( str ); end
|
77
|
+
def normalize_name( str ) self.class.normalize_name( str ); end
|
78
|
+
|
79
|
+
|
80
|
+
|
81
|
+
|
82
|
+
def build_attributes_by_name( recs )
|
83
|
+
h = {}
|
84
|
+
recs.each_with_index do |rec|
|
85
|
+
names = [rec.name] + rec.more_names
|
86
|
+
|
87
|
+
names.each do |name|
|
88
|
+
key = normalize_key( name )
|
89
|
+
key << "_(#{rec.gender}+#{rec.size})" if rec.attribute?
|
90
|
+
|
91
|
+
if h[ key ]
|
92
|
+
puts "!!! ERROR - attribute name is not unique:"
|
93
|
+
pp rec
|
94
|
+
puts "duplicate:"
|
95
|
+
pp h[key]
|
96
|
+
exit 1
|
97
|
+
end
|
98
|
+
h[ key ] = rec
|
99
|
+
end
|
100
|
+
end
|
101
|
+
## pp h
|
102
|
+
h
|
103
|
+
end
|
104
|
+
|
105
|
+
|
106
|
+
def build_recs( recs ) ## build and normalize (meta data) records
|
107
|
+
|
108
|
+
## sort by id
|
109
|
+
recs = recs.sort do |l,r|
|
110
|
+
l['id'].to_i( 10 ) <=> r['id'].to_i( 10 ) # use base10 (decimal)
|
111
|
+
end
|
112
|
+
|
113
|
+
## assert all recs are in order by id (0 to size)
|
114
|
+
recs.each_with_index do |rec, exp_id|
|
115
|
+
id = rec['id'].to_i(10)
|
116
|
+
if id != exp_id
|
117
|
+
puts "!! ERROR - meta data record ids out-of-order - expected id #{exp_id}; got #{id}"
|
118
|
+
exit 1
|
119
|
+
end
|
120
|
+
end
|
121
|
+
|
122
|
+
## convert to "wrapped / immutable" kind-of struct
|
123
|
+
recs = recs.map do |rec|
|
124
|
+
id = rec['id'].to_i( 10 )
|
125
|
+
name = normalize_name( rec['name'] )
|
126
|
+
gender = normalize_gender( rec['gender'] )
|
127
|
+
size = normalize_size( rec['size'] )
|
128
|
+
type = rec['type']
|
129
|
+
|
130
|
+
more_names = (rec['more_names'] || '').split( '|' )
|
131
|
+
more_names = more_names.map {|str| normalize_name( str ) }
|
132
|
+
|
133
|
+
Metadata::Sprite.new(
|
134
|
+
id: id,
|
135
|
+
name: name,
|
136
|
+
type: type,
|
137
|
+
gender: gender,
|
138
|
+
size: size,
|
139
|
+
more_names: more_names )
|
140
|
+
end
|
141
|
+
recs
|
142
|
+
end # method build_recs
|
143
|
+
|
144
|
+
|
145
|
+
|
146
|
+
|
147
|
+
def initialize( image_path="./spritesheet.png",
|
148
|
+
meta_path="./spritesheet.csv",
|
149
|
+
image_class: )
|
150
|
+
@image_class = image_class
|
151
|
+
|
152
|
+
@sheet = Pixelart::ImageComposite.read( image_path,
|
153
|
+
width: 24,
|
154
|
+
height: 24 )
|
155
|
+
recs = CsvHash.read( meta_path )
|
156
|
+
|
157
|
+
@recs = build_recs( recs )
|
158
|
+
|
159
|
+
## lookup by "case/space-insensitive" name / key
|
160
|
+
@attributes_by_name = build_attributes_by_name( @recs )
|
161
|
+
end
|
162
|
+
|
163
|
+
|
164
|
+
def spritesheet() @sheet; end
|
165
|
+
alias_method :sheet, :spritesheet
|
166
|
+
|
167
|
+
|
168
|
+
def records() @recs; end
|
169
|
+
alias_method :meta, :records
|
170
|
+
|
171
|
+
|
172
|
+
def find_meta( q, gender: nil,
|
173
|
+
size: nil,
|
174
|
+
style: nil ) ## note: gender (m/f) required for attributes!!!
|
175
|
+
|
176
|
+
key = normalize_key( q ) ## normalize q(uery) string/symbol
|
177
|
+
|
178
|
+
keys = [] ## note allow lookup by more than one keys
|
179
|
+
## e.g. if gender set try f/m first and than try unisex as fallback
|
180
|
+
if gender
|
181
|
+
gender = normalize_gender( gender )
|
182
|
+
## auto-fill size if not passed in
|
183
|
+
## for f(emale) => s(mall)
|
184
|
+
## m(ale) => l(arge)
|
185
|
+
size = if size.nil?
|
186
|
+
gender == 'f' ? 's' : 'l'
|
187
|
+
else
|
188
|
+
normalize_size( size )
|
189
|
+
end
|
190
|
+
|
191
|
+
###
|
192
|
+
# try (auto-add) style-specific version first (fallback to "regular" if not found)
|
193
|
+
if style
|
194
|
+
## for now only support natural series
|
195
|
+
style_key = if style.downcase.start_with?( 'natural' )
|
196
|
+
'natural'
|
197
|
+
else
|
198
|
+
puts "!! ERROR - unknown attribute style #{style}; sorry"
|
199
|
+
exit 1
|
200
|
+
end
|
201
|
+
|
202
|
+
keys << "#{key}#{style_key}_(#{gender}+#{size})"
|
203
|
+
## auto-add (u)niversal size as fallback
|
204
|
+
keys << "#{key}#{style_key}_(#{gender}+u)" if size == 's' || size == 'l'
|
205
|
+
## auto-add u(nisex) as fallback
|
206
|
+
keys << "#{key}#{style_key}_(u+#{size})" if gender == 'f' || gender == 'm'
|
207
|
+
end
|
208
|
+
|
209
|
+
|
210
|
+
keys << "#{key}_(#{gender}+#{size})"
|
211
|
+
## auto-add (u)niversal size as fallback
|
212
|
+
keys << "#{key}_(#{gender}+u)" if size == 's' || size == 'l'
|
213
|
+
## auto-add u(nisex) as fallback
|
214
|
+
keys << "#{key}_(u+#{size})" if gender == 'f' || gender == 'm'
|
215
|
+
else
|
216
|
+
keys << key
|
217
|
+
end
|
218
|
+
|
219
|
+
|
220
|
+
rec = nil
|
221
|
+
keys.each do |key|
|
222
|
+
rec = @attributes_by_name[ key ]
|
223
|
+
if rec
|
224
|
+
puts " lookup >#{key}< => #{rec.id}: #{rec.name} / #{rec.type} (#{rec.gender}+#{rec.size})"
|
225
|
+
# pp rec
|
226
|
+
break
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
230
|
+
if rec.nil?
|
231
|
+
puts "!! WARN - no lookup found for #{keys.size} key(s) >#{keys.inspect}<"
|
232
|
+
end
|
233
|
+
|
234
|
+
rec
|
235
|
+
end
|
236
|
+
|
237
|
+
|
238
|
+
def find( q, gender: nil, size: nil, style: nil ) ## gender (m/f) required for attributes!!!
|
239
|
+
rec = find_meta( q, gender: gender, size: size, style: style )
|
240
|
+
|
241
|
+
## return image if record found
|
242
|
+
rec ? @sheet[ rec.id ] : nil
|
243
|
+
end
|
244
|
+
|
245
|
+
|
246
|
+
|
247
|
+
|
248
|
+
def to_recs( *values, style: nil, patch: nil )
|
249
|
+
archetype_name = values[0]
|
250
|
+
|
251
|
+
if archetype_name.is_a?( Pixelart::Image )
|
252
|
+
archetype = archetype_name
|
253
|
+
elsif patch && img=patch[ normalize_key(archetype_name) ]
|
254
|
+
archetype = img
|
255
|
+
else ## assume it's a string
|
256
|
+
### todo/fix: check for nil/not found!!!!
|
257
|
+
## todo/check/fix: assert meta record returned is archetype NOT attribute!!!!
|
258
|
+
archetype = find_meta( archetype_name )
|
259
|
+
if archetype.nil?
|
260
|
+
puts "!! ERROR - archetype >#{archetype}< not found; sorry"
|
261
|
+
exit 1
|
262
|
+
end
|
263
|
+
end
|
264
|
+
|
265
|
+
recs = [archetype]
|
266
|
+
|
267
|
+
## note: attribute lookup requires gender from archetype!!!!
|
268
|
+
if archetype.is_a?( Pixelart::Image )
|
269
|
+
### for now assume (support only)
|
270
|
+
## large & male (l/m) for "inline/patch" archetypes - why? why not?
|
271
|
+
## change male to unisex - why? why not? (note: for now unisex is not doing a backup lookup using male/female)
|
272
|
+
attribute_gender = 'm'
|
273
|
+
attribute_size = 'l'
|
274
|
+
else
|
275
|
+
attribute_gender = archetype.gender
|
276
|
+
attribute_size = archetype.size
|
277
|
+
end
|
278
|
+
|
279
|
+
attribute_names = values[1..-1]
|
280
|
+
attribute_names.each do |attribute_name|
|
281
|
+
## note: quick hack - allow "inline" raw images for now - why? why not?
|
282
|
+
## pass through as-is
|
283
|
+
if attribute_name.is_a?( Pixelart::Image )
|
284
|
+
recs << attribute_name
|
285
|
+
elsif patch && img=patch[ normalize_key(attribute_name) ]
|
286
|
+
recs << img
|
287
|
+
else
|
288
|
+
rec = find_meta( attribute_name,
|
289
|
+
gender: attribute_gender,
|
290
|
+
size: attribute_size,
|
291
|
+
style: style )
|
292
|
+
if rec.nil?
|
293
|
+
puts "!! ERROR - attribute >#{attribute_name}< for (#{attribute_gender}+#{attribute_size}) not found; sorry"
|
294
|
+
exit 1
|
295
|
+
end
|
296
|
+
recs << rec
|
297
|
+
end
|
298
|
+
end
|
299
|
+
|
300
|
+
recs
|
301
|
+
end
|
302
|
+
|
303
|
+
|
304
|
+
|
305
|
+
|
306
|
+
def generate_image( *values, style: nil, patch: nil )
|
307
|
+
## check: rename patch to more/extras/foreign or ... - why? why not?
|
308
|
+
|
309
|
+
recs = to_recs( *values, style: style, patch: patch )
|
310
|
+
|
311
|
+
punk = @image_class.new( 24, 24 )
|
312
|
+
|
313
|
+
recs.each do |rec|
|
314
|
+
## note: quick hack - allow "inline" raw images for now - why? why not?
|
315
|
+
## pass through as-is
|
316
|
+
img = if rec.is_a?( Pixelart::Image )
|
317
|
+
rec
|
318
|
+
else
|
319
|
+
@sheet[ rec.id ]
|
320
|
+
end
|
321
|
+
punk.compose!( img )
|
322
|
+
end
|
323
|
+
|
324
|
+
punk
|
325
|
+
end
|
326
|
+
alias_method :generate, :generate_image
|
327
|
+
|
328
|
+
end # class Generator
|
329
|
+
|
330
|
+
end # module Punk
|
@@ -0,0 +1,20 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Marilyn
|
4
|
+
|
5
|
+
class Image < Pixelart::Image
|
6
|
+
|
7
|
+
MARILYN_ATTRIBUTES = ['Female 3', 'Wild Blonde', 'Mole',
|
8
|
+
'Blue Eye Shadow']
|
9
|
+
|
10
|
+
def self.generate( *values, style: nil )
|
11
|
+
punk = Punk::Image.generate( *MARILYN_ATTRIBUTES,
|
12
|
+
*values, style: style )
|
13
|
+
phunk = punk.mirror
|
14
|
+
|
15
|
+
## wrap in Marilyn class (note: use/ requires inner image)
|
16
|
+
new( phunk.width, phunk.height, phunk.image )
|
17
|
+
end
|
18
|
+
end # class Image
|
19
|
+
end # module Marilyn
|
20
|
+
|
@@ -0,0 +1,24 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Philip
|
4
|
+
|
5
|
+
class Image < Pixelart::Image
|
6
|
+
|
7
|
+
## note: right-looking ("pre-phlipped") philip
|
8
|
+
PHILIP = Pixelart::Image.read( "#{Pixelart::Module::Punks.root}/config/philip-24x24.png" )
|
9
|
+
|
10
|
+
def self.generate( *values )
|
11
|
+
punk = Image.new( 24, 24 )
|
12
|
+
punk.compose!( PHILIP )
|
13
|
+
|
14
|
+
values.each do |name|
|
15
|
+
attribute = Punk::Sheet.find_by( name: name,
|
16
|
+
gender: 'm' )
|
17
|
+
punk.compose!( attribute )
|
18
|
+
end
|
19
|
+
|
20
|
+
phunk = punk.mirror
|
21
|
+
phunk
|
22
|
+
end
|
23
|
+
end # class Image
|
24
|
+
end # module Philip
|
data/lib/punks/phunks.rb
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
|
2
|
+
module Phunk
|
3
|
+
|
4
|
+
class Image < Pixelart::Image
|
5
|
+
|
6
|
+
def self.generate( *values, style: nil )
|
7
|
+
punk = Punk::Image.generate( *values, style: style )
|
8
|
+
phunk = punk.mirror
|
9
|
+
|
10
|
+
## wrap in Phunks class (note: use/ requires inner image)
|
11
|
+
new( phunk.width, phunk.height, phunk.image )
|
12
|
+
end
|
13
|
+
end # class Image
|
14
|
+
end # module Phunk
|
data/lib/punks/punks.rb
ADDED
@@ -0,0 +1,123 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Punk
|
4
|
+
|
5
|
+
class Image < Pixelart::Image
|
6
|
+
def self.generator
|
7
|
+
### todo/fix: break out/ split off spritesheet from generator!!!!
|
8
|
+
@generator ||= Generator.new( "#{Pixelart::Module::Punks.root}/config/punks-24x24.png",
|
9
|
+
"#{Pixelart::Module::Punks.root}/config/punks-24x24.csv", image_class: Image )
|
10
|
+
end
|
11
|
+
|
12
|
+
|
13
|
+
def self.generate( *values, style: nil, patch: nil )
|
14
|
+
|
15
|
+
if values[0].is_a?( String )
|
16
|
+
##### add style option / hack - why? why not?
|
17
|
+
if style
|
18
|
+
values = if style.downcase.index( 'natural') && style.downcase.index( '2')
|
19
|
+
["#{values[0]} (N2)"] + values[1..-1]
|
20
|
+
elsif style.downcase[0] == 'n' ## starting with n - always assume natural(s)
|
21
|
+
## auto-add (N) for Natural to archetype
|
22
|
+
["#{values[0]} (N)"] + values[1..-1]
|
23
|
+
else
|
24
|
+
puts "!! ERROR - unknown punk style #{style}; sorry"
|
25
|
+
exit 1
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
###### hack for black&white
|
30
|
+
## auto-add b&w (black&white) to all attribute names e.g.
|
31
|
+
## Eyes => Eyes B&W
|
32
|
+
## Smile => Smile B&W
|
33
|
+
## ....
|
34
|
+
archetype_key = Generator.normalize_key( values[0] )
|
35
|
+
if archetype_key.end_with?( 'bw' ) || ## e.g. B&W
|
36
|
+
archetype_key.end_with?( '1bit') ## e.g. 1-Bit or 1Bit
|
37
|
+
|
38
|
+
values = [values[0]] + values[1..-1].map do |attribute|
|
39
|
+
if attribute.is_a?( Pixelart::Image )
|
40
|
+
attribute
|
41
|
+
else
|
42
|
+
attribute_key = Generator.normalize_key( attribute )
|
43
|
+
if ['wildhair'].include?( attribute_key ) ## pass through known b&w attributes by "default"
|
44
|
+
attribute
|
45
|
+
elsif attribute_key.index( "black" )
|
46
|
+
attribute ## pass through as-is
|
47
|
+
else
|
48
|
+
"#{attribute} B&W"
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
pp values
|
54
|
+
end
|
55
|
+
|
56
|
+
# note: female mouth by default has "custom" colors (not black)
|
57
|
+
# for every 1/2/3/4 (human) skin tone and for zombie
|
58
|
+
# auto-"magically" add mapping
|
59
|
+
#
|
60
|
+
# todo/check/fix - add more "contraints"
|
61
|
+
# for mapping to only kick-in for "basic" versions
|
62
|
+
# and not "colored" e.g. golden and such - why? why not?
|
63
|
+
#
|
64
|
+
# move this mapping here to "post-lookup" processing
|
65
|
+
# to get/incl. more "meta" attribute info - why? why not?
|
66
|
+
if archetype_key.index( 'female1' ) ||
|
67
|
+
archetype_key.index( 'female2' ) ||
|
68
|
+
archetype_key.index( 'female3' ) ||
|
69
|
+
archetype_key.index( 'female4' ) ||
|
70
|
+
archetype_key.index( 'zombiefemale' )
|
71
|
+
|
72
|
+
values = [values[0]] + values[1..-1].map do |attribute|
|
73
|
+
if attribute.is_a?( Pixelart::Image )
|
74
|
+
attribute
|
75
|
+
else
|
76
|
+
attribute_key = Generator.normalize_key( attribute )
|
77
|
+
|
78
|
+
if attribute_key == 'smile' || attribute_key == 'frown'
|
79
|
+
attribute += if archetype_key.index( 'zombiefemale' ) then ' Zombie'
|
80
|
+
elsif archetype_key.index( 'female1' ) then ' 1'
|
81
|
+
elsif archetype_key.index( 'female2' ) then ' 2'
|
82
|
+
elsif archetype_key.index( 'female3' ) then ' 3'
|
83
|
+
elsif archetype_key.index( 'female4' ) then ' 4'
|
84
|
+
else
|
85
|
+
puts "!! ERROR - smile or frown (mouth expression) not supported for archetype:"
|
86
|
+
pp values
|
87
|
+
exit 1
|
88
|
+
end
|
89
|
+
end
|
90
|
+
attribute
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
generator.generate( *values, style: style, patch: patch )
|
97
|
+
end # method Image.generate
|
98
|
+
end # class Image
|
99
|
+
|
100
|
+
|
101
|
+
|
102
|
+
class Spritesheet
|
103
|
+
def self.builtin
|
104
|
+
## for now get spritesheet via generator
|
105
|
+
Image.generator
|
106
|
+
end
|
107
|
+
## note: for now class used for "namespace" only
|
108
|
+
def self.find_by( name:, gender: nil, size: nil ) ## return archetype/attribute image by name
|
109
|
+
# note: pass along name as q (query string)
|
110
|
+
builtin.find( name,
|
111
|
+
gender: gender,
|
112
|
+
size: size )
|
113
|
+
end
|
114
|
+
end # class Spritesheet
|
115
|
+
## add convenience (alternate spelling) alias - why? why not?
|
116
|
+
SpriteSheet = Spritesheet
|
117
|
+
Sheet = Spritesheet
|
118
|
+
Sprite = Spritesheet
|
119
|
+
end # module Punk
|
120
|
+
|
121
|
+
|
122
|
+
|
123
|
+
|
@@ -0,0 +1,36 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Punkxl
|
4
|
+
|
5
|
+
class Spritesheet
|
6
|
+
def self.builtin
|
7
|
+
@builtin ||= Pixelart::Spritesheet.read( "#{Pixelart::Module::Punks.root}/config/punks_xl-32x32.png",
|
8
|
+
"#{Pixelart::Module::Punks.root}/config/punks_xl-32x32.csv",
|
9
|
+
width: 32,
|
10
|
+
height: 32 )
|
11
|
+
end
|
12
|
+
|
13
|
+
## note: for now class used for "namespace" only
|
14
|
+
def self.find_by( name: ) ## return archetype/attribute image by name
|
15
|
+
builtin.find_by( name: name )
|
16
|
+
end
|
17
|
+
end # class Spritesheet
|
18
|
+
## add convenience (alternate spelling) alias - why? why not?
|
19
|
+
SpriteSheet = Spritesheet
|
20
|
+
Sheet = Spritesheet
|
21
|
+
Sprite = Spritesheet
|
22
|
+
|
23
|
+
|
24
|
+
class Image < Pixelart::Image
|
25
|
+
def self.generator
|
26
|
+
@generator ||= Artfactory.use( Punkxl::Sheet.builtin,
|
27
|
+
image_class: Image )
|
28
|
+
end
|
29
|
+
def self.generate( *names )
|
30
|
+
generator.generate( *names )
|
31
|
+
end
|
32
|
+
end # class Image
|
33
|
+
|
34
|
+
|
35
|
+
end # module Punkxl
|
36
|
+
|
data/lib/punks/version.rb
CHANGED
data/lib/punks.rb
CHANGED
@@ -7,50 +7,42 @@ require 'artfactory/base'
|
|
7
7
|
## our own code
|
8
8
|
require 'punks/version' # note: let version always go first
|
9
9
|
|
10
|
+
require 'punks/generator'
|
10
11
|
|
11
12
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
## --- 24x24 series
|
14
|
+
require 'punks/punks'
|
15
|
+
require 'punks/phunks'
|
16
|
+
require 'punks/marilyns'
|
17
|
+
require 'punks/philips'
|
18
|
+
## --- 32x32 series
|
19
|
+
require 'punks/punks_xl'
|
16
20
|
|
17
|
-
class Spritesheet
|
18
|
-
def self.builtin
|
19
|
-
@builtin ||= Pixelart::Spritesheet.read( "#{Pixelart::Module::Punks.root}/config/punks_xl-32x32.png",
|
20
|
-
"#{Pixelart::Module::Punks.root}/config/punks_xl-32x32.csv",
|
21
|
-
width: 32,
|
22
|
-
height: 32 )
|
23
|
-
end
|
24
21
|
|
25
|
-
## note: for now class used for "namespace" only
|
26
|
-
def self.find_by( name: ) ## return archetype/attribute image by name
|
27
|
-
builtin.find_by( name: name )
|
28
|
-
end
|
29
|
-
end # class Spritesheet
|
30
|
-
## add convenience (alternate spelling) alias - why? why not?
|
31
|
-
SpriteSheet = Spritesheet
|
32
|
-
Sheet = Spritesheet
|
33
|
-
Sprite = Spritesheet
|
34
22
|
|
35
23
|
|
36
|
-
class Image < Pixelart::Image
|
37
|
-
def self.generator
|
38
|
-
@generator ||= Artfactory.use( Punkxl::Sheet.builtin,
|
39
|
-
image_class: Image )
|
40
|
-
end
|
41
|
-
def self.generate( *names )
|
42
|
-
generator.generate( *names )
|
43
|
-
end
|
44
|
-
end # class Image
|
45
24
|
|
46
|
-
|
47
|
-
|
25
|
+
### add some convenience shortcuts
|
26
|
+
Cryptopunks = Punk
|
27
|
+
CryptoPunks = Punk
|
28
|
+
Punks = Punk
|
29
|
+
## add singular too -why? why not?
|
30
|
+
Cryptopunk = Punk
|
31
|
+
CryptoPunk = Punk
|
48
32
|
|
49
33
|
|
50
34
|
### add some convenience shortcuts / alternate spelling variants
|
51
35
|
PunkXL = Punkxl
|
52
36
|
PunkXl = Punkxl
|
53
37
|
|
38
|
+
### add some convenience shortcuts / alternate spelling variants
|
39
|
+
Phunks = Phunk
|
40
|
+
|
41
|
+
### add some convenience shortcuts / alternate spelling variants
|
42
|
+
Philips = Philip
|
43
|
+
|
44
|
+
### add some convenience shortcuts / alternate spelling variants
|
45
|
+
Marilyns = Marilyn
|
54
46
|
|
55
47
|
|
56
48
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: punks
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Gerald Bauer
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2022-
|
11
|
+
date: 2022-07-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: pixelart
|
@@ -86,9 +86,9 @@ dependencies:
|
|
86
86
|
- - "~>"
|
87
87
|
- !ruby/object:Gem::Version
|
88
88
|
version: '3.23'
|
89
|
-
description: punks - generate your own 24×24 or 32×32 punk
|
90
|
-
images (off chain) from text attributes (via
|
91
|
-
zoom for bigger sizes and more
|
89
|
+
description: punks - generate your own 24×24 (or 32×32) punk, phunk, philip, marilyn
|
90
|
+
'n' more (pixel) avatar / character images (off chain) from text attributes (via
|
91
|
+
built-in spritesheet); incl. 2x/4x/8x zoom for bigger sizes and more
|
92
92
|
email: wwwmake@googlegroups.com
|
93
93
|
executables: []
|
94
94
|
extensions: []
|
@@ -101,9 +101,18 @@ files:
|
|
101
101
|
- Manifest.txt
|
102
102
|
- README.md
|
103
103
|
- Rakefile
|
104
|
+
- config/philip-24x24.png
|
105
|
+
- config/punks-24x24.csv
|
106
|
+
- config/punks-24x24.png
|
104
107
|
- config/punks_xl-32x32.csv
|
105
108
|
- config/punks_xl-32x32.png
|
106
109
|
- lib/punks.rb
|
110
|
+
- lib/punks/generator.rb
|
111
|
+
- lib/punks/marilyns.rb
|
112
|
+
- lib/punks/philips.rb
|
113
|
+
- lib/punks/phunks.rb
|
114
|
+
- lib/punks/punks.rb
|
115
|
+
- lib/punks/punks_xl.rb
|
107
116
|
- lib/punks/version.rb
|
108
117
|
homepage: https://github.com/cryptopunksnotdead/cryptopunks
|
109
118
|
licenses:
|
@@ -129,7 +138,7 @@ requirements: []
|
|
129
138
|
rubygems_version: 3.3.7
|
130
139
|
signing_key:
|
131
140
|
specification_version: 4
|
132
|
-
summary: punks - generate your own 24×24 or 32×32 punk
|
133
|
-
images (off chain) from text attributes (via built-in
|
134
|
-
zoom for bigger sizes and more
|
141
|
+
summary: punks - generate your own 24×24 (or 32×32) punk, phunk, philip, marilyn 'n'
|
142
|
+
more (pixel) avatar / character images (off chain) from text attributes (via built-in
|
143
|
+
spritesheet); incl. 2x/4x/8x zoom for bigger sizes and more
|
135
144
|
test_files: []
|