Skip to content

Commit 524a78c

Browse files
committed
fix: Coerce page/line passed to Paginated/Scrollable menus, use onValueChange functions as callbacks
1 parent b8642a2 commit 524a78c

File tree

4 files changed

+32
-14
lines changed

4 files changed

+32
-14
lines changed

guiy-example/src/main/kotlin/com/mineinabyss/guiy/example/gui/PaginatedMenu.kt

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,15 +21,16 @@ fun PaginatedMenu() {
2121
) {
2222
var items by remember {
2323
val materials = Material.entries
24-
mutableStateOf((1..100).map { ItemStack(materials[it]) })
24+
mutableStateOf((1..103).map { ItemStack(materials[it]) })
2525
}
2626
var page by remember { mutableStateOf(0) }
2727
Paginated(
2828
items,
2929
page = page,
30+
onPageChange = { page = it },
3031
navbarPosition = NavbarPosition.END,
31-
previousButton = { Item(Material.RED_CONCRETE, "Previous", modifier = Modifier.clickable { page-- }) },
32-
nextButton = { Item(Material.BLUE_CONCRETE, "Next", modifier = Modifier.clickable { page++ }) },
32+
previousButton = { Item(Material.RED_CONCRETE, "Previous") },
33+
nextButton = { Item(Material.BLUE_CONCRETE, "Next") },
3334
) { pageItems ->
3435
HorizontalGrid(Modifier.size(4, 5)) {
3536
pageItems.forEach { item ->

guiy-example/src/main/kotlin/com/mineinabyss/guiy/example/gui/ScrollingMenu.kt

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,10 +27,11 @@ fun ScrollingMenu() {
2727
Scrollable(
2828
items,
2929
line = line,
30+
onLineChange = { line = it },
3031
scrollDirection = ScrollDirection.VERTICAL,
3132
navbarPosition = NavbarPosition.END,
32-
previousButton = { Item(Material.RED_CONCRETE, "Previous", modifier = Modifier.clickable { line-- }) },
33-
nextButton = { Item(Material.BLUE_CONCRETE, "Next", modifier = Modifier.clickable { line++ }) },
33+
previousButton = { Item(Material.RED_CONCRETE, "Previous") },
34+
nextButton = { Item(Material.BLUE_CONCRETE, "Next") },
3435
) { pageItems ->
3536
VerticalGrid(Modifier.fillMaxSize()) {
3637
pageItems.forEach { item ->

src/main/kotlin/com/mineinabyss/guiy/components/lists/Paginated.kt

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import com.mineinabyss.guiy.layout.Column
1010
import com.mineinabyss.guiy.layout.Row
1111
import com.mineinabyss.guiy.layout.Size
1212
import com.mineinabyss.guiy.modifiers.*
13+
import com.mineinabyss.guiy.modifiers.click.clickable
1314
import com.mineinabyss.guiy.modifiers.placement.padding.padding
1415
import com.mineinabyss.idofront.items.editItemMeta
1516
import org.bukkit.Material
@@ -24,6 +25,7 @@ import org.bukkit.inventory.ItemStack
2425
fun <T> Paginated(
2526
items: List<T>,
2627
page: Int,
28+
onPageChange: (page: Int) -> Unit,
2729
nextButton: @Composable () -> Unit,
2830
previousButton: @Composable () -> Unit,
2931
navbarPosition: NavbarPosition = NavbarPosition.BOTTOM,
@@ -36,20 +38,26 @@ fun <T> Paginated(
3638
) {
3739
var size by remember { mutableStateOf(Size(0, 0)) }
3840
val itemsPerPage = size.width * size.height
41+
val pageCount = if (itemsPerPage == 0) 1 else (-((-items.size).floorDiv(itemsPerPage))).coerceAtLeast(1)
42+
val coercedPage = page.coerceIn(0, pageCount - 1)
3943
Box(Modifier.fillMaxSize()) {
40-
val start = page * itemsPerPage
41-
val end = (page + 1) * itemsPerPage
44+
val start = coercedPage * itemsPerPage
45+
val end = (coercedPage + 1) * itemsPerPage
4246
val pageItems = remember(items, start, end) {
43-
if (start < 0) emptyList()
47+
if (start < 0 || start >= items.size) emptyList()
4448
else items.subList(start, end.coerceAtMost(items.size))
4549
}
4650
NavbarLayout(
4751
position = navbarPosition,
4852
navbar = {
4953
NavbarButtons(navbarPosition, navbarBackground) {
50-
if (page > 0) previousButton()
54+
if (coercedPage > 0) Box(Modifier.clickable { onPageChange(coercedPage - 1) }) {
55+
previousButton()
56+
}
5157
else Spacer(1, 1)
52-
if (end < items.size) nextButton()
58+
if (end < items.size) Box(Modifier.clickable { onPageChange(coercedPage + 1) }) {
59+
nextButton()
60+
}
5361
else Spacer(1, 1)
5462
}
5563
},

src/main/kotlin/com/mineinabyss/guiy/components/lists/Scrollable.kt

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import com.mineinabyss.guiy.components.Spacer
55
import com.mineinabyss.guiy.layout.Box
66
import com.mineinabyss.guiy.layout.Size
77
import com.mineinabyss.guiy.modifiers.Modifier
8+
import com.mineinabyss.guiy.modifiers.click.clickable
89
import com.mineinabyss.guiy.modifiers.fillMaxSize
910
import com.mineinabyss.guiy.modifiers.onSizeChanged
1011
import com.mineinabyss.idofront.items.editItemMeta
@@ -24,6 +25,7 @@ enum class ScrollDirection {
2425
fun <T> Scrollable(
2526
items: List<T>,
2627
line: Int,
28+
onLineChange: (line: Int) -> Unit,
2729
scrollDirection: ScrollDirection,
2830
nextButton: @Composable () -> Unit,
2931
previousButton: @Composable () -> Unit,
@@ -38,20 +40,26 @@ fun <T> Scrollable(
3840
var size by remember { mutableStateOf(Size(0, 0)) }
3941
val itemsPerLine = if (scrollDirection == ScrollDirection.VERTICAL) size.width else size.height
4042
val totalLines = if (scrollDirection == ScrollDirection.VERTICAL) size.height else size.width
43+
val lineCount = if(itemsPerLine == 0) 1 else (-((-items.size).floorDiv(itemsPerLine))).coerceAtLeast(1)
44+
val coercedLine = line.coerceIn(0, lineCount - 1)
4145
Box(Modifier.fillMaxSize()) {
42-
val start = line * itemsPerLine
46+
val start = coercedLine * itemsPerLine
4347
val end = start + (itemsPerLine * totalLines)
4448
val pageItems = remember(items, start, end) {
45-
if (start < 0) emptyList()
49+
if (start < 0 || start >= items.size) emptyList()
4650
else items.subList(start, end.coerceAtMost(items.size))
4751
}
4852
NavbarLayout(
4953
position = navbarPosition,
5054
navbar = {
5155
NavbarButtons(navbarPosition, navbarBackground) {
52-
if (line > 0) previousButton()
56+
if (coercedLine > 0) Box(Modifier.clickable { onLineChange(coercedLine - 1) }) {
57+
previousButton()
58+
}
5359
else Spacer(1, 1)
54-
if (end < items.size) nextButton()
60+
if (end < items.size) Box(Modifier.clickable { onLineChange(coercedLine + 1) }) {
61+
nextButton()
62+
}
5563
else Spacer(1, 1)
5664
}
5765
},

0 commit comments

Comments
 (0)