gtk2mp3 0.7.0 → 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 +7 -0
- data/LICENSE +21 -0
- data/README.md +30 -0
- data/bin/gtk2mp3 +39 -27
- data/cache/dbm.json +1 -0
- data/data/VERSION +1 -0
- data/lib/gtk2mp3/config.rb +33 -0
- data/lib/gtk2mp3/gui.rb +106 -0
- data/lib/gtk2mp3.rb +10 -186
- metadata +78 -51
- data/README.txt +0 -7
- data/lib/gtk2mp3/appconfig.rb +0 -56
- data/lib/gtk2mp3/couple.rb +0 -99
- data/lib/gtk2mp3/playlist.rb +0 -24
- data/pngs/icon.png +0 -0
- /data/{pngs → data}/logo.png +0 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: e0d866ff929a7c03c6e19e83cfca86db84719676d4a9e613735c9ba0b88de06e
|
4
|
+
data.tar.gz: ee1c1383e5c900e7ffd40f2a2bbfe2a34bc0b31719cba081dfeb7aabe348fd72
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: ad2ba586dd898b47f00ef0a49f4e6b4fe61b9f4659f7f4c5a489d9be7b0b85ab706125c8dc23f81849f038c748286511047a7e15c65c2bdd688644f95bda0c69
|
7
|
+
data.tar.gz: cf27a1781f38117f293521f365fcdcd702f7e1148a16977c5e56f665eb185fc19d27fba33163ccab7c5ab5880a211d4f7e0fea74346d4e5e25c4b3619350b814
|
data/LICENSE
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2018 carlosjhr64
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in
|
13
|
+
all copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
21
|
+
THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,30 @@
|
|
1
|
+
# Gtk2Mp3 I: Posser
|
2
|
+
|
3
|
+
* [github](https://www.github.com/carlosjhr64/gtk2mp3)
|
4
|
+
* [rubygems]((https://rubygems.org/gems/gtk2mp3)
|
5
|
+
|
6
|
+
## DESCRIPTION:
|
7
|
+
|
8
|
+
A "Next!" button gui for [MPD/MPC](https://www.musicpd.org/).
|
9
|
+
|
10
|
+
## SYNOPSIS
|
11
|
+
|
12
|
+
gtk2mp3 --help
|
13
|
+
|
14
|
+
## HELP
|
15
|
+
|
16
|
+
Usage:
|
17
|
+
gtk2mp3 [:options+]
|
18
|
+
Options:
|
19
|
+
-h --help
|
20
|
+
-v --version
|
21
|
+
-f --force Skips mpd prechecks
|
22
|
+
--noinit Don't reset the playlist
|
23
|
+
# Notes #
|
24
|
+
# Requires MPD/MPC.
|
25
|
+
# See https://www.musicpd.org/clients/mpc/.
|
26
|
+
|
27
|
+
## INSTALL
|
28
|
+
|
29
|
+
$ sudo gem install gtk2mp3
|
30
|
+
|
data/bin/gtk2mp3
CHANGED
@@ -1,33 +1,45 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
|
-
require '
|
3
|
-
gem 'gtk2applib', '~> 15.3'
|
4
|
-
$help = <<EOT
|
2
|
+
require 'help_parser'
|
5
3
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
4
|
+
module Gtk2Mp3
|
5
|
+
VERSION = '1.0.0'
|
6
|
+
end
|
7
|
+
OPTIONS = HelpParser[Gtk2Mp3::VERSION,<<HELP]
|
8
|
+
Usage:
|
9
|
+
gtk2mp3 [:options+]
|
10
|
+
Options:
|
11
|
+
-h --help
|
12
|
+
-v --version
|
13
|
+
-f --force \tSkips mpd prechecks
|
14
|
+
--noinit \tDon't reset the playlist
|
15
|
+
# Notes #
|
16
|
+
# Requires MPD/MPC.
|
17
|
+
# See https://www.musicpd.org/clients/mpc/.
|
18
|
+
HELP
|
11
19
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
+
unless OPTIONS.force?
|
21
|
+
unless ['/etc/mpd.conf','~/.mpdconf'].all?{|_|File.exist? File.expand_path _}
|
22
|
+
$stderr.puts 'Missing /etc/mpd.conf and/or ~/.mpdconf'
|
23
|
+
exit 72 # EX_OSFILE
|
24
|
+
end
|
25
|
+
unless system 'ps -C mpd'
|
26
|
+
unless system 'mpd'
|
27
|
+
$stderr.puts 'Could not start the mpd daemon.'
|
28
|
+
exit 69 # EX_UNAVAILABLE
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
20
32
|
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
Gtk2MP3::GUI.new(window,program)
|
26
|
-
window.show_all
|
33
|
+
unless OPTIONS.noinit?
|
34
|
+
unless system 'mpc clear' and system 'mpc ls | mpc add'
|
35
|
+
$stderr.puts 'Could not initialize mpd\'s playlist'
|
36
|
+
exit 76 # EX_PROTOCOL
|
27
37
|
end
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
Gtk2MP3::Couple.dump
|
32
|
-
program.finalize
|
38
|
+
system 'mpc random on'
|
39
|
+
system 'mpc consume off'
|
40
|
+
system 'mpc repeat on'
|
33
41
|
end
|
42
|
+
|
43
|
+
require 'gtk2mp3'
|
44
|
+
Gtk3App.main(Gtk2Mp3)
|
45
|
+
system 'mpc stop'
|
data/cache/dbm.json
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
{}
|
data/data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
1.0.0
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module Gtk2Mp3
|
2
|
+
using Rafini::String
|
3
|
+
APPDIR = File.dirname File.dirname __dir__
|
4
|
+
CONFIG = {
|
5
|
+
PLAYED: 30,
|
6
|
+
DBM: "#{XDG['CACHE']}/gtk3app/gtk2mp3/dbm.json",
|
7
|
+
thing: {
|
8
|
+
HelpFile: 'https://github.com/carlosjhr64/gtk2mp3',
|
9
|
+
Logo: "#{XDG['DATA']}/gtk3app/gtk2mp3/logo.png",
|
10
|
+
window: {
|
11
|
+
set_title: 'Gtk2Mp3',
|
12
|
+
set_default_size: [100,60],
|
13
|
+
set_window_position: :center,
|
14
|
+
},
|
15
|
+
NEXT: [label: 'Next!'],
|
16
|
+
next_button!: [:NEXT, 'clicked'],
|
17
|
+
next_item!: [:NEXT, 'activate'],
|
18
|
+
STOP: [label: 'Stop'],
|
19
|
+
stop_button!: [:STOP, 'clicked'],
|
20
|
+
stop_item!: [:STOP, 'activate'],
|
21
|
+
VBOX: [:vertical],
|
22
|
+
HBOX: [:horizontal],
|
23
|
+
about_dialog: {
|
24
|
+
set_program_name: 'Gtk2Mp3',
|
25
|
+
set_version: VERSION.semantic(0..1),
|
26
|
+
set_copyright: '(c) 2018 CarlosJHR64',
|
27
|
+
set_comments: 'A MPD/MPC "Next!" Button',
|
28
|
+
set_website: 'https://github.com/carlosjhr64/gtk2mp3',
|
29
|
+
set_website_label: 'See it at GitHub!',
|
30
|
+
},
|
31
|
+
}
|
32
|
+
}
|
33
|
+
end
|
data/lib/gtk2mp3/gui.rb
ADDED
@@ -0,0 +1,106 @@
|
|
1
|
+
module Gtk2Mp3
|
2
|
+
def self.run(program)
|
3
|
+
GUI.new(program)
|
4
|
+
end
|
5
|
+
|
6
|
+
class GUI
|
7
|
+
MUTEX = Mutex.new
|
8
|
+
ID = lambda{|_|File.basename(_.strip.split(/\n/).first.strip,'.*')}
|
9
|
+
|
10
|
+
def play?(id)
|
11
|
+
rand(@db[id].to_i+1)==0
|
12
|
+
end
|
13
|
+
|
14
|
+
def random_song
|
15
|
+
n = @list.length
|
16
|
+
loop do
|
17
|
+
id = @list[rand(n)]
|
18
|
+
return id if play?(id)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
def next_song
|
23
|
+
@label.text = @playing = ID[`mpc searchplay filename '#{random_song}'`]
|
24
|
+
end
|
25
|
+
|
26
|
+
def down(id)
|
27
|
+
if count=@db[id]
|
28
|
+
count -= 1
|
29
|
+
if count>0
|
30
|
+
@db[id] = count
|
31
|
+
else
|
32
|
+
@db.delete(id)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def up(id)
|
38
|
+
@db[id] = @db[id].to_i+1
|
39
|
+
end
|
40
|
+
|
41
|
+
def db_update
|
42
|
+
if @skipped
|
43
|
+
up(@skipped) if Time.now-@time<CONFIG[:PLAYED]
|
44
|
+
elsif @played
|
45
|
+
down(@played)
|
46
|
+
@playing = ID[`mpc current`]
|
47
|
+
if play?(@playing)
|
48
|
+
@label.text = @playing
|
49
|
+
else
|
50
|
+
next_song
|
51
|
+
end
|
52
|
+
end
|
53
|
+
@time,@played,@skipped = Time.now,@playing,nil
|
54
|
+
end
|
55
|
+
|
56
|
+
def mpc_idle_player
|
57
|
+
loop do
|
58
|
+
system 'mpc idle player'
|
59
|
+
MUTEX.synchronize{db_update}
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def next_song!
|
64
|
+
MUTEX.synchronize do
|
65
|
+
@skipped = @playing
|
66
|
+
next_song
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
def stop_song!
|
71
|
+
MUTEX.synchronize do
|
72
|
+
@skipped = @playing = @played = nil
|
73
|
+
system 'mpc stop'
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
def initialize(program)
|
78
|
+
window,minime,menu = program.window,program.mini_menu,program.app_menu
|
79
|
+
@db = JSON.parse File.read(CONFIG[:DBM])
|
80
|
+
window.signal_connect('delete-event'){File.write(CONFIG[:DBM], JSON.pretty_generate(@db))}
|
81
|
+
|
82
|
+
# Build
|
83
|
+
vbox = Such::Box.new(window, :VBOX)
|
84
|
+
hbox = Such::Box.new(vbox, :HBOX)
|
85
|
+
Such::Button.new(hbox, :next_button!){next_song!}
|
86
|
+
Such::Button.new(hbox, :stop_button!){stop_song!}
|
87
|
+
@label = Such::Label.new(vbox)
|
88
|
+
menu.each{|_|_.destroy if _.label=='Full Screen' or _.label=='Help'}
|
89
|
+
minime.each{|_|_.destroy}
|
90
|
+
minime.append_menu_item(:stop_item!){stop_song!}
|
91
|
+
minime.append_menu_item(:next_item!){next_song!}
|
92
|
+
|
93
|
+
# Inits
|
94
|
+
@list = `mpc listall`.lines.map{|_|ID[_]}.uniq
|
95
|
+
@skipped=@playing=nil
|
96
|
+
next_song!
|
97
|
+
@time,@played = Time.now,@playing
|
98
|
+
Thread.new do
|
99
|
+
sleep(1) # mpd needs a little time to settle
|
100
|
+
mpc_idle_player
|
101
|
+
end
|
102
|
+
|
103
|
+
window.show_all
|
104
|
+
end
|
105
|
+
end
|
106
|
+
end
|
data/lib/gtk2mp3.rb
CHANGED
@@ -1,189 +1,13 @@
|
|
1
|
-
|
2
|
-
require '
|
3
|
-
# Configuration defined in gtk2mp3/appconfig
|
4
|
-
# Gtk2AppLib defined
|
1
|
+
# This is a Gtk3App.
|
2
|
+
require 'gtk3app'
|
5
3
|
|
6
|
-
|
7
|
-
|
4
|
+
# Standard Libraries
|
5
|
+
require 'json'
|
8
6
|
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
@pipe = nil
|
13
|
-
self.open
|
14
|
-
end
|
15
|
-
def _read
|
16
|
-
@gui.couple.promote
|
17
|
-
@gui.previous = @gui.current
|
18
|
-
@gui.load_song
|
19
|
-
end
|
20
|
-
def read
|
21
|
-
@pipe.each do |line|
|
22
|
-
line.strip!
|
23
|
-
$stderr.puts line if $trace
|
24
|
-
if line =~ /^\@I\s+(\S.*)$/ then
|
25
|
-
# :-??
|
26
|
-
elsif line =~ /^@E/ then
|
27
|
-
@gui.load_song
|
28
|
-
elsif line == '@P 0' then
|
29
|
-
_read if @gui.continue
|
30
|
-
end
|
31
|
-
end
|
32
|
-
end
|
33
|
-
def open
|
34
|
-
if !@pipe then
|
35
|
-
@pipe = IO.popen(Configuration::PLAYER,'w+') # IO defined
|
36
|
-
self.puts Configuration::C_SILENCE
|
37
|
-
@thread = Thread.new { self.read }
|
38
|
-
sleep(Configuration::SLEEP)
|
39
|
-
end
|
40
|
-
end
|
41
|
-
def puts(string)
|
42
|
-
self.open
|
43
|
-
@pipe.puts string
|
44
|
-
@pipe.flush
|
45
|
-
end
|
46
|
-
def close
|
47
|
-
if @pipe then
|
48
|
-
@thread.kill
|
49
|
-
@thread = nil
|
50
|
-
@pipe.close
|
51
|
-
@pipe = nil
|
52
|
-
end
|
53
|
-
end
|
54
|
-
end
|
7
|
+
# This Gem.
|
8
|
+
require_relative 'gtk2mp3/config.rb'
|
9
|
+
require_relative 'gtk2mp3/gui.rb'
|
55
10
|
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
attr_writer :previous
|
60
|
-
|
61
|
-
def initialize(window,program)
|
62
|
-
@playlist = Gtk2MP3::Playlist.new(Configuration::DIRECTORY)
|
63
|
-
@current = ''
|
64
|
-
@previous = ''
|
65
|
-
@continue = true
|
66
|
-
@pipe = Pipe.new(self)
|
67
|
-
window.signal_connect('destroy'){ @pipe.close }
|
68
|
-
|
69
|
-
vbox = Gtk2AppLib::Widgets::VBox.new(window)
|
70
|
-
|
71
|
-
hbox = Gtk2AppLib::Widgets::HBox.new(vbox)
|
72
|
-
@info = Gtk2AppLib::Widgets::Label.new(*Configuration::INFO+[hbox])
|
73
|
-
|
74
|
-
hbox = Gtk2AppLib::Widgets::HBox.new(vbox)
|
75
|
-
Gtk2AppLib::Widgets::Label.new(*Configuration::SPACER1+[hbox]) # Spacer
|
76
|
-
Gtk2AppLib::Widgets::Button.new(*Configuration::NEXT+[hbox]){ self.skip_song }
|
77
|
-
spacer = Configuration::SPACER2+[hbox]
|
78
|
-
if Configuration::PAUSE then
|
79
|
-
Gtk2AppLib::Widgets::Label.new(*spacer) # Spacer
|
80
|
-
Gtk2AppLib::Widgets::Button.new(*Configuration::PAUSE+[hbox]){ self.pause_song }
|
81
|
-
end
|
82
|
-
if Configuration::STOP then
|
83
|
-
Gtk2AppLib::Widgets::Label.new(*spacer) # Spacer
|
84
|
-
Gtk2AppLib::Widgets::Button.new(*Configuration::STOP+[hbox]){ self.stop_song }
|
85
|
-
end
|
86
|
-
if Configuration::EDIT then
|
87
|
-
Gtk2AppLib::Widgets::Label.new(*spacer) # Spacer
|
88
|
-
Gtk2AppLib::Widgets::Button.new(*Configuration::EDIT+[hbox]) do
|
89
|
-
self.stop_song!
|
90
|
-
sleep(Configuration::SLEEP)
|
91
|
-
filename = self.current
|
92
|
-
copy = File.join( Gtk2AppLib::USERDIR, File.basename(filename) )
|
93
|
-
if system( "xterm -e cutmp3 -i #{filename} -O #{copy}" )
|
94
|
-
if File.exist?(copy)
|
95
|
-
File.rename( copy, filename ) # replace with edited file
|
96
|
-
end
|
97
|
-
end
|
98
|
-
sleep(Configuration::SLEEP)
|
99
|
-
self.play_current
|
100
|
-
end
|
101
|
-
end
|
102
|
-
if Configuration::DELETE then
|
103
|
-
Gtk2AppLib::Widgets::Label.new(*Configuration::SPACER3+[hbox]) # Spacer
|
104
|
-
Gtk2AppLib::Widgets.define_composite(:CheckButton,:Button)
|
105
|
-
Gtk2AppLib::Widgets::CheckButtonButton.new(*Configuration::DELETE+[hbox]){|is,*dummies|
|
106
|
-
cb = is.checkbutton
|
107
|
-
if cb.active? then
|
108
|
-
self.delete_song
|
109
|
-
cb.active = false
|
110
|
-
end
|
111
|
-
}
|
112
|
-
end
|
113
|
-
|
114
|
-
Gtk2AppLib::Widgets::Label.new(*Configuration::SPACER4+[hbox]) # Spacer
|
115
|
-
|
116
|
-
self.load_song
|
117
|
-
self.program_appends(program)
|
118
|
-
end
|
119
|
-
|
120
|
-
def program_appends(program)
|
121
|
-
program.append_app_menu(Configuration::RELOAD){ @playlist.reload }
|
122
|
-
program.append_dock_menu(Configuration::PAUSE.first){ self.pause_song } if Configuration::PAUSE
|
123
|
-
program.append_dock_menu(Configuration::STOP.first){ self.stop_song } if Configuration::STOP
|
124
|
-
program.append_dock_menu(Configuration::NEXT.first){ self.skip_song }
|
125
|
-
end
|
126
|
-
|
127
|
-
def _random_song
|
128
|
-
@current = @playlist.random
|
129
|
-
$stderr.puts @current if $trace
|
130
|
-
@couple = Gtk2MP3::Couple.new(@current,@previous)
|
131
|
-
$stderr.puts "#{@couple.keys.last} #{@couple.treshold}" if $trace
|
132
|
-
end
|
133
|
-
|
134
|
-
def random_song
|
135
|
-
plays = false
|
136
|
-
while !plays do
|
137
|
-
_random_song
|
138
|
-
plays = @couple.play?
|
139
|
-
end
|
140
|
-
end
|
141
|
-
|
142
|
-
def play_current
|
143
|
-
@pipe.puts "#{Configuration::C_LOAD} #{@current}"
|
144
|
-
@time = Time.now
|
145
|
-
end
|
146
|
-
|
147
|
-
def load_song
|
148
|
-
self.random_song
|
149
|
-
@info.text = File.basename(@current,MP3) # File defined
|
150
|
-
self.play_current
|
151
|
-
end
|
152
|
-
|
153
|
-
def demote
|
154
|
-
@couple.demote if Time.now - @time < 60.0
|
155
|
-
end
|
156
|
-
|
157
|
-
def skip_song
|
158
|
-
(@continue)? demote: (@continue = true)
|
159
|
-
self.load_song
|
160
|
-
end
|
161
|
-
|
162
|
-
def stop_song!
|
163
|
-
@pipe.puts Configuration::C_STOP
|
164
|
-
@pipe.close
|
165
|
-
end
|
166
|
-
|
167
|
-
def stop_song
|
168
|
-
if @continue then
|
169
|
-
@previous = ''
|
170
|
-
@continue = false
|
171
|
-
stop_song!
|
172
|
-
else
|
173
|
-
@continue = true
|
174
|
-
self.load_song
|
175
|
-
end
|
176
|
-
end
|
177
|
-
|
178
|
-
def pause_song
|
179
|
-
@pipe.puts Configuration::C_PAUSE
|
180
|
-
end
|
181
|
-
|
182
|
-
def delete_song
|
183
|
-
File.unlink(@current)
|
184
|
-
@playlist.delete(@current)
|
185
|
-
Couple.delete(@current)
|
186
|
-
self.load_song
|
187
|
-
end
|
188
|
-
end
|
189
|
-
end
|
11
|
+
# Requires:
|
12
|
+
#`ruby`
|
13
|
+
#`mpd`
|
metadata
CHANGED
@@ -1,71 +1,98 @@
|
|
1
|
-
--- !ruby/object:Gem::Specification
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
2
|
name: gtk2mp3
|
3
|
-
version: !ruby/object:Gem::Version
|
4
|
-
|
5
|
-
version: 0.7.0
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 1.0.0
|
6
5
|
platform: ruby
|
7
|
-
authors:
|
8
|
-
- carlosjhr64
|
6
|
+
authors:
|
7
|
+
- carlosjhr64
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
11
|
+
date: 2018-03-03 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: help_parser
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '6.3'
|
20
|
+
- - ">="
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: 6.3.0
|
23
|
+
type: :runtime
|
17
24
|
prerelease: false
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
25
|
+
version_requirements: !ruby/object:Gem::Requirement
|
26
|
+
requirements:
|
27
|
+
- - "~>"
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '6.3'
|
30
|
+
- - ">="
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: 6.3.0
|
33
|
+
- !ruby/object:Gem::Dependency
|
34
|
+
name: gtk3app
|
35
|
+
requirement: !ruby/object:Gem::Requirement
|
36
|
+
requirements:
|
37
|
+
- - "~>"
|
38
|
+
- !ruby/object:Gem::Version
|
39
|
+
version: '2.0'
|
40
|
+
- - ">="
|
41
|
+
- !ruby/object:Gem::Version
|
42
|
+
version: 2.0.2
|
24
43
|
type: :runtime
|
25
|
-
|
26
|
-
|
44
|
+
prerelease: false
|
45
|
+
version_requirements: !ruby/object:Gem::Requirement
|
46
|
+
requirements:
|
47
|
+
- - "~>"
|
48
|
+
- !ruby/object:Gem::Version
|
49
|
+
version: '2.0'
|
50
|
+
- - ">="
|
51
|
+
- !ruby/object:Gem::Version
|
52
|
+
version: 2.0.2
|
53
|
+
description: 'A "Next!" button gui for MPD/MPC.
|
54
|
+
|
55
|
+
'
|
27
56
|
email: carlosjhr64@gmail.com
|
28
|
-
executables:
|
57
|
+
executables:
|
29
58
|
- gtk2mp3
|
30
59
|
extensions: []
|
31
|
-
|
32
60
|
extra_rdoc_files: []
|
33
|
-
|
34
|
-
|
35
|
-
-
|
36
|
-
- ./lib/gtk2mp3/couple.rb
|
37
|
-
- ./lib/gtk2mp3/playlist.rb
|
38
|
-
- ./lib/gtk2mp3.rb
|
39
|
-
- ./pngs/icon.png
|
40
|
-
- ./pngs/logo.png
|
41
|
-
- ./README.txt
|
61
|
+
files:
|
62
|
+
- LICENSE
|
63
|
+
- README.md
|
42
64
|
- bin/gtk2mp3
|
43
|
-
|
44
|
-
|
45
|
-
|
65
|
+
- cache/dbm.json
|
66
|
+
- data/VERSION
|
67
|
+
- data/logo.png
|
68
|
+
- lib/gtk2mp3.rb
|
69
|
+
- lib/gtk2mp3/config.rb
|
70
|
+
- lib/gtk2mp3/gui.rb
|
71
|
+
homepage: https://github.com/carlosjhr64/gtk2mp3
|
72
|
+
licenses:
|
73
|
+
- MIT
|
74
|
+
metadata: {}
|
46
75
|
post_install_message:
|
47
76
|
rdoc_options: []
|
48
|
-
|
49
|
-
require_paths:
|
77
|
+
require_paths:
|
50
78
|
- lib
|
51
|
-
required_ruby_version: !ruby/object:Gem::Requirement
|
52
|
-
|
53
|
-
requirements:
|
79
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
80
|
+
requirements:
|
54
81
|
- - ">="
|
55
|
-
- !ruby/object:Gem::Version
|
56
|
-
version:
|
57
|
-
required_rubygems_version: !ruby/object:Gem::Requirement
|
58
|
-
|
59
|
-
requirements:
|
82
|
+
- !ruby/object:Gem::Version
|
83
|
+
version: '0'
|
84
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
85
|
+
requirements:
|
60
86
|
- - ">="
|
61
|
-
- !ruby/object:Gem::Version
|
62
|
-
version:
|
63
|
-
requirements:
|
64
|
-
-
|
87
|
+
- !ruby/object:Gem::Version
|
88
|
+
version: '0'
|
89
|
+
requirements:
|
90
|
+
- 'mpc: off'
|
91
|
+
- 'ruby: ruby 2.5.0p0 (2017-12-25 revision 61468) [x86_64-linux]'
|
92
|
+
- 'mpd: Music Player Daemon 0.20.10'
|
65
93
|
rubyforge_project:
|
66
|
-
rubygems_version:
|
94
|
+
rubygems_version: 2.7.3
|
67
95
|
signing_key:
|
68
|
-
specification_version:
|
69
|
-
summary:
|
96
|
+
specification_version: 4
|
97
|
+
summary: A "Next!" button gui for MPD/MPC.
|
70
98
|
test_files: []
|
71
|
-
|
data/README.txt
DELETED
data/lib/gtk2mp3/appconfig.rb
DELETED
@@ -1,56 +0,0 @@
|
|
1
|
-
module Gtk2AppLib # Gtk2AppLib defined
|
2
|
-
module Configuration
|
3
|
-
WINDOW_DEFAULT_SIZE[0],WINDOW_DEFAULT_SIZE[1] = 0,0 # WINDOW_DEFAULT_SIZE defined in gtk2applib/configuration
|
4
|
-
MENU[:dock] = '_Dock' # MENU defined in gtk2applib/configuration
|
5
|
-
end
|
6
|
-
end
|
7
|
-
|
8
|
-
module Gtk2MP3
|
9
|
-
module Configuration
|
10
|
-
# File defined
|
11
|
-
# ARGV defined as command line arguments
|
12
|
-
# Gtk defined in gtk2
|
13
|
-
# Where is your MP3 directory?
|
14
|
-
dialog = Gtk::FileChooserDialog.new("Choose Mp3 Directory", nil, Gtk::FileChooser::ACTION_SELECT_FOLDER, nil,
|
15
|
-
[Gtk::Stock::CANCEL, Gtk::Dialog::RESPONSE_CANCEL], [Gtk::Stock::OPEN, Gtk::Dialog::RESPONSE_ACCEPT])
|
16
|
-
directory = (ARGV.shift) || nil # '/path/to/mp3s' # give it a good default, dude!
|
17
|
-
if directory && File.exist?(directory) && File.directory?(directory) then
|
18
|
-
dialog.filename = directory
|
19
|
-
end
|
20
|
-
if dialog.run == Gtk::Dialog::RESPONSE_ACCEPT
|
21
|
-
directory = dialog.filename
|
22
|
-
else
|
23
|
-
exit
|
24
|
-
end
|
25
|
-
dialog.destroy
|
26
|
-
DIRECTORY = directory
|
27
|
-
|
28
|
-
options = {:modify_font => Gtk2AppLib::Configuration::FONT[:LARGE]}.freeze
|
29
|
-
SPACER1 = [' ', options].freeze
|
30
|
-
SPACER2 = [' ', options].freeze
|
31
|
-
SPACER3 = [' ', options].freeze
|
32
|
-
SPACER4 = [' ', options].freeze
|
33
|
-
INFO = ['Gtk2 MP3 Next!!!!',{:modify_font => Gtk2AppLib::Configuration::FONT[:SMALL]}].freeze
|
34
|
-
|
35
|
-
RELOAD = '_Reload'
|
36
|
-
|
37
|
-
clicked = 'clicked'
|
38
|
-
NEXT = ['Next!', options, clicked].freeze
|
39
|
-
PAUSE = ['Pause', options, clicked].freeze # this one can be set to nil
|
40
|
-
STOP = ['Stop', options, clicked].freeze # this one can be set to nil
|
41
|
-
DELETE = ['Delete', options, clicked].freeze # this one can be set to nil
|
42
|
-
EDIT = (Gtk2AppLib::Configuration::X && Gtk2AppLib.which([['cutmp3', ' ']]))? ['Edit', options, clicked].freeze : nil # this one can be set to nil
|
43
|
-
|
44
|
-
SELECT_A_FILE = [['Select a file', Gtk::FileChooser::ACTION_OPEN],Gtk2AppLib::HNIL].freeze
|
45
|
-
|
46
|
-
PLAYER = 'mpg123 -q -a hw:0,0 -R' # 'mpg123 -q -R'
|
47
|
-
# mpg123 commands
|
48
|
-
C_PAUSE = 'P'
|
49
|
-
C_STOP = 'S'
|
50
|
-
C_SILENCE = 'SILENCE'
|
51
|
-
C_LOAD = 'L'
|
52
|
-
C_QUIT = 'Q'
|
53
|
-
|
54
|
-
SLEEP = 0.5
|
55
|
-
end
|
56
|
-
end
|
data/lib/gtk2mp3/couple.rb
DELETED
@@ -1,99 +0,0 @@
|
|
1
|
-
# Gtk2AppLib defined
|
2
|
-
# File defined
|
3
|
-
module Gtk2MP3 # Gtk2MP3 defined
|
4
|
-
class Couple # Couple defined
|
5
|
-
BASE = Hash.new(1.0)
|
6
|
-
BASE_DUMP = Gtk2AppLib::USERDIR + '/base.dump'
|
7
|
-
|
8
|
-
COUPLE = Hash.new(1.0)
|
9
|
-
COUPLE_DUMP = Gtk2AppLib::USERDIR + '/couple.dump'
|
10
|
-
|
11
|
-
LEARNING = Math.sqrt(2.0) # Math defined, built in
|
12
|
-
SEP = '/'
|
13
|
-
SEPX = Regexp.new(SEP) # Regexp defined, built in
|
14
|
-
|
15
|
-
def initialize(candidate,previous)
|
16
|
-
@candidate = candidate
|
17
|
-
@previous = previous
|
18
|
-
self.keys!
|
19
|
-
self.threshold!
|
20
|
-
end
|
21
|
-
|
22
|
-
def self._load(dump,hash)
|
23
|
-
fh = File.open(dump,'r')
|
24
|
-
fh.each do |line|
|
25
|
-
if line=~/^(.*)\s([\d\.]+)\s*$/ then
|
26
|
-
hash[$1.strip] = $2.to_f
|
27
|
-
end
|
28
|
-
end
|
29
|
-
fh.close
|
30
|
-
end
|
31
|
-
def self.load
|
32
|
-
Couple._load(BASE_DUMP,BASE) if File.exist?(BASE_DUMP)
|
33
|
-
Couple._load(COUPLE_DUMP,COUPLE) if File.exist?(COUPLE_DUMP)
|
34
|
-
end
|
35
|
-
|
36
|
-
def self.delete(current)
|
37
|
-
key = File.basename(current,Gtk2MP3::MP3)
|
38
|
-
BASE.delete(key)
|
39
|
-
COUPLE.delete_if{|pair| pair.split(SEPX).include?(key)}
|
40
|
-
end
|
41
|
-
|
42
|
-
def self._dump(dump,hash)
|
43
|
-
# Note that the default value is 1.0, so no need to save 1.0 values.
|
44
|
-
# File.open(dump,'w'){|fh| hash.each{|k,v| fh.puts "#{k}\t#{v}" if v < 1.0 } }
|
45
|
-
fh = File.open(dump,'w')
|
46
|
-
hash.each{|key,value| fh.puts "#{key}\t#{value}" if value < 1.0 }
|
47
|
-
fh.close
|
48
|
-
end
|
49
|
-
def self.dump
|
50
|
-
Couple._dump(BASE_DUMP,BASE)
|
51
|
-
Couple._dump(COUPLE_DUMP,COUPLE)
|
52
|
-
end
|
53
|
-
|
54
|
-
def keys!
|
55
|
-
@base = File.basename(@candidate,Gtk2MP3::MP3)
|
56
|
-
@couple = @base + SEP + File.basename(@previous,Gtk2MP3::MP3)
|
57
|
-
end
|
58
|
-
|
59
|
-
def keys
|
60
|
-
return @base, @couple
|
61
|
-
end
|
62
|
-
|
63
|
-
def threshold!
|
64
|
-
@threshold = BASE[@base] * COUPLE[@couple]
|
65
|
-
end
|
66
|
-
|
67
|
-
def treshold
|
68
|
-
@threshold
|
69
|
-
end
|
70
|
-
|
71
|
-
def promote
|
72
|
-
BASE[@base] *= LEARNING
|
73
|
-
COUPLE[@couple] *= LEARNING
|
74
|
-
BASE[@base] = 1.0 if BASE[@base] > 1.0
|
75
|
-
COUPLE[@couple] = 1.0 if COUPLE[@couple] > 1.0
|
76
|
-
end
|
77
|
-
|
78
|
-
def promote!
|
79
|
-
self.promote
|
80
|
-
self.threshold!
|
81
|
-
end
|
82
|
-
|
83
|
-
def demote
|
84
|
-
BASE[@base] /= LEARNING
|
85
|
-
COUPLE[@couple] /= LEARNING
|
86
|
-
BASE[@base] = 0.25 if BASE[@base] < 0.25
|
87
|
-
COUPLE[@couple] = 0.25 if COUPLE[@couple] < 0.25
|
88
|
-
end
|
89
|
-
|
90
|
-
def demote!
|
91
|
-
self.demote
|
92
|
-
self.threshold!
|
93
|
-
end
|
94
|
-
|
95
|
-
def play?
|
96
|
-
return rand < @threshold
|
97
|
-
end
|
98
|
-
end
|
99
|
-
end
|
data/lib/gtk2mp3/playlist.rb
DELETED
@@ -1,24 +0,0 @@
|
|
1
|
-
require 'find' # Find defined
|
2
|
-
|
3
|
-
module Gtk2MP3
|
4
|
-
class Playlist < Array # [] defined in Array
|
5
|
-
IS_MP3 = Regexp.new(/\.mp3$/) # Regexp defined, built in
|
6
|
-
|
7
|
-
def initialize(directory)
|
8
|
-
super()
|
9
|
-
@directory = directory
|
10
|
-
self.reload
|
11
|
-
$stderr.puts "Playlist length #{self.length}" if $trace
|
12
|
-
end
|
13
|
-
|
14
|
-
def reload
|
15
|
-
self.clear
|
16
|
-
Find.find(@directory){|fn| self.push(fn) if fn=~IS_MP3 }
|
17
|
-
raise 'no mp3s found' if self.length < 1
|
18
|
-
end
|
19
|
-
|
20
|
-
def random
|
21
|
-
self[ rand(self.length) ]
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
data/pngs/icon.png
DELETED
Binary file
|
/data/{pngs → data}/logo.png
RENAMED
File without changes
|