class_name BubbleHoverDrawer extends Control enum DrawerMode { RIGHT, LEFT_VERTICAL, } const DRAWER_COLOR: Color = Color(0.031, 0.122, 0.169, 1.0) const TEXT_COLOR: Color = Color(0.764706, 0.87451, 0.901961, 1.0) const RIGHT_SIZE: Vector2 = Vector2(132.0, 48.0) const LEFT_VERTICAL_SIZE: Vector2 = Vector2(50.0, 176.0) const OVERLAP: float = 12.0 var host_button: BaseButton var drawer_mode: DrawerMode = DrawerMode.RIGHT var _panel: Panel var _label: Label func configure( button: BaseButton, drawer_text: String, mode: DrawerMode, ) -> void: host_button = button drawer_mode = mode mouse_filter = Control.MOUSE_FILTER_IGNORE show_behind_parent = true _build_controls() _label.text = drawer_text _refresh_label_layout() refresh_layout() set_reveal(0.0) func refresh_layout() -> void: if host_button == null: return if drawer_mode == DrawerMode.RIGHT: size = RIGHT_SIZE position = Vector2( host_button.size.x - OVERLAP, (host_button.size.y - size.y) * 0.5, ) pivot_offset = Vector2(0.0, size.y * 0.5) else: size = LEFT_VERTICAL_SIZE position = Vector2( -size.x + OVERLAP, (host_button.size.y - size.y) * 0.5, ) pivot_offset = Vector2(size.x, size.y * 0.5) _refresh_label_layout() func set_reveal(amount: float) -> void: var reveal: float = clampf(amount, 0.0, 1.0) visible = reveal > 0.001 scale = Vector2(maxf(reveal, 0.001), 1.0) func _build_controls() -> void: if _panel != null: return _panel = Panel.new() _panel.mouse_filter = Control.MOUSE_FILTER_IGNORE _panel.set_anchors_and_offsets_preset(Control.PRESET_FULL_RECT) var panel_style := StyleBoxFlat.new() panel_style.bg_color = DRAWER_COLOR panel_style.corner_radius_top_left = 12 panel_style.corner_radius_top_right = 12 panel_style.corner_radius_bottom_right = 12 panel_style.corner_radius_bottom_left = 12 _panel.add_theme_stylebox_override("panel", panel_style) add_child(_panel) _label = Label.new() _label.mouse_filter = Control.MOUSE_FILTER_IGNORE _label.add_theme_color_override("font_color", TEXT_COLOR) _label.add_theme_font_size_override("font_size", 20) _label.horizontal_alignment = HORIZONTAL_ALIGNMENT_CENTER _label.vertical_alignment = VERTICAL_ALIGNMENT_CENTER add_child(_label) func _refresh_label_layout() -> void: if _label == null: return if drawer_mode == DrawerMode.RIGHT: _label.rotation = 0.0 _label.position = Vector2.ZERO _label.size = size else: _label.rotation = -PI * 0.5 _label.position = Vector2(-OVERLAP * 0.5, size.y) _label.size = Vector2(size.y, size.x)