Add Z index and view sorting
This commit is contained in:
parent
27bad18931
commit
b2499ad247
|
@ -26,6 +26,8 @@ class Window {
|
||||||
*/
|
*/
|
||||||
val views: List<View> = _views
|
val views: List<View> = _views
|
||||||
|
|
||||||
|
private var viewsSortedByZIndex: List<View> = listOf()
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds the given view as a top-level view in this window.
|
* Adds the given view as a top-level view in this window.
|
||||||
*
|
*
|
||||||
|
@ -34,6 +36,9 @@ class Window {
|
||||||
*/
|
*/
|
||||||
fun <T: View> addView(view: T): T {
|
fun <T: View> addView(view: T): T {
|
||||||
_views.add(view)
|
_views.add(view)
|
||||||
|
viewsSortedByZIndex = views.sortedBy(View::zIndex)
|
||||||
|
|
||||||
|
view.window = this
|
||||||
view.solver = solver
|
view.solver = solver
|
||||||
|
|
||||||
view.wasAdded()
|
view.wasAdded()
|
||||||
|
@ -42,11 +47,22 @@ class Window {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Attempts to find a top level view of this window that contains the given point.
|
* Finds all views in this window at the given point.
|
||||||
* If there are multiple overlapping views, which one this method returns is undefined.
|
|
||||||
*
|
*
|
||||||
* @param point The point to find views at, in the coordinate system of the window.
|
* @param point The point to find views at, in the coordinate system of the window.
|
||||||
* @return The view, if any, that contains the given point.
|
* @return All views that contain the point.
|
||||||
|
*/
|
||||||
|
fun viewsAtPoint(point: Point): List<View> {
|
||||||
|
return views.filter { point in it.frame }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Attempts to find a top level view of this window that contains the given point.
|
||||||
|
* If there are multiple overlapping views, which one this method returns is undefined.
|
||||||
|
* [viewsAtPoint] may be used, and the resulting List sorted by [View.zIndex].
|
||||||
|
*
|
||||||
|
* @param point The point to find views at, in the coordinate system of the window.
|
||||||
|
* @return the Veiw, if any, that contain the given point.
|
||||||
*/
|
*/
|
||||||
fun viewAtPoint(point: Point): View? {
|
fun viewAtPoint(point: Point): View? {
|
||||||
return views.firstOrNull { point in it.frame }
|
return views.firstOrNull { point in it.frame }
|
||||||
|
@ -69,7 +85,7 @@ class Window {
|
||||||
* @param delta The time elapsed since the last frame.
|
* @param delta The time elapsed since the last frame.
|
||||||
*/
|
*/
|
||||||
fun draw(mouse: Point, delta: Float) {
|
fun draw(mouse: Point, delta: Float) {
|
||||||
views.forEach {
|
viewsSortedByZIndex.forEach {
|
||||||
val mouseInView = Point(mouse.x - it.frame.left, mouse.y - it.frame.top)
|
val mouseInView = Point(mouse.x - it.frame.left, mouse.y - it.frame.top)
|
||||||
it.draw(mouseInView, delta)
|
it.draw(mouseInView, delta)
|
||||||
}
|
}
|
||||||
|
@ -84,7 +100,7 @@ class Window {
|
||||||
* @return Whether the mouse click was handled by a view.
|
* @return Whether the mouse click was handled by a view.
|
||||||
*/
|
*/
|
||||||
fun mouseClicked(point: Point, mouseButton: MouseButton): Boolean {
|
fun mouseClicked(point: Point, mouseButton: MouseButton): Boolean {
|
||||||
val view = viewAtPoint(point)
|
val view = viewsAtPoint(point).minBy(View::zIndex)
|
||||||
if (view != null) {
|
if (view != null) {
|
||||||
val pointInView = Point(point.x - view.frame.left, point.y - view.frame.top)
|
val pointInView = Point(point.x - view.frame.left, point.y - view.frame.top)
|
||||||
return view.mouseClicked(pointInView, mouseButton)
|
return view.mouseClicked(pointInView, mouseButton)
|
||||||
|
|
|
@ -78,6 +78,12 @@ open class View() {
|
||||||
*/
|
*/
|
||||||
lateinit var bounds: Rect
|
lateinit var bounds: Rect
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The position on the Z-axis of this view.
|
||||||
|
* Views are rendered from lowest Z index to highest. Clicks are handled from highest to lowest.
|
||||||
|
*/
|
||||||
|
var zIndex: Double = 0.0
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The intrinsic size of this view's content. May be null if the view doesn't have any content or there is no
|
* The intrinsic size of this view's content. May be null if the view doesn't have any content or there is no
|
||||||
* intrinsic size.
|
* intrinsic size.
|
||||||
|
@ -104,6 +110,9 @@ open class View() {
|
||||||
var superview: View? = null
|
var superview: View? = null
|
||||||
// _subviews is the internal, mutable object since we only want it to by mutated by the add/removeSubview methods
|
// _subviews is the internal, mutable object since we only want it to by mutated by the add/removeSubview methods
|
||||||
private val _subviews = LinkedList<View>()
|
private val _subviews = LinkedList<View>()
|
||||||
|
|
||||||
|
private var subviewsSortedByZIndex: List<View> = listOf()
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The list of all the subviews of this view.
|
* The list of all the subviews of this view.
|
||||||
* This list should never by mutated directly, only by the [addSubview]/[removeSubview] methods.
|
* This list should never by mutated directly, only by the [addSubview]/[removeSubview] methods.
|
||||||
|
@ -143,6 +152,8 @@ open class View() {
|
||||||
*/
|
*/
|
||||||
fun <T: View> addSubview(view: T): T {
|
fun <T: View> addSubview(view: T): T {
|
||||||
_subviews.add(view)
|
_subviews.add(view)
|
||||||
|
subviewsSortedByZIndex = subviews.sortedBy(View::zIndex)
|
||||||
|
|
||||||
view.superview = this
|
view.superview = this
|
||||||
view.solver = solver
|
view.solver = solver
|
||||||
|
|
||||||
|
@ -151,9 +162,20 @@ open class View() {
|
||||||
return view
|
return view
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Finds all subviews that contain the given point.
|
||||||
|
*
|
||||||
|
* @param point The point to find subviews for, in the coordinate system of this view.
|
||||||
|
* @return All views that contain the given point.
|
||||||
|
*/
|
||||||
|
fun subviewsAtPoint(point: Point): List<View> {
|
||||||
|
return subviews.filter { point in it.frame }
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Attempts to find a subview which contains the given point.
|
* Attempts to find a subview which contains the given point.
|
||||||
* If multiple subviews contain the given point, which one this method returns is undefined.
|
* If multiple subviews contain the given point, which one this method returns is undefined.
|
||||||
|
* [subviewsAtPoint] may be used, and the resulting List sorted by [View.zIndex].
|
||||||
*
|
*
|
||||||
* @param point The point to find a subview for, in the coordinate system of this view.
|
* @param point The point to find a subview for, in the coordinate system of this view.
|
||||||
* @return The view, if any, that contains the given point.
|
* @return The view, if any, that contains the given point.
|
||||||
|
@ -233,7 +255,7 @@ open class View() {
|
||||||
|
|
||||||
drawContent(mouse, delta)
|
drawContent(mouse, delta)
|
||||||
|
|
||||||
subviews.forEach {
|
subviewsSortedByZIndex.forEach {
|
||||||
val mouseInView = convert(mouse, to = it)
|
val mouseInView = convert(mouse, to = it)
|
||||||
it.draw(mouseInView, delta)
|
it.draw(mouseInView, delta)
|
||||||
}
|
}
|
||||||
|
@ -261,7 +283,7 @@ open class View() {
|
||||||
* @return Whether the mouse click was handled by this view or any subviews.
|
* @return Whether the mouse click was handled by this view or any subviews.
|
||||||
*/
|
*/
|
||||||
open fun mouseClicked(point: Point, mouseButton: MouseButton): Boolean {
|
open fun mouseClicked(point: Point, mouseButton: MouseButton): Boolean {
|
||||||
val view = subviewAtPoint(point)
|
val view = subviewsAtPoint(point).maxBy(View::zIndex)
|
||||||
if (view != null) {
|
if (view != null) {
|
||||||
val pointInView = convert(point, to = view)
|
val pointInView = convert(point, to = view)
|
||||||
return view.mouseClicked(pointInView, mouseButton)
|
return view.mouseClicked(pointInView, mouseButton)
|
||||||
|
|
Loading…
Reference in New Issue