So I have the following in my project.
The code for each is as follows:
ContentView
import SwiftUI
import UIKit
struct ContentView: View {
var body: some View {
VStack(alignment: .center, spacing: 0) {
VStack {
Color.blue
.frame(height: 50)
}
VStack {
HStack {
Color.green
.frame(height: 100)
Text("Text")
Color.green
.frame(height: 100)
}
}
VStack { // content view
GeometryReader { geometry in
VStack {
CustomViewRepresentable()
.frame(width: geometry.size.width, height: geometry.size.height)
.background(.gray)
.border(.red, width: 1)
}
.frame(width: geometry.size.width, height: geometry.size.height)
}
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
CustomView
import UIKit
class CustomView: UIView {
private let containerView = UIView()
override func layoutSubviews() {
containerView.center = self.center
}
func addContainerView() {
containerView.frame = CGRect(origin: .zero, size: CGSize(width: 300, height: 300))
addSubview(containerView)
containerView.center = self.center
}
}
CustomViewRepresentable
import UIKit
import SwiftUI
struct CustomViewRepresentable: UIViewRepresentable {
typealias UIViewType = CustomView
func makeUIView(context: Context) -> CustomView {
let customView = CustomView(frame: CGRect(x: 0, y: 0, width: 300, height: 300))
customView.addContainerView()
return customView
}
func updateUIView(_ uiView: CustomView, context: Context) {
}
}
The issue that I'm facing is that the containerView inside CustomView does not display unless I initialise CustomView with a frame inside the representable.
func makeUIView(context: Context) -> CustomView {
let customView = CustomView(frame: CGRect(x: 0, y: 0, width: 300, height: 300))
I don't understand why this is needed because I'd like the CustomView to take the full width and height of the VStack that it is embedded into. Therefore I figured that just doing
CustomViewRepresentable()
.frame(width: geometry.size.width, height: geometry.size.height)
inside the VStack should just work, but apparently it does not. So what is the best way for the CustomViewRepresentable
to fill its parent while keeping the containerView
always centered within it?
No need to provide the CustomView
frame in func makeUIView(context: Context) -> CustomView
function. After replacing let customView = CustomView(frame: CGRect(x: 0, y: 0, width: 300, height: 300))
code with let customView = CustomView()
working at my end. Please check with the code below.
ContenView
import SwiftUI
import UIKit
struct ContentView: View {
var body: some View {
VStack(alignment: .center, spacing: 0) {
VStack {
Color.blue
.frame(height: 50)
}
VStack {
HStack {
Color.green
.frame(height: 100)
Text("Text")
Color.green
.frame(height: 100)
}
}
VStack { // content view
GeometryReader { geometry in
VStack {
CustomViewRepresentable()
.background(.gray)
.border(.red, width: 1)
}
.frame(width: geometry.size.width, height: geometry.size.height)
}
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
CustomView
import UIKit
class CustomView: UIView {
private let containerView = UIView()
override func layoutSubviews() {
containerView.center = self.center
}
func addContainerView() {
containerView.frame = CGRect(origin: .zero, size: CGSize(width: 300, height: 300))
addSubview(containerView)
containerView.center = self.center
}
}
CustomViewRepresentable
import UIKit
import SwiftUI
struct CustomViewRepresentable: UIViewRepresentable {
typealias UIViewType = CustomView
func makeUIView(context: Context) -> CustomView {
let customView = CustomView(frame: CGRect(x: 0, y: 0, width: 300, height: 300))
customView.addContainerView()
return customView
}
func updateUIView(_ uiView: CustomView, context: Context) {
}
}