Merge pull request #59398 from Calinou/animation-track-editor-keyframe-draw-hover

This commit is contained in:
Rémi Verschelde 2022-04-13 13:07:03 +02:00 committed by GitHub
commit 383cac9d1e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 63 additions and 1 deletions

View File

@ -2252,6 +2252,8 @@ void AnimationTrackEdit::_notification(int p_what) {
break;
case NOTIFICATION_MOUSE_EXIT:
hovered = false;
// When the mouse cursor exits the track, we're no longer hovering any keyframe.
hovering_key_idx = -1;
update();
[[fallthrough]];
case NOTIFICATION_DRAG_END: {
@ -2365,7 +2367,13 @@ void AnimationTrackEdit::draw_key(int p_index, float p_pixels_sec, int p_x, bool
}
}
draw_texture(icon_to_draw, ofs);
// Use a different color for the currently hovered key.
// The color multiplier is chosen to work with both dark and light editor themes,
// and on both unselected and selected key icons.
draw_texture(
icon_to_draw,
ofs,
p_index == hovering_key_idx ? get_theme_color(SNAME("folder_icon_modulate"), SNAME("FileDialog")) : Color(1, 1, 1));
}
// Helper.
@ -2952,6 +2960,59 @@ void AnimationTrackEdit::gui_input(const Ref<InputEvent> &p_event) {
}
Ref<InputEventMouseMotion> mm = p_event;
if (mm.is_valid()) {
const int previous_hovering_key_idx = hovering_key_idx;
// Hovering compressed keyframes for editing is not possible.
if (!animation->track_is_compressed(track)) {
const float scale = timeline->get_zoom_scale();
const int limit = timeline->get_name_limit();
const int limit_end = get_size().width - timeline->get_buttons_width();
// Left Border including space occupied by keyframes on t=0.
const int limit_start_hitbox = limit - type_icon->get_width();
const Point2 pos = mm->get_position();
if (pos.x >= limit_start_hitbox && pos.x <= limit_end) {
// Use the same logic as key selection to ensure that hovering accurately represents
// which key will be selected when clicking.
int key_idx = -1;
float key_distance = 1e20;
hovering_key_idx = -1;
// Hovering should happen in the opposite order of drawing for more accurate overlap hovering.
for (int i = animation->track_get_key_count(track) - 1; i >= 0; i--) {
Rect2 rect = get_key_rect(i, scale);
float offset = animation->track_get_key_time(track, i) - timeline->get_value();
offset = offset * scale + limit;
rect.position.x += offset;
if (rect.has_point(pos)) {
if (is_key_selectable_by_distance()) {
const float distance = ABS(offset - pos.x);
if (key_idx == -1 || distance < key_distance) {
key_idx = i;
key_distance = distance;
hovering_key_idx = i;
}
} else {
// First one does it.
hovering_key_idx = i;
break;
}
}
}
print_line(hovering_key_idx);
if (hovering_key_idx != previous_hovering_key_idx) {
// Required to draw keyframe hover feedback on the correct keyframe.
update();
}
}
}
}
if (mm.is_valid() && (mm->get_button_mask() & MouseButton::MASK_LEFT) != MouseButton::NONE && moving_selection_attempt) {
if (!moving_selection) {
moving_selection = true;

View File

@ -173,6 +173,7 @@ class AnimationTrackEdit : public Control {
bool hovered = false;
bool clicking_on_name = false;
int hovering_key_idx = -1;
void _zoom_changed();