blob: c21efea35de99db0bbff8b244d40435250a63fc5 [file] [log] [blame]
/*
* Copyright 2025 Google LLC
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include "tools/graphite/precompile/PrecompileEffectFactories.h"
#include "include/effects/SkRuntimeEffect.h"
#include "include/gpu/graphite/precompile/PrecompileBlender.h"
#include "include/gpu/graphite/precompile/PrecompileColorFilter.h"
#include "include/gpu/graphite/precompile/PrecompileRuntimeEffect.h"
#include "include/gpu/graphite/precompile/PrecompileShader.h"
#include "src/core/SkRuntimeEffectPriv.h"
namespace skiatest::graphite {
using namespace skgpu::graphite;
namespace PrecompileFactories {
//--------------------------------------------------------------------------------------------------
const char* GetAnnulusShaderCode() {
static const char* sCode =
// draw a annulus centered at "center" w/ inner and outer radii in "radii"
"uniform float2 center;"
"uniform float2 radii;"
"half4 main(float2 xy) {"
"float len = length(xy - center);"
"half value = len < radii.x ? 0.0 : (len > radii.y ? 0.0 : 1.0);"
"return half4(value);"
"}";
return sCode;
}
SkRuntimeEffect* GetAnnulusShaderEffect() {
SkRuntimeEffect::Options options;
options.fName = "AnnulusShader";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(SkRuntimeEffect::MakeForShader,
GetAnnulusShaderCode(),
options);
return sEffect;
}
std::pair<sk_sp<SkShader>, sk_sp<PrecompileShader>> CreateAnnulusRuntimeShader() {
SkRuntimeEffect* effect = GetAnnulusShaderEffect();
static const float kUniforms[4] = { 50.0f, 50.0f, 40.0f, 50.0f };
sk_sp<SkData> uniforms = SkData::MakeWithCopy(kUniforms, sizeof(kUniforms));
sk_sp<SkShader> s = effect->makeShader(std::move(uniforms), /* children= */ {});
sk_sp<PrecompileShader> o = PrecompileRuntimeEffects::MakePrecompileShader(sk_ref_sp(effect));
return { std::move(s), std::move(o) };
}
//--------------------------------------------------------------------------------------------------
SkRuntimeEffect* GetSrcBlenderEffect() {
SkRuntimeEffect::Options options;
options.fName = "SrcBlender";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForBlender,
"half4 main(half4 src, half4 dst) {"
"return src;"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkBlender>, sk_sp<PrecompileBlender>> CreateSrcRuntimeBlender() {
SkRuntimeEffect* effect = GetSrcBlenderEffect();
sk_sp<SkBlender> b = effect->makeBlender(/* uniforms= */ nullptr);
sk_sp<PrecompileBlender> o =
PrecompileRuntimeEffects::MakePrecompileBlender(sk_ref_sp(effect));
return { std::move(b) , std::move(o) };
}
SkRuntimeEffect* GetDstBlenderEffect() {
SkRuntimeEffect::Options options;
options.fName = "DstBlender";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForBlender,
"half4 main(half4 src, half4 dst) {"
"return dst;"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkBlender>, sk_sp<PrecompileBlender>> CreateDstRuntimeBlender() {
SkRuntimeEffect* effect = GetDstBlenderEffect();
sk_sp<SkBlender> b = effect->makeBlender(/* uniforms= */ nullptr);
sk_sp<PrecompileBlender> o =
PrecompileRuntimeEffects::MakePrecompileBlender(sk_ref_sp(effect));
return { std::move(b) , std::move(o) };
}
SkRuntimeEffect* GetComboBlenderEffect() {
SkRuntimeEffect::Options options;
options.fName = "ComboBlender";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForBlender,
"uniform float blendFrac;"
"uniform blender a;"
"uniform blender b;"
"half4 main(half4 src, half4 dst) {"
"return (blendFrac * a.eval(src, dst)) + ((1 - blendFrac) * b.eval(src, dst));"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkBlender>, sk_sp<PrecompileBlender>> CreateComboRuntimeBlender() {
SkRuntimeEffect* effect = GetComboBlenderEffect();
auto [src, srcO] = CreateSrcRuntimeBlender();
auto [dst, dstO] = CreateDstRuntimeBlender();
SkRuntimeEffect::ChildPtr children[] = { src, dst };
const float kUniforms[] = { 1.0f };
sk_sp<SkData> uniforms = SkData::MakeWithCopy(kUniforms, sizeof(kUniforms));
sk_sp<SkBlender> b = effect->makeBlender(std::move(uniforms), children);
sk_sp<PrecompileBlender> o = PrecompileRuntimeEffects::MakePrecompileBlender(
sk_ref_sp(effect),
{{ {{ srcO }}, {{ dstO }} }});
return { std::move(b) , std::move(o) };
}
//--------------------------------------------------------------------------------------------------
SkRuntimeEffect* GetDoubleColorFilterEffect() {
SkRuntimeEffect::Options options;
options.fName = "DoubleColorFilter";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForColorFilter,
"half4 main(half4 c) {"
"return 2*c;"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkColorFilter>, sk_sp<PrecompileColorFilter>> CreateDoubleRuntimeColorFilter() {
SkRuntimeEffect* effect = GetDoubleColorFilterEffect();
return { effect->makeColorFilter(/* uniforms= */ nullptr),
PrecompileRuntimeEffects::MakePrecompileColorFilter(sk_ref_sp(effect)) };
}
SkRuntimeEffect* GetHalfColorFilterEffect() {
SkRuntimeEffect::Options options;
// We withhold this name to test out the default name case
//options.fName = "HalfColorFilter";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForColorFilter,
"half4 main(half4 c) {"
"return 0.5*c;"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkColorFilter>, sk_sp<PrecompileColorFilter>> CreateHalfRuntimeColorFilter() {
SkRuntimeEffect* effect = GetHalfColorFilterEffect();
return { effect->makeColorFilter(/* uniforms= */ nullptr),
PrecompileRuntimeEffects::MakePrecompileColorFilter(sk_ref_sp(effect)) };
}
SkRuntimeEffect* GetComboColorFilterEffect() {
SkRuntimeEffect::Options options;
options.fName = "ComboColorFilter";
static SkRuntimeEffect* sEffect = SkMakeRuntimeEffect(
SkRuntimeEffect::MakeForColorFilter,
"uniform float blendFrac;"
"uniform colorFilter a;"
"uniform colorFilter b;"
"half4 main(half4 c) {"
"return (blendFrac * a.eval(c)) + ((1 - blendFrac) * b.eval(c));"
"}",
options);
return sEffect;
}
std::pair<sk_sp<SkColorFilter>, sk_sp<PrecompileColorFilter>> CreateComboRuntimeColorFilter() {
SkRuntimeEffect* effect = GetComboColorFilterEffect();
auto [src, srcO] = CreateDoubleRuntimeColorFilter();
auto [dst, dstO] = CreateHalfRuntimeColorFilter();
SkRuntimeEffect::ChildPtr children[] = { src, dst };
const float kUniforms[] = { 0.5f };
sk_sp<SkData> uniforms = SkData::MakeWithCopy(kUniforms, sizeof(kUniforms));
sk_sp<SkColorFilter> cf = effect->makeColorFilter(std::move(uniforms), children);
sk_sp<PrecompileColorFilter> o =
PrecompileRuntimeEffects::MakePrecompileColorFilter(sk_ref_sp(effect),
{{ {{ srcO }}, {{ dstO }} }});
return { std::move(cf) , std::move(o) };
}
} // namespace PrecompileFactories
} // namespace skiatest::graphite