Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/alecdotninja/flic
An unofficial Ruby implementation of the fliclib (use Flic IoT buttons in Ruby!)
https://github.com/alecdotninja/flic
bluetooth flic flic-buttons fliclib ruby
Last synced: 27 days ago
JSON representation
An unofficial Ruby implementation of the fliclib (use Flic IoT buttons in Ruby!)
- Host: GitHub
- URL: https://github.com/alecdotninja/flic
- Owner: alecdotninja
- License: mit
- Created: 2016-08-11T07:50:09.000Z (over 8 years ago)
- Default Branch: master
- Last Pushed: 2016-12-16T03:04:24.000Z (about 8 years ago)
- Last Synced: 2024-12-01T11:21:42.578Z (about 1 month ago)
- Topics: bluetooth, flic, flic-buttons, fliclib, ruby
- Language: Ruby
- Homepage:
- Size: 72.3 KB
- Stars: 6
- Watchers: 5
- Forks: 1
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE.txt
Awesome Lists containing this project
README
# Flic
Flic is a lightweight but thread-safe Ruby implementation of the [Fliclib](https://github.com/50ButtonsEach/fliclib-linux-hci/blob/master/ProtocolDocumentation.md). It interfaces with [flicd](https://github.com/50ButtonsEach/fliclib-linux-hci), and allows [Flic buttons](https://flic.io/) to be used as an input for Ruby applications.## Installation
Add this line to your application's Gemfile:```ruby
gem 'flic'
```And then execute:
$ bundle
Or install it yourself as:
$ gem install flic
## Simple Usage
The easiest way to get up an running is to use `Flic::SimpleClient`. It is a thin wrapper around `Flic::Client` that provides a simplified, synchronous API for the most intuative uses of a Flic button.### Establishing a connection to `flicd`
By default, `flicd` binds to `localhost` on port `5551`. These are also the defaults for `Filc::SimpleClient`. This means that if you are running `flicd` on your local machine, establishing a connection is as easy as creating a new instance of `Flic::SimpleClient`. For other configurations, you can initialize `Flic::SimpleCient` with host and port. For example, `Flic::SimpleClient.new('192.168.1.200', 5553)` will open a connection to `flicd` on `192.168.1.200` listening on port `5553`.### Getting a list of buttons
To get a list of verified buttons (buttons associated and ready to be used with a given `flicd`), call `Flic::SimpleClient#buttons`. This will return a list of button's bluetooth addresses.### Connecting a new button
A button must be in public mode before it can be added. To put a button in public mode, press and hold it for at least 7 seconds. `Flic::SimpleClient#connect_button` will return the bluetooh address of the button that was added or `nil` if no button was added.### Disconnecting a button
Similarly, a button may be disconnected by passing `Flic::SimpleClient#disconnect_button` a button's bluetooth address.### Listening for button events
`Flic::SimpleClient#listen` accepts a latency mode (`:low`, `:normal`, or `:high`) as it's first argument and button bluetooth addresses as its other arguments. For each event that occurs to those buttons, it yields the bluetooth address of the button responsible for a given event, the type of click involved in the event (`:button_down`, `:button_up`, `:button_single_click`, `:button_double_click`, or `:button_hold`), the time in seconds since the event occured, and whether the event was queued. **It will block until the connection is closed or the block raises some other exception.**### Closing the connection to `flicd`
To gracefully cleanup all connection channels and close the socket connection, call `Flic::SimpleClient#shutdown`. Once a `Flic::SimpleClient` has been shutdown it will close the underlying socket and cannot be used anymore.### Example
This is the script that I wrote to allow some of my Flic buttons to control Wink-enabled smart devices in home.
```ruby
#!/usr/bin/env rubyrequire 'bundler/setup'
require 'flic'
require 'httparty'# These bluetooth addresses were obtained from SimpleClient#connect_button
COFFEE_TABLE_BUTTON = 'XX:XX:XX:XX:XX:XX'
LIVING_ROOM_BUTTON = 'XX:XX:XX:XX:XX:XX'
BEDROOM_BUTTON = 'XX:XX:XX:XX:XX:XX'
NIGHTSTAND_BUTTON = 'XX:XX:XX:XX:XX:XX'# Obtained from https://winkbearertoken.appspot.com/
WINK_REQUEST_OPTIONS = {
headers: {
Authorization: 'Bearer XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'
}
}# Get a list of all scenes
# HTTParty.get('https://api.wink.com/users/me/scenes', WINK_REQUEST_OPTIONS)
SCENES = {
arriving: 'XXXXXXX',
leaving: 'XXXXXXX',
sleeping: 'XXXXXXX',
turn_on_living_room_lights: 'XXXXXXX',
turn_off_living_room_lights: 'XXXXXXX',
turn_on_bedroom_lights: 'XXXXXXX',
turn_off_bedroom_lights: 'XXXXXXX',
waking_up: 'XXXXXXX'
}ACTIONS = {
COFFEE_TABLE_BUTTON => {
button_single_click: :turn_on_living_room_lights,
button_double_click: :turn_off_living_room_lights,
button_hold: :leaving
},
LIVING_ROOM_BUTTON => {
button_single_click: :turn_on_living_room_lights,
button_double_click: :turn_off_living_room_lights,
button_hold: :leaving
},
BEDROOM_BUTTON => {
button_single_click: :turn_on_bedroom_lights,
button_double_click: :turn_off_bedroom_lights,
button_hold: :sleeping
},
NIGHTSTAND_BUTTON => {
button_single_click: :turn_on_bedroom_lights,
button_double_click: :turn_off_bedroom_lights,
button_hold: :waking_up
}
}# Let's get this party started!
begin
puts '[*] Opening a connection to flicd...'
client = Flic::SimpleClient.newputs '[*] Entering main loop'
client.listen(:low, COFFEE_TABLE_BUTTON, LIVING_ROOM_BUTTON, BEDROOM_BUTTON, NIGHTSTAND_BUTTON) do |button, event, latency|
begin
scene = SCENES[ACTIONS[button][event]]if scene && latency < 5
puts "[*] [#{button}] Handling #{event}"HTTParty.post("https://api.wink.com/scenes/#{scene}/activate", WINK_REQUEST_OPTIONS)
else
puts "[*] [#{button}] Ignoring #{event}"
end
rescue StandardError => error
puts "[!] Whoops! `#{error.inspect}` occured while processing #{event} on #{button}."
end
end
rescue StandardError => error
puts "[!] Whoops! #{error.inspect} occured. Wait for a few seconds and restart everything."
sleep 3retry
rescue Interrupt
puts '[*] Shutting down gracefully because of an interrupt'client.shutdown
end
```## Advanced Usage
The interface of `Flic::Client` closely mirrors [the official Java implimentation](https://github.com/50ButtonsEach/fliclib-linux-hci/tree/master/clientlib/java). Unlike `Flic::SimpleClient`, none of it's methods are blocking except `Flic::Client#handle_next_event` which blocks until the next event is recevied and dispatches it to the approprate handlers and `Flic::Client#enter_main_loop` which blocks until the client is shutdown and dispatches events as they are received. Ideally, `Flic::Client#enter_main_loop` should be run in a dedicated networking / event dispatch thread.## Contributing
Bug reports and pull requests are welcome on GitHub at https://github.com/anarchocurious/flic.## License
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).