OverviewFilesCommitsIssuesDocsReleasesPeers

hypercore-kb / hyper-social / keet-social / demo / chat_demo.gd

116 lines · gd ref:
extends Control
## 2D chat demo using keet-social plugin.
## Connects to keet-daemon, lists rooms, and enables chatting.

@onready var client: KeetClient = $KeetClient
@onready var room_manager: KeetRoom = $KeetRoom
@onready var chat: KeetChat = $KeetChat
@onready var identity: KeetIdentity = $KeetIdentity

@onready var status_label: Label = $UI/TopBar/StatusLabel
@onready var room_list: ItemList = $UI/HSplit/RoomPanel/RoomList
@onready var chat_log: RichTextLabel = $UI/HSplit/ChatPanel/VBox/ChatLog
@onready var input_field: LineEdit = $UI/HSplit/ChatPanel/VBox/HBox/InputField
@onready var send_button: Button = $UI/HSplit/ChatPanel/VBox/HBox/SendButton
@onready var room_title: Label = $UI/HSplit/ChatPanel/RoomTitle

var _rooms: Array = []
var _current_room: String = ""
var _identity_name: String = "unknown"


func _ready() -> void:
	# Wire up client
	client.connected.connect(_on_connected)
	client.disconnected.connect(_on_disconnected)

	# Wire up room manager
	room_manager.client = client
	room_manager.rooms_loaded.connect(_on_rooms_loaded)

	# Wire up chat
	chat.client = client
	chat.message_received.connect(_on_message_received)
	chat.messages_loaded.connect(_on_history_loaded)

	# Wire up identity
	identity.client = client

	# Wire up UI
	send_button.pressed.connect(_on_send)
	input_field.text_submitted.connect(_on_text_submitted)
	room_list.item_selected.connect(_on_room_selected)

	status_label.text = "Connecting..."
	room_title.text = "Select a room"


func _on_connected() -> void:
	status_label.text = "Connected"
	identity.get_identity(func(ident: Dictionary):
		_identity_name = ident.get("displayName", ident.get("name", "unknown"))
		status_label.text = "Connected as %s" % _identity_name
	)
	room_manager.list_rooms()


func _on_disconnected() -> void:
	status_label.text = "Disconnected - retrying..."
	chat.stop_polling()


func _on_rooms_loaded(rooms: Array) -> void:
	_rooms = rooms
	room_list.clear()
	for room: Variant in rooms:
		if room is Dictionary:
			room_list.add_item(room.get("title", room.get("roomId", "?")))


func _on_room_selected(index: int) -> void:
	if index < 0 or index >= _rooms.size():
		return
	var room: Dictionary = _rooms[index]
	_current_room = room.get("roomId", "")
	room_title.text = room.get("title", _current_room)
	chat_log.clear()
	chat.watch(_current_room)
	chat.load_history()


func _on_history_loaded(messages: Array) -> void:
	chat_log.clear()
	for msg: Variant in messages:
		if msg is Dictionary:
			_append_message(msg)


func _on_message_received(msg: Dictionary) -> void:
	_append_message(msg)


func _on_send() -> void:
	_send_message()


func _on_text_submitted(_text: String) -> void:
	_send_message()


func _send_message() -> void:
	var text := input_field.text.strip_edges()
	if text == "" or _current_room == "":
		return
	input_field.text = ""
	chat.send(text)


func _append_message(msg: Dictionary) -> void:
	var name: String = msg.get("name", msg.get("memberId", "?"))
	var text: String = msg.get("text", "")
	var is_system: bool = msg.get("system", false)
	if is_system:
		chat_log.append_text("[color=gray]--- %s ---[/color]\n" % text)
	else:
		chat_log.append_text("[b]%s:[/b] %s\n" % [name, text])