airstream 0.3.4 → 0.3.6
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.
- data/bin/airimg +23 -3
- data/bin/airstream +34 -46
- data/lib/airstream.rb +1 -1
- data/lib/airstream/device.rb +98 -0
- data/lib/airstream/io.rb +27 -4
- data/lib/airstream/version.rb +1 -1
- metadata +4 -4
- data/lib/airstream/server.rb +0 -42
data/bin/airimg
CHANGED
@@ -2,11 +2,21 @@
|
|
2
2
|
|
3
3
|
require 'airstream'
|
4
4
|
|
5
|
+
def self.exit(status)
|
6
|
+
Airstream::Io.show_input
|
7
|
+
puts "\n" # clear output
|
8
|
+
super status
|
9
|
+
end
|
10
|
+
|
5
11
|
options = {
|
6
12
|
reciever: '192.168.1.8',
|
7
13
|
interval: 3
|
8
14
|
}
|
9
15
|
|
16
|
+
EXIT_OK = 0
|
17
|
+
EXIT_ERROR = 1
|
18
|
+
EXIT_NO_HOST = 68
|
19
|
+
|
10
20
|
CONFIG_FILE = File.join(ENV['HOME'], '.airstreamrc')
|
11
21
|
|
12
22
|
if File.exists? CONFIG_FILE
|
@@ -53,19 +63,29 @@ begin
|
|
53
63
|
exit 68
|
54
64
|
end
|
55
65
|
|
56
|
-
|
66
|
+
device = Airstream::Device.new(options[:reciever])
|
57
67
|
|
68
|
+
io = Airstream::Io.new
|
69
|
+
io.quiet = options[:quiet]
|
70
|
+
io.verbose = options[:verbose]
|
71
|
+
io.puts "=> press ["+Airstream::Io::KEY_QUIT+"] to exit airstream"
|
72
|
+
Airstream::Io.hide_input
|
58
73
|
ARGV.each do |file|
|
59
|
-
|
74
|
+
device.image = file
|
60
75
|
sleep options[:interval]
|
76
|
+
io.catch_input
|
77
|
+
break if io.quit?
|
61
78
|
end
|
62
79
|
|
80
|
+
|
63
81
|
rescue Interrupt
|
64
82
|
STDERR.puts
|
65
83
|
STDERR.puts "exiting"
|
66
|
-
exit
|
84
|
+
exit EXIT_OK
|
67
85
|
rescue OptionParser::InvalidArgument => ex
|
68
86
|
STDERR.puts ex.message
|
69
87
|
STDERR.puts option_parser
|
88
|
+
exit EXIT_ERROR
|
70
89
|
end
|
71
90
|
|
91
|
+
exit EXIT_OK
|
data/bin/airstream
CHANGED
@@ -2,6 +2,12 @@
|
|
2
2
|
|
3
3
|
require 'airstream'
|
4
4
|
|
5
|
+
def self.exit(status)
|
6
|
+
Airstream::Io.show_input
|
7
|
+
puts "\n" # clear output
|
8
|
+
super status
|
9
|
+
end
|
10
|
+
|
5
11
|
options = {
|
6
12
|
reciever: '192.168.1.8',
|
7
13
|
quiet: false,
|
@@ -11,6 +17,12 @@ options = {
|
|
11
17
|
|
12
18
|
CONFIG_FILE = File.join(ENV['HOME'], '.airstreamrc')
|
13
19
|
|
20
|
+
EXIT_OK = 0
|
21
|
+
EXIT_ERROR = 1
|
22
|
+
EXIT_NO_HOST = 68
|
23
|
+
|
24
|
+
UPDATE_TIMEOUT = 0.2
|
25
|
+
|
14
26
|
if File.exists? CONFIG_FILE
|
15
27
|
options_config = YAML.load_file(CONFIG_FILE)
|
16
28
|
options.merge!(options_config)
|
@@ -51,15 +63,16 @@ Basic options: (configure default in ~/.airstreamrc)
|
|
51
63
|
opts.on("-v", "--version",
|
52
64
|
"output version information then quit") do |path|
|
53
65
|
puts "airstream v" + Airstream::VERSION
|
54
|
-
exit
|
66
|
+
exit EXIT_OK
|
55
67
|
end
|
56
68
|
end
|
57
69
|
|
58
70
|
if ARGV.empty?
|
59
71
|
STDERR.puts "No arguments given"
|
60
72
|
STDERR.puts option_parser
|
61
|
-
exit
|
73
|
+
exit EXIT_ERROR
|
62
74
|
end
|
75
|
+
playlist = ARGV
|
63
76
|
|
64
77
|
begin
|
65
78
|
|
@@ -67,64 +80,39 @@ begin
|
|
67
80
|
|
68
81
|
unless options[:reciever]
|
69
82
|
STDERR.puts "No host given"
|
70
|
-
exit
|
83
|
+
exit EXIT_NO_HOST
|
71
84
|
end
|
72
85
|
|
73
86
|
io = Airstream::Io.new
|
74
87
|
io.quiet = options[:quiet]
|
75
88
|
io.verbose = options[:verbose]
|
76
|
-
|
77
|
-
|
78
|
-
puts "=>
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
io.
|
83
|
-
|
84
|
-
|
85
|
-
io.print "loading"
|
86
|
-
while server.loading?
|
87
|
-
io.print "."
|
88
|
-
sleep(0.7)
|
89
|
-
end
|
90
|
-
io.puts " done"
|
91
|
-
|
92
|
-
video_title = File.basename(file, '.mp4')
|
93
|
-
pbar_options = {
|
94
|
-
title: video_title,
|
95
|
-
total: server.video_duration,
|
96
|
-
format: '%t |%b%i| %p%%'
|
97
|
-
}
|
98
|
-
|
99
|
-
io.hide_input
|
100
|
-
pbar = ProgressBar.create(pbar_options)
|
101
|
-
while (elapsed_time=server.video_position) < server.video_duration
|
102
|
-
io.catch_input
|
103
|
-
break if io.quit? || io.skip?
|
104
|
-
pbar.progress = elapsed_time
|
105
|
-
formatted_time = Time.at(elapsed_time).gmtime.strftime('%R:%S')
|
106
|
-
pbar.title = "#{video_title} #{formatted_time}"
|
107
|
-
sleep 0.5
|
108
|
-
end
|
109
|
-
io.show_input
|
110
|
-
pbar.finish
|
111
|
-
break if io.quit?
|
112
|
-
end
|
89
|
+
device = Airstream::Device.new(options[:reciever], playlist)
|
90
|
+
|
91
|
+
io.puts "=> press ["+Airstream::Io::KEY_QUIT+"] to exit airstream"
|
92
|
+
Airstream::Io.hide_input
|
93
|
+
begin
|
94
|
+
sleep UPDATE_TIMEOUT
|
95
|
+
io.catch_input
|
96
|
+
device.update io
|
97
|
+
end until io.quit? || device.finished?
|
113
98
|
|
114
99
|
rescue Airplay::Protocol::InvalidMediaError
|
115
100
|
STDERR.puts
|
116
101
|
STDERR.puts "invalid media file"
|
117
|
-
exit
|
118
|
-
rescue NoMethodError # @FIX webrick raises no method error
|
119
|
-
|
120
|
-
|
121
|
-
|
102
|
+
exit EXIT_ERROR
|
103
|
+
# rescue NoMethodError # @FIX webrick raises no method error
|
104
|
+
# STDERR.puts
|
105
|
+
# STDERR.puts "file host shutdown"
|
106
|
+
# exit EXIT_OK
|
122
107
|
rescue Interrupt
|
123
108
|
STDERR.puts
|
124
109
|
STDERR.puts "exiting"
|
125
|
-
exit
|
110
|
+
exit EXIT_ERROR
|
126
111
|
rescue OptionParser::InvalidArgument => ex
|
127
112
|
STDERR.puts ex.message
|
128
113
|
STDERR.puts option_parser
|
114
|
+
exit EXIT_ERROR
|
129
115
|
end
|
130
116
|
|
117
|
+
exit EXIT_OK
|
118
|
+
|
data/lib/airstream.rb
CHANGED
@@ -0,0 +1,98 @@
|
|
1
|
+
|
2
|
+
module Airstream
|
3
|
+
# pbar = ProgressBar.create(pbar_options)
|
4
|
+
# while (elapsed_time=server.video_position) < server.video_duration
|
5
|
+
# io.catch_input
|
6
|
+
# break if io.quit? || io.skip?
|
7
|
+
# pbar.progress = elapsed_time
|
8
|
+
# formatted_time = Time.at(elapsed_time).gmtime.strftime('%R:%S')
|
9
|
+
# pbar.title = "#{video_title} #{formatted_time}"
|
10
|
+
# sleep 0.5
|
11
|
+
# end
|
12
|
+
# io.show_input
|
13
|
+
# pbar.finish
|
14
|
+
class Device
|
15
|
+
|
16
|
+
@local_httpd_allowed = false
|
17
|
+
@current_file_index
|
18
|
+
|
19
|
+
def initialize(reciever, files=[])
|
20
|
+
@video_files = files
|
21
|
+
@reciever = Airstream::Node.new reciever
|
22
|
+
@current_file_index = 0
|
23
|
+
self.video = files.first unless files.empty?
|
24
|
+
end
|
25
|
+
|
26
|
+
def image=(image_file)
|
27
|
+
@reciever.send_image image_file
|
28
|
+
end
|
29
|
+
|
30
|
+
def video=(video_file)
|
31
|
+
@pbar.finish unless @pbar == nil
|
32
|
+
@video_duration = nil
|
33
|
+
video = Video.new(video_file)
|
34
|
+
@player = @reciever.send_video(video.url)
|
35
|
+
print "loading"
|
36
|
+
while loading?
|
37
|
+
print "."
|
38
|
+
sleep 0.8
|
39
|
+
end
|
40
|
+
@pbar = ProgressBar.create({ format: '%t |%b%i| %p%%', total: video_duration })
|
41
|
+
@video_title = File.basename(video_file, File.extname(video_file))
|
42
|
+
end
|
43
|
+
|
44
|
+
def update(io)
|
45
|
+
elapsed_time = video_position
|
46
|
+
formatted_time = Time.at(elapsed_time).gmtime.strftime('%R:%S')
|
47
|
+
@pbar.title = "#{@video_title} #{formatted_time}"
|
48
|
+
if io.quit?
|
49
|
+
Airstream::Io.show_input
|
50
|
+
exit # TODO skip to last fil, no exit
|
51
|
+
elsif io.skip? || video_duration <= elapsed_time
|
52
|
+
@current_file_index += 1
|
53
|
+
self.video = @video_files[@current_file_index] if @video_files.count > @current_file_index
|
54
|
+
elsif io.prev?
|
55
|
+
if @current_file_index == 0
|
56
|
+
@reciever.scrub(0)
|
57
|
+
else
|
58
|
+
@current_file_index -= 1
|
59
|
+
self.video = @video_files[@current_file_index] if @video_files.count > @current_file_index
|
60
|
+
end
|
61
|
+
elsif io.fwd?
|
62
|
+
@reciever.scrub(video_position + 30) if video_position + 30 < video_duration
|
63
|
+
elsif io.back?
|
64
|
+
@reciever.scrub(video_position - 30) if video_position - 30 > 0
|
65
|
+
elsif io.pause?
|
66
|
+
paused? ? @player.pause : @player.resume
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
def finished?
|
71
|
+
!! (@current_file_index == @video_files.count-1) && (video_position == video_duration)
|
72
|
+
end
|
73
|
+
|
74
|
+
def allow_local_httpd=(is_allowed)
|
75
|
+
@local_httpd_allowed = is_allowed
|
76
|
+
end
|
77
|
+
|
78
|
+
def local_httpd_allowed?
|
79
|
+
@local_httpd_allowed
|
80
|
+
end
|
81
|
+
|
82
|
+
def loading?
|
83
|
+
@reciever.scrub['position'] == 0
|
84
|
+
end
|
85
|
+
|
86
|
+
def video_position
|
87
|
+
@pbar.progress = @reciever.scrub['position']
|
88
|
+
end
|
89
|
+
|
90
|
+
def video_duration
|
91
|
+
@video_duration = @video_duration || @reciever.scrub['duration']
|
92
|
+
end
|
93
|
+
|
94
|
+
def paused?
|
95
|
+
@paused = !@paused || false
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
data/lib/airstream/io.rb
CHANGED
@@ -3,6 +3,13 @@ require 'io/wait'
|
|
3
3
|
|
4
4
|
module Airstream
|
5
5
|
class Io
|
6
|
+
KEY_QUIT = 'q'
|
7
|
+
KEY_SKIP = '>'
|
8
|
+
KEY_PREV = '<'
|
9
|
+
KEY_FWD = '.'
|
10
|
+
KEY_BACK = ','
|
11
|
+
KEY_PAUSE = ' '
|
12
|
+
|
6
13
|
attr_writer :quiet, :verbose
|
7
14
|
attr_reader :key
|
8
15
|
|
@@ -18,11 +25,11 @@ module Airstream
|
|
18
25
|
STDOUT.puts msg if @verbose
|
19
26
|
end
|
20
27
|
|
21
|
-
def hide_input
|
28
|
+
def self.hide_input
|
22
29
|
`stty raw -echo`
|
23
30
|
end
|
24
31
|
|
25
|
-
def show_input
|
32
|
+
def self.show_input
|
26
33
|
`stty -raw echo`
|
27
34
|
end
|
28
35
|
|
@@ -36,11 +43,27 @@ module Airstream
|
|
36
43
|
end
|
37
44
|
|
38
45
|
def quit?
|
39
|
-
@key ==
|
46
|
+
@key == KEY_QUIT
|
40
47
|
end
|
41
48
|
|
42
49
|
def skip?
|
43
|
-
@key ==
|
50
|
+
@key == KEY_SKIP
|
51
|
+
end
|
52
|
+
|
53
|
+
def prev?
|
54
|
+
@key == KEY_PREV
|
55
|
+
end
|
56
|
+
|
57
|
+
def fwd?
|
58
|
+
@key == KEY_FWD
|
59
|
+
end
|
60
|
+
|
61
|
+
def back?
|
62
|
+
@key == KEY_BACK
|
63
|
+
end
|
64
|
+
|
65
|
+
def pause?
|
66
|
+
@key == KEY_PAUSE
|
44
67
|
end
|
45
68
|
end
|
46
69
|
end
|
data/lib/airstream/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: airstream
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.3.
|
4
|
+
version: 0.3.6
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2013-01-05 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: airplay
|
@@ -103,12 +103,12 @@ files:
|
|
103
103
|
- bin/airstream
|
104
104
|
- bin/airimg
|
105
105
|
- lib/airstream.rb
|
106
|
-
- lib/airstream/
|
106
|
+
- lib/airstream/device.rb
|
107
107
|
- lib/airstream/io.rb
|
108
108
|
- lib/airstream/network.rb
|
109
109
|
- lib/airstream/node.rb
|
110
|
+
- lib/airstream/version.rb
|
110
111
|
- lib/airstream/video.rb
|
111
|
-
- lib/airstream/server.rb
|
112
112
|
homepage: https://github.com/unused/airstream
|
113
113
|
licenses: []
|
114
114
|
post_install_message:
|
data/lib/airstream/server.rb
DELETED
@@ -1,42 +0,0 @@
|
|
1
|
-
|
2
|
-
module Airstream
|
3
|
-
class Server
|
4
|
-
|
5
|
-
@local_httpd_allowed = false
|
6
|
-
|
7
|
-
def initialize(reciever)
|
8
|
-
@device = Airstream::Node.new reciever
|
9
|
-
end
|
10
|
-
|
11
|
-
def image=(image_file)
|
12
|
-
@device.send_image image_file
|
13
|
-
end
|
14
|
-
|
15
|
-
def video=(video_file)
|
16
|
-
@video_duration = nil
|
17
|
-
video = Video.new(video_file)
|
18
|
-
@device.send_video(video.url)
|
19
|
-
end
|
20
|
-
|
21
|
-
def allow_local_httpd=(is_allowed)
|
22
|
-
@local_httpd_allowed = is_allowed
|
23
|
-
end
|
24
|
-
|
25
|
-
def local_httpd_allowed?
|
26
|
-
@local_httpd_allowed
|
27
|
-
end
|
28
|
-
|
29
|
-
def loading?
|
30
|
-
@device.scrub['position'] == 0
|
31
|
-
end
|
32
|
-
|
33
|
-
def video_position
|
34
|
-
@device.scrub['position']
|
35
|
-
end
|
36
|
-
|
37
|
-
def video_duration
|
38
|
-
@video_duration = @video_duration || @device.scrub['duration']
|
39
|
-
end
|
40
|
-
|
41
|
-
end
|
42
|
-
end
|