xref: /freebsd/stand/lua/drawer.lua (revision a07d59d1daafdaae0d1b1ad1f977f9eda92dc83b)
1--
2-- Copyright (c) 2015 Pedro Souza <pedrosouza@freebsd.org>
3-- All rights reserved.
4--
5-- Redistribution and use in source and binary forms, with or without
6-- modification, are permitted provided that the following conditions
7-- are met:
8-- 1. Redistributions of source code must retain the above copyright
9--    notice, this list of conditions and the following disclaimer.
10-- 2. Redistributions in binary form must reproduce the above copyright
11--    notice, this list of conditions and the following disclaimer in the
12--    documentation and/or other materials provided with the distribution.
13--
14-- THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15-- ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16-- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17-- ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18-- FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19-- DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20-- OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21-- HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22-- LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23-- OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24-- SUCH DAMAGE.
25--
26-- $FreeBSD$
27--
28
29local drawer = {};
30
31local color = require("color");
32local screen = require("screen");
33
34drawer.brand_position = {x = 2, y = 1};
35drawer.fbsd_logo = {
36	"  ______               ____   _____ _____  ",
37	" |  ____|             |  _ \\ / ____|  __ \\ ",
38	" | |___ _ __ ___  ___ | |_) | (___ | |  | |",
39	" |  ___| '__/ _ \\/ _ \\|  _ < \\___ \\| |  | |",
40	" | |   | | |  __/  __/| |_) |____) | |__| |",
41	" | |   | | |    |    ||     |      |      |",
42	" |_|   |_|  \\___|\\___||____/|_____/|_____/ "
43};
44
45drawer.logo_position = {x = 46, y = 1};
46drawer.beastie_color = {
47	"               \027[31m,        ,",
48	"              /(        )`",
49	"              \\ \\___   / |",
50	"              /- \027[37m_\027[31m  `-/  '",
51	"             (\027[37m/\\/ \\\027[31m \\   /\\",
52	"             \027[37m/ /   |\027[31m `    \\",
53	"             \027[34mO O   \027[37m) \027[31m/    |",
54	"             \027[37m`-^--'\027[31m`<     '",
55	"            (_.)  _  )   /",
56	"             `.___/`    /",
57	"               `-----' /",
58	"  \027[33m<----.\027[31m     __ / __   \\",
59	"  \027[33m<----|====\027[31mO)))\027[33m==\027[31m) \\) /\027[33m====|",
60	"  \027[33m<----'\027[31m    `--' `.__,' \\",
61	"               |        |",
62	"                \\       /       /\\",
63	"           \027[36m______\027[31m( (_  / \\______/",
64	"         \027[36m,'  ,-----'   |",
65	"         `--{__________)\027[37m"
66};
67
68drawer.beastie = {
69	"               ,        ,",
70	"              /(        )`",
71	"              \\ \\___   / |",
72	"              /- _  `-/  '",
73	"             (/\\/ \\ \\   /\\",
74	"             / /   | `    \\",
75	"             O O   ) /    |",
76	"             `-^--'`<     '",
77	"            (_.)  _  )   /",
78	"             `.___/`    /",
79	"               `-----' /",
80	"  <----.     __ / __   \\",
81	"  <----|====O)))==) \\) /====|",
82	"  <----'    `--' `.__,' \\",
83	"               |        |",
84	"                \\       /       /\\",
85	"           ______( (_  / \\______/",
86	"         ,'  ,-----'   |",
87	"         `--{__________)"
88};
89
90drawer.fbsd_logo_shift = {x = 5, y = 4};
91drawer.fbsd_logo_v = {
92	"  ______",
93	" |  ____| __ ___  ___ ",
94	" | |__ | '__/ _ \\/ _ \\",
95	" |  __|| | |  __/  __/",
96	" | |   | | |    |    |",
97	" |_|   |_|  \\___|\\___|",
98	"  ____   _____ _____",
99	" |  _ \\ / ____|  __ \\",
100	" | |_) | (___ | |  | |",
101	" |  _ < \\___ \\| |  | |",
102	" | |_) |____) | |__| |",
103	" |     |      |      |",
104	" |____/|_____/|_____/"
105};
106
107drawer.orb_shift = {x = 2, y = 4};
108drawer.orb_color = {
109	"  \027[31m```                        \027[31;1m`\027[31m",
110	" s` `.....---...\027[31;1m....--.```   -/\027[31m",
111	" +o   .--`         \027[31;1m/y:`      +.\027[31m",
112	"  yo`:.            \027[31;1m:o      `+-\027[31m",
113	"   y/               \027[31;1m-/`   -o/\027[31m",
114	"  .-                  \027[31;1m::/sy+:.\027[31m",
115	"  /                     \027[31;1m`--  /\027[31m",
116	" `:                          \027[31;1m:`\027[31m",
117	" `:                          \027[31;1m:`\027[31m",
118	"  /                          \027[31;1m/\027[31m",
119	"  .-                        \027[31;1m-.\027[31m",
120	"   --                      \027[31;1m-.\027[31m",
121	"    `:`                  \027[31;1m`:`",
122	"      \027[31;1m.--             `--.",
123	"         .---.....----.\027[37m"
124};
125
126drawer.orb = {
127	"  ```                        `",
128	" s` `.....---.......--.```   -/",
129	" +o   .--`         /y:`      +.",
130	"  yo`:.            :o      `+-",
131	"   y/               -/`   -o/",
132	"  .-                  ::/sy+:.",
133	"  /                     `--  /",
134	" `:                          :`",
135	" `:                          :`",
136	"  /                          /",
137	"  .-                        -.",
138	"   --                      -.",
139	"    `:`                  `:`",
140	"      .--             `--.",
141	"         .---.....----."
142};
143
144drawer.none = {""};
145
146drawer.none_shift = {x = 17, y = 0};
147
148drawer.menu_position = {x = 6, y = 11};
149
150drawer.box_pos_dim = {x = 3, y = 10, w = 41, h = 11};
151
152function drawer.drawscreen(menu_opts)
153	-- drawlogo() must go first.
154	-- it determines the positions of other elements
155	drawer.drawlogo();
156        drawer.drawbrand();
157        drawer.drawbox();
158	return drawer.drawmenu(menu_opts);
159end
160
161function drawer.drawmenu(m)
162	x = drawer.menu_position.x;
163	y = drawer.menu_position.y;
164
165	-- print the menu and build the alias table
166	local alias_table = {};
167	local entry_num = 0;
168	for line_num, e in ipairs(m) do
169		if (e.entry_type ~= "separator") then
170			entry_num = entry_num + 1;
171			screen.setcursor(x, y + line_num);
172			print(entry_num .. ". "..e.name());
173
174			-- fill the alias table
175			alias_table[tostring(entry_num)] = e;
176			for n, a in ipairs(e.alias) do
177				alias_table[a] = e;
178			end
179		else
180			screen.setcursor(x, y + line_num);
181			print(e.name());
182		end
183	end
184	return alias_table;
185end
186
187
188function drawer.drawbox()
189	x = drawer.box_pos_dim.x;
190	y = drawer.box_pos_dim.y;
191	w = drawer.box_pos_dim.w;
192	h = drawer.box_pos_dim.h;
193
194	local hl = string.char(0xCD);
195	local vl = string.char(0xBA);
196
197	local tl = string.char(0xC9);
198	local bl = string.char(0xC8);
199	local tr = string.char(0xBB);
200	local br = string.char(0xBC);
201
202	screen.setcursor(x, y); print(tl);
203	screen.setcursor(x, y+h); print(bl);
204	screen.setcursor(x+w, y); print(tr);
205	screen.setcursor(x+w, y+h); print(br);
206
207	for i = 1, w-1 do
208		screen.setcursor(x+i, y);
209		print(hl);
210		screen.setcursor(x+i, y+h);
211		print(hl);
212	end
213
214	for i = 1, h-1 do
215		screen.setcursor(x, y+i);
216		print(vl);
217		screen.setcursor(x+w, y+i);
218		print(vl);
219	end
220
221	screen.setcursor(x+(w/2)-9, y);
222	print("Welcome to FreeBSD");
223end
224
225function drawer.draw(x, y, logo)
226	for i = 1, #logo do
227		screen.setcursor(x, y + i);
228		print(logo[i]);
229	end
230end
231
232function drawer.drawbrand()
233	local x = tonumber(loader.getenv("loader_brand_x"));
234	local y = tonumber(loader.getenv("loader_brand_y"));
235
236	if not x then
237		x = drawer.brand_position.x;
238	end
239	if not y then
240		y = drawer.brand_position.y;
241	end
242
243	local logo = load("return " .. tostring(loader.getenv("loader_brand")))();
244	if not logo then
245		logo = drawer.fbsd_logo;
246	end
247	drawer.draw(x, y, logo);
248end
249
250function drawer.drawlogo()
251	local x = tonumber(loader.getenv("loader_logo_x"));
252	local y = tonumber(loader.getenv("loader_logo_y"));
253
254	if not x then
255		x = drawer.logo_position.x;
256	end
257	if not y then
258		y = drawer.logo_position.y;
259	end
260
261	local logo = loader.getenv("loader_logo");
262	local s = {x = 0, y = 0};
263	local colored = color.isEnabled();
264
265	if logo == "beastie" then
266		if colored then
267			logo = drawer.beastie_color;
268		end
269	elseif logo == "beastiebw" then
270		logo = drawer.beastie;
271	elseif logo == "fbsdbw" then
272		logo = drawer.fbsd_logo_v;
273		s = drawer.fbsd_logo_shift;
274	elseif logo == "orb" then
275		if colored then
276			logo = drawer.orb_color;
277		end
278		s = drawer.orb_shift;
279	elseif logo == "orbbw" then
280		logo = drawer.orb;
281		s = drawer.orb_shift;
282	elseif logo == "tribute" then
283		logo = drawer.fbsd_logo;
284	elseif logo == "tributebw" then
285		logo = drawer.fbsd_logo;
286	elseif logo == "none" then
287		--centre brand and text if no logo
288		drawer.brand_position.x = drawer.brand_position.x + drawer.none_shift.x;
289		drawer.brand_position.y = drawer.brand_position.y + drawer.none_shift.y;
290		drawer.menu_position.x = drawer.menu_position.x + drawer.none_shift.x;
291		drawer.menu_position.y = drawer.menu_position.y + drawer.none_shift.y;
292		drawer.box_pos_dim.x = drawer.box_pos_dim.x + drawer.none_shift.x;
293		drawer.box_pos_dim.y = drawer.box_pos_dim.y + drawer.none_shift.y;
294		--prevent redraws from moving menu further
295		drawer.none_shift.x = 0;
296		drawer.none_shift.y = 0;
297		logo = drawer.none;
298	end
299	if not logo then
300		if colored then
301			logo = drawer.orb_color;
302		else
303			logo = drawer.orb;
304		end
305	end
306	drawer.draw(x + s.x, y + s.y, logo);
307end
308
309return drawer
310