mirror of
https://github.com/PixarAnimationStudios/OpenSubdiv
synced 2024-11-09 13:50:05 +00:00
Merge pull request #1320 from davidgyu/dev_osd_patch_drawing_compatibilty
Improved osd patch drawing compatibility
This commit is contained in:
commit
3597371f84
@ -22,101 +22,11 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
//
|
// The following callback functions are used when evaluating tessellation
|
||||||
// typical shader composition ordering (see glDrawRegistry:_CompileShader)
|
// rates and when using legacy patch drawing.
|
||||||
//
|
|
||||||
//
|
|
||||||
// - glsl version string (#version 430)
|
|
||||||
//
|
|
||||||
// - common defines (#define OSD_ENABLE_PATCH_CULL, ...)
|
|
||||||
// - source defines (#define VERTEX_SHADER, ...)
|
|
||||||
//
|
|
||||||
// - osd headers (glslPatchCommon: varying structs,
|
|
||||||
// glslPtexCommon: ptex functions)
|
|
||||||
// - client header (Osd*Matrix(), displacement callback, ...)
|
|
||||||
//
|
|
||||||
// - osd shader source (glslPatchBSpline, glslPatchGregory, ...)
|
|
||||||
// or
|
|
||||||
// client shader source (vertex/geometry/fragment shader)
|
|
||||||
//
|
|
||||||
|
|
||||||
//----------------------------------------------------------
|
|
||||||
// Patches.Common
|
|
||||||
//----------------------------------------------------------
|
|
||||||
|
|
||||||
// XXXdyu all handling of varying data can be managed by client code
|
|
||||||
#ifndef OSD_USER_VARYING_DECLARE
|
|
||||||
#define OSD_USER_VARYING_DECLARE
|
|
||||||
// type var;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_USER_VARYING_ATTRIBUTE_DECLARE
|
|
||||||
#define OSD_USER_VARYING_ATTRIBUTE_DECLARE
|
|
||||||
// layout(location = loc) in type var;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_USER_VARYING_PER_VERTEX
|
|
||||||
#define OSD_USER_VARYING_PER_VERTEX()
|
|
||||||
// output.var = var;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_USER_VARYING_PER_CONTROL_POINT
|
|
||||||
#define OSD_USER_VARYING_PER_CONTROL_POINT(ID_OUT, ID_IN)
|
|
||||||
// output[ID_OUT].var = input[ID_IN].var
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_USER_VARYING_PER_EVAL_POINT
|
|
||||||
#define OSD_USER_VARYING_PER_EVAL_POINT(UV, a, b, c, d)
|
|
||||||
// output.var =
|
|
||||||
// mix(mix(input[a].var, input[b].var, UV.x),
|
|
||||||
// mix(input[c].var, input[d].var, UV.x), UV.y)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_USER_VARYING_PER_EVAL_POINT_TRIANGLE
|
|
||||||
#define OSD_USER_VARYING_PER_EVAL_POINT_TRIANGLE(UV, a, b, c)
|
|
||||||
// output.var =
|
|
||||||
// input[a].var * (1.0f-UV.x-UV.y) +
|
|
||||||
// input[b].var * UV.x +
|
|
||||||
// input[c].var * UV.y;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if __VERSION__ < 420
|
|
||||||
#define centroid
|
|
||||||
#endif
|
|
||||||
|
|
||||||
struct ControlVertex {
|
|
||||||
vec4 position;
|
|
||||||
#ifdef OSD_ENABLE_PATCH_CULL
|
|
||||||
ivec3 clipFlag;
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
// XXXdyu all downstream data can be handled by client code
|
|
||||||
struct OutputVertex {
|
|
||||||
vec4 position;
|
|
||||||
vec3 normal;
|
|
||||||
vec3 tangent;
|
|
||||||
vec3 bitangent;
|
|
||||||
vec4 patchCoord; // u, v, faceLevel, faceId
|
|
||||||
vec2 tessCoord; // tesscoord.st
|
|
||||||
#if defined OSD_COMPUTE_NORMAL_DERIVATIVES
|
|
||||||
vec3 Nu;
|
|
||||||
vec3 Nv;
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
// osd shaders need following functions defined
|
|
||||||
mat4 OsdModelViewMatrix();
|
mat4 OsdModelViewMatrix();
|
||||||
mat4 OsdProjectionMatrix();
|
mat4 OsdProjectionMatrix();
|
||||||
mat4 OsdModelViewProjectionMatrix();
|
|
||||||
float OsdTessLevel();
|
float OsdTessLevel();
|
||||||
int OsdGregoryQuadOffsetBase();
|
|
||||||
int OsdPrimitiveIdBase();
|
|
||||||
int OsdBaseVertex();
|
|
||||||
|
|
||||||
#ifndef OSD_DISPLACEMENT_CALLBACK
|
|
||||||
#define OSD_DISPLACEMENT_CALLBACK
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Patch Parameters
|
// Patch Parameters
|
||||||
@ -130,22 +40,6 @@ int OsdBaseVertex();
|
|||||||
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
||||||
// sharpness -- crease sharpness for single-crease patches
|
// sharpness -- crease sharpness for single-crease patches
|
||||||
//
|
//
|
||||||
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
|
||||||
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
|
||||||
// along with an optional client provided offset.
|
|
||||||
//
|
|
||||||
|
|
||||||
uniform isamplerBuffer OsdPatchParamBuffer;
|
|
||||||
|
|
||||||
int OsdGetPatchIndex(int primitiveId)
|
|
||||||
{
|
|
||||||
return (primitiveId + OsdPrimitiveIdBase());
|
|
||||||
}
|
|
||||||
|
|
||||||
ivec3 OsdGetPatchParam(int patchIndex)
|
|
||||||
{
|
|
||||||
return texelFetch(OsdPatchParamBuffer, patchIndex).xyz;
|
|
||||||
}
|
|
||||||
|
|
||||||
int OsdGetPatchFaceId(ivec3 patchParam)
|
int OsdGetPatchFaceId(ivec3 patchParam)
|
||||||
{
|
{
|
||||||
@ -239,38 +133,6 @@ vec4 OsdInterpolatePatchCoordTriangle(vec2 localUV, ivec3 patchParam)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// patch culling
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
#ifdef OSD_ENABLE_PATCH_CULL
|
|
||||||
|
|
||||||
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P) \
|
|
||||||
vec4 clipPos = OsdModelViewProjectionMatrix() * P; \
|
|
||||||
bvec3 clip0 = lessThan(clipPos.xyz, vec3(clipPos.w)); \
|
|
||||||
bvec3 clip1 = greaterThan(clipPos.xyz, -vec3(clipPos.w)); \
|
|
||||||
outpt.v.clipFlag = ivec3(clip0) + 2*ivec3(clip1); \
|
|
||||||
|
|
||||||
#define OSD_PATCH_CULL(N) \
|
|
||||||
ivec3 clipFlag = ivec3(0); \
|
|
||||||
for(int i = 0; i < N; ++i) { \
|
|
||||||
clipFlag |= inpt[i].v.clipFlag; \
|
|
||||||
} \
|
|
||||||
if (clipFlag != ivec3(3) ) { \
|
|
||||||
gl_TessLevelInner[0] = 0; \
|
|
||||||
gl_TessLevelInner[1] = 0; \
|
|
||||||
gl_TessLevelOuter[0] = 0; \
|
|
||||||
gl_TessLevelOuter[1] = 0; \
|
|
||||||
gl_TessLevelOuter[2] = 0; \
|
|
||||||
gl_TessLevelOuter[3] = 0; \
|
|
||||||
return; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P)
|
|
||||||
#define OSD_PATCH_CULL(N)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -582,7 +444,7 @@ OsdFlipMatrix(mat4 m)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Regular BSpline to Bezier
|
// Regular BSpline to Bezier
|
||||||
uniform mat4 Q = mat4(
|
const mat4 Q = mat4(
|
||||||
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
||||||
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
||||||
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
||||||
@ -590,7 +452,7 @@ uniform mat4 Q = mat4(
|
|||||||
);
|
);
|
||||||
|
|
||||||
// Infinitely Sharp (boundary)
|
// Infinitely Sharp (boundary)
|
||||||
uniform mat4 Mi = mat4(
|
const mat4 Mi = mat4(
|
||||||
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
||||||
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
||||||
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
||||||
|
@ -22,6 +22,128 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
|
//----------------------------------------------------------
|
||||||
|
// Patches.Common
|
||||||
|
//----------------------------------------------------------
|
||||||
|
|
||||||
|
// XXXdyu all handling of varying data can be managed by client code
|
||||||
|
#ifndef OSD_USER_VARYING_DECLARE
|
||||||
|
#define OSD_USER_VARYING_DECLARE
|
||||||
|
// type var;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef OSD_USER_VARYING_ATTRIBUTE_DECLARE
|
||||||
|
#define OSD_USER_VARYING_ATTRIBUTE_DECLARE
|
||||||
|
// layout(location = loc) in type var;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef OSD_USER_VARYING_PER_VERTEX
|
||||||
|
#define OSD_USER_VARYING_PER_VERTEX()
|
||||||
|
// output.var = var;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef OSD_USER_VARYING_PER_CONTROL_POINT
|
||||||
|
#define OSD_USER_VARYING_PER_CONTROL_POINT(ID_OUT, ID_IN)
|
||||||
|
// output[ID_OUT].var = input[ID_IN].var
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef OSD_USER_VARYING_PER_EVAL_POINT
|
||||||
|
#define OSD_USER_VARYING_PER_EVAL_POINT(UV, a, b, c, d)
|
||||||
|
// output.var =
|
||||||
|
// mix(mix(input[a].var, input[b].var, UV.x),
|
||||||
|
// mix(input[c].var, input[d].var, UV.x), UV.y)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef OSD_USER_VARYING_PER_EVAL_POINT_TRIANGLE
|
||||||
|
#define OSD_USER_VARYING_PER_EVAL_POINT_TRIANGLE(UV, a, b, c)
|
||||||
|
// output.var =
|
||||||
|
// input[a].var * (1.0f-UV.x-UV.y) +
|
||||||
|
// input[b].var * UV.x +
|
||||||
|
// input[c].var * UV.y;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if __VERSION__ < 420
|
||||||
|
#define centroid
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct ControlVertex {
|
||||||
|
vec4 position;
|
||||||
|
#ifdef OSD_ENABLE_PATCH_CULL
|
||||||
|
ivec3 clipFlag;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
// XXXdyu all downstream data can be handled by client code
|
||||||
|
struct OutputVertex {
|
||||||
|
vec4 position;
|
||||||
|
vec3 normal;
|
||||||
|
vec3 tangent;
|
||||||
|
vec3 bitangent;
|
||||||
|
vec4 patchCoord; // u, v, faceLevel, faceId
|
||||||
|
vec2 tessCoord; // tesscoord.st
|
||||||
|
#if defined OSD_COMPUTE_NORMAL_DERIVATIVES
|
||||||
|
vec3 Nu;
|
||||||
|
vec3 Nv;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
mat4 OsdModelViewProjectionMatrix();
|
||||||
|
int OsdGregoryQuadOffsetBase();
|
||||||
|
int OsdPrimitiveIdBase();
|
||||||
|
int OsdBaseVertex();
|
||||||
|
|
||||||
|
#ifndef OSD_DISPLACEMENT_CALLBACK
|
||||||
|
#define OSD_DISPLACEMENT_CALLBACK
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
||||||
|
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
||||||
|
// along with an optional client provided offset.
|
||||||
|
|
||||||
|
uniform isamplerBuffer OsdPatchParamBuffer;
|
||||||
|
|
||||||
|
int OsdGetPatchIndex(int primitiveId)
|
||||||
|
{
|
||||||
|
return (primitiveId + OsdPrimitiveIdBase());
|
||||||
|
}
|
||||||
|
|
||||||
|
ivec3 OsdGetPatchParam(int patchIndex)
|
||||||
|
{
|
||||||
|
return texelFetch(OsdPatchParamBuffer, patchIndex).xyz;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
// patch culling
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#ifdef OSD_ENABLE_PATCH_CULL
|
||||||
|
|
||||||
|
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P) \
|
||||||
|
vec4 clipPos = OsdModelViewProjectionMatrix() * P; \
|
||||||
|
bvec3 clip0 = lessThan(clipPos.xyz, vec3(clipPos.w)); \
|
||||||
|
bvec3 clip1 = greaterThan(clipPos.xyz, -vec3(clipPos.w)); \
|
||||||
|
outpt.v.clipFlag = ivec3(clip0) + 2*ivec3(clip1); \
|
||||||
|
|
||||||
|
#define OSD_PATCH_CULL(N) \
|
||||||
|
ivec3 clipFlag = ivec3(0); \
|
||||||
|
for(int i = 0; i < N; ++i) { \
|
||||||
|
clipFlag |= inpt[i].v.clipFlag; \
|
||||||
|
} \
|
||||||
|
if (clipFlag != ivec3(3) ) { \
|
||||||
|
gl_TessLevelInner[0] = 0; \
|
||||||
|
gl_TessLevelInner[1] = 0; \
|
||||||
|
gl_TessLevelOuter[0] = 0; \
|
||||||
|
gl_TessLevelOuter[1] = 0; \
|
||||||
|
gl_TessLevelOuter[2] = 0; \
|
||||||
|
gl_TessLevelOuter[3] = 0; \
|
||||||
|
return; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#else
|
||||||
|
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P)
|
||||||
|
#define OSD_PATCH_CULL(N)
|
||||||
|
#endif
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Legacy Gregory
|
// Legacy Gregory
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
@ -67,10 +67,18 @@ static const char *gregoryTriangleShaderSource =
|
|||||||
|
|
||||||
/*static*/
|
/*static*/
|
||||||
std::string
|
std::string
|
||||||
GLSLPatchShaderSource::GetCommonShaderSource() {
|
GLSLPatchShaderSource::GetPatchDrawingShaderSource() {
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss << std::string(commonShaderSource);
|
ss << std::string(commonShaderSource);
|
||||||
ss << std::string(commonTessShaderSource);
|
ss << std::string(commonTessShaderSource);
|
||||||
|
return ss.str();
|
||||||
|
}
|
||||||
|
|
||||||
|
/*static*/
|
||||||
|
std::string
|
||||||
|
GLSLPatchShaderSource::GetCommonShaderSource() {
|
||||||
|
std::stringstream ss;
|
||||||
|
ss << GetPatchDrawingShaderSource();
|
||||||
ss << std::string(patchLegacyShaderSource);
|
ss << std::string(patchLegacyShaderSource);
|
||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
@ -26,20 +26,39 @@
|
|||||||
#define OPENSUBDIV3_OSD_GLSL_PATCH_SHADER_SOURCE_H
|
#define OPENSUBDIV3_OSD_GLSL_PATCH_SHADER_SOURCE_H
|
||||||
|
|
||||||
#include "../version.h"
|
#include "../version.h"
|
||||||
#include <string>
|
|
||||||
#include "../far/patchDescriptor.h"
|
#include "../far/patchDescriptor.h"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
namespace OpenSubdiv {
|
namespace OpenSubdiv {
|
||||||
namespace OPENSUBDIV_VERSION {
|
namespace OPENSUBDIV_VERSION {
|
||||||
|
|
||||||
namespace Osd {
|
namespace Osd {
|
||||||
|
|
||||||
|
/// \brief Provides shader source which can be used by client code.
|
||||||
class GLSLPatchShaderSource {
|
class GLSLPatchShaderSource {
|
||||||
public:
|
public:
|
||||||
static std::string GetCommonShaderSource();
|
/// \brief Returns shader source which can be used to evaluate
|
||||||
|
/// position and first and second derivatives on piecewise parametric
|
||||||
|
/// patches resulting from subdivision refinement.
|
||||||
static std::string GetPatchBasisShaderSource();
|
static std::string GetPatchBasisShaderSource();
|
||||||
|
|
||||||
|
/// \brief Returns shader source which can be used while drawing
|
||||||
|
/// piecewise parametric patches resulting from subdivision refinement,
|
||||||
|
/// e.g. while using GPU HW tessellation.
|
||||||
|
static std::string GetPatchDrawingShaderSource();
|
||||||
|
|
||||||
|
/// \name Alternative methods
|
||||||
|
/// \{
|
||||||
|
/// These methods return shader source which can be used
|
||||||
|
/// while drawing. Unlike the methods above, the source returned
|
||||||
|
/// by these methods includes support for legacy patch types along
|
||||||
|
/// with dependencies on specific resource bindings and interstage
|
||||||
|
/// shader variable declarations.
|
||||||
|
|
||||||
|
static std::string GetCommonShaderSource();
|
||||||
|
|
||||||
static std::string GetVertexShaderSource(
|
static std::string GetVertexShaderSource(
|
||||||
Far::PatchDescriptor::Type type);
|
Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
@ -48,6 +67,8 @@ public:
|
|||||||
|
|
||||||
static std::string GetTessEvalShaderSource(
|
static std::string GetTessEvalShaderSource(
|
||||||
Far::PatchDescriptor::Type type);
|
Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
|
/// \}
|
||||||
};
|
};
|
||||||
|
|
||||||
} // end namespace Osd
|
} // end namespace Osd
|
||||||
|
@ -22,52 +22,11 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
//----------------------------------------------------------
|
// The following callback functions are used when evaluating tessellation
|
||||||
// Patches.Common
|
// rates and when using legacy patch drawing.
|
||||||
//----------------------------------------------------------
|
|
||||||
|
|
||||||
struct InputVertex {
|
|
||||||
float4 position : POSITION;
|
|
||||||
float3 normal : NORMAL;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct HullVertex {
|
|
||||||
float4 position : POSITION;
|
|
||||||
#ifdef OSD_ENABLE_PATCH_CULL
|
|
||||||
int3 clipFlag : CLIPFLAG;
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
// XXXdyu all downstream data can be handled by client code
|
|
||||||
struct OutputVertex {
|
|
||||||
float4 positionOut : SV_Position;
|
|
||||||
float4 position : POSITION1;
|
|
||||||
float3 normal : NORMAL;
|
|
||||||
float3 tangent : TANGENT;
|
|
||||||
float3 bitangent : TANGENT1;
|
|
||||||
float4 patchCoord : PATCHCOORD; // u, v, faceLevel, faceId
|
|
||||||
noperspective float4 edgeDistance : EDGEDISTANCE;
|
|
||||||
#if defined(OSD_COMPUTE_NORMAL_DERIVATIVES)
|
|
||||||
float3 Nu : TANGENT2;
|
|
||||||
float3 Nv : TANGENT3;
|
|
||||||
#endif
|
|
||||||
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
float2 vSegments : VSEGMENTS;
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
// osd shaders need following functions defined
|
|
||||||
float4x4 OsdModelViewMatrix();
|
float4x4 OsdModelViewMatrix();
|
||||||
float4x4 OsdProjectionMatrix();
|
float4x4 OsdProjectionMatrix();
|
||||||
float4x4 OsdModelViewProjectionMatrix();
|
|
||||||
float OsdTessLevel();
|
float OsdTessLevel();
|
||||||
int OsdGregoryQuadOffsetBase();
|
|
||||||
int OsdPrimitiveIdBase();
|
|
||||||
int OsdBaseVertex();
|
|
||||||
|
|
||||||
#ifndef OSD_DISPLACEMENT_CALLBACK
|
|
||||||
#define OSD_DISPLACEMENT_CALLBACK
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Patch Parameters
|
// Patch Parameters
|
||||||
@ -81,31 +40,6 @@ int OsdBaseVertex();
|
|||||||
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
||||||
// sharpness -- crease sharpness for single-crease patches
|
// sharpness -- crease sharpness for single-crease patches
|
||||||
//
|
//
|
||||||
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
|
||||||
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
|
||||||
// along with an optional client provided offset.
|
|
||||||
//
|
|
||||||
|
|
||||||
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
Buffer<uint3> OsdPatchParamBuffer : register( t0 );
|
|
||||||
#else
|
|
||||||
Buffer<uint2> OsdPatchParamBuffer : register( t0 );
|
|
||||||
#endif
|
|
||||||
|
|
||||||
int OsdGetPatchIndex(int primitiveId)
|
|
||||||
{
|
|
||||||
return (primitiveId + OsdPrimitiveIdBase());
|
|
||||||
}
|
|
||||||
|
|
||||||
int3 OsdGetPatchParam(int patchIndex)
|
|
||||||
{
|
|
||||||
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
return OsdPatchParamBuffer[patchIndex].xyz;
|
|
||||||
#else
|
|
||||||
uint2 p = OsdPatchParamBuffer[patchIndex].xy;
|
|
||||||
return int3(p.x, p.y, 0);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
int OsdGetPatchFaceId(int3 patchParam)
|
int OsdGetPatchFaceId(int3 patchParam)
|
||||||
{
|
{
|
||||||
@ -199,60 +133,6 @@ float4 OsdInterpolatePatchCoordTriangle(float2 localUV, int3 patchParam)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// patch culling
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
#ifdef OSD_ENABLE_PATCH_CULL
|
|
||||||
|
|
||||||
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P) \
|
|
||||||
float4 clipPos = mul(OsdModelViewProjectionMatrix(), P); \
|
|
||||||
int3 clip0 = int3(clipPos.x < clipPos.w, \
|
|
||||||
clipPos.y < clipPos.w, \
|
|
||||||
clipPos.z < clipPos.w); \
|
|
||||||
int3 clip1 = int3(clipPos.x > -clipPos.w, \
|
|
||||||
clipPos.y > -clipPos.w, \
|
|
||||||
clipPos.z > -clipPos.w); \
|
|
||||||
output.clipFlag = int3(clip0) + 2*int3(clip1); \
|
|
||||||
|
|
||||||
#define OSD_PATCH_CULL(N) \
|
|
||||||
int3 clipFlag = int3(0,0,0); \
|
|
||||||
for(int i = 0; i < N; ++i) { \
|
|
||||||
clipFlag |= patch[i].clipFlag; \
|
|
||||||
} \
|
|
||||||
if (any(clipFlag != int3(3,3,3))) { \
|
|
||||||
output.tessLevelInner[0] = 0; \
|
|
||||||
output.tessLevelInner[1] = 0; \
|
|
||||||
output.tessLevelOuter[0] = 0; \
|
|
||||||
output.tessLevelOuter[1] = 0; \
|
|
||||||
output.tessLevelOuter[2] = 0; \
|
|
||||||
output.tessLevelOuter[3] = 0; \
|
|
||||||
output.tessOuterLo = float4(0,0,0,0); \
|
|
||||||
output.tessOuterHi = float4(0,0,0,0); \
|
|
||||||
return output; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#define OSD_PATCH_CULL_TRIANGLE(N) \
|
|
||||||
int3 clipFlag = int3(0,0,0); \
|
|
||||||
for(int i = 0; i < N; ++i) { \
|
|
||||||
clipFlag |= patch[i].clipFlag; \
|
|
||||||
} \
|
|
||||||
if (any(clipFlag != int3(3,3,3))) { \
|
|
||||||
output.tessLevelInner[0] = 0; \
|
|
||||||
output.tessLevelOuter[0] = 0; \
|
|
||||||
output.tessLevelOuter[1] = 0; \
|
|
||||||
output.tessLevelOuter[2] = 0; \
|
|
||||||
output.tessOuterLo = float4(0,0,0,0); \
|
|
||||||
output.tessOuterHi = float4(0,0,0,0); \
|
|
||||||
return output; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P)
|
|
||||||
#define OSD_PATCH_CULL(N)
|
|
||||||
#define OSD_PATCH_CULL_TRIANGLE(N)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -564,7 +444,7 @@ OsdFlipMatrix(float4x4 m)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Regular BSpline to Bezier
|
// Regular BSpline to Bezier
|
||||||
static float4x4 Q = {
|
static const float4x4 Q = {
|
||||||
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
||||||
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
||||||
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
||||||
@ -572,7 +452,7 @@ static float4x4 Q = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
// Infinitely Sharp (boundary)
|
// Infinitely Sharp (boundary)
|
||||||
static float4x4 Mi = {
|
static const float4x4 Mi = {
|
||||||
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
1.f/6.f, 4.f/6.f, 1.f/6.f, 0.f,
|
||||||
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
0.f, 4.f/6.f, 2.f/6.f, 0.f,
|
||||||
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
0.f, 2.f/6.f, 4.f/6.f, 0.f,
|
||||||
|
@ -22,6 +22,128 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
|
//----------------------------------------------------------
|
||||||
|
// Patches.Common
|
||||||
|
//----------------------------------------------------------
|
||||||
|
|
||||||
|
struct InputVertex {
|
||||||
|
float4 position : POSITION;
|
||||||
|
float3 normal : NORMAL;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct HullVertex {
|
||||||
|
float4 position : POSITION;
|
||||||
|
#ifdef OSD_ENABLE_PATCH_CULL
|
||||||
|
int3 clipFlag : CLIPFLAG;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
// XXXdyu all downstream data can be handled by client code
|
||||||
|
struct OutputVertex {
|
||||||
|
float4 positionOut : SV_Position;
|
||||||
|
float4 position : POSITION1;
|
||||||
|
float3 normal : NORMAL;
|
||||||
|
float3 tangent : TANGENT;
|
||||||
|
float3 bitangent : TANGENT1;
|
||||||
|
float4 patchCoord : PATCHCOORD; // u, v, faceLevel, faceId
|
||||||
|
noperspective float4 edgeDistance : EDGEDISTANCE;
|
||||||
|
#if defined(OSD_COMPUTE_NORMAL_DERIVATIVES)
|
||||||
|
float3 Nu : TANGENT2;
|
||||||
|
float3 Nv : TANGENT3;
|
||||||
|
#endif
|
||||||
|
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
float2 vSegments : VSEGMENTS;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
float4x4 OsdModelViewProjectionMatrix();
|
||||||
|
int OsdGregoryQuadOffsetBase();
|
||||||
|
int OsdPrimitiveIdBase();
|
||||||
|
int OsdBaseVertex();
|
||||||
|
|
||||||
|
#ifndef OSD_DISPLACEMENT_CALLBACK
|
||||||
|
#define OSD_DISPLACEMENT_CALLBACK
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
||||||
|
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
||||||
|
// along with an optional client provided offset.
|
||||||
|
|
||||||
|
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
Buffer<uint3> OsdPatchParamBuffer : register( t0 );
|
||||||
|
#else
|
||||||
|
Buffer<uint2> OsdPatchParamBuffer : register( t0 );
|
||||||
|
#endif
|
||||||
|
|
||||||
|
int OsdGetPatchIndex(int primitiveId)
|
||||||
|
{
|
||||||
|
return (primitiveId + OsdPrimitiveIdBase());
|
||||||
|
}
|
||||||
|
|
||||||
|
int3 OsdGetPatchParam(int patchIndex)
|
||||||
|
{
|
||||||
|
#if defined OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
return OsdPatchParamBuffer[patchIndex].xyz;
|
||||||
|
#else
|
||||||
|
uint2 p = OsdPatchParamBuffer[patchIndex].xy;
|
||||||
|
return int3(p.x, p.y, 0);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
// patch culling
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#ifdef OSD_ENABLE_PATCH_CULL
|
||||||
|
|
||||||
|
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P) \
|
||||||
|
float4 clipPos = mul(OsdModelViewProjectionMatrix(), P); \
|
||||||
|
int3 clip0 = int3(clipPos.x < clipPos.w, \
|
||||||
|
clipPos.y < clipPos.w, \
|
||||||
|
clipPos.z < clipPos.w); \
|
||||||
|
int3 clip1 = int3(clipPos.x > -clipPos.w, \
|
||||||
|
clipPos.y > -clipPos.w, \
|
||||||
|
clipPos.z > -clipPos.w); \
|
||||||
|
output.clipFlag = int3(clip0) + 2*int3(clip1); \
|
||||||
|
|
||||||
|
#define OSD_PATCH_CULL(N) \
|
||||||
|
int3 clipFlag = int3(0,0,0); \
|
||||||
|
for(int i = 0; i < N; ++i) { \
|
||||||
|
clipFlag |= patch[i].clipFlag; \
|
||||||
|
} \
|
||||||
|
if (any(clipFlag != int3(3,3,3))) { \
|
||||||
|
output.tessLevelInner[0] = 0; \
|
||||||
|
output.tessLevelInner[1] = 0; \
|
||||||
|
output.tessLevelOuter[0] = 0; \
|
||||||
|
output.tessLevelOuter[1] = 0; \
|
||||||
|
output.tessLevelOuter[2] = 0; \
|
||||||
|
output.tessLevelOuter[3] = 0; \
|
||||||
|
output.tessOuterLo = float4(0,0,0,0); \
|
||||||
|
output.tessOuterHi = float4(0,0,0,0); \
|
||||||
|
return output; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define OSD_PATCH_CULL_TRIANGLE(N) \
|
||||||
|
int3 clipFlag = int3(0,0,0); \
|
||||||
|
for(int i = 0; i < N; ++i) { \
|
||||||
|
clipFlag |= patch[i].clipFlag; \
|
||||||
|
} \
|
||||||
|
if (any(clipFlag != int3(3,3,3))) { \
|
||||||
|
output.tessLevelInner[0] = 0; \
|
||||||
|
output.tessLevelOuter[0] = 0; \
|
||||||
|
output.tessLevelOuter[1] = 0; \
|
||||||
|
output.tessLevelOuter[2] = 0; \
|
||||||
|
output.tessOuterLo = float4(0,0,0,0); \
|
||||||
|
output.tessOuterHi = float4(0,0,0,0); \
|
||||||
|
return output; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#else
|
||||||
|
#define OSD_PATCH_CULL_COMPUTE_CLIPFLAGS(P)
|
||||||
|
#define OSD_PATCH_CULL(N)
|
||||||
|
#define OSD_PATCH_CULL_TRIANGLE(N)
|
||||||
|
#endif
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Legacy Gregory
|
// Legacy Gregory
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
@ -69,10 +69,18 @@ static const char *gregoryTriangleShaderSource =
|
|||||||
|
|
||||||
/*static*/
|
/*static*/
|
||||||
std::string
|
std::string
|
||||||
HLSLPatchShaderSource::GetCommonShaderSource() {
|
HLSLPatchShaderSource::GetPatchDrawingShaderSource() {
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss << std::string(commonShaderSource);
|
ss << std::string(commonShaderSource);
|
||||||
ss << std::string(commonTessShaderSource);
|
ss << std::string(commonTessShaderSource);
|
||||||
|
return ss.str();
|
||||||
|
}
|
||||||
|
|
||||||
|
/*static*/
|
||||||
|
std::string
|
||||||
|
HLSLPatchShaderSource::GetCommonShaderSource() {
|
||||||
|
std::stringstream ss;
|
||||||
|
ss << GetPatchDrawingShaderSource();
|
||||||
ss << std::string(patchLegacyShaderSource);
|
ss << std::string(patchLegacyShaderSource);
|
||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
@ -26,25 +26,46 @@
|
|||||||
#define OPENSUBDIV3_OSD_HLSL_PATCH_SHADER_SOURCE_H
|
#define OPENSUBDIV3_OSD_HLSL_PATCH_SHADER_SOURCE_H
|
||||||
|
|
||||||
#include "../version.h"
|
#include "../version.h"
|
||||||
#include <string>
|
|
||||||
#include "../far/patchDescriptor.h"
|
#include "../far/patchDescriptor.h"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
namespace OpenSubdiv {
|
namespace OpenSubdiv {
|
||||||
namespace OPENSUBDIV_VERSION {
|
namespace OPENSUBDIV_VERSION {
|
||||||
|
|
||||||
namespace Osd {
|
namespace Osd {
|
||||||
|
|
||||||
|
/// \brief Provides shader source which can be used by client code.
|
||||||
class HLSLPatchShaderSource {
|
class HLSLPatchShaderSource {
|
||||||
public:
|
public:
|
||||||
static std::string GetCommonShaderSource();
|
/// \brief Returns shader source which can be used to evaluate
|
||||||
|
/// position and first and second derivatives on piecewise parametric
|
||||||
|
/// patches resulting from subdivision refinement.
|
||||||
static std::string GetPatchBasisShaderSource();
|
static std::string GetPatchBasisShaderSource();
|
||||||
|
|
||||||
|
/// \brief Returns shader source which can be used while drawing
|
||||||
|
/// piecewise parametric patches resulting from subdivision refinement,
|
||||||
|
/// e.g. while using GPU HW tessellation.
|
||||||
|
static std::string GetPatchDrawingShaderSource();
|
||||||
|
|
||||||
|
/// \name Alternative methods
|
||||||
|
/// \{
|
||||||
|
/// These methods return shader source which can be used
|
||||||
|
/// while drawing. Unlike the methods above, the source returned
|
||||||
|
/// by these methods includes support for legacy patch types along
|
||||||
|
/// with dependencies on specific resource bindings and interstage
|
||||||
|
/// shader variable declarations.
|
||||||
|
|
||||||
|
static std::string GetCommonShaderSource();
|
||||||
|
|
||||||
static std::string GetVertexShaderSource(Far::PatchDescriptor::Type type);
|
static std::string GetVertexShaderSource(Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
static std::string GetHullShaderSource(Far::PatchDescriptor::Type type);
|
static std::string GetHullShaderSource(Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
static std::string GetDomainShaderSource(Far::PatchDescriptor::Type type);
|
static std::string GetDomainShaderSource(Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
|
/// @}
|
||||||
};
|
};
|
||||||
|
|
||||||
} // end namespace Osd
|
} // end namespace Osd
|
||||||
|
@ -24,173 +24,15 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
//----------------------------------------------------------
|
|
||||||
// Patches.Common
|
|
||||||
//----------------------------------------------------------
|
|
||||||
|
|
||||||
#include <metal_stdlib>
|
#include <metal_stdlib>
|
||||||
|
|
||||||
#define offsetof_(X, Y) &(((device X*)nullptr)->Y)
|
|
||||||
|
|
||||||
#define OSD_IS_ADAPTIVE (OSD_PATCH_REGULAR || OSD_PATCH_BOX_SPLINE_TRIANGLE || OSD_PATCH_GREGORY_BASIS || OSD_PATCH_GREGORY_TRIANGLE || OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY)
|
|
||||||
|
|
||||||
#ifndef OSD_MAX_TESS_LEVEL
|
|
||||||
#define OSD_MAX_TESS_LEVEL 64
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef OSD_NUM_ELEMENTS
|
|
||||||
#define OSD_NUM_ELEMENTS 3
|
|
||||||
#endif
|
|
||||||
|
|
||||||
using namespace metal;
|
using namespace metal;
|
||||||
|
|
||||||
using OsdPatchParamBufferType = packed_int3;
|
// The following callback functions are used when evaluating tessellation
|
||||||
|
// rates and when using legacy patch drawing.
|
||||||
struct OsdPerVertexGregory {
|
float4x4 OsdModelViewMatrix();
|
||||||
float3 P;
|
float4x4 OsdProjectionMatrix();
|
||||||
short3 clipFlag;
|
float OsdTessLevel();
|
||||||
int valence;
|
|
||||||
float3 e0;
|
|
||||||
float3 e1;
|
|
||||||
#if OSD_PATCH_GREGORY_BOUNDARY
|
|
||||||
int zerothNeighbor;
|
|
||||||
float3 org;
|
|
||||||
#endif
|
|
||||||
float3 r[OSD_MAX_VALENCE];
|
|
||||||
};
|
|
||||||
|
|
||||||
struct OsdPerPatchVertexGregory {
|
|
||||||
packed_float3 P;
|
|
||||||
packed_float3 Ep;
|
|
||||||
packed_float3 Em;
|
|
||||||
packed_float3 Fp;
|
|
||||||
packed_float3 Fm;
|
|
||||||
};
|
|
||||||
|
|
||||||
//----------------------------------------------------------
|
|
||||||
// HLSL->Metal Compatibility
|
|
||||||
//----------------------------------------------------------
|
|
||||||
|
|
||||||
float4 mul(float4x4 a, float4 b)
|
|
||||||
{
|
|
||||||
return a * b;
|
|
||||||
}
|
|
||||||
|
|
||||||
float3 mul(float4x4 a, float3 b)
|
|
||||||
{
|
|
||||||
float3x3 m(a[0].xyz, a[1].xyz, a[2].xyz);
|
|
||||||
return m * b;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
//----------------------------------------------------------
|
|
||||||
// Patches.Common
|
|
||||||
//----------------------------------------------------------
|
|
||||||
|
|
||||||
struct HullVertex {
|
|
||||||
float4 position;
|
|
||||||
#if OSD_ENABLE_PATCH_CULL
|
|
||||||
short3 clipFlag;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
float3 GetPosition() threadgroup
|
|
||||||
{
|
|
||||||
return position.xyz;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetPosition(float3 v) threadgroup
|
|
||||||
{
|
|
||||||
position.xyz = v;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// XXXdyu all downstream data can be handled by client code
|
|
||||||
struct OsdPatchVertex {
|
|
||||||
float3 position;
|
|
||||||
float3 normal;
|
|
||||||
float3 tangent;
|
|
||||||
float3 bitangent;
|
|
||||||
float4 patchCoord; //u, v, faceLevel, faceId
|
|
||||||
float2 tessCoord; // tesscoord.st
|
|
||||||
#if OSD_COMPUTE_NORMAL_DERIVATIVES
|
|
||||||
float3 Nu;
|
|
||||||
float3 Nv;
|
|
||||||
#endif
|
|
||||||
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
float2 vSegments;
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
struct OsdPerPatchTessFactors {
|
|
||||||
float4 tessOuterLo;
|
|
||||||
float4 tessOuterHi;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct OsdPerPatchVertexBezier {
|
|
||||||
packed_float3 P;
|
|
||||||
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
packed_float3 P1;
|
|
||||||
packed_float3 P2;
|
|
||||||
#if !USE_PTVS_SHARPNESS
|
|
||||||
float2 vSegments;
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
struct OsdPerPatchVertexGregoryBasis {
|
|
||||||
packed_float3 P;
|
|
||||||
};
|
|
||||||
|
|
||||||
#if OSD_PATCH_REGULAR || OSD_PATCH_BOX_SPLINE_TRIANGLE
|
|
||||||
using PatchVertexType = HullVertex;
|
|
||||||
using PerPatchVertexType = OsdPerPatchVertexBezier;
|
|
||||||
#elif OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY
|
|
||||||
using PatchVertexType = OsdPerVertexGregory;
|
|
||||||
using PerPatchVertexType = OsdPerPatchVertexGregory;
|
|
||||||
#elif OSD_PATCH_GREGORY_BASIS || OSD_PATCH_GREGORY_TRIANGLE
|
|
||||||
using PatchVertexType = HullVertex;
|
|
||||||
using PerPatchVertexType = OsdPerPatchVertexGregoryBasis;
|
|
||||||
#else
|
|
||||||
using PatchVertexType = OsdInputVertexType;
|
|
||||||
using PerPatchVertexType = OsdInputVertexType;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
//Shared buffers used by OSD that are common to all kernels
|
|
||||||
struct OsdPatchParamBufferSet
|
|
||||||
{
|
|
||||||
const device OsdInputVertexType* vertexBuffer [[buffer(VERTEX_BUFFER_INDEX)]];
|
|
||||||
const device unsigned* indexBuffer [[buffer(CONTROL_INDICES_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
const device OsdPatchParamBufferType* patchParamBuffer [[buffer(OSD_PATCHPARAM_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
device PerPatchVertexType* perPatchVertexBuffer [[buffer(OSD_PERPATCHVERTEX_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
#if !USE_PTVS_FACTORS
|
|
||||||
device OsdPerPatchTessFactors* patchTessBuffer [[buffer(OSD_PERPATCHTESSFACTORS_BUFFER_INDEX)]];
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY
|
|
||||||
const device int* quadOffsetBuffer [[buffer(OSD_QUADOFFSET_BUFFER_INDEX)]];
|
|
||||||
const device int* valenceBuffer [[buffer(OSD_VALENCE_BUFFER_INDEX)]];
|
|
||||||
#endif
|
|
||||||
|
|
||||||
const constant unsigned& kernelExecutionLimit [[buffer(OSD_KERNELLIMIT_BUFFER_INDEX)]];
|
|
||||||
};
|
|
||||||
|
|
||||||
//Shared buffers used by OSD that are common to all PTVS implementations
|
|
||||||
struct OsdVertexBufferSet
|
|
||||||
{
|
|
||||||
const device OsdInputVertexType* vertexBuffer [[buffer(VERTEX_BUFFER_INDEX)]];
|
|
||||||
const device unsigned* indexBuffer [[buffer(CONTROL_INDICES_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
const device OsdPatchParamBufferType* patchParamBuffer [[buffer(OSD_PATCHPARAM_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
device PerPatchVertexType* perPatchVertexBuffer [[buffer(OSD_PERPATCHVERTEX_BUFFER_INDEX)]];
|
|
||||||
|
|
||||||
#if !USE_PTVS_FACTORS
|
|
||||||
device OsdPerPatchTessFactors* patchTessBuffer [[buffer(OSD_PERPATCHTESSFACTORS_BUFFER_INDEX)]];
|
|
||||||
#endif
|
|
||||||
};
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Patch Parameters
|
// Patch Parameters
|
||||||
@ -204,25 +46,6 @@ struct OsdVertexBufferSet
|
|||||||
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
// bitfield -- refinement-level, non-quad, boundary, transition, uv-offset
|
||||||
// sharpness -- crease sharpness for single-crease patches
|
// sharpness -- crease sharpness for single-crease patches
|
||||||
//
|
//
|
||||||
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
|
||||||
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
|
||||||
// along with an optional client provided offset.
|
|
||||||
//
|
|
||||||
|
|
||||||
int3 OsdGetPatchParam(int patchIndex, const device OsdPatchParamBufferType* osdPatchParamBuffer)
|
|
||||||
{
|
|
||||||
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
|
||||||
return int3(osdPatchParamBuffer[patchIndex]);
|
|
||||||
#else
|
|
||||||
auto p = osdPatchParamBuffer[patchIndex];
|
|
||||||
return int3(p[0], p[1], 0);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
int OsdGetPatchIndex(int primitiveId)
|
|
||||||
{
|
|
||||||
return primitiveId;
|
|
||||||
}
|
|
||||||
|
|
||||||
int OsdGetPatchFaceId(int3 patchParam)
|
int OsdGetPatchFaceId(int3 patchParam)
|
||||||
{
|
{
|
||||||
@ -316,40 +139,6 @@ float4 OsdInterpolatePatchCoordTriangle(float2 localUV, int3 patchParam)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// patch culling
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
bool OsdCullPerPatchVertex(
|
|
||||||
threadgroup PatchVertexType* patch,
|
|
||||||
float4x4 ModelViewMatrix
|
|
||||||
)
|
|
||||||
{
|
|
||||||
#if OSD_ENABLE_BACKPATCH_CULL && OSD_PATCH_REGULAR
|
|
||||||
auto v0 = float3(ModelViewMatrix * patch[5].position);
|
|
||||||
auto v3 = float3(ModelViewMatrix * patch[6].position);
|
|
||||||
auto v12 = float3(ModelViewMatrix * patch[9].position);
|
|
||||||
|
|
||||||
auto n = normalize(cross(v3 - v0, v12 - v0));
|
|
||||||
v0 = normalize(v0 + v3 + v12);
|
|
||||||
|
|
||||||
if(dot(v0, n) > 0.6f)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
#if OSD_ENABLE_PATCH_CULL
|
|
||||||
short3 clipFlag = short3(0,0,0);
|
|
||||||
for(int i = 0; i < CONTROL_POINTS_PER_PATCH; ++i) {
|
|
||||||
clipFlag |= patch[i].clipFlag;
|
|
||||||
}
|
|
||||||
if (any(clipFlag != short3(3,3,3))) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -421,6 +210,17 @@ OsdUnivar4x4(float u, thread float* B, thread float* D, thread float* C)
|
|||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
struct OsdPerPatchVertexBezier {
|
||||||
|
packed_float3 P;
|
||||||
|
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
packed_float3 P1;
|
||||||
|
packed_float3 P2;
|
||||||
|
#if !USE_PTVS_SHARPNESS
|
||||||
|
float2 vSegments;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
float3
|
float3
|
||||||
OsdEvalBezier(float3 cp[16], float2 uv)
|
OsdEvalBezier(float3 cp[16], float2 uv)
|
||||||
{
|
{
|
||||||
@ -1088,6 +888,10 @@ OsdEvalPatchBezier(int3 patchParam, float2 UV,
|
|||||||
// Gregory Basis
|
// Gregory Basis
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
struct OsdPerPatchVertexGregoryBasis {
|
||||||
|
packed_float3 P;
|
||||||
|
};
|
||||||
|
|
||||||
void
|
void
|
||||||
OsdComputePerPatchVertexGregoryBasis(int3 patchParam, int ID, float3 cv,
|
OsdComputePerPatchVertexGregoryBasis(int3 patchParam, int ID, float3 cv,
|
||||||
device OsdPerPatchVertexGregoryBasis& result)
|
device OsdPerPatchVertexGregoryBasis& result)
|
||||||
@ -1444,3 +1248,4 @@ OsdEvalPatchGregoryTriangle(int3 patchParam, float2 UV, float3 cv[18],
|
|||||||
|
|
||||||
OsdEvalPatchBezierTriangle(patchParam, UV, bezcv, P, dPu, dPv, N, dNu, dNv);
|
OsdEvalPatchBezierTriangle(patchParam, UV, bezcv, P, dPu, dPv, N, dNu, dNv);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -81,6 +81,10 @@
|
|||||||
// (0,0) (1,0)
|
// (0,0) (1,0)
|
||||||
//
|
//
|
||||||
|
|
||||||
|
#ifndef OSD_MAX_TESS_LEVEL
|
||||||
|
#define OSD_MAX_TESS_LEVEL 64
|
||||||
|
#endif
|
||||||
|
|
||||||
float OsdComputePostProjectionSphereExtent(
|
float OsdComputePostProjectionSphereExtent(
|
||||||
const float4x4 OsdProjectionMatrix, float3 center, float diameter)
|
const float4x4 OsdProjectionMatrix, float3 center, float diameter)
|
||||||
{
|
{
|
||||||
|
@ -24,6 +24,200 @@
|
|||||||
// language governing permissions and limitations under the Apache License.
|
// language governing permissions and limitations under the Apache License.
|
||||||
//
|
//
|
||||||
|
|
||||||
|
//----------------------------------------------------------
|
||||||
|
// Patches.Common
|
||||||
|
//----------------------------------------------------------
|
||||||
|
|
||||||
|
#define offsetof_(X, Y) &(((device X*)nullptr)->Y)
|
||||||
|
|
||||||
|
#define OSD_IS_ADAPTIVE (OSD_PATCH_REGULAR || OSD_PATCH_BOX_SPLINE_TRIANGLE || OSD_PATCH_GREGORY_BASIS || OSD_PATCH_GREGORY_TRIANGLE || OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY)
|
||||||
|
|
||||||
|
#ifndef OSD_NUM_ELEMENTS
|
||||||
|
#define OSD_NUM_ELEMENTS 3
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct OsdPerVertexGregory {
|
||||||
|
float3 P;
|
||||||
|
short3 clipFlag;
|
||||||
|
int valence;
|
||||||
|
float3 e0;
|
||||||
|
float3 e1;
|
||||||
|
#if OSD_PATCH_GREGORY_BOUNDARY
|
||||||
|
int zerothNeighbor;
|
||||||
|
float3 org;
|
||||||
|
#endif
|
||||||
|
float3 r[OSD_MAX_VALENCE];
|
||||||
|
};
|
||||||
|
|
||||||
|
struct OsdPerPatchVertexGregory {
|
||||||
|
packed_float3 P;
|
||||||
|
packed_float3 Ep;
|
||||||
|
packed_float3 Em;
|
||||||
|
packed_float3 Fp;
|
||||||
|
packed_float3 Fm;
|
||||||
|
};
|
||||||
|
|
||||||
|
//----------------------------------------------------------
|
||||||
|
// HLSL->Metal Compatibility
|
||||||
|
//----------------------------------------------------------
|
||||||
|
|
||||||
|
float4 mul(float4x4 a, float4 b)
|
||||||
|
{
|
||||||
|
return a * b;
|
||||||
|
}
|
||||||
|
|
||||||
|
float3 mul(float4x4 a, float3 b)
|
||||||
|
{
|
||||||
|
float3x3 m(a[0].xyz, a[1].xyz, a[2].xyz);
|
||||||
|
return m * b;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
struct HullVertex {
|
||||||
|
float4 position;
|
||||||
|
#if OSD_ENABLE_PATCH_CULL
|
||||||
|
short3 clipFlag;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
float3 GetPosition() threadgroup
|
||||||
|
{
|
||||||
|
return position.xyz;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SetPosition(float3 v) threadgroup
|
||||||
|
{
|
||||||
|
position.xyz = v;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// XXXdyu all downstream data can be handled by client code
|
||||||
|
struct OsdPatchVertex {
|
||||||
|
float3 position;
|
||||||
|
float3 normal;
|
||||||
|
float3 tangent;
|
||||||
|
float3 bitangent;
|
||||||
|
float4 patchCoord; //u, v, faceLevel, faceId
|
||||||
|
float2 tessCoord; // tesscoord.st
|
||||||
|
#if OSD_COMPUTE_NORMAL_DERIVATIVES
|
||||||
|
float3 Nu;
|
||||||
|
float3 Nv;
|
||||||
|
#endif
|
||||||
|
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
float2 vSegments;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
struct OsdPerPatchTessFactors {
|
||||||
|
float4 tessOuterLo;
|
||||||
|
float4 tessOuterHi;
|
||||||
|
};
|
||||||
|
|
||||||
|
using OsdPatchParamBufferType = packed_int3;
|
||||||
|
|
||||||
|
#if OSD_PATCH_REGULAR || OSD_PATCH_BOX_SPLINE_TRIANGLE
|
||||||
|
using PatchVertexType = HullVertex;
|
||||||
|
using PerPatchVertexType = OsdPerPatchVertexBezier;
|
||||||
|
#elif OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY
|
||||||
|
using PatchVertexType = OsdPerVertexGregory;
|
||||||
|
using PerPatchVertexType = OsdPerPatchVertexGregory;
|
||||||
|
#elif OSD_PATCH_GREGORY_BASIS || OSD_PATCH_GREGORY_TRIANGLE
|
||||||
|
using PatchVertexType = HullVertex;
|
||||||
|
using PerPatchVertexType = OsdPerPatchVertexGregoryBasis;
|
||||||
|
#else
|
||||||
|
using PatchVertexType = OsdInputVertexType;
|
||||||
|
using PerPatchVertexType = OsdInputVertexType;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//Shared buffers used by OSD that are common to all kernels
|
||||||
|
struct OsdPatchParamBufferSet
|
||||||
|
{
|
||||||
|
const device OsdInputVertexType* vertexBuffer [[buffer(VERTEX_BUFFER_INDEX)]];
|
||||||
|
const device unsigned* indexBuffer [[buffer(CONTROL_INDICES_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
const device OsdPatchParamBufferType* patchParamBuffer [[buffer(OSD_PATCHPARAM_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
device PerPatchVertexType* perPatchVertexBuffer [[buffer(OSD_PERPATCHVERTEX_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
#if !USE_PTVS_FACTORS
|
||||||
|
device OsdPerPatchTessFactors* patchTessBuffer [[buffer(OSD_PERPATCHTESSFACTORS_BUFFER_INDEX)]];
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if OSD_PATCH_GREGORY || OSD_PATCH_GREGORY_BOUNDARY
|
||||||
|
const device int* quadOffsetBuffer [[buffer(OSD_QUADOFFSET_BUFFER_INDEX)]];
|
||||||
|
const device int* valenceBuffer [[buffer(OSD_VALENCE_BUFFER_INDEX)]];
|
||||||
|
#endif
|
||||||
|
|
||||||
|
const constant unsigned& kernelExecutionLimit [[buffer(OSD_KERNELLIMIT_BUFFER_INDEX)]];
|
||||||
|
};
|
||||||
|
|
||||||
|
//Shared buffers used by OSD that are common to all PTVS implementations
|
||||||
|
struct OsdVertexBufferSet
|
||||||
|
{
|
||||||
|
const device OsdInputVertexType* vertexBuffer [[buffer(VERTEX_BUFFER_INDEX)]];
|
||||||
|
const device unsigned* indexBuffer [[buffer(CONTROL_INDICES_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
const device OsdPatchParamBufferType* patchParamBuffer [[buffer(OSD_PATCHPARAM_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
device PerPatchVertexType* perPatchVertexBuffer [[buffer(OSD_PERPATCHVERTEX_BUFFER_INDEX)]];
|
||||||
|
|
||||||
|
#if !USE_PTVS_FACTORS
|
||||||
|
device OsdPerPatchTessFactors* patchTessBuffer [[buffer(OSD_PERPATCHTESSFACTORS_BUFFER_INDEX)]];
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
// These are stored in OsdPatchParamBuffer indexed by the value returned
|
||||||
|
// from OsdGetPatchIndex() which is a function of the current PrimitiveID
|
||||||
|
// along with an optional client provided offset.
|
||||||
|
|
||||||
|
int3 OsdGetPatchParam(int patchIndex, const device OsdPatchParamBufferType* osdPatchParamBuffer)
|
||||||
|
{
|
||||||
|
#if OSD_PATCH_ENABLE_SINGLE_CREASE
|
||||||
|
return int3(osdPatchParamBuffer[patchIndex]);
|
||||||
|
#else
|
||||||
|
auto p = osdPatchParamBuffer[patchIndex];
|
||||||
|
return int3(p[0], p[1], 0);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
int OsdGetPatchIndex(int primitiveId)
|
||||||
|
{
|
||||||
|
return primitiveId;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
// patch culling
|
||||||
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
bool OsdCullPerPatchVertex(
|
||||||
|
threadgroup PatchVertexType* patch,
|
||||||
|
float4x4 ModelViewMatrix
|
||||||
|
)
|
||||||
|
{
|
||||||
|
#if OSD_ENABLE_BACKPATCH_CULL && OSD_PATCH_REGULAR
|
||||||
|
auto v0 = float3(ModelViewMatrix * patch[5].position);
|
||||||
|
auto v3 = float3(ModelViewMatrix * patch[6].position);
|
||||||
|
auto v12 = float3(ModelViewMatrix * patch[9].position);
|
||||||
|
|
||||||
|
auto n = normalize(cross(v3 - v0, v12 - v0));
|
||||||
|
v0 = normalize(v0 + v3 + v12);
|
||||||
|
|
||||||
|
if(dot(v0, n) > 0.6f)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
#if OSD_ENABLE_PATCH_CULL
|
||||||
|
short3 clipFlag = short3(0,0,0);
|
||||||
|
for(int i = 0; i < CONTROL_POINTS_PER_PATCH; ++i) {
|
||||||
|
clipFlag |= patch[i].clipFlag;
|
||||||
|
}
|
||||||
|
if (any(clipFlag != short3(3,3,3))) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Legacy Gregory
|
// Legacy Gregory
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
@ -26,7 +26,9 @@
|
|||||||
#define OPENSUBDIV3_OSD_MTL_PATCH_SHADER_SOURCE_H
|
#define OPENSUBDIV3_OSD_MTL_PATCH_SHADER_SOURCE_H
|
||||||
|
|
||||||
#import "../version.h"
|
#import "../version.h"
|
||||||
|
|
||||||
#import "../far/patchDescriptor.h"
|
#import "../far/patchDescriptor.h"
|
||||||
|
|
||||||
#import <string>
|
#import <string>
|
||||||
|
|
||||||
namespace OpenSubdiv {
|
namespace OpenSubdiv {
|
||||||
@ -34,12 +36,29 @@ namespace OPENSUBDIV_VERSION {
|
|||||||
|
|
||||||
namespace Osd {
|
namespace Osd {
|
||||||
|
|
||||||
|
/// \brief Provides shader source which can be used by client code.
|
||||||
class MTLPatchShaderSource {
|
class MTLPatchShaderSource {
|
||||||
public:
|
public:
|
||||||
static std::string GetCommonShaderSource();
|
/// \brief Returns shader source which can be used to evaluate
|
||||||
|
/// position and first and second derivatives on piecewise parametric
|
||||||
|
/// patches resulting from subdivision refinement.
|
||||||
static std::string GetPatchBasisShaderSource();
|
static std::string GetPatchBasisShaderSource();
|
||||||
|
|
||||||
|
/// \brief Returns shader source which can be used while drawing
|
||||||
|
/// piecewise parametric patches resulting from subdivision refinement,
|
||||||
|
/// e.g. while using GPU HW tessellation.
|
||||||
|
static std::string GetPatchDrawingShaderSource();
|
||||||
|
|
||||||
|
/// \name Alternative methods
|
||||||
|
/// \{
|
||||||
|
/// These methods return shader source which can be used
|
||||||
|
/// while drawing. Unlike the methods above, the source returned
|
||||||
|
/// by these methods includes support for legacy patch types along
|
||||||
|
/// with dependencies on specific resource bindings and interstage
|
||||||
|
/// shader variable declarations.
|
||||||
|
|
||||||
|
static std::string GetCommonShaderSource();
|
||||||
|
|
||||||
static std::string GetVertexShaderSource(Far::PatchDescriptor::Type type);
|
static std::string GetVertexShaderSource(Far::PatchDescriptor::Type type);
|
||||||
|
|
||||||
static std::string GetHullShaderSource(Far::PatchDescriptor::Type type);
|
static std::string GetHullShaderSource(Far::PatchDescriptor::Type type);
|
||||||
@ -59,6 +78,9 @@ class MTLPatchShaderSource {
|
|||||||
static std::string GetDomainShaderSource(
|
static std::string GetDomainShaderSource(
|
||||||
Far::PatchDescriptor::Type type,
|
Far::PatchDescriptor::Type type,
|
||||||
Far::PatchDescriptor::Type fvarType);
|
Far::PatchDescriptor::Type fvarType);
|
||||||
|
|
||||||
|
/// @}
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // end namespace Osd
|
} // end namespace Osd
|
||||||
|
@ -147,20 +147,25 @@ GetPatchTypeSource(Far::PatchDescriptor::Type type) {
|
|||||||
|
|
||||||
/*static*/
|
/*static*/
|
||||||
std::string
|
std::string
|
||||||
MTLPatchShaderSource::GetCommonShaderSource() {
|
MTLPatchShaderSource::GetPatchDrawingShaderSource() {
|
||||||
#if TARGET_OS_IOS || TARGET_OS_TV
|
#if TARGET_OS_IOS || TARGET_OS_TV
|
||||||
return std::string("#define OSD_METAL_IOS 1\n")
|
return std::string("#define OSD_METAL_IOS 1\n")
|
||||||
.append(commonShaderSource)
|
.append(commonShaderSource)
|
||||||
.append(commonTessShaderSource)
|
.append(commonTessShaderSource);
|
||||||
.append(patchLegacyShaderSource);
|
|
||||||
#elif TARGET_OS_OSX
|
#elif TARGET_OS_OSX
|
||||||
return std::string("#define OSD_METAL_OSX 1\n")
|
return std::string("#define OSD_METAL_OSX 1\n")
|
||||||
.append(commonShaderSource)
|
.append(commonShaderSource)
|
||||||
.append(commonTessShaderSource)
|
.append(commonTessShaderSource);
|
||||||
.append(patchLegacyShaderSource);
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*static*/
|
||||||
|
std::string
|
||||||
|
MTLPatchShaderSource::GetCommonShaderSource() {
|
||||||
|
return GetPatchDrawingShaderSource()
|
||||||
|
.append(patchLegacyShaderSource);
|
||||||
|
}
|
||||||
|
|
||||||
/*static*/
|
/*static*/
|
||||||
std::string
|
std::string
|
||||||
MTLPatchShaderSource::GetPatchBasisShaderSource() {
|
MTLPatchShaderSource::GetPatchBasisShaderSource() {
|
||||||
|
Loading…
Reference in New Issue
Block a user