207 lines
3.5 KiB
Ruby
Executable File
207 lines
3.5 KiB
Ruby
Executable File
#!/usr/bin/env ruby
|
|
|
|
$PROGRAM_NAME = "moltenbar"
|
|
|
|
# Base worker class
|
|
class Worker
|
|
@@collector = []
|
|
|
|
class << self
|
|
def instances
|
|
return @@collector
|
|
end
|
|
end
|
|
|
|
def initialize(config, name, pipe)
|
|
@config = config
|
|
@name = name
|
|
@pipe_in = pipe
|
|
|
|
@my_config = config["mod"][name]
|
|
end
|
|
|
|
def run()
|
|
@wpid = fork do
|
|
$PROGRAM_NAME = "moltenbar: worker (#{@name})"
|
|
Signal.trap("INT") do; end
|
|
|
|
mainloop()
|
|
end
|
|
|
|
@@collector << self
|
|
|
|
return nil
|
|
end
|
|
|
|
def mainloop()
|
|
loop do
|
|
self.write("I am a dummy")
|
|
sleep(1)
|
|
end
|
|
end
|
|
|
|
def kill()
|
|
begin
|
|
if Process.getpgid(@wpid) == Process.getpgid($$)
|
|
printf("Killing pid: %s\n", @wpid)
|
|
Process.kill("HUP", @wpid)
|
|
end
|
|
rescue Errno::ESRCH => err
|
|
printf("%s: %s\n", err, @wpid)
|
|
end
|
|
end
|
|
|
|
def write(data)
|
|
@pipe_in.printf("%s\0%s\n", @name, data)
|
|
end
|
|
end
|
|
|
|
class DoSystem < Worker
|
|
def initialize(name, pipe)
|
|
@name = name
|
|
@pipe = pipe
|
|
end
|
|
|
|
def mainloop()
|
|
@pipe.each do |cmd|
|
|
system(cmd)
|
|
end
|
|
end
|
|
end
|
|
|
|
module Modules
|
|
@modules = {}
|
|
|
|
def self.add(name, class_name)
|
|
@modules[name] = class_name
|
|
end
|
|
|
|
def self.get()
|
|
return @modules
|
|
end
|
|
end
|
|
|
|
class Panel
|
|
attr_accessor :modData
|
|
|
|
def initialize(config)
|
|
@modData = {}
|
|
@config = config
|
|
end
|
|
|
|
def render
|
|
panel = @config["format"]
|
|
@modData.each do |modName, modData|
|
|
panel = panel.gsub(/@{#{modName}}/, modData)
|
|
end
|
|
|
|
@config["colours"].each do |colName, colValue|
|
|
panel = panel.gsub(/C{#{colName}}/, colValue)
|
|
end
|
|
|
|
return panel
|
|
end
|
|
end
|
|
|
|
# Kill the workers.
|
|
def cleanup
|
|
Worker.instances.each do |w|
|
|
w.kill
|
|
end
|
|
|
|
exit(0)
|
|
end
|
|
|
|
def get_x_dims()
|
|
return `xrandr`.scan(/current (\d+) x (\d+)/).flatten
|
|
end
|
|
|
|
require 'yaml'
|
|
require 'optparse'
|
|
|
|
options = {}
|
|
|
|
OptionParser.new do |opts|
|
|
opts.banner = "Usage: moltenvar [-c]"
|
|
|
|
opts.on("-cCONFIG_PATH", "--config=CONFIG_PATH", "Specify and alternative config location") do |v|
|
|
options[:config_file] = v
|
|
end
|
|
|
|
opts.on("-h", "--help", "Show this message") do
|
|
printf("%s", opts)
|
|
exit(0)
|
|
end
|
|
end.parse!
|
|
|
|
if ENV["XDG_CONFIG_HOME"] == nil
|
|
conf_dir = ENV["HOME"] + "/.config/moltenbar"
|
|
else
|
|
conf_dir = ENV["XDG_CONFIG_HOME"] + "/moltenbar"
|
|
end
|
|
|
|
options[:config_file] ||= conf_dir + "/rc.yaml"
|
|
|
|
config = YAML.load_file(options[:config_file])
|
|
|
|
config['mod_dir'] ||= conf_dir + "/mod"
|
|
|
|
Dir.new("#{config['mod_dir']}").each_child do |m|
|
|
printf("Loading module: #{m}\n")
|
|
load("#{config['mod_dir']}/#{m}")
|
|
end
|
|
|
|
pipe_r, pipe_w = IO.pipe
|
|
|
|
config["modules"].each do |modName, modType|
|
|
modClass = Modules.get[modType]
|
|
Object.const_get(modClass).new(config, modName, pipe_w).run
|
|
end
|
|
|
|
Signal.trap("INT") do cleanup; end
|
|
Signal.trap("TERM") do cleanup; end
|
|
|
|
if config['geometry'] == nil
|
|
config['gap'] ||= 0
|
|
config['height'] ||= 14
|
|
|
|
gap = config['gap'].to_i
|
|
|
|
if config['width'] == nil
|
|
y, x = get_x_dims()
|
|
config['width'] = y.to_i - (gap * 2)
|
|
end
|
|
|
|
config['geometry'] = "%{w}x%{h}+%{gap}+%{gap}" % [
|
|
w: config['width'],
|
|
h: config['height'],
|
|
gap: gap
|
|
]
|
|
end
|
|
|
|
lemonbar_cmd = [
|
|
"lemonbar",
|
|
"-g", config['geometry'],
|
|
"-f", config['fontspec'],
|
|
"-n", config['window_name'],
|
|
"-a", config['active_areas'],
|
|
"-F", config['colours']['fg'],
|
|
"-B", config['colours']['bg']
|
|
]
|
|
|
|
printf("Launching lemonbar as:\n %s\n", lemonbar_cmd.join(" "))
|
|
|
|
p = Panel.new(config)
|
|
IO.popen(lemonbar_cmd, "w+") do |pipe_lb|
|
|
pipe_lb.sync = true
|
|
|
|
DoSystem.new("system", pipe_lb).run
|
|
|
|
pipe_r.each do |line|
|
|
mod_name, data = line.chomp.split("\0")
|
|
data ||= ""
|
|
p.modData[mod_name] = data
|
|
pipe_lb.printf("%s\n", p.render())
|
|
end
|
|
end
|