ComputerCraft Archive

DropMenu

computer utility kepler155c github

Description

ComputerCraft OS

Installation

Copy one of these commands into your ComputerCraft terminal:

wget:wget https://raw.githubusercontent.com/kepler155c/opus/develop-1.8/sys/modules/opus/ui/components/DropMenu.lua dropmenu
Archive:wget https://cc.shobie.xyz/cc/get/gh-kepler155c-opus-sys-modules-opus-ui-components-dropmenu dropmenu
Quick Install: wget https://cc.shobie.xyz/cc/get/gh-kepler155c-opus-sys-modules-opus-ui-components-dropmenu DropMenu

Usage

Run: DropMenu

Tags

none

Source

View Original Source

Code Preview

local class = require('opus.class')
local UI    = require('opus.ui')
local Util  = require('opus.util')

UI.DropMenu = class(UI.MenuBar)
UI.DropMenu.defaults = {
	UIElement = 'DropMenu',
	backgroundColor = 'white',
	buttonClass = 'DropMenuItem',
}
function UI.DropMenu:layout()
	UI.MenuBar.layout(self)

	local maxWidth = 1
	for y,child in ipairs(self.children) do
		child.x = 1
		child.y = y
		if #(child.text or '') > maxWidth then
			maxWidth = #child.text
		end
	end
	for _,child in ipairs(self.children) do
		child.width = maxWidth + 2
		if child.spacer then
			child.inactive = true
			child.text = string.rep('-', child.width - 2)
		end
	end

	self.height = #self.children + 1
	self.width = maxWidth + 2

	if self.x + self.width > self.parent.width then
		self.x = self.parent.width - self.width + 1
	end

	self:reposition(self.x, self.y, self.width, self.height)
end

function UI.DropMenu:enable()
	local menuBar = self.parent:find(self.menuUid)
	local hasActive

	for _,c in pairs(self.children) do
		if not c.spacer and menuBar then
			c.inactive = not menuBar:getActive(c)
		end
		if not c.inactive then
			hasActive = true
		end
	end

	-- jump through a lot of hoops if all selections are inactive
	-- there's gotta be a better way
	-- lots of exception code just to handle drop menus
	self.focus = not hasActive and function() end

	UI.Window.enable(self)
	if self.focus then
		self:setFocus(self)
	else
		self:focusFirst()
	end
	self:draw()
end

function UI.DropMenu:disable()
	UI.Window.disable(self)
	self:remove()
end

function UI.DropMenu:eventHandler(event)
	if event.type == 'focus_lost' and self.enabled then
		if not (Util.contains(self.children, event.focused) or event.focused == self) then
			self:disable()
		end
	elseif event.type == 'mouse_out' and self.enabled then
		self:disable()
		self:setFocus(self.parent:find(self.lastFocus))
	else
		return UI.MenuBar.eventHandler(self, event)
	end
	return true
end

function UI.DropMenu.example()
	return UI.MenuBar {
		buttons = {
			{ text = 'File', dropdown = {
					{ text = 'Run',            event = 'run' },
					{ text = 'Shell        s', event = 'shell'  },
					{ spacer = true },
					{ text = 'Quit        ^q', event = 'quit'   },
			} },
			{ text = 'Edit', dropdown = {
				{ text = 'Copy',           event = 'run' },
				{ text = 'Paste        s', event = 'shell'  },
			} },
			{ text = '\187',
				x = -3,
				dropdown = {
					{ text = 'Associations', event = 'associate' },
			} },
		}
	}
end