I'm learning Kotlin and Jetpack Compose desktop. I've made a Sudoku solver and am now trying to make it graphical. My window dimensions are 800 X 800. I have 20.dp padding around all sides. My formula for placing the horizontal lines works perfect. I would think it would be the same for the vertical lines but they are offset. I found it interesting that the canvas width and height are less than what I declared the window dimensions to be. I played around with the height of the columns and it always drew the line as desired.
@Composable
fun displayPuzzle(answer: Array<Array<IntArray>>) {
var list = mutableStateListOf<String>()
for (x in answer[0]) list.addAll(x.map { it.toString() })
var columnHeighty by remember { mutableStateOf(0F) }
var columnWidthx by remember { mutableStateOf(0f) }
var pad = 20
LazyVerticalGrid(
columns = GridCells.Fixed(9),
contentPadding = PaddingValues(
start = pad.dp,
top = pad.dp,
end = pad.dp,
bottom = pad.dp
)
) {
items(list.size) { index ->
Card(
backgroundColor = Color.Red,
modifier = Modifier
.fillMaxWidth()
.fillMaxHeight()
.onGloballyPositioned { coordinates ->
columnWidthx = coordinates.size.width.toFloat()
columnHeighty = coordinates.size.height.toFloat()
},
border = BorderStroke(width = 1.dp, color = Color.White)
) {
Text(
text = list[index],
fontWeight = FontWeight.Bold,
fontSize = 30.sp,
color = Color(0xFF000000),
textAlign = TextAlign.Center,
modifier = Modifier.padding(23.dp)
)
}
}
}
Canvas(modifier = Modifier.fillMaxSize()) {
val canvasWidth = size.width
val canvasHeight = size.height
val strokeWidth = 5.0F
println("Canvas Width $canvasWidth")
println("Canvas Height $canvasHeight")
println("Column Width $columnWidthx")
println("Column Height $columnHeighty")
//Draw 1st vertical separator
drawLine(
start = Offset(x = columnWidthx * 3 + pad.toFloat(), y = pad.toFloat()),
end = Offset(x = columnWidthx * 3 + pad.toFloat(), y = canvasHeight - pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw 2nd vertical separator
drawLine(
start = Offset(x = columnWidthx * 6 + pad.toFloat(), y = pad.toFloat()),
end = Offset(x = columnWidthx * 6 + pad.toFloat(), y = canvasHeight - pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw 1st horizontal separator
drawLine(
start = Offset(x = pad.toFloat(), y = columnHeighty * 3 + pad.toFloat()),
end = Offset(x = canvasWidth - pad.toFloat() , y = columnHeighty * 3 + pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw 2nd horizontal seperator
drawLine(
start = Offset(x = pad.toFloat(), y = columnHeighty * 6 + pad.toFloat()),
end = Offset(x = canvasWidth - pad.toFloat() , y = columnHeighty * 6 + pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw top border
drawLine(
start = Offset(x = pad.toFloat(), y = pad.toFloat() + strokeWidth / 2),
end = Offset(x = canvasWidth - pad.toFloat() , y = pad.toFloat() + strokeWidth / 2),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw bottom border
drawLine(
start = Offset(x = pad.toFloat(), y = canvasHeight - pad.toFloat() - strokeWidth / 2),
end = Offset(x = canvasWidth - pad.toFloat() , y = canvasHeight - pad.toFloat() - strokeWidth / 2),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw left border
drawLine(
start = Offset(x = pad.toFloat(), y = pad.toFloat()),
end = Offset(x = pad.toFloat() , y = canvasHeight - pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
//Draw right border
drawLine(
start = Offset(x = canvasWidth - pad.toFloat(), y = pad.toFloat()),
end = Offset(x = canvasWidth - pad.toFloat() , y = canvasHeight - pad.toFloat()),
color = Color.Black,
strokeWidth = strokeWidth
)
}
}
Window(onCloseRequest = ::exitApplication) {
window.minimumSize = Dimension(800,800)
displayPuzzle(finalAnswer[0])
}
I figured out the width of the cells was varying by 1 dp. I used Modifier.requiredWidth and it works as desired.