Skip to content

Commit

Permalink
Updated deps and fixed bugs.
Browse files Browse the repository at this point in the history
* Works now with ruby 1.9.2+ (Fixes #8)
* uses curses gem instead of rkumar/ncurses (Fixes #8)
* uses json_pure instead of json
* added the capability to download tracks (Fixes #1)
* added config file and command arguments
* mpg123 doesn't go silent after fast switching (Fixes #3)
  • Loading branch information
kulpae committed Feb 16, 2014
1 parent cf0de5b commit 10b8d74
Show file tree
Hide file tree
Showing 6 changed files with 430 additions and 130 deletions.
2 changes: 1 addition & 1 deletion LICENSE
@@ -1,6 +1,6 @@
The MIT License

Copyright (C) 2011 by Paul Koch.
Copyright (C) 2014 by Paul Koch.

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
Expand Down
60 changes: 42 additions & 18 deletions README.md
Expand Up @@ -5,26 +5,19 @@ for playback.

## Installation

Install mpg123, ruby 1.9 and ncurses with a package manager of your
Install mpg123, ruby 1.9.2, curses and json_pure with a package manager of your
destribution.

Then install the required gems.

If you are using RVM:
<pre>
gem install ncurses
gem install curses json_pure
</pre>

Without RVM you need to obtain write permissions with sudo:
<pre>
sudo gem install ncurses
</pre>

If it fails installing `ncurses`, then this step is also required:
(If using RVM, ignore `sudo`)
<pre>
wget http://github.com/downloads/rkumar/rbcurse/ncurses-1.2.4.gem
sudo gem install --local ncurses-1.2.4.gem
sudo gem install curses json_pure
</pre>

## Usage
Expand All @@ -37,29 +30,60 @@ From the terminal start with:
cloudruby http://soundcloud.com/crassmix/feint-clockwork-hearts-crass
</pre>

Inside of Ncurses:
Shortcuts:
<table style="font-family: monospace">
<tr><th width="70px" align="left">Key</th><th>Description</th></tr>
<tr><td>q | Q </td><td>Quit</td></tr>
<tr><td>+ | = </td><td>Increase Volume</td></tr>
<tr><td>- | _ </td><td>Decrease Volume</td></tr>
<tr><td>ESC | q | Q </td><td>Quit</td></tr>
<tr><td>+ | = </td><td>Increase volume</td></tr>
<tr><td>- | _ </td><td>Decrease volume</td></tr>
<tr><td>n | N | Up </td><td>Next track</td></tr>
<tr><td>p | P | Down </td><td>Previous track</td></tr>
<tr><td>m | M </td><td>Toggle mute</td></tr>
<tr><td>d | D </td><td>Download file</td></tr>
<tr><td>v | V </td><td>About dialog</td></tr>
<tr><td>Spacebar </td><td>Toggle playback</td></tr>
</table>

## Download

With 'd' or 'D' you can download a downloadable file from soundcloud. The file
will be placed inside your download directory specified with **--download_dir** argument
or inside your **~/.cloudruby.json**. If none of these are given, the current working
directory is used.

## Screenshot

![Screenshot showing ncurses user interface](https://lh5.googleusercontent.com/-G8tsAizLZeA/TkbN9K5aAFI/AAAAAAAAAG0/EhACmmuct7s/s800/cloudruby-%2525237767fc4.png)
![Screenshot showing curses user interface](https://dl.dropboxusercontent.com/u/16104361/images/cloudruby-default.png)
![Screenshot showing customized curses user interface](https://dl.dropboxusercontent.com/u/16104361/images/cloudruby-custom.png)

## Config

Cloudruby can be customized through **~/.cloudruby.json** file.

### Example
```json
{
"download_dir": "~/music",
"curses": {
"colors": {
"default": ["white", "black"],
"playlist": ["green", "black"],
"playlist_active": ["red", "black"],
"progress": ["cyan", "black"],
"progress_bar": ["blue", "white"],
"title": ["cyan"],
"artist": ["magenta"]
}
}
}
```

## Known Bugs
* Going through the playlist too fast causes silence for some time
There are 7 different 'colors', defined with a foreground and a background color.

## Author
Paul Koch [kulpae]

http://www.uraniumlane.de
http://www.uraniumlane.net/users/kulpae

## License
see LICENSE.
41 changes: 36 additions & 5 deletions cloudruby
Expand Up @@ -3,19 +3,21 @@
require 'pp'
require 'observer'
require 'logger'
require 'json/pure'
require_relative 'soundcloud.rb'
require_relative 'mpg123player.rb'
require_relative 'ncurses_ui.rb'

class Cloudruby
def init(q)
def init(q, config)
@config = config
@cloud = SoundCloud.new "76796f79392f9398288cdac3fe3391c0"
@player = MPG123Player.new
@ui = NCursesUI.new self
@ui = NCursesUI.new self, (@config[:ncurses] || @config[:curses])

#@logger = Logger.new "logfile.log"
# @logger = Logger.new "logfile.log"
@logger = Logger.new STDERR
#@logger.level = Logger::DEBUG
# @logger.level = Logger::DEBUG
@logger.level = Logger::Severity::UNKNOWN

@player.logger = @logger
Expand Down Expand Up @@ -87,6 +89,10 @@ class Cloudruby
end
end

def download
@cloud.download @config[:download_dir]
end

# quit app and free all resources
def quit
@ui.close
Expand All @@ -96,8 +102,33 @@ class Cloudruby
end
end
if $0 == __FILE__
@config = {}
@query = []
cfile = File.join Dir.home, ".#{File.basename($0)}.json"

ARGV.each do |a|
if a[0, 2] == "--"
a = a[2..-1]
key, value = a.split("=", 2)
@config[key.to_sym] = value || true
else
@query << a
end
end

if @config[:noconfig].nil? && File.readable?(cfile)
File.open cfile, 'r' do |file|
jsonconf = JSON.load file, nil, :symbolize_names => true
@config = jsonconf.merge(@config)
end
end

@config[:download_dir] ||= Dir.pwd

@query = @query.join " "

c = Cloudruby.new
c.init ARGV[0]
c.init @query, @config
c.run
end

35 changes: 30 additions & 5 deletions mpg123player.rb
Expand Up @@ -8,9 +8,11 @@ class MPG123Player
def initialize()
@volume = 100
@muted = false
@inqueue = []
begin
@pin, @pout, @perr = Open3.popen3 "mpg123 --keep-open --remote"
Thread.new do watch end
Thread.new do mpg123read end
Thread.new do mpg123send end
changed
notify_observers :state => :inited
rescue => err
Expand Down Expand Up @@ -97,18 +99,41 @@ def close()
end

def mpg123puts(out)
@pin.puts out
@logger.debug {">> #{out}" } #
@inqueue << out
@logger.debug {">> #{out}"} #
end

private

def watch
def mpg123send
while not @pin.closed?
begin
last_cmd = nil
@logger.debug "queue size #{@inqueue.size}"
@inqueue.select! do |cmd|
if cmd[0,4] == "load"
last_cmd = cmd
false
else
true
end
end
@inqueue << last_cmd unless last_cmd.nil?
while out = @inqueue.shift
@pin.puts out
end
select(nil, nil, nil, 0.4)
rescue
end
end
end

def mpg123read
while not @pout.closed?
begin
io = IO.select([@pout, @perr])
io = io.first.first
response = io.read_nonblock 400
response = io.read_nonblock 1024
lines = response.split "\n"
lines.each do |line|
@logger.debug {"<< #{line}"} #
Expand Down

0 comments on commit 10b8d74

Please sign in to comment.