From f000f5fb25ae5164d40badc79aad7b791b417164 Mon Sep 17 00:00:00 2001 From: Kamil Jarosz Date: Fri, 22 Mar 2024 01:08:10 +0100 Subject: [PATCH 1/5] core: Move FocusTracker to Stage --- core/src/display_object/stage.rs | 9 +++++++++ core/src/player.rs | 8 +------- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/core/src/display_object/stage.rs b/core/src/display_object/stage.rs index 990fa5fd5d36..9fb90ce209f7 100644 --- a/core/src/display_object/stage.rs +++ b/core/src/display_object/stage.rs @@ -15,6 +15,7 @@ use crate::display_object::interactive::{ }; use crate::display_object::{render_base, DisplayObjectBase, DisplayObjectPtr}; use crate::events::{ClipEvent, ClipEventResult}; +use crate::focus_tracker::FocusTracker; use crate::prelude::*; use crate::string::{FromWStr, WStr}; use crate::tag_utils::SwfMovie; @@ -147,6 +148,9 @@ pub struct StageData<'gc> { /// identity matrix unless explicitly set from ActionScript) #[collect(require_static)] viewport_matrix: Matrix, + + /// A tracker for the current keyboard focused element + focus_tracker: FocusTracker<'gc>, } impl<'gc> Stage<'gc> { @@ -184,6 +188,7 @@ impl<'gc> Stage<'gc> { stage3ds: vec![], movie, viewport_matrix: Matrix::IDENTITY, + focus_tracker: FocusTracker::new(gc_context), }, )); stage.set_is_root(gc_context, true); @@ -732,6 +737,10 @@ impl<'gc> Stage<'gc> { Avm2::dispatch_event(context, full_screen_event, stage); } } + + pub fn focus_tracker(&self) -> FocusTracker<'gc> { + self.0.read().focus_tracker + } } impl<'gc> TDisplayObject<'gc> for Stage<'gc> { diff --git a/core/src/player.rs b/core/src/player.rs index bd47e1005a0b..911b3f9cd1b5 100644 --- a/core/src/player.rs +++ b/core/src/player.rs @@ -33,7 +33,6 @@ use crate::events::GamepadButton; use crate::events::{ButtonKeyCode, ClipEvent, ClipEventResult, KeyCode, MouseButton, PlayerEvent}; use crate::external::{ExternalInterface, ExternalInterfaceProvider, NullFsCommandProvider}; use crate::external::{FsCommandProvider, Value as ExternalValue}; -use crate::focus_tracker::FocusTracker; use crate::frame_lifecycle::{run_all_phases_avm2, FramePhase}; use crate::library::Library; use crate::limits::ExecutionLimit; @@ -159,9 +158,6 @@ struct GcRootData<'gc> { /// External interface for (for example) JavaScript <-> ActionScript interaction external_interface: ExternalInterface<'gc>, - /// A tracker for the current keyboard focused element - focus_tracker: FocusTracker<'gc>, - /// Manager of active sound instances. audio_manager: AudioManager<'gc>, @@ -1841,7 +1837,6 @@ impl Player { let mut root_data = gc_root.data.write(gc_context); let mouse_hovered_object = root_data.mouse_hovered_object; let mouse_pressed_object = root_data.mouse_pressed_object; - let focus_tracker = root_data.focus_tracker; #[allow(unused_variables)] let ( @@ -1906,7 +1901,7 @@ impl Player { start_time: self.start_time, update_start: Instant::now(), max_execution_duration: self.max_execution_duration, - focus_tracker, + focus_tracker: stage.focus_tracker(), times_get_time_called: 0, time_offset: &mut self.time_offset, audio_manager, @@ -2450,7 +2445,6 @@ impl PlayerBuilder { external_interface_providers, fs_command_provider, ), - focus_tracker: FocusTracker::new(gc_context), library: Library::empty(), load_manager: LoadManager::new(), mouse_hovered_object: None, From 0be9ca9cb40e5706baf30fde00bd2a027b7e41c7 Mon Sep 17 00:00:00 2001 From: Kamil Jarosz Date: Wed, 27 Mar 2024 15:22:17 +0100 Subject: [PATCH 2/5] swf: Add Rectangle::grow method --- swf/src/types/rectangle.rs | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/swf/src/types/rectangle.rs b/swf/src/types/rectangle.rs index edd5b11dbb3e..2479290ff7ed 100644 --- a/swf/src/types/rectangle.rs +++ b/swf/src/types/rectangle.rs @@ -130,6 +130,17 @@ impl Rectangle { && self.y_min <= other.y_max && self.y_max >= other.y_min } + + #[must_use] + pub fn grow(mut self, amount: T) -> Self { + if self.is_valid() { + self.x_min -= amount; + self.x_max += amount; + self.y_min -= amount; + self.y_max += amount; + } + self + } } impl Default for Rectangle { From f360666a5e23fe55caa63c8b29e2d237f7f4b3c6 Mon Sep 17 00:00:00 2001 From: Kamil Jarosz Date: Fri, 22 Mar 2024 01:08:10 +0100 Subject: [PATCH 3/5] core: Render yellow highlight on keyboard focus This patch implements rendering of the yellow rectangle around a focused element after pressing Tab. Focus tracker which is responsible for keeping track of the current focus is now also responsible for keeping track of the highlight and rendering thereof. --- core/src/display_object.rs | 5 + core/src/display_object/avm1_button.rs | 5 + core/src/display_object/movie_clip.rs | 5 + core/src/display_object/stage.rs | 2 + core/src/focus_tracker.rs | 94 ++++++++++++++++-- core/src/player.rs | 11 ++ swf/src/types/color.rs | 3 + .../acid/output.expected.png | Bin 18889 -> 4981 bytes 8 files changed, 115 insertions(+), 10 deletions(-) diff --git a/core/src/display_object.rs b/core/src/display_object.rs index 14310e999e65..12457a5a22af 100644 --- a/core/src/display_object.rs +++ b/core/src/display_object.rs @@ -1926,6 +1926,11 @@ pub trait TDisplayObject<'gc>: None } + /// Whether this object may be highlighted by tab ordering. + fn is_highlight_enabled(&self) -> bool { + false + } + /// Whether this display object has been created by ActionScript 3. /// When this flag is set, changes from SWF `RemoveObject` tags are /// ignored. diff --git a/core/src/display_object/avm1_button.rs b/core/src/display_object/avm1_button.rs index f867db2a86ba..a61680938655 100644 --- a/core/src/display_object/avm1_button.rs +++ b/core/src/display_object/avm1_button.rs @@ -430,6 +430,11 @@ impl<'gc> TDisplayObject<'gc> for Avm1Button<'gc> { self.0.tab_index.get().map(|i| i as i64) } + fn is_highlight_enabled(&self) -> bool { + // TODO focusrect support + true + } + fn avm1_unload(&self, context: &mut UpdateContext<'_, 'gc>) { let had_focus = self.0.has_focus.get(); if had_focus { diff --git a/core/src/display_object/movie_clip.rs b/core/src/display_object/movie_clip.rs index 29bd73075c15..801190717eba 100644 --- a/core/src/display_object/movie_clip.rs +++ b/core/src/display_object/movie_clip.rs @@ -3041,6 +3041,11 @@ impl<'gc> TDisplayObject<'gc> for MovieClip<'gc> { fn tab_index(&self) -> Option { self.0.read().tab_index.map(|i| i as i64) } + + fn is_highlight_enabled(&self) -> bool { + // TODO focusrect support + true + } } impl<'gc> TDisplayObjectContainer<'gc> for MovieClip<'gc> { diff --git a/core/src/display_object/stage.rs b/core/src/display_object/stage.rs index 9fb90ce209f7..93c40bad002c 100644 --- a/core/src/display_object/stage.rs +++ b/core/src/display_object/stage.rs @@ -847,6 +847,8 @@ impl<'gc> TDisplayObject<'gc> for Stage<'gc> { render_base((*self).into(), context); + self.focus_tracker().render_highlight(context); + if self.should_letterbox() { self.draw_letterbox(context); } diff --git a/core/src/focus_tracker.rs b/core/src/focus_tracker.rs index d137163827bd..0f184e120629 100644 --- a/core/src/focus_tracker.rs +++ b/core/src/focus_tracker.rs @@ -1,25 +1,58 @@ use crate::avm1::Avm1; use crate::avm1::Value; -use crate::context::UpdateContext; +use crate::context::{RenderContext, UpdateContext}; pub use crate::display_object::{ DisplayObject, TDisplayObject, TDisplayObjectContainer, TextSelection, }; +use crate::drawing::Drawing; use either::Either; -use gc_arena::lock::GcLock; -use gc_arena::{Collect, Mutation}; -use swf::Twips; +use gc_arena::barrier::unlock; +use gc_arena::lock::Lock; +use gc_arena::{Collect, Gc, Mutation}; +use ruffle_render::shape_utils::DrawCommand; +use std::cell::RefCell; +use swf::{Color, LineJoinStyle, Point, Twips}; + +#[derive(Collect)] +#[collect(no_drop)] +pub struct FocusTrackerData<'gc> { + focus: Lock>>, + highlight: RefCell, +} + +enum Highlight { + Inactive, + Active(Drawing), +} #[derive(Clone, Copy, Collect)] #[collect(no_drop)] -pub struct FocusTracker<'gc>(GcLock<'gc, Option>>); +pub struct FocusTracker<'gc>(Gc<'gc, FocusTrackerData<'gc>>); impl<'gc> FocusTracker<'gc> { + const HIGHLIGHT_WIDTH: Twips = Twips::from_pixels_i32(3); + const HIGHLIGHT_COLOR: Color = Color::YELLOW; + + // Although at 3px width Round and Miter are similar + // to each other, it seems that FP uses Round. + const HIGHLIGHT_LINE_JOIN_STYLE: LineJoinStyle = LineJoinStyle::Round; + pub fn new(mc: &Mutation<'gc>) -> Self { - Self(GcLock::new(mc, None.into())) + Self(Gc::new( + mc, + FocusTrackerData { + focus: Lock::new(None), + highlight: RefCell::new(Highlight::Inactive), + }, + )) + } + + pub fn reset_highlight(&self) { + self.0.highlight.replace(Highlight::Inactive); } pub fn get(&self) -> Option> { - self.0.get() + self.0.focus.get() } pub fn set( @@ -27,11 +60,15 @@ impl<'gc> FocusTracker<'gc> { focused_element: Option>, context: &mut UpdateContext<'_, 'gc>, ) { - let old = self.0.get(); + let old = self.0.focus.get(); // Check if the focused element changed. if old.map(|o| o.as_ptr()) != focused_element.map(|o| o.as_ptr()) { - self.0.set(context.gc(), focused_element); + let focus = unlock!(Gc::write(context.gc(), self.0), FocusTrackerData, focus); + focus.set(focused_element); + + // The highlight always follows the focus. + self.update_highlight(); if let Some(old) = old { old.on_focus_changed(context, false, focused_element); @@ -89,7 +126,7 @@ impl<'gc> FocusTracker<'gc> { .peekable(); let first = tab_order.peek().copied(); - let next = if let Some(current_focus) = self.0.get() { + let next = if let Some(current_focus) = self.get() { // Find the next object which should take the focus. tab_order .skip_while(|o| o.as_ptr() != current_focus.as_ptr()) @@ -102,7 +139,44 @@ impl<'gc> FocusTracker<'gc> { if next.is_some() { self.set(next.copied(), context); + self.update_highlight(); + } + } + + fn update_highlight(&self) { + self.0.highlight.replace(self.redraw_highlight()); + } + + fn redraw_highlight(&self) -> Highlight { + let Some(focus) = self.get() else { + return Highlight::Inactive; + }; + + if !focus.is_highlight_enabled() { + return Highlight::Inactive; } + + let bounds = focus.world_bounds().grow(-Self::HIGHLIGHT_WIDTH / 2); + let mut drawing = Drawing::new(); + drawing.set_line_style(Some( + swf::LineStyle::new() + .with_width(Self::HIGHLIGHT_WIDTH) + .with_color(Self::HIGHLIGHT_COLOR) + .with_join_style(Self::HIGHLIGHT_LINE_JOIN_STYLE), + )); + drawing.draw_command(DrawCommand::MoveTo(Point::new(bounds.x_min, bounds.y_min))); + drawing.draw_command(DrawCommand::LineTo(Point::new(bounds.x_min, bounds.y_max))); + drawing.draw_command(DrawCommand::LineTo(Point::new(bounds.x_max, bounds.y_max))); + drawing.draw_command(DrawCommand::LineTo(Point::new(bounds.x_max, bounds.y_min))); + drawing.draw_command(DrawCommand::LineTo(Point::new(bounds.x_min, bounds.y_min))); + + Highlight::Active(drawing) + } + + pub fn render_highlight(&self, context: &mut RenderContext<'_, 'gc>) { + if let Highlight::Active(ref highlight) = *self.0.highlight.borrow() { + highlight.render(context); + }; } fn order_custom(tab_order: &mut Vec) { diff --git a/core/src/player.rs b/core/src/player.rs index 911b3f9cd1b5..0b0313a55811 100644 --- a/core/src/player.rs +++ b/core/src/player.rs @@ -1187,6 +1187,17 @@ impl Player { tracker.cycle(context, reversed); }); } + + if matches!( + event, + PlayerEvent::MouseDown { .. } + | PlayerEvent::MouseUp { .. } + | PlayerEvent::MouseMove { .. } + ) { + self.mutate_with_update_context(|context| { + context.focus_tracker.reset_highlight(); + }); + } } /// Update dragged object, if any. diff --git a/swf/src/types/color.rs b/swf/src/types/color.rs index cc885c9241fb..4965c343b4e4 100644 --- a/swf/src/types/color.rs +++ b/swf/src/types/color.rs @@ -23,6 +23,9 @@ impl Color { pub const RED: Self = Self::from_rgb(0xFF0000, 255); pub const GREEN: Self = Self::from_rgb(0x00FF00, 255); pub const BLUE: Self = Self::from_rgb(0x0000FF, 255); + pub const YELLOW: Self = Self::from_rgb(0xFFFF00, 255); + pub const CYAN: Self = Self::from_rgb(0x00FFFF, 255); + pub const MAGENTA: Self = Self::from_rgb(0xFF00FF, 255); /// Creates a `Color` from a 32-bit `rgb` value and an `alpha` value. /// diff --git a/tests/tests/swfs/visual/shumway_acid_tests/acid/output.expected.png b/tests/tests/swfs/visual/shumway_acid_tests/acid/output.expected.png index 2fbb4fac329ef58b79fb4921f3fe8caeb19b1507..d4e7be29ca02dd8e92ef29ea7c8e36c8501508f2 100644 GIT binary patch literal 4981 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 Date: Fri, 22 Mar 2024 01:08:55 +0100 Subject: [PATCH 4/5] tests: Add focus_highlight/focus_highlight_basic --- .../focus_highlight_basic/input.json | 29 +++++++++++++ .../output.01_highlight_under.expected.png | Bin 0 -> 1601 bytes .../output.02_highlight_over.expected.png | Bin 0 -> 1577 bytes .../output.03_after_mouse_move.expected.png | Bin 0 -> 1560 bytes .../output.04_after_mouse_up.expected.png | Bin 0 -> 1560 bytes .../output.05_after_mouse_down.expected.png | Bin 0 -> 1560 bytes .../output.06_after_key_down.expected.png | Bin 0 -> 1577 bytes .../output.07_after_focus_change.expected.png | Bin 0 -> 1601 bytes ...08_after_focus_change_and_tab.expected.png | Bin 0 -> 1577 bytes ...ocus_change_without_highlight.expected.png | Bin 0 -> 1601 bytes .../focus_highlight_basic/output.txt | 0 .../focus_highlight_basic/test.as | 15 +++++++ .../focus_highlight_basic/test.swf | Bin 0 -> 369 bytes .../focus_highlight_basic/test.toml | 40 ++++++++++++++++++ 14 files changed, 84 insertions(+) create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/input.json create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.01_highlight_under.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.02_highlight_over.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.03_after_mouse_move.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.04_after_mouse_up.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.05_after_mouse_down.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.06_after_key_down.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.07_after_focus_change.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.08_after_focus_change_and_tab.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.09_after_focus_change_without_highlight.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.txt create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.as create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.swf create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.toml diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/input.json b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/input.json new file mode 100644 index 000000000000..bc6b2cac1fb0 --- /dev/null +++ b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/input.json @@ -0,0 +1,29 @@ +[ + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "MouseMove", "pos": [42, 42] }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "MouseDown", "pos": [42, 42], "btn": "Left" }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "MouseUp", "pos": [42, 42], "btn": "Left" }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "KeyDown", "key_code": 97 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 27 }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "KeyDown", "key_code": 27 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "KeyDown", "key_code": 27 }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "MouseMove", "pos": [42, 42] }, + { "type": "KeyDown", "key_code": 27 }, + { "type": "Wait" } +] diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.01_highlight_under.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.01_highlight_under.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..0fc566afa01c5ef769a5e7ded82b717a530d663e GIT binary patch literal 1601 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~v{)7srr_TW@b{+IW$+Gcp+*A_{yWpC;B7%iX3>FQW1sNC)u`oEyAcNu% z2J0h-Vn}3S0O})+Qt$z5Ad70@WB}>IO6}8-JXn#nwyi+HGToVB$3{a&kh%r~GAIEx zus#gR;dPL``^-DfW*6nXpPd~WBXfWu2jZIz(|6f~M&5nHU3zcUk8^XnPcupM^x|bkl+s1zS=|j~s%n1x;IKq?? z*JZ@M`V?~d&(HiRXZJHR)SWp-rZ4`Rxw@1TiEO{Q)qtsi@dhLpCFp-G7Fk`#kTG|} zMkEnM3OU6FD8-OmY(O=TRcru@DV)UyBGche(!)T-tU*MGLY3I;WSX%+e(UANEJn60Kn<*qB#Pk>3jOfM|Ip&pS;-Fg8vpw z$zo~Xj{yczA`>`>NTyJOmhaT`%1OI^n)YX@F)Z-cBO@3<;Z1HZK=ok_210@y!VDlK zdrvpnw(?>4Xg*FVdQ&MBb@0F$W{m;e9( literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.03_after_mouse_move.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.03_after_mouse_move.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..b8879305f6c861ee0cc67ca83686f6b97a11888d GIT binary patch literal 1560 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj2G;wYE{-7;x8B~^$a}~@ z#5J&K&&2YgG_SHxKK*TNOr3|E`ijpnc+@T2@hf_g4FiMP2NOmH1s?{67EaQs1_MTr zKC&nQHLyOCD278U3_uNJQ4TY}`mj<73zC|CTb{qnA)L8ZlJUXWqcpH4JbYT^$$PbD z<3oiR4AjMi89*-KAcJB^WCH0UivmS7P&;W9IVl60qVT1R10K{;xl-<`njxgN@xNA0p{;xl-<`njxgN@xNA0p{;xl-<`njxgN@xNA0pn60Kn<*qB#Pk>3jOfM|Ip&pS;-Fg8vpw z$zo~Xj{yczA`>`>NTyJOmhaT`%1OI^n)YX@F)Z-cBO@3<;Z1HZK=ok_210@y!VDlK zdrvpnw(?>4Xg*FVdQ&MBb@0F$W{m;e9( literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.07_after_focus_change.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.07_after_focus_change.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..0fc566afa01c5ef769a5e7ded82b717a530d663e GIT binary patch literal 1601 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~v{)7srr_TW@b{+IW$+Gcp+*A_{yWpC;B7%iX3>FQW1sNC)u`oEyAcNu% z2J0h-Vn}3S0O})+Qt$z5Ad70@WB}>IO6}8-JXn#nwyi+HGToVB$3{a&kh%r~GAIEx zus#gR;dPL``^-DfW*6nXpPd~WBXfWu2jZIz(|6f~M&5nHU3zcUk8^XnPcupM^x|bkl+s1zS=|j~s%n1x;IKq?? z*JZ@M`V?~d&(HiRXZJHR)SWp-rZ4`Rxw@1TiEO{Q)qtsi@dhLpCFp-G7Fk`#kTG|} zMkEnM3OU6FD8-OmY(O=TRcru@DV)UyBGche(!)T-tU*MGLY3I;WSX%+e(UANEJn60Kn<*qB#Pk>3jOfM|Ip&pS;-Fg8vpw z$zo~Xj{yczA`>`>NTyJOmhaT`%1OI^n)YX@F)Z-cBO@3<;Z1HZK=ok_210@y!VDlK zdrvpnw(?>4Xg*FVdQ&MBb@0F$W{m;e9( literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.09_after_focus_change_without_highlight.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/output.09_after_focus_change_without_highlight.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..0fc566afa01c5ef769a5e7ded82b717a530d663e GIT binary patch literal 1601 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~v{)7srr_TW@b{+IW$+Gcp+*A_{yWpC;B7%iX3>FQW1sNC)u`oEyAcNu% z2J0h-Vn}3S0O})+Qt$z5Ad70@WB}>IO6}8-JXn#nwyi+HGToVB$3{a&kh%r~GAIEx zus#gR;dPL``^-DfW*6nXpPd~WBXfWu2jZIz(|6f~M&5nHU3zcUk8^XnPcupM^x|bkl+s1zS=|j~s%n1x;IKq?? z*JZ@M`V?~d&(HiRXZJHR)SWp-rZ4`Rxw@1TiEO{Q)qtsi@dhLpCFp-G7Fk`#kTG|} zMkEnM3OU6FD8-OmY(O=TRcru@DV)UyBGche(!)T-tU*MGLY3I;WSX%+e(UANEJzV$IQrA8*N@%6{#slqfv>H}jD za%Tpy??=XDI%eDQ2l6C)>O9qCXo_QDuz4$l9-E<>Q)xhk)~uV&Q#`R;g1p)HyB`R! zimk|v1l&8A_5obIwr%M(lN)H*^>Zg|h?gvbw}P12bX;!nGn8v5yzaubcKKz|zOX=l z9CNo|8yx%GB(Z5*aJai8#z8lXy)fIBY29T}B`S(k9szk0MA`~sv?+WRolHe1Q_)dM z4pWNg#5;+GMKCG{F literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.toml b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.toml new file mode 100644 index 000000000000..5d121cbea9ec --- /dev/null +++ b/tests/tests/swfs/visual/focus_highlight/focus_highlight_basic/test.toml @@ -0,0 +1,40 @@ +num_ticks = 9 + +[image_comparisons."output.01_highlight_under"] +tolerance = 0 +trigger = 1 + +[image_comparisons."output.02_highlight_over"] +tolerance = 0 +trigger = 2 + +[image_comparisons."output.03_after_mouse_move"] +tolerance = 0 +trigger = 3 + +[image_comparisons."output.04_after_mouse_up"] +tolerance = 0 +trigger = 4 + +[image_comparisons."output.05_after_mouse_down"] +tolerance = 0 +trigger = 5 + +[image_comparisons."output.06_after_key_down"] +tolerance = 0 +trigger = 6 + +[image_comparisons."output.07_after_focus_change"] +tolerance = 0 +trigger = 7 + +[image_comparisons."output.08_after_focus_change_and_tab"] +tolerance = 0 +trigger = 8 + +[image_comparisons."output.09_after_focus_change_without_highlight"] +tolerance = 0 +trigger = 9 + +[player_options] +with_renderer = { optional = false, sample_count = 1 } From ebef44719703214e2a3e0f5c88709e5fc1115b8e Mon Sep 17 00:00:00 2001 From: Kamil Jarosz Date: Fri, 22 Mar 2024 01:09:06 +0100 Subject: [PATCH 5/5] tests: Add focus_highlight/focus_highlight_render --- .../focus_highlight_render/input.json | 14 ++++++++ .../output.01.expected.png | Bin 0 -> 1648 bytes .../output.02.expected.png | Bin 0 -> 1651 bytes .../output.03.expected.png | Bin 0 -> 1695 bytes .../output.04.expected.png | Bin 0 -> 1623 bytes .../output.05.expected.png | Bin 0 -> 1615 bytes .../output.06.expected.png | Bin 0 -> 1639 bytes .../focus_highlight_render/output.txt | 0 .../focus_highlight_render/test.as | 12 +++++++ .../focus_highlight_render/test.swf | Bin 0 -> 474 bytes .../focus_highlight_render/test.toml | 30 ++++++++++++++++++ 11 files changed, 56 insertions(+) create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/input.json create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.01.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.02.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.03.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.04.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.05.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.06.expected.png create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.txt create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.as create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.swf create mode 100644 tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.toml diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/input.json b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/input.json new file mode 100644 index 000000000000..236b14c3c242 --- /dev/null +++ b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/input.json @@ -0,0 +1,14 @@ +[ + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" }, + { "type": "KeyDown", "key_code": 9 }, + { "type": "Wait" } +] diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.01.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.01.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..614e24635ca7d9ef64e9580d0dfd89605b66dfa6 GIT binary patch literal 1648 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~zj~7srr_TW{}P%xyLh zX$#!_$?Ya*TGQMaFW+ZRZPyCrI{3|!ndPUD=6t=N6`nvN@*bS#U|>jOVo>lQgKFUf z>%*Wf>?}K*y2{gE-HqYE{F^fv7!I*8Jc!)=Z&KKw$DdB{HGIDT5py7i;t*y4>4Q>x zR!A~3@Fdu_S+w=ya1F?77*0eLY%pL1DZ!+wuD4m9tm-N3d;2ija%Sy)-iL0}QVm&t zC`hBY0@Y0fc%a}0Dj|!aYBZsS0hDJjJ&lFIe$DZU^jmW8wC`>(#1S&U;5x9|?gM-F z*E#)n@Axphme&8UL3kHveV=g=`01_5B+2j(i0DI&7m1C_HJ z$HKB@AIW&$@oC^3N&y?-rMXn{;EhQVObmEaE@nnY&Hcb&1u2126@k7&$qWqd4$wB- paYhZUw1=7!QF+9t%LeZn=Eb2pTk~UrJb*O`gQu&X%Q~loCIG_SOilm* literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.02.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.02.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..2d936211017d2aa5c57f7cbdaad34aeda876e5c1 GIT binary patch literal 1651 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~w~C7srr_TW{|k>^-a? z;1C#baboo$)0y*PF25-i)eKD0jFi|P?kG|8LyB*mpdc$l0+YQP0|SRJ14AMc>6C&G zSRV$}aMV;eA@(ZAgOvtM(^8VbCO5dxEAlvWOUfpHQe!VC14vH`8B~J-BS;^VIxu^d zAcF(b@0pJz%+$bw0%TAOhgcYZ`Y@@8SnuLVf6o;5C4XMOXQpABqR*1=c^n`5b8z?@ z6o?psfhI_fr=fv`>USb}Bn8NUy(Y>GKa%aQ|9yLWaQqVM!qp*a-&AG>NtK^! zlc*NCNFEHkere8=8+X*aU+sNveWh+!!~-E|VFrg8;G|13MOIpe<`F{Ci%0<eZ>gixlMwbhlkI>iaX||Th96s`1oySDO}HU(SU~MkwRwv; zjgz3=5=qCrt=B}JcW_MSEMO+yr5MQ#Ggo2FYFGt9F$>I_q)}6XyfWP;M7u~ZF`V82 z33jBEgeW@*38MO>BDlB1fQ=!6Z72l=FwGK~IckpTt2k(VTo>*72w0ggc)I$ztaD0e F0sz+;H5C8= literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.03.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.03.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..908cf577e5ffff08d203d2d79db85c3596815490 GIT binary patch literal 1695 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj2DUU$7srr_TW|09<~17# zGz9K`ZOhd!567wc(>BpN*18ye;*QTHWNN!8s&g`t73Mv{?1!H0pNg_Cru z!GIB@k1R?+4XlqOia~R!3DCJb2{+p;c%+3H9A+>uaF9VUBr<{YVN!SQnw*)ab6ev0 z#&hdVwXfVN<>cb#L8W5Jf7Y0~w-k8(bl zcWrb2)bPpMw*vjUOVNj+A@7GKd&a73U&HQi&-q-To;WwQ!+%4LdW`q|v-XFMu`s-7 z!<7W`PRp-hJiu}8pYmR}`RU0_3?Pg5EOypp= z(*{f%)G6-{_*p6)l4xj_*UevVn{;6B-uZ(+*?kb0EXa_Xs?1Qf8B(Mjh_5@vD8-@7 lV3!0;K&ZI@E05r@onmar`qrOmzpI-JA3%MM>VpH_ z(~R_Qo|k%W5mrCd-1wNmq1K$+X)Hh7^~i8D$Y`J^84j_KO*sJl4Af2<1q>XJ2I8m( zabm&@H5=!Dy;rhkU-&X;;4&nF!x)unc>jt28pDEFk85xBzeA1$p`b^iv9<8*XpXR(Crjtn9)YXd|x$b1|!1` jrlAxP#3##tN7TI~G^F;=_>}^zFc>^t{an^LB{Ts5BUBvV literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.05.expected.png b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/output.05.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..86b591d4b5cc6784c2901c930ac772107f91e811 GIT binary patch literal 1615 zcmeAS@N?(olHy`uVBq!ia0y~yU{YgXV4T3g1{9gKb@gTj1~xHI7srr_TW{}fEIe!= z;Bv9KU3R7V2DL@%*S7e{R?0+}Ro1L$))D=)(?!{ni{Sy2oeu*8hcE*}A`|J90#Gkd zA6ZljCs-dzltbv%G$w|O1p8>4!$(;d1c07DL|HRE*sQw9fi-+#g%oEST z08EA?M=eA{XsBn6AS@{oiX5!*2XyKKBezL27#FOECb^dU9k`MxRufPKiHQ0=C)1kl z9h1<#H}S}EmI?-OQql}+>LRP$AU1Na6)me)Wf?o>d-gCK$faH&{kh;FWX!-2{(zQA t4V!PEr6)J&)*;)#%k#6hw9i@8Yg@OTnP0|^SD|W>2}1*CjU*$3f)4{j3n%GRg8?H* zA6b-u8dx7m6vNuBWfF`GA_capeTm6T3>?A?42fh=ApZjOVNeZMWmEl%Y)#JWB~I^}7+B}0JY#CoNh`a@pQntzsT!@rvZcM4N_C^q0MDUQ}h2-)I mql7|B-Pj5-5=wHrN74r^wdC~m?(79tAPktlj{Ku@*FTzQLmEEn zWi8u;0BhmT6HpIT3jERobsH+hIke|5UTwU(h1C@zsGCY`GA0nMo9f>rh1x=(El4!b zb2CwKg`l0GJ;>nw!jFY5#zac)HI;whP@1wopbVIh(RvNMCL6)*TKepMoED}hJmXdi zr+(hutVd5i?KTUS6>6YS^aVBe#v4S?s@U-LlGS;F$~FD8`d;=$Y!3|QPxR7i^%nLCWQfx@| QLaGZf4z+&!KYn$qAm1+NRR910 literal 0 HcmV?d00001 diff --git a/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.toml b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.toml new file mode 100644 index 000000000000..bc3457e83e28 --- /dev/null +++ b/tests/tests/swfs/visual/focus_highlight/focus_highlight_render/test.toml @@ -0,0 +1,30 @@ +num_ticks = 6 + +[image_comparisons."output.01"] +trigger = 1 +max_outliers = 4 + +[image_comparisons."output.02"] +trigger = 2 +max_outliers = 4 + +[image_comparisons."output.03"] +trigger = 3 +max_outliers = 4 + +[image_comparisons."output.04"] +trigger = 4 +max_outliers = 4 + +[image_comparisons."output.05"] +trigger = 5 +# Position of the cursor does not matter, +# what matters is that there's no highlight. +max_outliers = 100 + +[image_comparisons."output.06"] +trigger = 6 +max_outliers = 4 + +[player_options] +with_renderer = { optional = false, sample_count = 1 }