Refactored a lot of stuff.
Added property lists. Renamed FileAdapter to FileSystemAdapter. And more smaller stuff.
This commit is contained in:
@@ -4,19 +4,51 @@ extends Container
|
||||
class_name UIB_DynamicGridContainer
|
||||
|
||||
var __DEFAULT_CONSTRAINTS = UIB_DynamicGridConstraints.new()
|
||||
const __META_CONSTRAINTS = "__uib_dynamic_grind_constraints__"
|
||||
|
||||
export(int, 1, 100) var columns := 1 setget _set_columns
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _notification(what):
|
||||
if what == NOTIFICATION_SORT_CHILDREN:
|
||||
__sort_children()
|
||||
|
||||
func __get_constraints(node : Node) -> UIB_DynamicGridConstraints:
|
||||
################
|
||||
# overridables #
|
||||
################
|
||||
func _get_constraints(node : Node) -> UIB_DynamicGridConstraints:
|
||||
var constraints := get_existing_constraints(node)
|
||||
return constraints if constraints else __DEFAULT_CONSTRAINTS
|
||||
|
||||
################
|
||||
# public stuff #
|
||||
################
|
||||
static func get_existing_constraints(node : Node) -> UIB_DynamicGridConstraints:
|
||||
if node.has_meta(__META_CONSTRAINTS):
|
||||
return node.get_meta(__META_CONSTRAINTS).object
|
||||
|
||||
for child in node.get_children():
|
||||
if child is UIB_DynamicGridConstraints:
|
||||
return child
|
||||
return __DEFAULT_CONSTRAINTS
|
||||
return null
|
||||
|
||||
static func get_constraints(node : Node) -> UIB_DynamicGridConstraints:
|
||||
var constraints := get_existing_constraints(node)
|
||||
if constraints != null:
|
||||
return constraints
|
||||
|
||||
if !node.has_meta(__META_CONSTRAINTS):
|
||||
var wrapper := GDB_ReferenceWrapper.new()
|
||||
wrapper.object = UIB_DynamicGridConstraints.new()
|
||||
node.set_meta(__META_CONSTRAINTS, wrapper)
|
||||
|
||||
return node.get_meta(__META_CONSTRAINTS).object
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __sort_children():
|
||||
var column_widths := []
|
||||
var column_expand := []
|
||||
@@ -32,7 +64,7 @@ func __sort_children():
|
||||
for child in get_children():
|
||||
if !child is Control || !child.visible:
|
||||
continue
|
||||
var constraints := __get_constraints(child)
|
||||
var constraints := _get_constraints(child)
|
||||
|
||||
if col + constraints.colspan > columns:
|
||||
col = 0
|
||||
@@ -67,7 +99,7 @@ func __sort_children():
|
||||
var row_height := 0.0
|
||||
col = 0
|
||||
for child in row:
|
||||
var constraints := __get_constraints(child)
|
||||
var constraints := _get_constraints(child)
|
||||
child.rect_position = pos
|
||||
|
||||
var width := 0.0
|
||||
@@ -88,7 +120,10 @@ func __sort_children():
|
||||
pos.y += row_height
|
||||
pos.x = 0.0
|
||||
rect_min_size.y = pos.y
|
||||
|
||||
|
||||
###########
|
||||
# setters #
|
||||
###########
|
||||
func _set_columns(value : int):
|
||||
if value != columns:
|
||||
columns = value
|
||||
|
||||
116
scripts/types/controls/entity_tree.gd
Normal file
116
scripts/types/controls/entity_tree.gd
Normal file
@@ -0,0 +1,116 @@
|
||||
extends Tree
|
||||
|
||||
class_name UIB_EntityTree
|
||||
|
||||
export(Array, String) var column_ids := [].duplicate()
|
||||
export(Array, String) var column_titles := [].duplicate()
|
||||
export(NodePath) var selected_entity_adapter := ""
|
||||
|
||||
onready var __selected_entity_adapter := get_node_or_null(selected_entity_adapter) as GDB_DataAdapter
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _ready():
|
||||
create_item() # invisible root
|
||||
hide_root = true
|
||||
columns = column_ids.size()
|
||||
select_mode = SELECT_ROW
|
||||
set_column_titles_visible(true)
|
||||
|
||||
for col in range(min(columns, column_titles.size())):
|
||||
set_column_title(col, column_titles[col])
|
||||
|
||||
connect("item_selected", self, "_on_item_selected")
|
||||
if __selected_entity_adapter != null:
|
||||
__selected_entity_adapter.connect("data_changed", self, "_on_selected_entity_adapter_data_changed")
|
||||
|
||||
################
|
||||
# public stuff #
|
||||
################
|
||||
func add_entity(entity : Object) -> void:
|
||||
if !GDB_Entity.is_valid_entity(entity):
|
||||
printerr("UIB_EntityTree: attempted to add invalid entity")
|
||||
return
|
||||
|
||||
var itm := create_item()
|
||||
itm.set_metadata(0, entity)
|
||||
var col := 0
|
||||
for id in column_ids:
|
||||
var prop : Object = entity.get_property_by_id(id)
|
||||
|
||||
if prop == null:
|
||||
col += 1
|
||||
continue
|
||||
|
||||
itm.set_text(col, GDB_Property.get_prop_value_as_string(prop))
|
||||
col += 1
|
||||
|
||||
GDBUtility.try_connect(prop, "value_changed", self, "_on_property_value_changed", [entity, id])
|
||||
|
||||
func select_entity(entity : Object) -> void:
|
||||
if entity == null:
|
||||
return # TODO: unselect?
|
||||
var itm := __item_from_entity(entity)
|
||||
if itm == null:
|
||||
return # TODO: unselect?
|
||||
itm.select(0)
|
||||
|
||||
func get_selected_entity() -> Object:
|
||||
var entities := get_selected_entities()
|
||||
if !entities.empty():
|
||||
return entities[0]
|
||||
return null
|
||||
|
||||
func get_selected_entities() -> Array: # n/a yet
|
||||
var entities := []
|
||||
var itm := get_selected()
|
||||
|
||||
while itm != null:
|
||||
var entity_ := __entity_from_item(itm)
|
||||
if entity_ != null:
|
||||
entities.append(entity_)
|
||||
itm = get_next_selected(itm)
|
||||
return entities
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __entity_from_item(itm : TreeItem) -> Object:
|
||||
return itm.get_metadata(0) as Object
|
||||
|
||||
func __item_from_entity(entity : Object) -> TreeItem:
|
||||
return GDBUIUtility.find_tree_item_with_meta(get_root(), entity)
|
||||
|
||||
func __update_row(entity : Object, column := ""):
|
||||
if column == "":
|
||||
for col in column_ids:
|
||||
if col != "":
|
||||
__update_row(entity, col)
|
||||
return
|
||||
|
||||
var itm := __item_from_entity(entity)
|
||||
var col_idx := column_ids.find(column)
|
||||
|
||||
if itm == null || col_idx < 0:
|
||||
return
|
||||
|
||||
var prop := entity.get_property_by_id(column) as Object
|
||||
if prop == null:
|
||||
return
|
||||
|
||||
itm.set_text(col_idx, GDB_Property.get_prop_value_as_string(prop))
|
||||
|
||||
############
|
||||
# handlers #
|
||||
############
|
||||
func _on_item_selected() -> void:
|
||||
if __selected_entity_adapter != null:
|
||||
__selected_entity_adapter.data = get_selected_entity()
|
||||
|
||||
func _on_selected_entity_adapter_data_changed() -> void:
|
||||
if __selected_entity_adapter.data != get_selected_entity():
|
||||
select_entity(__selected_entity_adapter.data)
|
||||
|
||||
func _on_property_value_changed(entity : Object, property_id : String) -> void:
|
||||
__update_row(entity, property_id)
|
||||
@@ -46,7 +46,9 @@ class DetailsColumnType:
|
||||
func _get_name() -> String:
|
||||
return tr("Type")
|
||||
func _get_value(entry) -> String:
|
||||
if entry._is_folder():
|
||||
if entry._is_link():
|
||||
return tr("Link")
|
||||
elif entry._is_folder():
|
||||
return tr("Folder")
|
||||
else:
|
||||
return tr("File")
|
||||
@@ -82,7 +84,7 @@ class DetailsColumnModifiedTime:
|
||||
return entry0._get_modified_time() < entry1._get_modified_time()
|
||||
|
||||
class __ParentFolderEntry:
|
||||
extends UIB_FileAdapter.FileEntry
|
||||
extends UIB_FilesystemAdapter.FileEntry
|
||||
|
||||
var real_entry
|
||||
|
||||
@@ -99,11 +101,12 @@ const CHECKBOX_COLUMN_WIDTH = 25
|
||||
|
||||
export(ViewMode) var view_mode = ViewMode.DETAILS setget _set_view_mode
|
||||
export(Checkable) var checkable = Checkable.NONE setget _set_checkable
|
||||
export(NodePath) var folder_adapter := ""
|
||||
export var allow_navigation := true
|
||||
export var show_up_entry := true
|
||||
var adapter : UIB_FileAdapter setget _set_adapter
|
||||
var adapter : UIB_FilesystemAdapter setget _set_adapter
|
||||
var filter : UIB_FileFilter setget _set_filter
|
||||
var current_folder : UIB_FileAdapter.FileEntry setget _set_current_folder
|
||||
var current_folder : UIB_FilesystemAdapter.FileEntry setget _set_current_folder
|
||||
var details_columns := [
|
||||
DetailsColumnName.new(),
|
||||
DetailsColumnType.new(),
|
||||
@@ -113,13 +116,14 @@ var details_columns := [
|
||||
var __special_columns := []
|
||||
var __sort_column := 0
|
||||
var __sort_reverse := false
|
||||
onready var __folder_adapter := get_node_or_null(folder_adapter) as GDB_DataAdapter
|
||||
|
||||
func _ready():
|
||||
hide_root = true
|
||||
select_mode = Tree.SELECT_ROW
|
||||
|
||||
if adapter == null:
|
||||
adapter = UIB_LocalFileAdapter.new()
|
||||
adapter = UIB_LocalFilesystemAdapter.new()
|
||||
|
||||
if current_folder == null:
|
||||
current_folder = adapter._get_root()
|
||||
@@ -129,6 +133,13 @@ func _ready():
|
||||
connect("item_activated", self, "_on_item_activated")
|
||||
connect("item_selected", self, "_on_item_selected")
|
||||
connect("column_title_pressed", self, "_on_column_title_pressed")
|
||||
|
||||
if __folder_adapter != null:
|
||||
__folder_adapter.connect("data_changed", self, "_on_folder_adapter_data_changed")
|
||||
if __folder_adapter.data:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
else:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
@@ -213,7 +224,7 @@ func _set_view_mode(value):
|
||||
view_mode = value
|
||||
__update_entries()
|
||||
|
||||
func _set_adapter(value : UIB_FileAdapter):
|
||||
func _set_adapter(value : UIB_FilesystemAdapter):
|
||||
if value != adapter:
|
||||
adapter = value
|
||||
__update_entries()
|
||||
@@ -223,11 +234,13 @@ func _set_filter(value : UIB_FileFilter):
|
||||
filter = value
|
||||
__update_entries()
|
||||
|
||||
func _set_current_folder(value : UIB_FileAdapter.FileEntry):
|
||||
func _set_current_folder(value : UIB_FilesystemAdapter.FileEntry):
|
||||
if value != current_folder:
|
||||
current_folder = value
|
||||
emit_signal("current_folder_changed")
|
||||
__update_entries()
|
||||
if __folder_adapter != null:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
func _set_checkable(value):
|
||||
if value != checkable:
|
||||
@@ -272,6 +285,9 @@ func _on_column_title_pressed(idx : int):
|
||||
__sort_reverse = false
|
||||
__update_entries()
|
||||
|
||||
func _on_folder_adapter_data_changed() -> void:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
|
||||
###########
|
||||
# signals #
|
||||
###########
|
||||
|
||||
81
scripts/types/controls/folder_default_button.gd
Normal file
81
scripts/types/controls/folder_default_button.gd
Normal file
@@ -0,0 +1,81 @@
|
||||
extends ToolButton
|
||||
|
||||
class_name UIB_FolderDefaultButton
|
||||
|
||||
enum Type {
|
||||
FOLDER_UP,
|
||||
FAVOURITE
|
||||
}
|
||||
|
||||
export(Type) var type := Type.FAVOURITE
|
||||
export(NodePath) var folder_adapter := ""
|
||||
export(Texture) var icon_active : Texture = null
|
||||
|
||||
var current_folder : UIB_FilesystemAdapter.FileEntry = null
|
||||
|
||||
onready var __folder_adapter := get_node_or_null(folder_adapter) as GDB_DataAdapter
|
||||
onready var __icon_inactive = icon
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _ready() -> void:
|
||||
if __folder_adapter == null:
|
||||
printerr("This UIB_FolderDefaultButton is missing a folder_adapter, it will do nothing.")
|
||||
disabled = true
|
||||
return
|
||||
|
||||
if __folder_adapter.data:
|
||||
__set_current_folder(__folder_adapter.data)
|
||||
|
||||
__update_disabled()
|
||||
|
||||
__folder_adapter.connect("data_changed", self, "_on_folder_adapter_data_changed")
|
||||
GDBUX.connect_static("favourite_places_changed", self, "_on_favourite_places_changed")
|
||||
|
||||
func _pressed() -> void:
|
||||
match type:
|
||||
Type.FOLDER_UP:
|
||||
__set_current_folder(current_folder._get_parent())
|
||||
Type.FAVOURITE:
|
||||
if GDBUX.is_favourite_place(current_folder):
|
||||
GDBUX.remove_favourite_place(current_folder)
|
||||
else:
|
||||
GDBUX.add_favourite_place(current_folder)
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __set_current_folder(value : UIB_FilesystemAdapter.FileEntry) -> void:
|
||||
if value != current_folder:
|
||||
current_folder = value
|
||||
__folder_adapter.data = current_folder
|
||||
__update_disabled()
|
||||
__update_icon()
|
||||
|
||||
func __update_disabled() -> void:
|
||||
if current_folder == null:
|
||||
disabled = true
|
||||
return
|
||||
|
||||
match type:
|
||||
Type.FOLDER_UP:
|
||||
disabled = (current_folder._get_parent() == null)
|
||||
Type.FAVOURITE:
|
||||
disabled = false
|
||||
|
||||
func __update_icon():
|
||||
if type == Type.FAVOURITE:
|
||||
if GDBUX.is_favourite_place(current_folder):
|
||||
icon = icon_active
|
||||
else:
|
||||
icon = __icon_inactive
|
||||
|
||||
############
|
||||
# handlers #
|
||||
############
|
||||
func _on_folder_adapter_data_changed() -> void:
|
||||
__set_current_folder(__folder_adapter.data)
|
||||
|
||||
func _on_favourite_places_changed() -> void:
|
||||
__update_icon()
|
||||
@@ -2,9 +2,13 @@ extends LineEdit
|
||||
|
||||
class_name UIB_FolderEdit
|
||||
|
||||
export(NodePath) var folder_adapter := ""
|
||||
|
||||
var suggestion_popup := UIB_SuggestionPopup.new()
|
||||
var adapter : UIB_FileAdapter
|
||||
var current_folder : UIB_FileAdapter.FileEntry setget _set_current_folder
|
||||
var adapter : UIB_FilesystemAdapter
|
||||
var current_folder : UIB_FilesystemAdapter.FileEntry setget _set_current_folder
|
||||
|
||||
onready var __folder_adapter := get_node_or_null(folder_adapter) as GDB_DataAdapter
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
@@ -13,6 +17,16 @@ func _ready():
|
||||
call_deferred("__setup")
|
||||
connect("text_changed", self, "_on_text_changed")
|
||||
connect("text_entered", self, "_on_text_entered")
|
||||
|
||||
if adapter == null:
|
||||
adapter = UIB_LocalFilesystemAdapter.new()
|
||||
|
||||
if __folder_adapter:
|
||||
__folder_adapter.connect("data_changed", self, "_on_folder_adapter_data_changed")
|
||||
if __folder_adapter.data:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
else:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
@@ -59,6 +73,8 @@ func _set_current_folder(value):
|
||||
current_folder = value
|
||||
text = current_folder._get_path()
|
||||
emit_signal("current_folder_changed")
|
||||
if __folder_adapter != null:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
############
|
||||
# handlers #
|
||||
@@ -73,6 +89,9 @@ func _on_suggestion_accepted(suggestion):
|
||||
__update_current_folder()
|
||||
__update_suggestions()
|
||||
|
||||
func _on_folder_adapter_data_changed() -> void:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
|
||||
###########
|
||||
# signals #
|
||||
###########
|
||||
|
||||
@@ -13,9 +13,9 @@ export(DefaultFolder) var default_folder = DefaultFolder.HOME
|
||||
export(NodePath) var folder_up_action
|
||||
export(NodePath) var folder_favourite_action
|
||||
export var custom_default_folder := ""
|
||||
var adapter : UIB_FileAdapter = UIB_LocalFileAdapter.new()
|
||||
var adapter : UIB_FilesystemAdapter = UIB_LocalFilesystemAdapter.new()
|
||||
|
||||
var current_folder : UIB_FileAdapter.FileEntry setget set_current_folder
|
||||
var current_folder : UIB_FilesystemAdapter.FileEntry setget set_current_folder
|
||||
var __folder_up_action : UIB_SimpleAction
|
||||
var __folder_favourite_action : UIB_SimpleAction
|
||||
var __nodes := []
|
||||
|
||||
@@ -18,17 +18,16 @@ class __DefaultItem:
|
||||
icon = icon_
|
||||
label = label_
|
||||
|
||||
var __DEFAULT_ITEMS := [
|
||||
__DefaultItem.new(GDBFsUtil.get_home_folder(), preload("res://addons/de.mewin.gduibasics/images/home32.svg"), tr("Home"))
|
||||
]
|
||||
|
||||
export(Mode) var mode = Mode.DEFAULT setget _set_mode
|
||||
export(Array, String) var places := [] setget _set_places
|
||||
export(Array, Texture) var icons := []
|
||||
export(Array, String) var names := []
|
||||
export(NodePath) var folder_adapter := ""
|
||||
|
||||
var adapter : UIB_FileAdapter
|
||||
var current_folder : UIB_FileAdapter.FileEntry setget _set_current_folder
|
||||
var adapter : UIB_FilesystemAdapter
|
||||
var current_folder : UIB_FilesystemAdapter.FileEntry setget _set_current_folder
|
||||
|
||||
onready var __folder_adapter := get_node_or_null(folder_adapter) as GDB_DataAdapter
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
@@ -36,6 +35,16 @@ var current_folder : UIB_FileAdapter.FileEntry setget _set_current_folder
|
||||
func _ready():
|
||||
call_deferred("__update_items")
|
||||
|
||||
if adapter == null:
|
||||
adapter = UIB_LocalFilesystemAdapter.new()
|
||||
|
||||
if __folder_adapter:
|
||||
__folder_adapter.connect("data_changed", self, "_on_folder_adapter_data_changed")
|
||||
if __folder_adapter.data:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
else:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
connect("item_activated", self, "_on_item_activated")
|
||||
GDBUX.connect_static("favourite_places_changed", self, "_on_favourite_places_changed")
|
||||
|
||||
@@ -44,8 +53,6 @@ func _ready():
|
||||
#################
|
||||
func __update_items():
|
||||
clear()
|
||||
if !adapter:
|
||||
return
|
||||
|
||||
match mode:
|
||||
Mode.DEFAULT:
|
||||
@@ -54,7 +61,7 @@ func __update_items():
|
||||
__add_custom_places()
|
||||
|
||||
func __add_default_places():
|
||||
for default_place in __DEFAULT_ITEMS:
|
||||
for default_place in __get_default_places():
|
||||
var folder := adapter._get_file(default_place.place)
|
||||
if !folder || !folder._is_folder():
|
||||
continue
|
||||
@@ -75,7 +82,7 @@ func __add_custom_places():
|
||||
var icon : Texture = icons[i] if i < icons.size() else null
|
||||
__add_place(folder, icon, label)
|
||||
|
||||
func __add_place(folder : UIB_FileAdapter.FileEntry, icon : Texture, label := ""):
|
||||
func __add_place(folder : UIB_FilesystemAdapter.FileEntry, icon : Texture, label := ""):
|
||||
if !icon:
|
||||
icon = preload("res://addons/de.mewin.gduibasics/images/folder32.svg")
|
||||
if !label:
|
||||
@@ -89,6 +96,14 @@ func __select_current_folder():
|
||||
if get_item_metadata(i)._get_path() == current_folder._get_path():
|
||||
select(i)
|
||||
|
||||
func __get_default_places() -> Array:
|
||||
var places := [
|
||||
__DefaultItem.new(GDBFsUtil.get_home_folder(), preload("res://addons/de.mewin.gduibasics/images/home32.svg"), tr("Home"))
|
||||
]
|
||||
for special_folder in GDBFsUtil.get_special_folders():
|
||||
places.append(__DefaultItem.new(special_folder.path, preload("res://addons/de.mewin.gduibasics/images/folder32.svg"), special_folder.name))
|
||||
return places
|
||||
|
||||
###########
|
||||
# setters #
|
||||
###########
|
||||
@@ -106,6 +121,8 @@ func _set_current_folder(value):
|
||||
if value != current_folder:
|
||||
current_folder = value
|
||||
emit_signal("current_folder_changed")
|
||||
if __folder_adapter:
|
||||
__folder_adapter.data = current_folder
|
||||
|
||||
############
|
||||
# handlers #
|
||||
@@ -116,6 +133,10 @@ func _on_item_activated(idx):
|
||||
func _on_favourite_places_changed():
|
||||
if mode == Mode.DEFAULT:
|
||||
__update_items()
|
||||
|
||||
func _on_folder_adapter_data_changed() -> void:
|
||||
_set_current_folder(__folder_adapter.data)
|
||||
|
||||
###########
|
||||
# signals #
|
||||
###########
|
||||
|
||||
51
scripts/types/controls/property_check_box.gd
Normal file
51
scripts/types/controls/property_check_box.gd
Normal file
@@ -0,0 +1,51 @@
|
||||
extends CheckBox
|
||||
|
||||
class_name UIB_PropertyCheckBox
|
||||
|
||||
var property : Object = null setget _set_property
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _pressed() -> void:
|
||||
if property == null:
|
||||
return
|
||||
property.set_value(pressed)
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __init_property() -> void:
|
||||
text = __text_from_property()
|
||||
pressed = property.get_value() if property != null else false
|
||||
disabled = (property == null)
|
||||
|
||||
if property != null:
|
||||
GDBUtility.try_connect(property, "value_changed", self, "_on_property_value_changed")
|
||||
|
||||
func __text_from_property() -> String:
|
||||
if property == null:
|
||||
return ""
|
||||
return property.get_name()
|
||||
|
||||
###########
|
||||
# setters #
|
||||
###########
|
||||
func _set_property(property_ : Object) -> void:
|
||||
if property_ != null && (!GDB_Property.is_valid_property(property_) || property_.get_type() != TYPE_BOOL):
|
||||
printerr("Attempting to set invalid property in UIB_PropertyCheckBox.")
|
||||
return
|
||||
|
||||
if property_ != property:
|
||||
if property:
|
||||
GDBUtility.disconnect_all(property, self)
|
||||
property = property_
|
||||
__init_property()
|
||||
|
||||
############
|
||||
# handlers #
|
||||
############
|
||||
func _on_property_value_changed() -> void:
|
||||
var value = property.get_value()
|
||||
if value != pressed:
|
||||
pressed = value
|
||||
169
scripts/types/controls/property_list.gd
Normal file
169
scripts/types/controls/property_list.gd
Normal file
@@ -0,0 +1,169 @@
|
||||
extends UIB_DynamicGridContainer
|
||||
|
||||
class_name UIB_PropertyList
|
||||
|
||||
export(NodePath) var entity_adapter := ""
|
||||
|
||||
var entity : Object = null setget _set_entity
|
||||
var _properties := [].duplicate()
|
||||
var __controls_per_property := [].duplicate()
|
||||
onready var __entity_adapter := get_node_or_null(entity_adapter) as GDB_DataAdapter
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _ready() -> void:
|
||||
self.columns = 2
|
||||
|
||||
if __entity_adapter != null:
|
||||
__entity_adapter.connect("data_changed", self, "_on_entity_adapter_data_changed")
|
||||
|
||||
################
|
||||
# overridables #
|
||||
################
|
||||
func _make_controls(property : Object) -> Array:
|
||||
match property.get_type():
|
||||
GDB_Property.TYPE_HEADER:
|
||||
return _make_header(property)
|
||||
TYPE_INT, TYPE_REAL, TYPE_STRING:
|
||||
return _make_controls_simple(property)
|
||||
TYPE_BOOL:
|
||||
return _make_controls_bool(property)
|
||||
_:
|
||||
return []
|
||||
|
||||
func _make_header(property : Object) -> Array:
|
||||
assert(property.get_type() == GDB_Property.TYPE_HEADER)
|
||||
var header := preload("res://addons/de.mewin.gduibasics/scenes/property_list/header.tscn").instance()
|
||||
header.label = property.get_name()
|
||||
header.texture = GDB_Property.get_prop_icon(property)
|
||||
get_constraints(header).colspan = self.columns
|
||||
return [header]
|
||||
|
||||
func _make_controls_simple(property : Object) -> Array:
|
||||
var label := preload("res://addons/de.mewin.gduibasics/scenes/property_list/property_label.tscn").instance()
|
||||
label.label = property.get_name()
|
||||
label.texture = GDB_Property.get_prop_icon(property)
|
||||
|
||||
var edit := UIB_SimplePropertyEdit.new()
|
||||
edit.property = property
|
||||
edit.size_flags_horizontal |= SIZE_EXPAND
|
||||
|
||||
return [
|
||||
label, edit
|
||||
]
|
||||
|
||||
func _make_controls_bool(property : Object) -> Array:
|
||||
var checkbox := UIB_PropertyCheckBox.new()
|
||||
checkbox.property = property
|
||||
checkbox.size_flags_horizontal |= SIZE_EXPAND
|
||||
get_constraints(checkbox).colspan = self.columns
|
||||
return [
|
||||
checkbox
|
||||
]
|
||||
|
||||
################
|
||||
# public stuff #
|
||||
################
|
||||
func add_property(property : Object, insert_before := -1) -> void: # no type to allow ducktyping
|
||||
if find_property(property) >= 0:
|
||||
return
|
||||
if !GDB_Property.is_valid_property(property):
|
||||
printerr("Attempting to add invalid property object to property list: ", property)
|
||||
return
|
||||
|
||||
var control_insert_index := -1
|
||||
var insert_index : int
|
||||
|
||||
if insert_before < 0:
|
||||
insert_index = _properties.size()
|
||||
else:
|
||||
insert_index = min(insert_index, _properties.size())
|
||||
control_insert_index = __find_control_index_before(insert_index)
|
||||
_properties.insert(insert_index, property)
|
||||
|
||||
# create controls
|
||||
var controls := _make_controls(property)
|
||||
__controls_per_property.insert(insert_index, controls)
|
||||
|
||||
for control in controls:
|
||||
add_child(control)
|
||||
|
||||
if control_insert_index >= 0:
|
||||
for control in controls:
|
||||
move_child(control, control_insert_index)
|
||||
control_insert_index += 1
|
||||
|
||||
emit_signal("property_added", insert_index)
|
||||
|
||||
func remove_property(property : Object) -> bool:
|
||||
var index := find_property(property)
|
||||
if index < 0:
|
||||
return false
|
||||
|
||||
# remove actual property
|
||||
GDBUtility.disconnect_all(property, self)
|
||||
_properties.remove(index)
|
||||
|
||||
# remove controls
|
||||
for control in __controls_per_property[index]:
|
||||
control.queue_free()
|
||||
__controls_per_property.remove(index)
|
||||
|
||||
emit_signal("property_removed", property)
|
||||
return true
|
||||
|
||||
func find_property(property : Object) -> int:
|
||||
return _properties.find(property)
|
||||
|
||||
func clear_properties() -> void:
|
||||
_properties.clear()
|
||||
__controls_per_property.clear()
|
||||
|
||||
for child in get_children():
|
||||
child.queue_free()
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __find_control_index_before(index : int) -> int:
|
||||
if index >= __controls_per_property.size():
|
||||
return -1
|
||||
var controls : Array = __controls_per_property[index]
|
||||
if controls.empty():
|
||||
return __find_control_index_before(index + 1)
|
||||
return controls[0].get_position_in_parent()
|
||||
|
||||
func __init_entity() -> void:
|
||||
clear_properties()
|
||||
if entity == null:
|
||||
return
|
||||
|
||||
for property in entity.get_properties():
|
||||
add_property(property)
|
||||
|
||||
###########
|
||||
# setters #
|
||||
###########
|
||||
func _set_entity(entity_ : Object) -> void:
|
||||
if entity_ != null && !GDB_Entity.is_valid_entity(entity_):
|
||||
printerr("Attempting to set invalid entity in UIB_PropertyList.")
|
||||
return
|
||||
|
||||
if entity_ != entity:
|
||||
entity = entity_
|
||||
if __entity_adapter != null:
|
||||
__entity_adapter.data = entity
|
||||
__init_entity()
|
||||
|
||||
############
|
||||
# handlers #
|
||||
############
|
||||
func _on_entity_adapter_data_changed() -> void:
|
||||
_set_entity(__entity_adapter.data)
|
||||
|
||||
###########
|
||||
# signals #
|
||||
###########
|
||||
signal property_added(index)
|
||||
signal property_removed(index)
|
||||
@@ -6,6 +6,7 @@ class_name UIB_RecentPlacesList
|
||||
# overrides #
|
||||
#############
|
||||
func _ready():
|
||||
mode = Mode.CUSTOM
|
||||
places = GDBSettings.get_value(GDBConstants.SETTING_RECENT_PLACES, [])
|
||||
|
||||
GDBSettings.connect_static("setting_changed", self, "_on_setting_changed")
|
||||
|
||||
102
scripts/types/controls/simple_property_edit.gd
Normal file
102
scripts/types/controls/simple_property_edit.gd
Normal file
@@ -0,0 +1,102 @@
|
||||
extends LineEdit
|
||||
|
||||
class_name UIB_SimplePropertyEdit
|
||||
|
||||
var property : Object = null setget _set_property
|
||||
|
||||
var __caret_pos := 0
|
||||
var __last_valid_text := ""
|
||||
|
||||
#############
|
||||
# overrides #
|
||||
#############
|
||||
func _ready() -> void:
|
||||
connect("text_changed", self, "_on_text_changed")
|
||||
|
||||
func _gui_input(event : InputEvent) -> void:
|
||||
__caret_pos = caret_position
|
||||
|
||||
#################
|
||||
# private stuff #
|
||||
#################
|
||||
func __init_property() -> void:
|
||||
text = __text_from_property()
|
||||
editable = (property != null)
|
||||
__validate_text()
|
||||
|
||||
if property != null:
|
||||
GDBUtility.try_connect(property, "value_changed", self, "_on_property_value_changed")
|
||||
|
||||
func __text_from_property() -> String:
|
||||
if property == null:
|
||||
return ""
|
||||
match property.get_type():
|
||||
TYPE_INT, TYPE_REAL:
|
||||
return str(property.get_value())
|
||||
TYPE_STRING:
|
||||
return property.get_value()
|
||||
_:
|
||||
printerr("UIB_SimplePropertyEdit: unsupported property type: %s" % GDBUtility.type_name(property.get_type()))
|
||||
return ""
|
||||
|
||||
func __text_to_property() -> bool:
|
||||
if property == null:
|
||||
return false
|
||||
var value
|
||||
match property.get_type():
|
||||
TYPE_INT:
|
||||
value = int(text)
|
||||
TYPE_REAL:
|
||||
value = float(text)
|
||||
TYPE_STRING:
|
||||
value = text
|
||||
_:
|
||||
printerr("UIB_SimplePropertyEdit: unsupported property type: %s" % GDBUtility.type_name(property.get_type()))
|
||||
return false
|
||||
if !GDB_Property.is_prop_value_valid(property, value):
|
||||
return false
|
||||
property.set_value(value)
|
||||
return true
|
||||
|
||||
func __is_text_valid() -> bool:
|
||||
if property == null:
|
||||
return false
|
||||
match property.get_type():
|
||||
TYPE_INT:
|
||||
return text == "" || text.is_valid_integer()
|
||||
TYPE_REAL:
|
||||
return text == "" || text.is_valid_float()
|
||||
return true
|
||||
|
||||
func __validate_text() -> void:
|
||||
if !__is_text_valid() || !__text_to_property():
|
||||
# var old_caret := caret_position
|
||||
text = __last_valid_text
|
||||
caret_position = __caret_pos
|
||||
else:
|
||||
__last_valid_text = text
|
||||
|
||||
###########
|
||||
# setters #
|
||||
###########
|
||||
func _set_property(property_ : Object) -> void:
|
||||
if property_ != null && !GDB_Property.is_valid_property(property_):
|
||||
printerr("Attempting to set invalid property in UIB_SimplePropertyEdit.")
|
||||
return
|
||||
|
||||
if property_ != property:
|
||||
if property:
|
||||
GDBUtility.disconnect_all(property, self)
|
||||
property = property_
|
||||
__init_property()
|
||||
|
||||
############
|
||||
# handlers #
|
||||
############
|
||||
func _on_text_changed(new_text : String) -> void:
|
||||
__validate_text()
|
||||
|
||||
func _on_property_value_changed() -> void:
|
||||
var new_text := __text_from_property()
|
||||
if new_text != text:
|
||||
text = new_text
|
||||
Reference in New Issue
Block a user