Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
//
// ClipEffectUITests.swift
// OpenSwiftUIUITests

import Testing
import SnapshotTesting

@MainActor
@Suite(.snapshots(record: .never, diffTool: diffTool))
struct ClipEffectUITests {
@Test(.disabled("Shape is not implemented correctly"))
func clipShapeCircle() {
struct ContentView: View {
var body: some View {
Color.blue
.frame(width: 100, height: 100)
.clipShape(Circle())
}
}
openSwiftUIAssertSnapshot(of: ContentView())
}

@Test(.disabled("Shape is not implemented correctly"))
func clipShapeRoundedRectangle() {
struct ContentView: View {
var body: some View {
Color.blue
.frame(width: 100, height: 60)
.clipShape(RoundedRectangle(cornerRadius: 15))
}
}
openSwiftUIAssertSnapshot(of: ContentView())
}

@Test(.disabled("Shape is not implemented correctly"))
func clipShapeCapsule() {
struct ContentView: View {
var body: some View {
Color.blue
.frame(width: 100, height: 50)
.clipShape(Capsule())
}
}
openSwiftUIAssertSnapshot(of: ContentView())
}

@Test
func clipped() {
struct ContentView: View {
var body: some View {
Color.blue
.frame(width: 150, height: 150)
.offset(x: 25, y: 25)
.frame(width: 100, height: 100)
.clipped()
.background { Color.red }
}
}
openSwiftUIAssertSnapshot(of: ContentView())
}

@Test(.disabled("Shape is not implemented correctly"))
func clipShapeEllipse() {
struct ContentView: View {
var body: some View {
Color.blue
.frame(width: 100, height: 60)
.clipShape(Ellipse())
}
}
openSwiftUIAssertSnapshot(of: ContentView())
}
}

7 changes: 6 additions & 1 deletion Example/SharedExample/ContentView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,11 @@ import Foundation

struct ContentView: View {
var body: some View {
AsyncImageExample()
Color.blue
.frame(width: 80, height: 60)
.scaleEffect(0.5)
.background { Color.red }
.frame(width: 10, height: 10)
.clipped()
}
}
28 changes: 27 additions & 1 deletion Sources/OpenSwiftUICore/Graphic/GraphicsContext.swift
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,7 @@ package enum PathDrawingStyle {
/// resolution and color scheme --- to resolve types like ``Image`` and
/// ``Color`` that appear in the context. You can also access values stored
/// in the environment for your own purposes.
@available(OpenSwiftUI_v3_0, *)
@frozen
public struct GraphicsContext {
@usableFromInline
Expand Down Expand Up @@ -484,7 +485,32 @@ public struct GraphicsContext {
self.init(rawValue: CGBlendMode.plusLighter.rawValue)
}
}


// MARK: - GraphicsContext.ClipOptions

/// Options that affect the use of clip shapes.
///
/// Use these options to affect how OpenSwiftUI interprets a clip shape
/// when you call ``clip(to:style:options:)`` to add a path to the array of
/// clip shapes, or when you call ``clipToLayer(opacity:options:content:)``
/// to add a clipping layer.
@frozen
public struct ClipOptions: OptionSet {
public let rawValue: UInt32

@inlinable
public init(rawValue: UInt32) {
self.rawValue = rawValue
}

/// An option to invert the shape or layer alpha as the clip mask.
///
/// When you use this option, OpenSwiftUI uses `1 - alpha` instead of
/// `alpha` for the given clip shape.
@inlinable
public static var inverse: ClipOptions { Self(rawValue: 1 << 0) }
}

// FIXME
package enum ResolvedShading: Sendable {
case backdrop(Color.Resolved)
Expand Down
11 changes: 0 additions & 11 deletions Sources/OpenSwiftUICore/Render/DisplayList/DisplayList.swift
Original file line number Diff line number Diff line change
Expand Up @@ -550,17 +550,6 @@ extension DisplayList {

package struct AccessibilityNodeAttachment {}

extension GraphicsContext {
@frozen
public struct ClipOptions: OptionSet {
public let rawValue: UInt32

public init(rawValue: UInt32) {
self.rawValue = rawValue
}
}
}

package protocol _DisplayList_AnyEffectAnimation {}

package struct ResolvedShadowStyle {}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,20 @@
public import Foundation
//
// ClipEffect.swift
// OpenSwiftUICore
//
// Audited for 6.5.4
// Status: Blocked by HoverEffectContent and VisualEffect

public import OpenCoreGraphicsShims

// MARK: - ClipEffect

/// An effect to mask a view by a clip shape.
@available(OpenSwiftUI_v1_0, *)
@frozen
public struct _ClipEffect<ClipShape> where ClipShape: Shape {
public struct _ClipEffect<ClipShape>: RendererEffect where ClipShape: Shape {
public var shape: ClipShape

public var style: FillStyle

@inlinable
Expand All @@ -17,16 +27,18 @@ public struct _ClipEffect<ClipShape> where ClipShape: Shape {
get { shape.animatableData }
set { shape.animatableData = newValue }
}

public typealias AnimatableData = ClipShape.AnimatableData
public typealias Body = Swift.Never
}

// FIXME
extension _ClipEffect: PrimitiveViewModifier {}
package func effectValue(size: CGSize) -> DisplayList.Effect {
.clip(
shape.effectivePath(in: CGRect(origin: .zero, size: size)),
style,
)
}
}

// MARK: - View Extension

@available(OpenSwiftUI_v1_0, *)
extension View {

/// Sets a clipping shape for this view.
Expand Down Expand Up @@ -128,3 +140,7 @@ extension View {
)
}
}

// TODO: HoverEffectContent + clipShape

// TODO: VisualEffect + clipShape
4 changes: 3 additions & 1 deletion Sources/OpenSwiftUICore/Shape/Shape.swift
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,9 @@ extension Shape {

package func effectivePath(in rect: CGRect) -> Path {
// _threadGeometryProxyData
_openSwiftUIUnimplementedFailure()
_openSwiftUIUnimplementedWarning()
let p = path(in: rect)
return p
}
}

Expand Down
Loading