class_name VNTextbox extends PanelContainer const VN_REVEAL_TIME = 0.01 var label:AdvancedRichText; var parsedOutText = "" var revealTimer:float = 0; var lineStarts:Array[int] = []; var newlineIndexes:Array[int] = []; var currentViewScrolled = true; var isSpeedupDown = false; var isClosed:bool = false: get(): return !self.visible; set(value): self.visible = !value; signal textboxClosing func _ready() -> void: label = $MarginContainer/Label isClosed = true func _process(delta: float) -> void: if label.getFinalText() == "": isClosed = true; return; if label.visible_characters >= label.getCharactersDisplayedCount(): if (label.maxLines + label.startLine) < label.getTotalLineCount(): # Not on last page. if Input.is_action_just_pressed("interact"): label.startLine += label.maxLines; label.visible_characters = 0; currentViewScrolled = false; return currentViewScrolled = true; else: # On last page if Input.is_action_just_released("interact"): textboxClosing.emit(); isClosed = true; currentViewScrolled = true return; if Input.is_action_just_pressed("interact"): isSpeedupDown = true; elif Input.is_action_just_released("interact"): isSpeedupDown = false; elif !Input.is_action_pressed("interact"): isSpeedupDown = false; revealTimer += delta; if isSpeedupDown: revealTimer += delta; if revealTimer > VN_REVEAL_TIME: revealTimer = 0; label.visible_characters += 1; func setText(text:String) -> void: isClosed = false; revealTimer = 0; currentViewScrolled = false; label.visible_characters = 0; label.startLine = 0; label.text = "" await get_tree().process_frame# Absolutely needed to make the text wrap label.text = text; label.visible_characters = 0;