Skip to content

Commit

Permalink
@MetalBuffer -> name, type
Browse files Browse the repository at this point in the history
  • Loading branch information
gadirom committed Jul 28, 2022
1 parent 8f94829 commit 94a9267
Show file tree
Hide file tree
Showing 6 changed files with 106 additions and 21 deletions.
23 changes: 10 additions & 13 deletions Example/Example/Example/ContentView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -50,8 +50,12 @@ struct ContentView: View {
@MetalState var dilateSize = 3
@MetalState var laplacianBias: Float = 0.5

@MetalBuffer<Particle>(count: particleCount) var particlesBuffer
@MetalBuffer<Vertex>(count: particleCount*3) var vertexBuffer
@MetalBuffer<Particle>(count: particleCount,
metalType: "Particle",
metalName: "particles") var particlesBuffer
@MetalBuffer<Vertex>(count: particleCount*3,
metalType: "Vertex",
metalName: "vertices") var vertexBuffer

@MetalState var vertexCount = 3 * particleCount
@MetalState var particleScale: Float = 1
Expand All @@ -64,14 +68,8 @@ struct ContentView: View {
VStack{
MetalBuilderView(librarySource: metalFunctions, isDrawing: $isDrawing){ viewportSize in
Compute("particleFunction")
.buffer(particlesBuffer, offset: 0,
argument: .init(space: "device", type: "Particle",
name: "particles",
index: 0))
.buffer(vertexBuffer, offset: 0,
argument: .init(space: "device", type: "Vertex",
name: "vertices",
index: 1))
.buffer(particlesBuffer, offset: 0, space: "device")
.buffer(vertexBuffer, offset: 0, space: "device")
.bytes(viewportSize,
argument: .init(space: "constant", type: "uint2",
name: "viewport", index: 2))
Expand All @@ -82,9 +80,7 @@ struct ContentView: View {
//.grid(size: $mSize)
Render(vertex: "vertexShader", fragment: "fragmentShader")
.toTexture(targetTexture)
.vertexBuf(vertexBuffer, offset: 0,
argument: .init(space: "constant", type: "Vertex",
name: "vertices", index: 0))
.vertexBuf(vertexBuffer, offset: 0)
.vertexBytes(viewportSize,
argument: .init(space: "constant", type: "uint2",
name: "viewport", index: 2))
Expand All @@ -94,6 +90,7 @@ struct ContentView: View {
l.bias = laplacianBias
l.encode(commandBuffer: commandBuffer, inPlaceTexture: &(targetTexture.texture!), fallbackCopyAllocator: copyAllocator)
}
//Seems that Laplacian can't be modified through superclass init!
// MPSUnary{MPSImageLaplacian(device: $0)}
// .source(targetTexture)
// .value($laplacianBias, for: "bias")
Expand Down
4 changes: 4 additions & 0 deletions Sources/MetalBuilder/MetalResultBuilder.swift
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,7 @@ public enum MetalResultBuilder{
}

public typealias MetalBuilderResult = [MetalBuilderComponent]

enum MetalBuilderResultBuilderError: Error {
case bufferArgumentError(String), textureArgumentError(String)
}
31 changes: 31 additions & 0 deletions Sources/MetalBuilder/Parser/MetalFunctionArgument.swift
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,37 @@ public struct MetalBufferArgument{
self.name = name
self.index = index
}
public init<T>(_ container: MTLBufferContainer<T>,
space: String, type: String?=nil, name: String?=nil, index: Int) throws{

var t: String?
if let type = container.metalType{
t = type
}
if let type = type{
t = type
}
guard let type = t
else {
throw MetalBuilderResultBuilderError
.bufferArgumentError("No Metal type for buffer!")
}

var n: String?
if let name = container.metalName{
n = name
}
if let name = name{
n = name
}
guard let name = n
else {
throw MetalBuilderResultBuilderError
.bufferArgumentError("No Metal name for buffer!")
}

self.init(space: space, type: type, name: name, index: index)
}
}

public struct MetalBytesArgument{
Expand Down
22 changes: 18 additions & 4 deletions Sources/MetalBuilder/PropertyWrappers/MetalBuffer.swift
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@
import SwiftUI
import MetalKit

/// Declares an MTLBufferContainer state
///
/// metalType and metalName - supposed type and name for the buffer in MSL code
@propertyWrapper
public final class MetalBuffer<T>{
public var wrappedValue: MTLBufferContainer<T>
Expand All @@ -10,8 +13,8 @@ public final class MetalBuffer<T>{
self.wrappedValue = wrappedValue
}

public init(count: Int){
self.wrappedValue = MTLBufferContainer<T>(count: count)
public init(count: Int, metalType: String? = nil, metalName: String? = nil){
self.wrappedValue = MTLBufferContainer<T>(count: count, metalType: metalType, metalName: metalName)
}
}

Expand All @@ -20,17 +23,28 @@ case bufferNotCreated
}

public class BufferContainer{

var buffer: MTLBuffer?

public let count: Int
public var elementSize: Int?

init(count: Int) {
public var metalType: String?
public var metalName: String?

init(count: Int, metalType: String? = nil, metalName: String? = nil) {
self.count = count

self.metalType = metalType
self.metalName = metalName
}
}

/// Container class for MTLBuffer
///
/// You can access it's content on CPU through 'pointer'
public final class MTLBufferContainer<T>: BufferContainer{
//public var buffer: MTLBuffer?

public var pointer: UnsafeMutablePointer<T>?

func create(device: MTLDevice) throws{
Expand Down
22 changes: 20 additions & 2 deletions Sources/MetalBuilder/ResultBuilderComponents/Compute.swift
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,9 @@ public struct Compute: MetalBuilderComponent{

var kernelArguments: [MetalFunctionArgument] = []

var bufferIndexCounter = 0
var TextureIndexCounter = 0

public init(_ kernel: String){
self.kernel = kernel
}
Expand All @@ -42,19 +45,28 @@ public struct Compute: MetalBuilderComponent{

// chaining functions for result builder
public extension Compute{
func buffer<T>(_ container: MTLBufferContainer<T>, offset: Int, index: Int)->Compute{
func buffer<T>(_ container: MTLBufferContainer<T>, offset: Int = 0, index: Int)->Compute{
var c = self
let buf = Buffer(container: container, offset: offset, index: index)
c.buffers.append(buf)
return c
}
func buffer<T>(_ container: MTLBufferContainer<T>, offset: Int, argument: MetalBufferArgument)->Compute{
func buffer<T>(_ container: MTLBufferContainer<T>, offset: Int = 0, argument: MetalBufferArgument)->Compute{
var c = self
c.kernelArguments.append(.buffer(argument))
let buf = Buffer(container: container, offset: offset, index: argument.index)
c.buffers.append(buf)
return c
}
func buffer<T>(_ container: MTLBufferContainer<T>, offset: Int = 0,
space: String, type: String?=nil, name: String?=nil) -> Compute{

let argument = try! MetalBufferArgument(container, space: space, type: type, name: name, index: bufferIndexCounter)

var c = self.buffer(container, offset: offset, argument: argument)
c.bufferIndexCounter += 1
return c
}
func bytes<T>(_ binding: Binding<T>, index: Int)->Compute{
var c = self
let bytes = Bytes(binding: binding, index: index)
Expand Down Expand Up @@ -86,6 +98,12 @@ public extension Compute{
c.drawableTextureIndex = index
return c
}
func drawableTexture(argument: MetalTextureArgument)->Compute{
var c = self
c.kernelArguments.append(.texture(argument))
c.drawableTextureIndex = argument.index
return c
}
func grid(size: Binding<MTLSize>)->Compute{
var c = self
c.gridFit = .size(size)
Expand Down
25 changes: 23 additions & 2 deletions Sources/MetalBuilder/ResultBuilderComponents/Render.swift
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,9 @@ public struct Render: MetalBuilderComponent{

var vertexArguments: [MetalFunctionArgument] = []
var fragmentArguments: [MetalFunctionArgument] = []

var vertexBufferCounter = 0
var fragmentBufferCounter = 0
public init(vertex: String, fragment: String, type: MTLPrimitiveType = .triangle, start: Int = 0, count: Int = 3){
self.vertexFunc = vertex
self.fragmentFunc = fragment
Expand All @@ -83,19 +86,28 @@ public extension Render{
r.vertexCount = count
return r
}
func vertexBuf<T>(_ container: MTLBufferContainer<T>, offset: Int, index: Int)->Render{
func vertexBuf<T>(_ container: MTLBufferContainer<T>, offset: Int = 0, index: Int)->Render{
var r = self
let buf = Buffer(container: container, offset: offset, index: index)
r.vertexBufs.append(buf)
return r
}
func vertexBuf<T>(_ container: MTLBufferContainer<T>, offset: Int, argument: MetalBufferArgument)->Render{
func vertexBuf<T>(_ container: MTLBufferContainer<T>, offset: Int = 0, argument: MetalBufferArgument)->Render{
var r = self
r.vertexArguments.append(MetalFunctionArgument.buffer(argument))
let buf = Buffer(container: container, offset: offset, index: argument.index)
r.vertexBufs.append(buf)
return r
}
func vertexBuf<T>(_ container: MTLBufferContainer<T>, offset: Int = 0,
space: String = "constant", type: String?=nil, name: String?=nil) -> Render{

let argument = try! MetalBufferArgument(container, space: space, type: type, name: name, index: vertexBufferCounter)

var r = self.vertexBuf(container, offset: offset, argument: argument)
r.vertexBufferCounter += 1
return r
}
func fragBuf<T>(_ container: MTLBufferContainer<T>, offset: Int, index: Int)->Render{
var r = self
let buf = Buffer(container: container, offset: offset, index: index)
Expand All @@ -109,6 +121,15 @@ public extension Render{
r.fragBufs.append(buf)
return r
}
func fragBuf<T>(_ container: MTLBufferContainer<T>, offset: Int = 0,
space: String, type: String?=nil, name: String?=nil) -> Render{

let argument = try! MetalBufferArgument(container, space: space, type: type, name: name, index: fragmentBufferCounter)

var r = self.fragBuf(container, offset: offset, argument: argument)
r.fragmentBufferCounter += 1
return r
}
func vertexBytes<T>(_ binding: Binding<T>, index: Int)->Render{
var r = self
let bytes = Bytes(binding: binding, index: index)
Expand Down

0 comments on commit 94a9267

Please sign in to comment.