Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Custom Cursor #6923

Open
wants to merge 9 commits into
base: master
Choose a base branch
from
Open

Custom Cursor #6923

wants to merge 9 commits into from

Conversation

TheColorRed
Copy link
Contributor

Allows the user to use a custom window cursor.

Example usage:

import { Button } from "std-widgets.slint";

export component AppWindow inherits Window {
  property <int> counter: 0;
  property <[image]> cursors: [
    @image-url("cursors/red.png"),
    @image-url("cursors/green.png"),
    @image-url("cursors/blue.png"),
    @image-url("cursors/pink.png"),
  ];

  cursor: cursors[counter];
  cursor-hotspot-x: 20px;
  cursor-hotspot-y: 0px;

  width: 800px;
  height: 600px;

  TouchArea {
    clicked => {
      root.counter += 1;
      if (root.counter >= root.cursors.length) {
        root.counter = 0;
      }
    }
  }
}

@TheColorRed
Copy link
Contributor Author

Looking for feedback, There are a few things I was unsure of.

The TODO. Not sure if it should only update when the input changes, as I am not sure if it should run on every frame.

@FloVanGH FloVanGH requested a review from ogoffart November 27, 2024 09:23
@ogoffart
Copy link
Member

Thanks for the contribution! Custom cursor images is a nice feature. However, I think this would fit better as an extension of the existing mouse-cursor property on TouchArea rather than adding new properties to Window.

We could change the type of the mouse-cursor property to support either the predefined MouseCursor enum or a custom cursor struct (e.g., { cursor: image, hotspot-x: int, hotspot-y: int }). That's be IMHO a more intuitive and flexible API.

That said, I realize this would be a more complex change, especially around adding implicit conversions or supporting both the enum and a struct. So, I’d be happy to guide you through it if you’re interested. Or we could still consider to add a simpler approach with a custom-mouse-cursor property on the TouchArea.

(Note that the hotspot values would need to be integers (in the cursor image's coordinate system), not lengths. It's not impacted by the scale factor.)

Thanks again for contributing to Slint! We really appreciate your effort. Sorry that we’re not taking that as is, but we want to make sure the API is well-designed since we need to maintain it and keep compatibility in the long run. 😊

@TheColorRed
Copy link
Contributor Author

So, I’d be happy to guide you through it if you’re interested.

Yeah, that would be great!

  • I tried implementing the enum: MouseCursor::Custom { image: crate::graphics::Image, hotspot_x: int, hotspot_y: int }. However, the macro didn't understand it, and I am not very familiar with creating macros (just using them).
  • I am not sure if you know or saw in my PR that adding a custom cursor does require access to the event_loop: event_loop.create_custom_cursor(source.unwrap()), so I am not sure how much that would change the implementation, as I wasn't sure how to access it in the set_mouse_cursor() function or the WindowAdapterInternal impl.

@ogoffart
Copy link
Member

Indeed, enums in data aren't currently supported by the macro for declaring Slint enums in enums.rs. So, there are two alternatives:

  1. Implement it manually, similar to how EasingCurve is done.
  2. Introduce an extra type, like we have for Brush and Color.

Either way, we'd likely need an enum similar to EasingCurve and ensure the type is in langtype::Type.

As for accessing the winit event loop, you can use crate::event_loop::with_window_target from the WindowAdapterInternal.

Let me know if you need any further guidance! 😊

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants