iyOmSd/Title: SwiftUI

[SwiftUI] Button CornerRadius 효과주기 border, stroke, strokeBorder

냄수 2022. 2. 26. 19:50
반응형

개발하면서 버튼에 라운드를 적용했고 테두리를 주려고하는데
짤림현상이 나타났어요
삽질좀 한 내용을 공유하려고해요

문제가된 코드입니다

func 문제코드() -> some View {
    Button {
        print("버튼 클릭!")
    } label: {
        Text("테두리 있는 버튼")
            .foregroundColor(.pink)
            .frame(width: 200, height: 60)
    }
    .background(.black)
    .border(.pink, width: 2)
    .cornerRadius(8)
}

코드만 보면 전혀 문제가 없어보이지만
실제로 버튼을보면
모서리쪽에 어색한 부분이 있다는걸 느끼실거에요

이러한 문제가있어서 다른방법으로
border를 줘봤지만 다 실패했었어요
(얇은 테두리시 문제 현상 발생해요 두꺼우면 티가안나요)

이때 발견한게 stroke으로도 테두리를 줄 수 있는데
stroke을 사용한 뷰를 사용하면 테두리가 이쁘게 나오더라구요!



그래서
border와 stroke의 차이를 찾아보려다가
storkeBorder라는것도있어서 함께 정리해볼게요

border
View타입에 있는속성이고
선을 그릴때 뷰의 바깥쪽에서부터 그린다고해요
-> Text같은 View에 사용가능

stroke
Shape타입에 있는속성이고
선을 그릴때 center에서부터 그린다고해요
반은 뷰의 안쪽, 반은 뷰의 바깥쪽을 그리는거죠
-> Rectangle같은 Shape에 사용가능

strokeBorder
InsettableShape타입에 있는 속성이고
InsettableShape는 Shape를 채택한 프로토콜이에요
뷰의 안쪽으로 선을 그린다고해요
-> Rectangle같은 Shape에 사용가능

글로 잘 이해가 안가지만 사진을 보면 바로이해가 가요

테두리에 알파값을줘서 뒤의 영역이 보이게끔 구현했어요
검은색영역은 모두 200 * 60으로 같은 크기의 뷰이고 그위에 테두리를 추가한거에요
테두리가 생기는 위치가 다른게 보이죠??


border는 테두리가 뷰 바깥부터 그려지기때문에
strokeBorder와 살짝 비슷해보이면서 약간 다르네요
테두리가 얇을 때 문제가되요 이처럼 내부의 뷰영역을 건들지 않도록 설계되어있네요

stroke는 테두리가 뷰의 반에 걸친게 보이죠
내부도 직각이아니라 둥근 영역처럼 보여지네요!
바깥쪽이 남은건 검은색 뷰에 같은 cornerRadius를 줘서 둥글게 하면 안보이기 때문에 패스!

strokeBorder는 테두리가 뷰의 안쪽에서 그려져서
뷰 내부가 조금 작게보일 수 있는 효과가 있네요
바깥쪽이 남은건 검은색 뷰에 같은 cornerRadius를 줘서 둥글게 하면 안보이기 때문에 패스!


상황에 맞게 잘 골라쓰면 좋을 것 같네요!

struct Test: View {
    var body: some View {
        VStack(spacing: 0) {
            Text("border사용").background(.blue)
            example1()
            Text("stroke사용").background(.blue)
            example2()
            Text("strokeBorder사용").background(.blue)
            example3()
        }
    }
    
    func example1() -> some View {
        Rectangle()
            .frame(width: 200, height: 60)
            .background(.black)
            .border(.pink.opacity(0.5), width: 4)
            .cornerRadius(8)
    }
    
    func example2() -> some View {
        RoundedRectangle(cornerRadius: 8)
            .stroke(.pink.opacity(0.5), lineWidth: 4)
            .frame(width: 200, height: 60)
            .background(.black)
    }
    
    func example3() -> some View {
        RoundedRectangle(cornerRadius: 8)
            .strokeBorder(.pink.opacity(0.5), lineWidth: 4)
            .frame(width: 200, height: 60)
            .background(.black)
    }
}
반응형