Рисуем виджет часов с помощью lua+cairo

Разработка скриптов на lua. Создание виджетов, диалогов и т.д.
Ответить
Аватара пользователя
olgmen
Сообщения: 155
Зарегистрирован: 30 ноя 2012, 11:00
Темы: 32
Откуда: Санкт-Петербург
Статус: Не в сети

Рисуем виджет часов с помощью lua+cairo

Сообщение olgmen » 26 дек 2013, 09:46

Создание виджета в панель awesome

Вольный перевод из http://awesome.naquadah.org/wiki/Writing_own_widgets

В awesome 3.5 возможно создание виджета без использования imagebox. Для начала напишем виджет аналоговых часов. Открываем rc.lua в своём любимом редакторе и ниже строки

-- {{{ Wibox

пишем строку, которая создаст наш виджет

local analogclock = wibox.widget.base.make_widget()

Далее пишем функцию analogclock.fit которая возвращает доступные ширину и высоту виджета. Данные берутся из высоты панели и создается виджет, в форме квадрата, который может вписаться в панель

analogclock.fit = function(analogclock, width, height)
local size = math.min(width, height)
return size, size
end


Цвет полученного виджета автоматически берется из theme.lua и имеет значение цвета фона, theme.bg_normal. Тем самым, виджет по цвету не будет выделяться на панели. Далее пишем функцию, в которую можно поместить то, что вы желаете вывести на панель, это может быть графический рисунок, текст или что угодно, всё зависит от вашей фантазии, но мы сейчас нарисуем часы. Цвет часов будет равен цвету автоматически взятому из theme.lua, theme.fg_normal, так что по цветовой гамме виджет хорошо впишется в панель. Итак пишем функцию

analogclock.draw = function(analogclock, wibox, cr, width, height)

Расчитываем размер радиуса часов, т.к. вписываем часы в квадрат, то можно использовать только ширину или высоту виджета

local r = (width - (width % 2))/2

теперь используя cairo задаем толщину линий, которыми будет выводиться рисунок, возьмем ширину линии в 1 точку (пиксель)

cr:set_line_width (1)

Для вывода окружности, циферблата, будем использовать команду

cr:arc(x, y, radius, 0, 2*math.pi)

Немного об этой команде, она выводит окружность с центром x, y с радиусом равным radius, начало окружности в точке 0, конец окружности в точке 2*math.pi. В cairo длина окружности задается в радианах, и полная окружность равна 2 * пи. Так как у нас центр окружности находится в центре квадратного виджета, то координаты центра равны радиусу. Пишем строку, которая задаёт размеры окружности окружности. Для того чтобы окружность чисто вписалась в виджет, уменьшим радиус окружности на толщину линии.

cr:arc(r, r, r - 1, 0, 2*math.pi)

Даём команду на вывод окружности

cr:stroke()

Если сейчас закрыть функцию, написав

end

в разделе -- Widgets that are aligned to the right нашего rc.lua добавить

right_layout:add(analogclock)

то в панели будет выведена окружность. Но нам нужны часы, поэтому продолжим

Забираем данные о времени из нашей системы. Вообще то таким способом мы забираем все данные о времени и дате, но далее мы будем использовать только данные о времени

local t = os.date("*t")

Переводим данные для часов в радианы, получается длинная формула, но стрелка будет двигаться плавно, а не перескакивать с часа на час

local ht = ((t.hour % 12) / 12 + t.min / 720 + t.sec / 43200) * 2 * math.pi

Точка на окружности для часов, координаты hx, hy расчитываем по формуле

local hx = math.floor(0.60 * r * math.sin(ht))
local hy = -math.floor(0.60 * r * math.cos(ht))


Переводим данные для минут

local mt = (t.min / 60 + t.sec / 3600) * 2 * math.pi

Высчитываем точку на окружности

local mx = math.floor(0.90 * r * math.sin(mt))
local my = -math.floor(0.90 * r * math.cos(mt))

Теперь для секунд

local st = t.sec / 60 * 2 * math.pi

Координаты на окружности

local sx = math.floor(0.90 * r * math.sin(st))
local sy = -math.floor(0.90 * r * math.cos(st))


Осталось нарисовать стрелки. Для этого необходимо указать начальную точку, "ось стрелки"

cr:move_to (r,r)

задаем линию часовой стрелки стрелки

cr:line_to (r+hx, r+hy)

то же самое делаем и для минутной стрелки

cr:move_to (r,r)
cr:line_to (r+mx, r+my)


и даём команду на вывод часовой и минутной стрелки. Мы их выводим отдельно, так как секундная стрелка будет окрашена в красный цвет. Иначе все стрелки будут окрашены в красный цвет.

cr:stroke()

Задаём красный цвет секундной стрелке, цвет задаётся по системе RGBA

cr:set_source_rgba(1,0,0,0.5)

Теперь координаты оси, направление и выводим

cr:move_to (r,r)
cr:line_to (r+sx, r+sy)
cr:stroke()


Закрываем функцию

end

Часы готовы. Помещаем команду вывода часов в панель. В разделе -- Widgets that are aligned to the right нашего rc.lua добавить

right_layout:add(analogclock)

Перезапускаем awesome и любуемся своей работой.

Текст виджета под спойлером

[spoiler]--analogclock
local analogclock = wibox.widget.base.make_widget()

analogclock.fit = function(analogclock, width, height)
local size = math.min(width, height)
return size, size
end

analogclock.draw = function(analogclock, wibox, cr, width, height)
local r = (width - (width % 2))/2
cr:set_line_width (1)
cr:arc(r,r,r-1,0,2*math.pi)
cr:stroke()
local t = os.date("*t")
local ht = ((t.hour % 12) / 12 + t.min / 720 + t.sec / 43200) * 2 * math.pi
local hx = math.floor(0.60 * r * math.sin(ht))
local hy = -math.floor(0.60 * r * math.cos(ht))
local mt = (t.min / 60 + t.sec / 3600) * 2 * math.pi
local mx = math.floor(0.90 * r * math.sin(mt))
local my = -math.floor(0.90 * r * math.cos(mt))
local st = t.sec / 60 * 2 * math.pi
local sx = math.floor(0.90 * r * math.sin(st))
local sy = -math.floor(0.90 * r * math.cos(st))
cr:move_to (r,r)
cr:line_to (r+hx, r+hy)
cr:move_to (r,r)
cr:line_to (r+mx, r+my)
cr:stroke()
cr:set_source_rgba(1,0,0,0.5)
cr:move_to (r,r)
cr:line_to (r+sx, r+sy)
cr:stroke()
end[/spoiler]
Кто ищет, тот всегда найдет

Arch Linux
Conky - 1.9

Аватара пользователя
lumberjack
Модератор
Сообщения: 1009
Зарегистрирован: 30 сен 2012, 04:04
Темы: 152
Откуда: Сургут
Статус: Не в сети

Re: Рисуем виджет часов с помощью lua+cairo

Сообщение lumberjack » 26 дек 2013, 13:50

olgmen, а можно картинку? :)

Аватара пользователя
olgmen
Сообщения: 155
Зарегистрирован: 30 ноя 2012, 11:00
Темы: 32
Откуда: Санкт-Петербург
Статус: Не в сети

Re: Рисуем виджет часов с помощью lua+cairo

Сообщение olgmen » 26 дек 2013, 16:19

Картинку выкладывал в "Делимся виджетами"

Изображение

Изображение
Кто ищет, тот всегда найдет

Arch Linux
Conky - 1.9

Ответить

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 0 гостей