Hello together,
following issue. I would like to have the UI look like that in landscape mode:
in the middle, there should be a recangle in ratio 4:3. the length should be derived by the available screen height. The space left and right shall have the same size and are VStacks for further use of button elements. So the rectangle is centered to the landscape screen. below you see the code.
import Foundation
import SwiftUI
// MARK: - ScoreboardView
struct ScoreboardView: View {
@Environment(\.horizontalSizeClass) var hSizeClass
@Environment(\.verticalSizeClass) var vSizeClass
// View
var body: some View {
// device orientation: portrait
if hSizeClass == .compact && vSizeClass == .regular {
ScoreboardViewPortrait() // pass SteteObject scoreboard to Portrait view
}
//device orientation: landscape
else {
ScoreboardViewLandscape()
}
}
}
// MARK: - Preview
struct ScoreboardView_Previews: PreviewProvider {
static var previews: some View {
Group {
ScoreboardView()
}
}
}
struct ScoreboardViewPortrait: View {
// View - device orientation: portrait
var body: some View {
Text("Hello World")
}
}
struct ScoreboardViewLandscape: View {
// View - device orientation: landscape
var body: some View {
HStack {
VStack {
Text("Test")
}
GeometryReader { geometry in
ZStack {
// get display sizes
let screenWidth = UIScreen.main.bounds.width
let screenHeigth = UIScreen.main.bounds.height
let screenX = Double(geometry.size.width)
let screenY = Double(geometry.size.height)
let topPadding = 10.0
let bottomPadding = 0.0
// LED-Wall size
let rectY = (screenHeigth+screenY)/2.0-topPadding-bottomPadding
let rectX = 4*rectY/3
// LED-Scoreboard
ZStack {
// Scoreboard background
Rectangle()
.frame(width: rectX, height: rectY)
.opacity(0.1)
.background(LinearGradient(gradient: Gradient(colors: [.white, Color(.red), Color(.blue)]), startPoint: .top, endPoint: .bottom))
// Scoreboard grid ( 4 x 4, ratio 4:3)
ForEach(0..<5) { idx in
Path({ path in
let x = (screenX-rectX)/2 + Double(idx)*rectX/4
path.move(to: CGPoint(x: x, y: topPadding))
path.addLine(to: CGPoint(x: x, y: rectY+topPadding))
path.move(to: CGPoint(x: (screenX-4*rectY/3)/2, y: Double(idx)*rectY/4+topPadding))
path.addLine(to: CGPoint(x: (screenX+4*rectY/3)/2, y: Double(idx)*rectY/4+topPadding))
})
.stroke(Color.black, style: StrokeStyle(lineWidth: 1, dash: [3]))
}
}
//.edgesIgnoringSafeArea(.all)
}
}
VStack{
Text("Test")
}
}
.background(Color.gray)
.edgesIgnoringSafeArea(.all)
}
}
And that’s what the simulator shows to me:
Maybe you recognize the problems:
1.) the text in the left VStack does not appear
2.) rectangle and grid don’t match
The variations of the rectangle and the grid are even bigger, when I uncomment “.edgesIgnoringSafeArea(.all)”. See below
The text in the left Stack shows up, the rectangle goes from top to bottom, the grid looks like it should be. It get’s more interesting, when “bottomPadding=10.0” (get’s a value). But it’s still not what I’m expecting …
Due to the fact, that the rectangle has the same values (rectX, rectY) as the grid and .frame(rectX,rectY) should center it on the available UI space, I can’t explain, why the rectangle and the grid don’t match in any case.
Any explanation or better coding tips are appreciated very much!
Peter