ordbase 1.0.0

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 ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 1153ed377c1c27ca1949b44cf8f572eee29f41a22f3cf2bbb212249c08892986
4
+ data.tar.gz: 13f2cbc4bfcfe29322dff646066ae7b3440791b0ca2d5dfed3548d69c4280b75
5
+ SHA512:
6
+ metadata.gz: e17fd8a4f60c5f3c41ab648e9460a5829b1d63cad5c2cea04a45b3ee06a09dca8d58065a6f3dc016e440f2bca68a2a0d3be88a34cca0d79c6968467fadcd44f5
7
+ data.tar.gz: 82ec1b35e9929645401a920605a7b22bc2a5e81e313b56da65615eafed9854abdd307fb974e71a92d69f2ddcf6a778f0a3dd8edad7a2de43995086edfa502803
data/CHANGELOG.md ADDED
@@ -0,0 +1,3 @@
1
+ ### 0.0.1 / 2023-02-11
2
+
3
+ * Everything is new. First release
data/Manifest.txt ADDED
@@ -0,0 +1,9 @@
1
+ CHANGELOG.md
2
+ Manifest.txt
3
+ README.md
4
+ Rakefile
5
+ bin/ordbase
6
+ lib/ordbase.rb
7
+ lib/ordbase/collection.rb
8
+ lib/ordbase/stats.rb
9
+ lib/ordbase/tool.rb
data/README.md ADDED
@@ -0,0 +1,171 @@
1
+ # ordbase
2
+
3
+ ordbase gem - "right-clicker" (off-chain) ordinals (pixel art) command-line tool, machinery & helpers for Bitcoin, Litcoin, Dogecoin & co.
4
+
5
+
6
+ * home :: [github.com/pixelartexchange/artbase](https://github.com/pixelartexchange/artbase)
7
+ * bugs :: [github.com/pixelartexchange/artbase/issues](https://github.com/pixelartexchange/artbase/issues)
8
+ * gem :: [rubygems.org/gems/ordbase](https://rubygems.org/gems/ordbase)
9
+ * rdoc :: [rubydoc.info/gems/ordbase](http://rubydoc.info/gems/ordbase)
10
+
11
+
12
+
13
+ ## Command-Line Usage
14
+
15
+ Let's use the 100 Ordinal Punks collection to try out the
16
+ `ordbase` command-line tool shipping with the ordbase package.
17
+
18
+ Tip: New to Ordinal Punks? For some background see [**Awesome 100 Ordinal Punks (Anno 2023) Notes - 24×24 Pixel Art on the (Bitcoin) Blockchain »**](https://github.com/cryptopunksnotdead/cryptopunks/tree/master/awesome-ordinalpunks)
19
+
20
+
21
+ ### Step 0: Prepare A Tabular Dataset (List) Of All Ordinals w/ ID
22
+
23
+ For now a manual step - prepare a list of all ordinals with id in the comma-separated values (.csv) tabular dataset format.
24
+ Example - [ordinalpunks/ordinals.csv](https://github.com/pixelartexchange/ordinals.sandbox/blob/master/ordinalpunks/ordinals.csv):
25
+
26
+ ``` csv
27
+ num, id
28
+ 1, 96d87d7e59d75ebc0e6144b09fdd96355fcdaa86fd098d64c46f19a424012bbei0
29
+ 2, acda637db995df796b35035fd978cc1a947f1e6fd5215968da88b7e38a7e4b37i0
30
+ 3, 0406654dffdd01a49794bd8531bf33721986cc7c6546f871962adee921a39a9di0
31
+ 4, 2fe9bb034f60db694701acb23a76c3d7d5aba4328dbd315764f6ee406ba41786i0
32
+ 5, dcfa240f2681d1e4a8948120a3a64567262e3c78d5497cb4e97351bfa836b638i0
33
+ 6, 16df62c86321895df2b93236d103c935015ed77e189485be649ce2c7e6ac8a4ei0
34
+ 7, 81e8d9159b8e9a27c692a5bb3ba18ca037757e94e975b53e175eaaeb2c52f15ai0
35
+ 8, c2e15fe87c4b1fd61de65f2804858e6d1152b6316bcb9c2b39b69c9c21638f5di0
36
+ 9, 3ed569f3a92ade9f1b47031eb2db2045e7dee3e00787954a88c67ed2ad9854bbi0
37
+ ...
38
+ ```
39
+
40
+
41
+ ### Step 1: Download All Pixel Art Images Via Ordinals.com
42
+
43
+ Use
44
+
45
+ ```
46
+ $ ordbase ordinalpunks image # or
47
+ $ ordbase ordinalpunks img
48
+ ```
49
+
50
+ to download all images via the ordinals.com (web) service.
51
+ All images get stored in the (temporary) `token-i/` directory.
52
+ Resulting in:
53
+
54
+ ```
55
+ /ordinalpunks
56
+ ordinals.csv
57
+ /token-i
58
+ 1.png
59
+ 2.png
60
+ 3.png
61
+ ...
62
+ ```
63
+
64
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/1.png)
65
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/2.png)
66
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/3.png)
67
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/4.png)
68
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/5.png)
69
+ ![](https://github.com/pixelartexchange/artbase/raw/master/ordbase/i/6.png)
70
+ ...
71
+
72
+
73
+
74
+
75
+ ### Step 2: Downsample ("Pixelate") All Pixel Art Images
76
+
77
+ Note: Most pixel art collections upload / inscribe images with a zoom.
78
+ The ordinal punks, for example, use a 8x zoom factor for the 24×24px originals, thus,
79
+ resulting in 192×192px.
80
+
81
+
82
+ Add a ["artbase-compatible"](https://github.com/pixelartexchange/artbase) collection configuration file to lists the source format(s)
83
+ and the minimal true pixel format.
84
+ Example - [ordinalpunks/collection.yml](https://github.com/pixelartexchange/ordinals.sandbox/blob/master/ordinalpunks/collection.yml):
85
+
86
+ ``` yaml
87
+ slug: ordinalpunks
88
+ count: 100
89
+ format: 24x24
90
+ source: 192x192
91
+ offset: 1
92
+ ```
93
+
94
+ Use
95
+
96
+ ```
97
+ $ ordbase ordinalpunks pixelate # or
98
+ $ ordbase ordinalpunks px
99
+ ```
100
+
101
+ to downsample ("pixelate") all images
102
+ in the (temporary) `token-i/` directory.
103
+ Resulting in a `24x24`/ directory with all images
104
+ in the "minimal" `24x24` format:
105
+
106
+ ```
107
+ /ordinalpunks
108
+ ordinals.csv
109
+ collections.yml
110
+ /24x24
111
+ 1.png
112
+ 2.png
113
+ 3.png
114
+ ...
115
+ ```
116
+
117
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/1.png)
118
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/2.png)
119
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/3.png)
120
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/4.png)
121
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/5.png)
122
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/ordinalpunks/24x24/6.png)
123
+ ...
124
+
125
+
126
+
127
+ ### Bonus: Step 3: Make An All-In-One Collect'Em All Composite Image
128
+
129
+
130
+ Use
131
+
132
+ ```
133
+ $ ordbase ordinalpunks composite # or
134
+ $ ordbase ordinalpunks comp
135
+ ```
136
+
137
+ to make an all-in-one image composite for the complete collection.
138
+ Resulting in `/tmp/ordinalpunks.png` (~11kb).
139
+
140
+
141
+ ![](https://github.com/pixelartexchange/ordinals.sandbox/raw/master/i/ordinalpunks.png)
142
+
143
+
144
+ That's it for now.
145
+
146
+
147
+
148
+
149
+ ## Bonus: More Ordinal Pixel Art Collections
150
+
151
+
152
+ See the [**Ordinals (Pixel Art) Sandbox (& Cache)**](https://github.com/pixelartexchange/ordinals.sandbox)
153
+ for more collections incl. Bitcoin Punks (24×24), Ordinal Mini Doges (24×24),
154
+ Extra Ordinal Women (32×32), Ordinal Penguins (35×35),
155
+ Ordinal Birds (42×42), Bitcoin Bears (48×48) and much more.
156
+
157
+ Add your sandbox or "right-clicker" ordinal backup / archive / gallery here. Yes, you can.
158
+
159
+
160
+
161
+ ## License
162
+
163
+ The scripts are dedicated to the public domain.
164
+ Use it as you please with no restrictions whatsoever.
165
+
166
+
167
+ ## Questions? Comments?
168
+
169
+ Post them over at the [Help & Support](https://github.com/geraldb/help) page. Thanks.
170
+
171
+
data/Rakefile ADDED
@@ -0,0 +1,39 @@
1
+ require 'hoe'
2
+
3
+
4
+ ###
5
+ # hack/ quick fix for broken intuit_values - overwrite with dummy
6
+ class Hoe
7
+ def intuit_values( input ); end
8
+ end
9
+
10
+
11
+ Hoe.spec 'ordbase' do
12
+
13
+ self.version = '1.0.0'
14
+
15
+ self.summary = 'ordbase gem - "right-clicker" (off-chain) ordinals (pixel art) command-line tool, machinery & helpers for Bitcoin, Litecoin, Dogecoin & co.'
16
+ self.description = summary
17
+
18
+ self.urls = { home: 'https://github.com/pixelartexchange/artbase' }
19
+
20
+ self.author = 'Gerald Bauer'
21
+ self.email = 'wwwmake@googlegroups.com'
22
+
23
+ # switch extension to .markdown for gihub formatting
24
+ self.readme_file = 'README.md'
25
+ self.history_file = 'CHANGELOG.md'
26
+
27
+ self.extra_deps = [
28
+ ['ordinals'],
29
+ ['pixelart'],
30
+ ]
31
+
32
+ self.licenses = ['Public Domain']
33
+
34
+ self.spec_extras = {
35
+ required_ruby_version: '>= 2.3'
36
+ }
37
+
38
+ end
39
+
data/bin/ordbase ADDED
@@ -0,0 +1,17 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ ###################
4
+ # == DEV TIPS:
5
+ #
6
+ # For local testing run like:
7
+ #
8
+ # ruby -Ilib bin/ordbase
9
+ #
10
+ # Set the executable bit in Linux. Example:
11
+ #
12
+ # % chmod a+x bin/ordbase
13
+ #
14
+
15
+ require 'ordinals'
16
+
17
+ Ordinals::Tool.main
@@ -0,0 +1,268 @@
1
+
2
+ module Ordinals
3
+
4
+
5
+ class Collection
6
+ attr_reader :slug,
7
+ :width, :height,
8
+ :sources
9
+
10
+
11
+ def initialize( slug )
12
+ @slug = slug
13
+
14
+ ## read config if present
15
+ config_path = "./#{@slug}/collection.yml"
16
+ if File.exist?( config_path )
17
+ config = read_yaml( config_path )
18
+ pp config
19
+
20
+ @width, @height = _parse_dimension( config['format'] )
21
+
22
+ ## note: allow multiple source formats / dimensions
23
+ ### e.g. convert 512x512 into [ [512,512] ]
24
+ ##
25
+ source = config['source']
26
+ source = [source] unless source.is_a?( Array )
27
+ @sources = source.map { |dimension| _parse_dimension( dimension ) }
28
+ end
29
+ end
30
+
31
+
32
+ def ordinals
33
+ @ordinals ||= begin
34
+ recs = read_csv( "./#{@slug}/ordinals.csv" )
35
+ puts " #{recs.size} record(s)"
36
+ recs
37
+ end
38
+ @ordinals
39
+ end
40
+
41
+ def count() ordinals.size; end
42
+ alias_method :size, :count
43
+
44
+
45
+
46
+ def each_ordinal( &block )
47
+ ordinals.each_with_index do |rec, i| ## pass along hash rec for now - why? why not?
48
+ block.call( rec, i )
49
+ end
50
+ end
51
+
52
+ ## add each_source_image or each_token_image or each_original_image or such - why? why not??
53
+
54
+
55
+
56
+ def each_image( &block )
57
+ each_ordinal do |rec, i|
58
+ id = rec['id']
59
+ num = rec.has_key?('num') ? rec['num'].to_i(10) : i+1
60
+
61
+ path = "./#{@slug}/#{@width}x#{@height}/#{num}.png"
62
+ img = Image.read( path )
63
+
64
+ block.call( img, num )
65
+ end
66
+ end
67
+
68
+
69
+
70
+ def image_dir() "./#{@slug}/token-i"; end
71
+
72
+
73
+
74
+ ## e.g. convert dimension (width x height) "24x24" or "24 x 24" to [24,24]
75
+ def _parse_dimension( str )
76
+ str.split( /x/i ).map { |str| str.strip.to_i }
77
+ end
78
+
79
+
80
+ def pixelate
81
+ each_ordinal do |rec, i|
82
+ id = rec['id']
83
+ num = rec.has_key?('num') ? rec['num'].to_i(10) : i+1
84
+
85
+ outpath = "./#{@slug}/#{@width}x#{@height}/#{num}.png"
86
+ next if File.exist?( outpath )
87
+
88
+ path = "#{image_dir}/#{num}.png"
89
+ puts "==> reading #{path}..."
90
+
91
+ img = Image.read( path )
92
+ puts " #{img.width}x#{img.height}"
93
+
94
+ ## check for source images
95
+ if !@sources.include?( [img.width, img.height] )
96
+ puts " !! ERROR - unexpected image size; sorry - expected:"
97
+ pp @sources
98
+ exit 1
99
+ end
100
+
101
+ ## check for special case source == format!!
102
+ if [img.width,img.height] == [@width,@height]
103
+ puts " note: saving image as is - no downsampling"
104
+ img.save( outpath )
105
+ else
106
+ steps_x = Image.calc_sample_steps( img.width, @width )
107
+ steps_y = Image.calc_sample_steps( img.height, @height )
108
+
109
+ img = img.sample( steps_x, steps_y )
110
+ img.save( outpath )
111
+ end
112
+ end
113
+ end
114
+
115
+
116
+
117
+
118
+ def make_composite( limit: nil )
119
+
120
+ composite_count = limit ? limit : count
121
+
122
+ cols, rows = case composite_count
123
+ when 10 then [5, 2]
124
+ when 12 then [4, 3]
125
+ when 15 then [5, 3]
126
+ when 20 then [5, 4]
127
+ when 50 then [10, 5]
128
+ when 69 then [10, 7]
129
+ when 80 then [10, 8]
130
+ when 88 then [10, 9]
131
+ when 98,99 then [10, 10]
132
+ when 100 then [10, 10]
133
+ when 101 then [11, 10]
134
+ when 111 then [11, 11]
135
+ when 130 then [10, 13]
136
+ when 512 then [20, 26]
137
+ else
138
+ raise ArgumentError, "sorry - unknown composite count #{composite_count} for now"
139
+ end
140
+
141
+ composite = ImageComposite.new( cols, rows,
142
+ width: @width,
143
+ height: @height )
144
+
145
+
146
+ image_count = 0
147
+ each_image do |img, num|
148
+ puts "==> #{num}"
149
+ composite << img
150
+
151
+ image_count += 1
152
+ break if image_count >= composite_count
153
+ end
154
+
155
+
156
+ composite.save( "./#{@slug}/tmp/#{@slug}.png" )
157
+ end
158
+
159
+
160
+
161
+ def convert_images
162
+ Image.convert( image_dir, from: 'jpg',
163
+ to: 'png' )
164
+
165
+ Image.convert( image_dir, from: 'gif',
166
+ to: 'png' )
167
+
168
+ Image.convert( image_dir, from: 'webp',
169
+ to: 'png' )
170
+ end
171
+
172
+
173
+
174
+ def fix_images ## todo - find a different names for resaving png images?
175
+ ## "repair" png images
176
+ ## starting w/
177
+ ## - why?
178
+ ##
179
+ ## verify_signature! - ChunkyPNG::SignatureMismatch:
180
+ ## PNG signature not found,
181
+ ## found "RIFF\\xFE\\b\\x00\\x00"
182
+ ## instead of "\\x89PNG\\r\\n\\x1A\\n"
183
+
184
+ Image.convert( image_dir, from: 'png',
185
+ to: 'png' )
186
+ end
187
+
188
+
189
+ def download_meta ## inscription metadata
190
+ each_ordinal do |rec, i|
191
+ id = rec['id']
192
+ num = rec.has_key?('num') ? rec['num'].to_i(10) : i+1
193
+
194
+ chain = Ordinals.config.chain
195
+ path = "../ordinals.cache/#{chain}/#{id}.json"
196
+ next if File.exist?( path )
197
+
198
+ puts "==> downloading #{chain} inscription meta #{num} w/ id #{id}..."
199
+
200
+ data = Ordinals.client.inscription( id )
201
+
202
+ write_json( path, data )
203
+
204
+ sleep( 1.0 ) ## sleep (delay_in_s)
205
+ end
206
+ end
207
+
208
+ def dump_stats
209
+ stats = InscriptionStats.new
210
+
211
+ each_ordinal do |rec, i|
212
+ id = rec['id']
213
+
214
+ chain = Ordinals.config.chain
215
+ path = "../ordinals.cache/#{chain}/#{id}.json"
216
+
217
+ data = read_json( path )
218
+ stats.update( data )
219
+ end
220
+
221
+ pp stats.data
222
+ puts
223
+ puts stats.format
224
+ end
225
+
226
+
227
+ def download_images
228
+ each_ordinal do |rec, i|
229
+ id = rec['id']
230
+ num = rec.has_key?('num') ? rec['num'].to_i(10) : i+1
231
+
232
+ ## note: add gif too (for check) - add more formats - why? why not?
233
+ next if File.exist?( "#{image_dir}/#{num}.png" ) ||
234
+ File.exist?( "#{image_dir}/#{num}.gif" ) ||
235
+ File.exist?( "#{image_dir}/#{num}.jpg" )
236
+
237
+
238
+ puts "==> downloading image ##{num}..."
239
+
240
+
241
+ content = Ordinals.client.content( id )
242
+
243
+ puts " content_type: #{content.type}, content_length: #{content.length}"
244
+
245
+ format = if content.type =~ %r{image/jpeg}i
246
+ 'jpg'
247
+ elsif content.type =~ %r{image/png}i
248
+ 'png'
249
+ elsif content.type =~ %r{image/gif}i
250
+ 'gif'
251
+ elsif content.type =~ %r{image/webp}i
252
+ 'webp'
253
+ else
254
+ puts "!! ERROR:"
255
+ puts " unknown image format content type: >#{content.type}<"
256
+ exit 1
257
+ end
258
+
259
+ ## save image - using b(inary) mode
260
+ write_blob( "#{image_dir}/#{num}.#{format}", content.blob )
261
+
262
+ sleep( 1.0 ) ## sleep (delay_in_s)
263
+ end
264
+ end
265
+
266
+ end # class Collection
267
+ end # module Ordinals
268
+
@@ -0,0 +1,142 @@
1
+
2
+
3
+ class InscriptionStats
4
+
5
+ TITLE_RX = /^Inscription[ ]+(?<ord>[0-9]+)$/
6
+ BYTES_RX = /^(?<bytes>[0-9]+)[ ]+bytes$/
7
+
8
+ def initialize
9
+ @stats = {
10
+ count: 0,
11
+ ord: { '<1000' => 0,
12
+ '<10000' => 0,
13
+ '<100000' => 0,
14
+ '<1000000' => 0,
15
+ 'min' => nil,
16
+ 'max' => nil, },
17
+ type: Hash.new(0),
18
+ bytes: { '<100' => 0,
19
+ '<1000' => 0,
20
+ '<10000' => 0,
21
+ '<100000' => 0,
22
+ '<1000000' => 0,
23
+ 'min' => nil,
24
+ 'max' => nil, },
25
+ }
26
+
27
+ @days = Hash.new(0)
28
+ end
29
+
30
+ def size() @stats[:count]; end
31
+
32
+
33
+
34
+ def update( data )
35
+ data = JSON.parse( data) if data.is_a?( String )
36
+
37
+ @stats[ :count ] += 1
38
+
39
+
40
+ ord = nil
41
+ if m=TITLE_RX.match( data['title'] )
42
+ ord = m[:ord].to_i(10)
43
+ else
44
+ puts "!! ERROR - cannot find ord in inscription title; sorry"
45
+ pp data
46
+ exit 1
47
+ end
48
+
49
+ if ord < 1000 then @stats[:ord]['<1000'] += 1
50
+ elsif ord < 10000 then @stats[:ord]['<10000'] += 1
51
+ elsif ord < 100000 then @stats[:ord]['<100000'] += 1
52
+ elsif ord < 1000000 then @stats[:ord]['<1000000'] += 1
53
+ else
54
+ puts "!! ERROR ord out-of-bounds"
55
+ exit 1
56
+ end
57
+
58
+ ## update min/max
59
+ @stats[:ord]['min'] = ord if ord < (@stats[:ord]['min'] || 9999999)
60
+ @stats[:ord]['max'] = ord if ord > (@stats[:ord]['max'] || -1)
61
+
62
+
63
+ bytes = nil
64
+ if m=BYTES_RX.match( data['content length'] )
65
+ bytes = m[:bytes].to_i(10)
66
+ else
67
+ puts "!! ERROR - cannot find bytes in inscription content length; sorry"
68
+ pp data
69
+ exit 1
70
+ end
71
+
72
+ if bytes < 100 then @stats[:bytes]['<100'] += 1
73
+ elsif bytes < 1000 then @stats[:bytes]['<1000'] += 1
74
+ elsif bytes < 10000 then @stats[:bytes]['<10000'] += 1
75
+ elsif bytes < 100000 then @stats[:bytes]['<100000'] += 1
76
+ elsif bytes < 1000000 then @stats[:bytes]['<1000000'] += 1
77
+ else
78
+ puts "!! ERROR bytes (content-length) out-of-bounds"
79
+ exit 1
80
+ end
81
+
82
+ ## update min/max
83
+ @stats[:bytes]['min'] = bytes if bytes < (@stats[:bytes]['min'] || 9999999)
84
+ @stats[:bytes]['max'] = bytes if bytes > (@stats[:bytes]['max'] || -1)
85
+
86
+
87
+ type = data['content type']
88
+
89
+ @stats[:type][ type ] += 1
90
+
91
+ ## "timestamp"=>"2023-02-05 01:45:22 UTC",
92
+ ts = Time.strptime( data['timestamp'], '%Y-%m-%d %H:%M:%S' )
93
+
94
+ @days[ ts.strftime('%Y-%m-%d') ] +=1
95
+ end # method update
96
+
97
+
98
+ def data ## rename to model or such - why? why not?
99
+ ## sort days
100
+ days = @days.sort {|l,r| l[0] <=> r[0] }
101
+ ## add to stats
102
+ @stats[:days] = {}
103
+ days.each {|k,v| @stats[:days][k] = v }
104
+ @stats
105
+ end
106
+
107
+ =begin
108
+ {:count=>101,
109
+ :ord=>{"<1000"=>0, "<10000"=>0, "<100000"=>101, "<1000000"=>0, "min"=>14343, "max"=>42901},
110
+ :type=>{"image/png"=>101},
111
+ :bytes=>{"<100"=>0, "<1000"=>101, "<10000"=>0, "<100000"=>0, "<1000000"=>0, "min"=>274, "max"=>512},
112
+ :days=>{"2023-02-22"=>10, "2023-02-25"=>17, "2023-02-26"=>74}}
113
+ =end
114
+
115
+ def format ## rename to pretty_print or such - why? why not?
116
+ stat = data
117
+
118
+ buf = String.new('')
119
+ buf << "#{stat[:count]} inscription(s)\n"
120
+
121
+ buf << "- from ##{stat[:ord]['min']} to ##{stat[:ord]['max']} (min. to max.)\n"
122
+ buf << " - <1000 => #{stat[:ord]['<1000']}\n" if stat[:ord]["<1000"] > 0
123
+ buf << " - <10000 => #{stat[:ord]['<10000']}\n" if stat[:ord]["<10000"] > 0
124
+ buf << " - <100000 => #{stat[:ord]['<100000']}\n" if stat[:ord]["<100000"] > 0
125
+ buf << " - <1000000 => #{stat[:ord]['<1000000']}\n" if stat[:ord]["<1000000"] > 0
126
+
127
+ buf << "- format(s)\n"
128
+ stat[:type].each do |k,v|
129
+ buf << " - #{k} => #{v}\n"
130
+ end
131
+
132
+ buf << "- day(s)\n"
133
+ stat[:days].each do |k,v|
134
+ buf << " - #{k} => #{v}\n"
135
+ end
136
+
137
+ buf
138
+ end
139
+
140
+ end ## class InscriptionStats
141
+
142
+
@@ -0,0 +1,130 @@
1
+ module Ordinals
2
+ class Tool
3
+
4
+ def self.main( args=ARGV )
5
+ puts "==> welcome to the ordbase tool with args:"
6
+ pp args
7
+
8
+ options = {
9
+ }
10
+
11
+ parser = OptionParser.new do |opts|
12
+ opts.on( "--doge", "--dogecoin", "Use Dogecoin / DOGE") do
13
+ ## switch to doge
14
+ Ordinals.config.chain = :doge
15
+ end
16
+ opts.on( "--ltc", "--litecoin", "Use Litecoin / LTC") do
17
+ ## switch to ltc
18
+ Ordinals.config.chain = :ltc
19
+ end
20
+ opts.on( "--btc", "--bitcoin", "Use Bitcoin / BTC") do
21
+ ## switch to btc (default)
22
+ Ordinals.config.chain = :btc
23
+ end
24
+
25
+ opts.on("--limit NUM", Integer,
26
+ "Limit collection (default: ∞)") do |num|
27
+ options[ :limit] = num
28
+ end
29
+
30
+ opts.on("-h", "--help", "Prints this help") do
31
+ puts opts
32
+ exit
33
+ end
34
+ end
35
+
36
+ parser.parse!( args )
37
+ puts "options:"
38
+ pp options
39
+
40
+ puts "args:"
41
+ pp args
42
+
43
+ if args.size < 1
44
+ puts "!! ERROR - no collection found - use <collection> <command>..."
45
+ puts ""
46
+ exit
47
+ end
48
+
49
+ slug = args[0]
50
+ command = args[1] || 'image'
51
+
52
+ if ['m', 'meta'].include?( command )
53
+ do_download_meta( slug )
54
+ elsif ['stat', 'stats'].include?( command )
55
+ do_dump_stats( slug )
56
+ elsif ['i','img', 'image'].include?( command )
57
+ do_download_images( slug )
58
+ elsif ['conv','convert'].include?( command )
59
+ do_convert_images( slug )
60
+ elsif ['fix'].include?( command )
61
+ do_fix_images( slug )
62
+ elsif ['px','pix', 'pixelate' ].include?( command )
63
+ do_pixelate( slug )
64
+ elsif ['comp','composite' ].include?( command )
65
+ if options.has_key?( :limit )
66
+ do_make_composite( slug, limit: options[:limit] )
67
+ else
68
+ do_make_composite( slug )
69
+ end
70
+ else
71
+ puts "!! ERROR - unknown command >#{command}<, sorry"
72
+ end
73
+
74
+ puts "bye"
75
+ end
76
+
77
+
78
+ def self.do_dump_stats( slug )
79
+ puts "==> dump inscription stats for collection >#{slug}<..."
80
+
81
+ col = Collection.new( slug )
82
+ col.dump_stats
83
+ end
84
+
85
+ def self.do_download_meta( slug )
86
+ puts "==> download meta for collection >#{slug}<..."
87
+
88
+ col = Collection.new( slug )
89
+ col.download_meta
90
+ end
91
+
92
+ def self.do_download_images( slug )
93
+ puts "==> download images for collection >#{slug}<..."
94
+
95
+ col = Collection.new( slug )
96
+ col.download_images
97
+ end
98
+
99
+
100
+ def self.do_convert_images( slug )
101
+ puts "==> convert images for collection >#{slug}<..."
102
+
103
+ col = Collection.new( slug )
104
+ col.convert_images
105
+ end
106
+
107
+ def self.do_fix_images( slug )
108
+ puts "==> fix images for collection >#{slug}<..."
109
+
110
+ col = Collection.new( slug )
111
+ col.fix_images
112
+ end
113
+
114
+
115
+ def self.do_pixelate( slug )
116
+ puts "==> downsample / pixelate images for collection >#{slug}<..."
117
+
118
+ col = Collection.new( slug )
119
+ col.pixelate
120
+ end
121
+
122
+ def self.do_make_composite( slug, limit: nil )
123
+ puts "==> make composite for collection >#{slug}<..."
124
+
125
+ col = Collection.new( slug )
126
+ col.make_composite( limit: limit )
127
+ end
128
+
129
+ end # class Tool
130
+ end # module Ordinals
data/lib/ordbase.rb ADDED
@@ -0,0 +1,16 @@
1
+
2
+ require 'ordinals'
3
+ require 'pixelart'
4
+
5
+ require 'optparse'
6
+
7
+
8
+
9
+ ## our own code
10
+ require_relative 'ordbase/collection'
11
+ require_relative 'ordbase/stats'
12
+
13
+ require_relative 'ordbase/tool'
14
+
15
+
16
+
metadata ADDED
@@ -0,0 +1,121 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: ordbase
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Gerald Bauer
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2023-03-23 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: ordinals
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: pixelart
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rdoc
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '4.0'
48
+ - - "<"
49
+ - !ruby/object:Gem::Version
50
+ version: '7'
51
+ type: :development
52
+ prerelease: false
53
+ version_requirements: !ruby/object:Gem::Requirement
54
+ requirements:
55
+ - - ">="
56
+ - !ruby/object:Gem::Version
57
+ version: '4.0'
58
+ - - "<"
59
+ - !ruby/object:Gem::Version
60
+ version: '7'
61
+ - !ruby/object:Gem::Dependency
62
+ name: hoe
63
+ requirement: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - "~>"
66
+ - !ruby/object:Gem::Version
67
+ version: '3.23'
68
+ type: :development
69
+ prerelease: false
70
+ version_requirements: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - "~>"
73
+ - !ruby/object:Gem::Version
74
+ version: '3.23'
75
+ description: ordbase gem - "right-clicker" (off-chain) ordinals (pixel art) command-line
76
+ tool, machinery & helpers for Bitcoin, Litecoin, Dogecoin & co.
77
+ email: wwwmake@googlegroups.com
78
+ executables:
79
+ - ordbase
80
+ extensions: []
81
+ extra_rdoc_files:
82
+ - CHANGELOG.md
83
+ - Manifest.txt
84
+ - README.md
85
+ files:
86
+ - CHANGELOG.md
87
+ - Manifest.txt
88
+ - README.md
89
+ - Rakefile
90
+ - bin/ordbase
91
+ - lib/ordbase.rb
92
+ - lib/ordbase/collection.rb
93
+ - lib/ordbase/stats.rb
94
+ - lib/ordbase/tool.rb
95
+ homepage: https://github.com/pixelartexchange/artbase
96
+ licenses:
97
+ - Public Domain
98
+ metadata: {}
99
+ post_install_message:
100
+ rdoc_options:
101
+ - "--main"
102
+ - README.md
103
+ require_paths:
104
+ - lib
105
+ required_ruby_version: !ruby/object:Gem::Requirement
106
+ requirements:
107
+ - - ">="
108
+ - !ruby/object:Gem::Version
109
+ version: '2.3'
110
+ required_rubygems_version: !ruby/object:Gem::Requirement
111
+ requirements:
112
+ - - ">="
113
+ - !ruby/object:Gem::Version
114
+ version: '0'
115
+ requirements: []
116
+ rubygems_version: 3.3.7
117
+ signing_key:
118
+ specification_version: 4
119
+ summary: ordbase gem - "right-clicker" (off-chain) ordinals (pixel art) command-line
120
+ tool, machinery & helpers for Bitcoin, Litecoin, Dogecoin & co.
121
+ test_files: []