Skip to content

Instantly share code, notes, and snippets.

@PLyczkowski
Created February 18, 2018 21:46
Show Gist options
  • Select an option

  • Save PLyczkowski/f86d29595105ed0d3b64bde45802e586 to your computer and use it in GitHub Desktop.

Select an option

Save PLyczkowski/f86d29595105ed0d3b64bde45802e586 to your computer and use it in GitHub Desktop.
A command line with autocomplete. Drop on LineEdit, run setup and it's good to go. Will emit command_fired signal.
extends LineEdit
signal command_fired(command) # Command is a string
var command_list
var found_commands
# Display
var panel_container
var v_box_container
var highlight
var highlight_position
var labels
# Settings
const max_visible_commands = 10
func setup(command_list): # Accepts an array of strings
command_list.sort()
self.command_list = command_list
found_commands = []
labels = []
self.connect("text_changed", self, "on_text_changed")
self.connect("focus_exited", self, "on_focus_exited")
# GUI
self.caret_blink = true
panel_container = PanelContainer.new()
panel_container.hide()
panel_container.set_anchors_and_margins_preset(PRESET_TOP_WIDE)
panel_container.margin_top = 23
add_child(panel_container)
v_box_container = VBoxContainer.new()
panel_container.add_child(v_box_container)
highlight = Panel.new()
highlight.show_behind_parent = true
func _input(event):
if self.has_focus() and self.visible and event.is_action("ui_down") and not event.is_echo() and event.is_pressed():
move_highlight(1)
accept_event()
if self.has_focus() and self.visible and event.is_action("ui_up") and not event.is_echo() and event.is_pressed():
move_highlight(-1)
accept_event()
if self.has_focus() and self.visible and event.is_action("ui_accept") and not event.is_echo() and event.is_pressed():
fire_command()
accept_event()
if self.has_focus() and self.visible and event.is_action("ui_cancel") and not event.is_echo() and event.is_pressed():
release_focus()
func on_text_changed(text):
found_commands = []
if text.length() > 0:
for command in command_list:
if command.match("*"+text+"*"):
found_commands.append(command)
if found_commands.size() == max_visible_commands:
break
display_commands(found_commands)
func on_focus_exited():
clear()
func display_commands(commands):
clear_labels()
if commands.size() > 0:
panel_container.show()
else:
panel_container.hide()
for command in found_commands:
var label = Label.new()
label.text = command
v_box_container.add_child(label)
labels.append(label)
panel_container.set_size( Vector2( panel_container.rect_size.x, panel_container.get_minimum_size().y) )
set_highlight(0)
func clear():
text = ""
func clear_labels():
for label in labels:
label.get_parent().remove_child(label)
labels = []
func set_highlight(position):
if labels.size() >= position + 1:
if highlight.get_parent():
highlight.get_parent().remove_child(highlight)
labels[position].add_child(highlight)
highlight.set_anchors_and_margins_preset(PRESET_WIDE)
highlight_position = position
func move_highlight(amount):
var new_position = highlight_position + amount
if new_position >= 0 and new_position <= labels.size() -1:
set_highlight(new_position)
func fire_command():
emit_signal("command_fired", labels[highlight_position].text)
clear()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment