From 4867fc8f2eb92928288ab798ee871885503e7d9f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Deal=28=E6=B6=93=E2=82=AC=E7=BB=BE=E8=B7=A8=E4=BC=92=29?= Date: Sat, 15 Jul 2023 00:21:23 +0800 Subject: [PATCH] Update pull_request_template.md (#1270) --- .github/pull_request_template.md | 5 +- 1k/build1k.ps1 | 231 +++++++++------ cmake/Modules/AXBuildHelpers.cmake | 10 +- cmake/Modules/AXGLSLCC.cmake | 63 ++--- core/CMakeLists.txt | 14 - core/platform/apple/FileUtils-apple.mm | 1 - core/platform/linux/FileUtils-linux.cpp | 10 +- core/platform/win32/FileUtils-win32.cpp | 3 - core/renderer/Shaders.cpp | 93 +++--- core/renderer/Shaders.h | 97 ++++--- core/renderer/backend/ProgramManager.cpp | 143 +++++----- core/renderer/backend/ProgramManager.h | 37 ++- core/renderer/backend/ProgramState.cpp | 40 +-- .../backend/metal/CommandBufferMTL.mm | 9 +- core/renderer/backend/metal/DeviceMTL.h | 9 - core/renderer/backend/metal/ProgramMTL.mm | 7 +- .../backend/metal/RenderPipelineMTL.mm | 17 +- core/renderer/backend/metal/ShaderModuleMTL.h | 12 +- .../renderer/backend/metal/ShaderModuleMTL.mm | 267 +++++++----------- core/renderer/backend/opengl/ProgramGL.cpp | 13 + core/renderer/shaders/3D_particle.frag | 2 +- .../shaders/3D_positionNormalTexture.vert | 2 + setup.ps1 | 19 +- .../Source/HelloWorldScene.cpp | 1 + tests/cpp-tests/Source/AppDelegate.cpp | 2 +- .../NewRendererTest/NewRendererTest.cpp | 4 +- .../TextureCacheTest/TextureCacheTest.cpp | 53 +++- .../TextureCacheTest/TextureCacheTest.h | 7 +- 28 files changed, 563 insertions(+), 608 deletions(-) diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md index 92cf958ab4..03e10873f2 100644 --- a/.github/pull_request_template.md +++ b/.github/pull_request_template.md @@ -1,4 +1,7 @@ -THIS PROJECT IS IN DEVELOPMENT MODE. Any pull requests should merge to branch `dev`, otherwise will be rejected immediately. +Which branch your pull-request should merge into? + +- `main`: BugFixs, Minor features +- `dev`: Big changes, big features, i.e. refactor render flow ## Describe your changes diff --git a/1k/build1k.ps1 b/1k/build1k.ps1 index 430e51ab05..58c4c2166e 100644 --- a/1k/build1k.ps1 +++ b/1k/build1k.ps1 @@ -50,13 +50,87 @@ # | macOS | osx,ios,tvos,watchos | xcode | cmake | # +$myRoot = $PSScriptRoot + +# ----------------- utils functions ----------------- + +$HOST_WIN = 0 # targets: win,uwp,android +$HOST_LINUX = 1 # targets: linux,android +$HOST_MAC = 2 # targets: android,ios,osx(macos),tvos,watchos + +# 0: windows, 1: linux, 2: macos +$IsWin = $IsWindows -or ("$env:OS" -eq 'Windows_NT') +if ($IsWin) { + $HOST_OS = $HOST_WIN + $envPathSep = ';' +} +else { + $envPathSep = ':' + if ($IsLinux) { + $HOST_OS = $HOST_LINUX + } + elseif ($IsMacOS) { + $HOST_OS = $HOST_MAC + } + else { + throw "Unsupported host OS to run build1k.ps1" + } +} + +$exeSuffix = if ($HOST_OS -eq 0) { '.exe' } else { '' } + +class build1k { + [void] println($msg) { + Write-Host "build1k: $msg" + } + + [void] print($msg) { + Write-Host "build1k: $msg" -NoNewline + } + + [System.Boolean] isfile([string]$path) { + return Test-Path $path -PathType Leaf + } + + [System.Boolean] isdir([string]$path) { + return Test-Path $path -PathType Container + } + + [void] mkdirs([string]$path) { + New-Item $path -ItemType Directory 1>$null + } + + [void] pause($msg) { + if ($Global:IsWin) { + $myProcess = [System.Diagnostics.Process]::GetCurrentProcess() + $parentProcess = $myProcess.Parent + if (!$parentProcess) { + $myPID = $myProcess.Id + $instance = Get-WmiObject Win32_Process -Filter "ProcessId = $myPID" + $parentProcess = Get-Process -Id $instance.ParentProcessID + } + $parentProcessName = $parentProcess.ProcessName + if ($parentProcessName -like "explorer") { + $this.print("$msg, press any key to continue . . .") + cmd /c pause 1>$null + } + } + else { + $this.println($msg) + } + } +} +$b1k = [build1k]::new() + +# ---------------------- manifest -------------------- # mode: # x.y.z+ : >= # x.y.z : == # * : any # x.y.z~x2.y2.z2 : range $manifest = @{ - msvc = '143+'; + # C:\Program Files\Microsoft Visual Studio\2022\Professional\VC\Redist\MSVC\14.36.32532\vc_redist.x64.exe + msvc = '14.36.32532'; ndk = 'r23c+'; xcode = '13.0.0~14.2.0'; # range clang = '15.0.0+'; @@ -66,23 +140,18 @@ $manifest = @{ glslcc = '1.7.6+'; ninja = '1.11.1+'; jdk = '11.0.19+'; + nsis = '3.09'; cmdlinetools = '7.0+'; # android cmdlinetools } -$myRoot = $PSScriptRoot - $manifest_file = Join-Path $myRoot 'manifest.ps1' -if (Test-Path $manifest_file -PathType Leaf) { +if ($b1k.isfile($manifest_file)) { . $manifest_file } # refer to: https://developer.android.com/studio#command-line-tools-only $cmdlinetools_rev = '9477386' -function b1k_print($msg) { - Write-Host "build1k: $msg" -} - $options = @{ p = $null; a = 'x64'; @@ -109,7 +178,7 @@ foreach ($arg in $args) { $options[$optName] = $arg } else { - b1k_print("Warning: ignore unrecognized option: $optName") + $b1k.println("Warning: ignore unrecognized option: $optName") } $optName = $null } @@ -117,37 +186,12 @@ foreach ($arg in $args) { $pwsh_ver = $PSVersionTable.PSVersion.ToString() -b1k_print "PowerShell $pwsh_ver" +$b1k.println("PowerShell $pwsh_ver") if (!$options.setupOnly) { - b1k_print $(Out-String -InputObject $options) + $b1k.println("$(Out-String -InputObject $options)") } -$HOST_WIN = 0 # targets: win,uwp,android -$HOST_LINUX = 1 # targets: linux,android -$HOST_MAC = 2 # targets: android,ios,osx(macos),tvos,watchos - -# 0: windows, 1: linux, 2: macos -$IsWin = $IsWindows -or ("$env:OS" -eq 'Windows_NT') -if ($IsWin) { - $HOST_OS = $HOST_WIN - $envPathSep = ';' -} -else { - $envPathSep = ':' - if ($IsLinux) { - $HOST_OS = $HOST_LINUX - } - elseif ($IsMacOS) { - $HOST_OS = $HOST_MAC - } - else { - throw "Unsupported host OS to run build1k.ps1" - } -} - -$exeSuffix = if ($HOST_OS -eq 0) { '.exe' } else { '' } - $CONFIG_DEFAULT_OPTIONS = @() $HOST_OS_NAME = $('windows', 'linux', 'macos').Get($HOST_OS) @@ -186,18 +230,14 @@ if (!$TOOLCHAIN_VER) { $TOOLCHAIN_NAME = $TOOLCHAIN } -function mkdirs($path) { - New-Item $path -ItemType Directory 1>$null -} - $prefix = if ($options.prefix) { $options.prefix } else { Join-Path $HOME 'build1k' } -if (!(Test-Path "$prefix" -PathType Container)) { - mkdirs $prefix +if (!$b1k.isdir($prefix)) { + $b1k.mkdirs($prefix) } -b1k_print "proj_dir=$((Get-Location).Path), prefix=$prefix" +$b1k.println("proj_dir=$((Get-Location).Path), prefix=$prefix") -function find_prog($name, $path = $null, $mode = 'ONLY', $cmd = $null, $param = $null, $silent = $false) { +function find_prog($name, $path = $null, $mode = 'ONLY', $cmd = $null, $params = @('--version'), $silent = $false) { if ($path) { $storedPATH = $env:PATH if ($mode -eq 'ONLY') { @@ -212,6 +252,8 @@ function find_prog($name, $path = $null, $mode = 'ONLY', $cmd = $null, $param = } if (!$cmd) { $cmd = $name } + $params = [array]$params + # try get match expr and preferred ver $checkVerCond = $null $requiredMin = '' @@ -255,7 +297,7 @@ function find_prog($name, $path = $null, $mode = 'ONLY', $cmd = $null, $param = $found_rets = $null # prog_path,prog_version if ($cmd_info) { $prog_path = $cmd_info.Source - $verStr = if (!$param) { $(. $cmd '--version' 2>$null) | Select-Object -First 1 } else { $(. $cmd '--version' $param 2>$null) | Select-Object -First 1 } + $verStr = $(. $cmd @params 2>$null) | Select-Object -First 1 if (!$verStr -or ($verStr.IndexOf('--version') -ne -1)) { $verInfo = $cmd_info.Version $verStr = "$($verInfo.Major).$($verInfo.Minor).$($verInfo.Revision)" @@ -268,22 +310,22 @@ function find_prog($name, $path = $null, $mode = 'ONLY', $cmd = $null, $param = if ($checkVerCond) { $matched = Invoke-Expression $checkVerCond if ($matched) { - if (!$silent) { b1k_print "Found suitable installed ${name}: $prog_path, version: $foundVer" } + if (!$silent) { $b1k.println("Found suitable installed ${name}: $prog_path, version: $foundVer") } $found_rets = $prog_path, $foundVer } else { - if (!$silent) { b1k_print "The installed ${name}: $prog_path, version: $foundVer not match required: $requiredVer" } + if (!$silent) { $b1k.println("The installed ${name}: $prog_path, version: $foundVer not match required: $requiredVer") } $found_rets = $null, $preferredVer } } else { - if (!$silent) { b1k_print "Found installed ${name}: $prog_path, version: $foundVer" } + if (!$silent) { $b1k.println("Found installed ${name}: $prog_path, version: $foundVer") } $found_rets = $prog_path, $foundVer } } else { if ($preferredVer) { - if (!$silent) { b1k_print "Not found $name, needs install: $preferredVer" } + if (!$silent) { $b1k.println("Not found $name, needs install: $preferredVer") } $found_rets = $null, $preferredVer } else { @@ -311,7 +353,8 @@ function exec_prog($prog, $params) { } function download_file($url, $out) { - b1k_print "Downloading $url to $out ..." + if($b1k.isfile($out)) { return } + $b1k.println("Downloading $url to $out ...") if ($pwsh_ver -ge '7.0') { curl -L $url -o $out } @@ -337,10 +380,10 @@ function setup_cmake() { $cmake_root = $(Join-Path $prefix $cmake_dir) $cmake_pkg_name = "$cmake_dir$cmake_suffix" $cmake_pkg_path = "$cmake_root$cmake_suffix" - if (!(Test-Path $cmake_root -PathType Container)) { + if ($b1k.isdir($cmake_root)) { $cmake_base_uri = 'https://github.com/Kitware/CMake/releases/download' $cmake_url = "$cmake_base_uri/v$cmake_ver/$cmake_pkg_name" - if (!(Test-Path $cmake_pkg_path -PathType Leaf)) { + if (!$b1k.isfile($cmake_pkg_path)) { download_file "$cmake_url" "$cmake_pkg_path" } @@ -349,7 +392,7 @@ function setup_cmake() { } elseif ($HOST_OS -eq $HOST_LINUX) { chmod 'u+x' "$cmake_pkg_path" - mkdirs $cmake_root + $b1k.mkdirs($cmake_root) & "$cmake_pkg_path" '--skip-license' '--exclude-subdir' "--prefix=$cmake_root" } elseif ($HOST_OS -eq $HOST_MAC) { @@ -370,7 +413,7 @@ function setup_cmake() { if (($null -ne $cmake_bin) -and ($env:PATH.IndexOf($cmake_bin) -eq -1)) { $env:PATH = "$cmake_bin$envPathSep$env:PATH" } - b1k_print "Using cmake: $cmake_prog, version: $cmake_ver" + $b1k.println("Using cmake: $cmake_prog, version: $cmake_ver") return $cmake_prog } else { @@ -388,15 +431,15 @@ function setup_nuget() { return $nuget_prog } - if (!(Test-Path -Path $nuget_bin -PathType Container)) { - mkdirs $nuget_bin + if (!$b1k.isdir($nuget_bin)) { + $b1k.mkdirs($nuget_bin) } $nuget_prog = Join-Path $nuget_bin 'nuget.exe' download_file "https://dist.nuget.org/win-x86-commandline/$nuget_ver/nuget.exe" $nuget_prog - if (Test-Path -Path $nuget_prog -PathType Leaf) { - b1k_print "Using nuget: $nuget_prog, version: $nuget_ver" + if ($b1k.isfile($nuget_prog)) { + $b1k.println("Using nuget: $nuget_prog, version: $nuget_ver") return $nuget_prog } else { @@ -404,6 +447,27 @@ function setup_nuget() { } } +function setup_nsis() { + if(!$manifest.Contains('nsis')) { return $null } + $nsis_prog, $nsis_ver = find_prog -name 'nsis' -cmd 'makensis' -params '/VERSION' + if ($nsis_prog) { + return $nsis_prog + } + + $nsis_bin = Join-Path $prefix "nsis-$nsis_ver" + if (!$b1k.isdir($nsis_bin)) { + download_file "https://nchc.dl.sourceforge.net/project/nsis/NSIS%203/$nsis_ver/nsis-$nsis_ver.zip" "$prefix/nsis-$nsis_ver.zip" + Expand-Archive -Path $prefix/nsis-$nsis_ver.zip -DestinationPath "$prefix" + } + if ($env:PATH.IndexOf($nsis_bin) -eq -1) { + $env:PATH = "$nsis_bin$envPathSep$env:PATH" + } + $nsis_prog = (Join-Path $nsis_bin "makensis$exeSuffix") + + $b1k.println("Using nsis: $nsis_prog, version: $nsis_ver") + return $nsis_prog +} + function setup_jdk() { if (!$manifest.Contains('jdk')) { return $null } $javac_prog, $jdk_ver = find_prog -name 'jdk' -cmd 'javac' @@ -413,9 +477,9 @@ function setup_jdk() { $suffix = $('windows-x64.zip', 'linux-x64.tar.gz', 'macOS-x64.tar.gz').Get($HOST_OS) $java_home = Join-Path $prefix "jdk-$jdk_ver" - if (!(Test-Path $java_home -PathType Container)) { + if (!$b1k.isdir($java_home)) { # refer to https://learn.microsoft.com/en-us/java/openjdk/download - if (!(Test-Path "$prefix/microsoft-jdk-$jdk_ver-$suffix" -PathType Leaf)) { + if (!$b1k.isfile("$prefix/microsoft-jdk-$jdk_ver-$suffix")) { download_file "https://aka.ms/download-jdk/microsoft-jdk-$jdk_ver-$suffix" "$prefix/microsoft-jdk-$jdk_ver-$suffix" } @@ -444,7 +508,7 @@ function setup_jdk() { throw "Install jdk $jdk_ver fail" } - b1k_print "Using jdk: $javac_prog, version: $jdk_ver" + $b1k.println("Using jdk: $javac_prog, version: $jdk_ver") return $javac_prog } @@ -458,16 +522,16 @@ function setup_glslcc() { } $suffix = $('win64.zip', 'linux.tar.gz', 'osx.tar.gz').Get($HOST_OS) - if (!(Test-Path $glslcc_bin -PathType Container)) { + if (!$b1k.isdir($glslcc_bin)) { $glslcc_pkg = "$prefix/glslcc-$suffix" - if (!(Test-Path $glslcc_pkg -PathType Leaf)) { + if (!$b1k.isfile($glslcc_pkg)) { download_file "https://github.com/septag/glslcc/releases/download/v$glslcc_ver/glslcc-$glslcc_ver-$suffix" "$glslcc_pkg" } if ($IsWin) { Expand-Archive -Path $glslcc_pkg -DestinationPath $glslcc_bin } else { - mkdirs $glslcc_bin + $b1k.mkdirs($glslcc_bin) tar xvf "$glslcc_pkg" -C $glslcc_bin } } @@ -476,7 +540,7 @@ function setup_glslcc() { } $glslcc_prog = (Join-Path $glslcc_bin "glslcc$exeSuffix") - b1k_print "Using glslcc: $glslcc_prog, version: $glslcc_ver" + $b1k.println("Using glslcc: $glslcc_prog, version: $glslcc_ver") return $glslcc_prog } @@ -500,7 +564,7 @@ function setup_ninja() { } $ninja_prog = (Join-Path $ninja_bin "ninja$exeSuffix") - b1k_print "Using ninja: $ninja_prog, version: $ninja_ver" + $b1k.println("Using ninja: $ninja_prog, version: $ninja_ver") return $ninja_prog } @@ -525,7 +589,7 @@ function setup_android_sdk() { $sdk_root = $null foreach ($sdk_root_env in $sdk_root_envs) { $sdk_dir = [Environment]::GetEnvironmentVariable($sdk_root_env) - b1k_print "Looking require $ndk_ver$IsGraterThan in env:$sdk_root_env=$sdk_dir" + $b1k.println("Looking require $ndk_ver$IsGraterThan in env:$sdk_root_env=$sdk_dir") if ("$sdk_dir" -ne '') { $sdk_root = $sdk_dir $ndk_root = $null @@ -536,7 +600,7 @@ function setup_android_sdk() { $ndk_rev_base = "$ndk_major.$ndk_minor" $ndk_parent = Join-Path $sdk_dir 'ndk' - if (!(Test-Path $ndk_parent -PathType Container)) { + if (!$b1k.isdir($ndk_parent)) { continue } @@ -546,7 +610,7 @@ function setup_android_sdk() { foreach ($item in $(Get-ChildItem -Path "$ndk_parent")) { $ndkDir = $item.FullName $sourceProps = "$ndkDir/source.properties" - if (Test-Path $sourceProps -PathType Leaf) { + if ($b1k.isfile($sourceProps)) { $verLine = $(Get-Content $sourceProps | Select-Object -Index 1) $ndk_rev = $($verLine -split '=').Trim()[1].split('.')[0..1] -join '.' $ndks.Add($ndk_rev, $ndkDir) @@ -565,36 +629,36 @@ function setup_android_sdk() { } if ($null -ne $ndk_root) { - b1k_print "Found $ndk_root in $sdk_root ..." + $b1k.println("Found $ndk_root in $sdk_root ...") break } } } - if (!(Test-Path "$ndk_root" -PathType Container)) { + if (!$b1k.isdir("$ndk_root")) { $sdkmanager_prog, $sdkmanager_ver = $null, $null - if (Test-Path "$sdk_root" -PathType Container) { - $sdkmanager_prog, $sdkmanager_ver = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$sdk_root/cmdline-tools/latest/bin" -param "--sdk_root=$sdk_root") + if ($b1k.isdir($sdk_root)) { + $sdkmanager_prog, $sdkmanager_ver = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$sdk_root/cmdline-tools/latest/bin" -params "--version", "--sdk_root=$sdk_root") } else { $sdk_root = Join-Path $prefix 'adt/sdk' - if (!(Test-Path -Path $sdk_root -PathType Container)) { - mkdirs $sdk_root + if (!$b1k.isdir($sdk_root)) { + $b1k.mkdirs($sdk_root) } } if (!$sdkmanager_prog) { - $sdkmanager_prog, $sdkmanager_ver = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$prefix/cmdline-tools/bin" -param "--sdk_root=$sdk_root") + $sdkmanager_prog, $sdkmanager_ver = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$prefix/cmdline-tools/bin" -params "--version", "--sdk_root=$sdk_root") $suffix = $('win', 'linux', 'mac').Get($HOST_OS) if (!$sdkmanager_prog) { - b1k_print "Installing cmdlinetools version: $sdkmanager_ver ..." + $b1k.println("Installing cmdlinetools version: $sdkmanager_ver ...") $cmdlinetools_pkg_name = "commandlinetools-$suffix-$($cmdlinetools_rev)_latest.zip" $cmdlinetools_pkg_path = Join-Path $prefix $cmdlinetools_pkg_name $cmdlinetools_url = "https://dl.google.com/android/repository/$cmdlinetools_pkg_name" download_file $cmdlinetools_url $cmdlinetools_pkg_path Expand-Archive -Path $cmdlinetools_pkg_path -DestinationPath "$prefix/" - $sdkmanager_prog, $_ = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$prefix/cmdline-tools/bin" -param "--sdk_root=$sdk_root" -silent $True) + $sdkmanager_prog, $_ = (find_prog -name 'cmdlinetools' -cmd 'sdkmanager' -path "$prefix/cmdline-tools/bin" -params "--version", "--sdk_root=$sdk_root" -silent $True) if (!$sdkmanager_prog) { throw "Install cmdlinetools version: $sdkmanager_ver fail" } @@ -603,7 +667,7 @@ function setup_android_sdk() { $matchInfos = (exec_prog -prog $sdkmanager_prog -params "--sdk_root=$sdk_root", '--list' | Select-String 'ndk;') if ($null -ne $matchInfos -and $matchInfos.Count -gt 0) { - b1k_print "Not found suitable android ndk, installing ..." + $b1k.println("Not found suitable android ndk, installing ...") $ndks = @{} foreach ($matchInfo in $matchInfos) { @@ -838,6 +902,7 @@ $cmake_prog = setup_cmake if ($BUILD_TARGET -eq 'win32') { $nuget_prog = setup_nuget + # $nsis_prog = setup_nsis if ($TOOLCHAIN_NAME -ne 'msvc') { $ninja_prog = setup_ninja $null = setup_clang @@ -862,7 +927,7 @@ if (!$options.setupOnly) { } # enter building steps - b1k_print "Building target $BUILD_TARGET on $HOST_OS_NAME with toolchain $TOOLCHAIN ..." + $b1k.println("Building target $BUILD_TARGET on $HOST_OS_NAME with toolchain $TOOLCHAIN ...") # step1. preprocess cross make options $CONFIG_ALL_OPTIONS = [array]$(& $proprocessTable[$BUILD_TARGET] -inputOptions $CONFIG_DEFAULT_OPTIONS) @@ -874,7 +939,7 @@ if (!$options.setupOnly) { # step2. apply additional cross make options $xopts = [array]$options.xc if ($xopts.Count -gt 0) { - b1k_print ("Apply additional cross make options: $($xopts), Count={0}" -f $xopts.Count) + $b1k.println("Apply additional cross make options: $($xopts), Count={0}" -f $xopts.Count) $CONFIG_ALL_OPTIONS += $xopts } if ("$($xopts)".IndexOf('-B') -eq -1) { @@ -893,7 +958,7 @@ if (!$options.setupOnly) { } } } - b1k_print ("CONFIG_ALL_OPTIONS=$CONFIG_ALL_OPTIONS, Count={0}" -f $CONFIG_ALL_OPTIONS.Count) + $b1k.println("CONFIG_ALL_OPTIONS=$CONFIG_ALL_OPTIONS, Count={0}" -f $CONFIG_ALL_OPTIONS.Count) # parsing build optimize flag from build_options $buildOptions = [array]$options.xb @@ -937,7 +1002,7 @@ if (!$options.setupOnly) { if ($TOOLCHAIN_NAME -eq 'xcode') { $BUILD_ALL_OPTIONS += '--', '-quiet' } - b1k_print ("BUILD_ALL_OPTIONS=$BUILD_ALL_OPTIONS, Count={0}" -f $BUILD_ALL_OPTIONS.Count) + $b1k.println("BUILD_ALL_OPTIONS=$BUILD_ALL_OPTIONS, Count={0}" -f $BUILD_ALL_OPTIONS.Count) cmake --build $BUILD_DIR $BUILD_ALL_OPTIONS | Out-Host } diff --git a/cmake/Modules/AXBuildHelpers.cmake b/cmake/Modules/AXBuildHelpers.cmake index 337dabdc94..7d929d8a4f 100644 --- a/cmake/Modules/AXBuildHelpers.cmake +++ b/cmake/Modules/AXBuildHelpers.cmake @@ -385,13 +385,10 @@ function(ax_setup_app_config app_name) ) endif() - if (IS_DIRECTORY ${GLSLCC_OUT_DIR}) - get_target_property(rt_output ${app_name} RUNTIME_OUTPUT_DIRECTORY) - if ((WIN32 AND (NOT WINRT)) OR LINUX) + if((WIN32 AND (NOT WINRT)) OR LINUX) + if (IS_DIRECTORY ${GLSLCC_OUT_DIR}) + get_target_property(rt_output ${app_name} RUNTIME_OUTPUT_DIRECTORY) ax_sync_target_res(${APP_NAME} LINK_TO "${rt_output}/${CMAKE_CFG_INTDIR}/axslc" FOLDERS ${GLSLCC_OUT_DIR} SYM_LINK 1 SYNC_TARGET_ID axslc) - elseif(APPLE) - ax_mark_multi_resources(compiled_shader_files RES_TO "Resources/axslc" FOLDERS ${GLSLCC_OUT_DIR}) - target_sources(${app_name} PRIVATE ${compiled_shader_files}) endif() endif() endfunction() @@ -601,5 +598,4 @@ endmacro() # import minimal AXGLSLCC.cmake for shader compiler support # the function: ax_target_compile_shaders avaiable from it -set(GLSLCC_FIND_PROG_ROOT "${_AX_ROOT}/tools/external/glslcc") include(AXGLSLCC) diff --git a/cmake/Modules/AXGLSLCC.cmake b/cmake/Modules/AXGLSLCC.cmake index 82a6497b51..d71f72230d 100644 --- a/cmake/Modules/AXGLSLCC.cmake +++ b/cmake/Modules/AXGLSLCC.cmake @@ -3,6 +3,15 @@ cmake_policy(SET CMP0057 NEW) ############################################################## ## enable shader lang by shader compiler: glslcc +find_program(GLSLCC_EXE NAMES glslcc + PATHS ${_AX_ROOT}/tools/external/glslcc +) + +if (NOT GLSLCC_EXE) + message("glslcc not found.") + message(FATAL_ERROR "Please run setup.ps1 again to download glslcc, and run CMake again.") +endif() + macro(glslcc_option variable value) if(NOT DEFINED ${variable}) set(${variable} ${value}) @@ -14,20 +23,6 @@ glslcc_option(GLSLCC_VERT_SOURCE_FILE_EXTENSIONS .vert;.vsh) glslcc_option(GLSLCC_OUT_DIR ${CMAKE_BINARY_DIR}/runtime/axslc) glslcc_option(GLSLCC_OUT_SUFFIX "") glslcc_option(GLSLCC_FLAT_UBOS TRUE) -glslcc_option(GLSLCC_FIND_PROG_ROOT "") - -if(APPLE) - set(GLSLCC_FLAT_UBOS FALSE) -endif() - -find_program(GLSLCC_EXE NAMES glslcc - PATHS ${GLSLCC_FIND_PROG_ROOT} -) - -if (NOT GLSLCC_EXE) - message("glslcc not found.") - message(FATAL_ERROR "Please run setup.ps1 again to download glslcc, and run CMake again.") -endif() message(STATUS "GLSLCC_FRAG_SOURCE_FILE_EXTENSIONS=${GLSLCC_FRAG_SOURCE_FILE_EXTENSIONS}") message(STATUS "GLSLCC_VERT_SOURCE_FILE_EXTENSIONS=${GLSLCC_VERT_SOURCE_FILE_EXTENSIONS}") @@ -39,11 +34,6 @@ define_property(SOURCE PROPERTY GLSLCC_INCLUDE_DIRS BRIEF_DOCS "Compiled shader include directories" FULL_DOCS "Compiled shader include directories, seperated with comma") -# PROPERTY: defines (optional) -define_property(SOURCE PROPERTY GLSLCC_DEFINES - BRIEF_DOCS "Compiled shader defines" - FULL_DOCS "Compiled shader defines, seperated with comma") - # Find shader sources in specified directory # syntax: ax_find_shaders(dir shader_sources [RECURSE]) # examples: @@ -87,8 +77,6 @@ function (ax_target_compile_shaders target_name) get_filename_component(FILE_NAME ${SC_FILE} NAME_WE) string(TOLOWER "${FILE_EXT}" FILE_EXT) - set(SC_DEFINES "") - # silent when compile shader success set(SC_FLAGS "--silent" "--err-format=msvc") @@ -106,17 +94,7 @@ function (ax_target_compile_shaders target_name) list(APPEND SC_FLAGS "--lang=glsl" "--profile=${SC_PROFILE}") elseif (APPLE) set(OUT_LANG "MSL") - list(APPEND SC_FLAGS "--lang=msl") - list(APPEND SC_DEFINES "METAL") - endif() - - # defines - get_source_file_property(SOURCE_SC_DEFINES ${SC_FILE} GLSLCC_DEFINES) - if (NOT (SOURCE_SC_DEFINES STREQUAL "NOTFOUND")) - list(APPEND SC_DEFINES ${SOURCE_SC_DEFINES}) - endif() - if (SC_DEFINES) - list(APPEND SC_FLAGS "--defines=${SC_DEFINES}") + list(APPEND SC_FLAGS "--lang=msl" "--defines=METAL") endif() # includes @@ -127,7 +105,7 @@ function (ax_target_compile_shaders target_name) list(APPEND INC_DIRS "${_AX_ROOT}/core/renderer/shaders") list(APPEND SC_FLAGS "--include-dirs=${INC_DIRS}") - # flat-ubos + # flat-ubs if(${GLSLCC_FLAT_UBOS}) list(APPEND SC_FLAGS "--flatten-ubos") endif() @@ -135,36 +113,27 @@ function (ax_target_compile_shaders target_name) # input if (${FILE_EXT} IN_LIST GLSLCC_FRAG_SOURCE_FILE_EXTENSIONS) list(APPEND SC_FLAGS "--frag=${SC_FILE}") - set(SC_TYPE "fs") + set(TYPE "fs") elseif(${FILE_EXT} IN_LIST GLSLCC_VERT_SOURCE_FILE_EXTENSIONS) - set(SC_TYPE "vs") + set(TYPE "vs") list(APPEND SC_FLAGS "--vert=${SC_FILE}") else() message(FATAL_ERROR "Invalid shader source, the file extesion must be one of .frag;.vert") endif() - # sgs, because Apple Metal lack of shader uniform reflect so use --sgs --refelect - if (APPLE) - list(APPEND SC_FLAGS "--sgs" "--reflect") - # need add suffix manually when flags contains --sgs - set(SC_SUFFIX "_${SC_TYPE}") - else() - set(SC_SUFFIX "") - endif() - # output set(OUT_DIR ${GLSLCC_OUT_DIR}) if (NOT (IS_DIRECTORY ${OUT_DIR})) file(MAKE_DIRECTORY ${OUT_DIR}) endif() if (NOT opt_CVAR) - list(APPEND SC_FLAGS "--output=${OUT_DIR}/${FILE_NAME}${GLSLCC_OUT_SUFFIX}${SC_SUFFIX}" ) + list(APPEND SC_FLAGS "--output=${OUT_DIR}/${FILE_NAME}${GLSLCC_OUT_SUFFIX}" ) # glscc will auto insert ${FILE_NAME}_vs.bin or ${FILE_NAME}_fs.bin # so we set OUTPUT to match with it, otherwise will cause cause incremental build to work incorrectly. - set(SC_OUTPUT "${OUT_DIR}/${FILE_NAME}_${SC_TYPE}${GLSLCC_OUT_SUFFIX}") + set(SC_OUTPUT "${OUT_DIR}/${FILE_NAME}_${TYPE}${GLSLCC_OUT_SUFFIX}") else() - set(SC_OUTPUT "${OUT_DIR}/${FILE_NAME}_${SC_TYPE}${GLSLCC_OUT_SUFFIX}.h") + set(SC_OUTPUT "${OUT_DIR}/${FILE_NAME}_${TYPE}${GLSLCC_OUT_SUFFIX}.h") list(APPEND SC_FLAGS "${OUT_FILE}" "--cvar=shader_rt_${FILE_NAME}" "--output=${SC_OUTPUT}") endif() diff --git a/core/CMakeLists.txt b/core/CMakeLists.txt index 12a65ae39b..6709a3da41 100644 --- a/core/CMakeLists.txt +++ b/core/CMakeLists.txt @@ -190,20 +190,6 @@ list(APPEND _AX_SRC ${_AX_HEADER}) add_library(${_AX_CORE_LIB} ${_AX_SRC}) -ax_find_shaders(${_AX_ROOT}/core/renderer/shaders BUILTIN_SHADER_SOURCES) - -# not final fix the macro not defined glslcc compiler errors -# set_source_files_properties( -# ${_AX_ROOT}/core/renderer/shaders/colorNormal.frag -# ${_AX_ROOT}/core/renderer/shaders/colorNormalTexture.frag -# ${_AX_ROOT}/core/renderer/shaders/positionNormalTexture.vert -# ${_AX_ROOT}/core/renderer/shaders/skinPositionNormalTexture.vert -# PROPERTIES GLSLCC_DEFINES -# "MAX_DIRECTIONAL_LIGHT_NUM=1,MAX_POINT_LIGHT_NUM=1,MAX_SPOT_LIGHT_NUM=1" -# ) -ax_target_compile_shaders(${_AX_CORE_LIB} FILES ${BUILTIN_SHADER_SOURCES}) - - if (WINRT) target_compile_options(${_AX_CORE_LIB} PUBLIC /ZW) endif() diff --git a/core/platform/apple/FileUtils-apple.mm b/core/platform/apple/FileUtils-apple.mm index e85890b7fb..ab9990b886 100644 --- a/core/platform/apple/FileUtils-apple.mm +++ b/core/platform/apple/FileUtils-apple.mm @@ -76,7 +76,6 @@ FileUtils* FileUtils::getInstance() s_sharedFileUtils = nullptr; AXLOG("ERROR: Could not init CCFileUtilsApple"); } - s_sharedFileUtils->addSearchPath("axslc"); } return s_sharedFileUtils; } diff --git a/core/platform/linux/FileUtils-linux.cpp b/core/platform/linux/FileUtils-linux.cpp index ea0a007e09..d9a0e35701 100644 --- a/core/platform/linux/FileUtils-linux.cpp +++ b/core/platform/linux/FileUtils-linux.cpp @@ -73,9 +73,9 @@ bool FileUtilsLinux::init() DECLARE_GUARD; // application path - std::string tmpPath = _checkPath("/proc/self/exe"); - std::string_view exePathSV{tmpPath}; - auto slash = tmpPath.find_last_of('/'); + std::string exePath = _checkPath("/proc/self/exe"); + std::string_view exePathSV{exePath}; + auto slash = exePath.find_last_of('/'); assert(slash != std::string::npos); auto exeDir = exePathSV.substr(0, slash + 1); @@ -112,10 +112,6 @@ bool FileUtilsLinux::init() if (!startedFromSelfLocation) addSearchPath(exeDir); - // linux: for load compiled shader from exeDir/axslc - tmpPath.resize(slash); - tmpPath += "/axslc"; - addSearchPath(tmpPath); return ret; } diff --git a/core/platform/win32/FileUtils-win32.cpp b/core/platform/win32/FileUtils-win32.cpp index 194e7bf07a..7c1d9dfece 100644 --- a/core/platform/win32/FileUtils-win32.cpp +++ b/core/platform/win32/FileUtils-win32.cpp @@ -124,9 +124,6 @@ bool FileUtilsWin32::init() if (!startedFromSelfLocation) addSearchPath(s_exeDir); - // win32: load compiled shader from exeDir/axslc - addSearchPath(s_exeDir + "/axslc"); - return bRet; } diff --git a/core/renderer/Shaders.cpp b/core/renderer/Shaders.cpp index 190f4e8fb2..320de04e23 100644 --- a/core/renderer/Shaders.cpp +++ b/core/renderer/Shaders.cpp @@ -29,58 +29,53 @@ THE SOFTWARE. NS_AX_BEGIN // -AX_DLL const std::string_view positionColor_vert = "positionColor_vs"; -AX_DLL const std::string_view positionColor_frag = "positionColor_fs"; -AX_DLL const std::string_view positionTexture_vert = "positionTexture_vs"; -AX_DLL const std::string_view positionTexture_frag = "positionTexture_fs"; -AX_DLL const std::string_view positionTextureColor_vert = "positionTextureColor_vs"; -AX_DLL const std::string_view positionTextureColor_frag = "positionTextureColor_fs"; -AX_DLL const std::string_view positionTextureColorAlphaTest_frag = "positionTextureColorAlphaTest_fs"; -AX_DLL const std::string_view label_normal_frag = "label_normal_fs"; -AX_DLL const std::string_view label_distanceNormal_frag = "label_distanceNormal_fs"; -AX_DLL const std::string_view labelOutline_frag = "labelOutline_fs"; -AX_DLL const std::string_view labelDistanceFieldGlow_frag = "labelDistanceFieldGlow_fs"; -AX_DLL const std::string_view positionColorLengthTexture_vert = "positionColorLengthTexture_vs"; -AX_DLL const std::string_view positionColorLengthTexture_frag = "positionColorLengthTexture_fs"; -AX_DLL const std::string_view positionColorTextureAsPointsize_vert = "positionColorTextureAsPointsize_vs"; -AX_DLL const std::string_view position_vert = "position_vs"; -AX_DLL const std::string_view layer_radialGradient_frag = "layer_radialGradient_fs"; -AX_DLL const std::string_view grayScale_frag = "grayScale_fs"; -AX_DLL const std::string_view positionUColor_vert = "positionUColor_vs"; -AX_DLL const std::string_view dualSampler_frag = "dualSampler_fs"; -AX_DLL const std::string_view dualSampler_gray_frag = "dualSampler_gray_fs"; -AX_DLL const std::string_view cameraClear_vert = "cameraClear_vs"; -AX_DLL const std::string_view cameraClear_frag = "cameraClear_fs"; -AX_DLL const std::string_view quadTexture_frag = "quadTexture_fs"; -AX_DLL const std::string_view quadTexture_vert = "quadTexture_vs"; -AX_DLL const std::string_view quadColor_frag = "quadColor_fs"; -AX_DLL const std::string_view quadColor_vert = "quadColor_vs"; +// backend shader file +#include "renderer/shaders/positionColor.vert" +#include "renderer/shaders/positionColor.frag" +#include "renderer/shaders/positionTexture.vert" +#include "renderer/shaders/positionTexture.frag" +#include "renderer/shaders/positionTextureColor.vert" +#include "renderer/shaders/positionTextureColor.frag" +#include "renderer/shaders/positionTextureColorAlphaTest.frag" +#include "renderer/shaders/label_normal.frag" +#include "renderer/shaders/label_distanceNormal.frag" +#include "renderer/shaders/label_outline.frag" +#include "renderer/shaders/label_distanceFieldGlow.frag" +#include "renderer/shaders/positionColorLengthTexture.vert" +#include "renderer/shaders/positionColorLengthTexture.frag" +#include "renderer/shaders/positionColorTextureAsPointsize.vert" +#include "renderer/shaders/position.vert" +#include "renderer/shaders/layer_radialGradient.frag" +#include "renderer/shaders/ui_Gray.frag" +#include "renderer/shaders/positionUColor.vert" +#include "renderer/shaders/dualSampler.frag" +#include "renderer/shaders/dualSampler_gray.frag" +#include "renderer/shaders/cameraClear.vert" +#include "renderer/shaders/cameraClear.frag" -AX_DLL const std::string_view hsv_frag = "hsv_fs"; -AX_DLL const std::string_view dualSampler_hsv_frag = "dualSampler_hsv_fs"; +#include "renderer/shaders/3D_color.frag" +#include "renderer/shaders/3D_colorNormal.frag" +#include "renderer/shaders/3D_colorNormalTexture.frag" +#include "renderer/shaders/3D_colorTexture.frag" +#include "renderer/shaders/3D_particle.vert" +#include "renderer/shaders/3D_particle.frag" +#include "renderer/shaders/3D_positionNormalTexture.vert" +#include "renderer/shaders/3D_positionTexture.vert" +#include "renderer/shaders/3D_skybox.vert" +#include "renderer/shaders/3D_skybox.frag" +#include "renderer/shaders/3D_terrain.frag" +#include "renderer/shaders/3D_terrain.vert" -AX_DLL const std::string_view videoTextureYUY2_frag = "videoTextureYUY2_fs"; -AX_DLL const std::string_view videoTextureNV12_frag = "videoTextureNV12_fs"; -AX_DLL const std::string_view videoTextureBGRA_frag = "videoTextureBGRA_fs"; +#include "renderer/shaders/lineColor.frag" +#include "renderer/shaders/lineColor.vert" -/* below is 3d shaders */ -AX_DLL const std::string_view lineColor3D_frag = "lineColor3D_fs"; -AX_DLL const std::string_view lineColor3D_vert = "lineColor3D_vs"; -AX_DLL const std::string_view color_frag = "color_fs"; -AX_DLL const std::string_view colorNormal_frag = "colorNormal_fs"; -AX_DLL const std::string_view colorNormalTexture_frag = "colorNormalTexture_fs"; -AX_DLL const std::string_view colorTexture_frag = "colorTexture_fs"; -AX_DLL const std::string_view particleTexture_frag = "particleTexture_fs"; -AX_DLL const std::string_view particleColor_frag = "particleColor_fs"; -AX_DLL const std::string_view particle_vert = "particle_vs"; -AX_DLL const std::string_view positionNormalTexture_vert = "positionNormalTexture_vs"; -AX_DLL const std::string_view skinPositionNormalTexture_vert = "skinPositionNormalTexture_vs"; -AX_DLL const std::string_view positionTexture3D_vert = "positionTexture3D_vs"; -AX_DLL const std::string_view skinPositionTexture_vert = "skinPositionTexture_vs"; -AX_DLL const std::string_view skybox_frag = "skybox_fs"; -AX_DLL const std::string_view skybox_vert = "skybox_vs"; -AX_DLL const std::string_view terrain_frag = "terrain_fs"; -AX_DLL const std::string_view terrain_vert = "terrain_vs"; +#include "renderer/shaders/hsv.frag" +#include "renderer/shaders/dualSampler_hsv.frag" + +#include "renderer/shaders/quad.vert" +#include "renderer/shaders/quad.frag" + +#include "renderer/shaders/videoTexture.frag" NS_AX_END diff --git a/core/renderer/Shaders.h b/core/renderer/Shaders.h index daaba5f8a2..0b18633654 100644 --- a/core/renderer/Shaders.h +++ b/core/renderer/Shaders.h @@ -39,59 +39,58 @@ THE SOFTWARE. NS_AX_BEGIN -extern AX_DLL const std::string_view positionColor_vert; -extern AX_DLL const std::string_view positionColor_frag; -extern AX_DLL const std::string_view positionTexture_vert; -extern AX_DLL const std::string_view positionTexture_frag; -extern AX_DLL const std::string_view positionTextureColor_vert; -extern AX_DLL const std::string_view positionTextureColor_frag; -extern AX_DLL const std::string_view positionTextureColorAlphaTest_frag; -extern AX_DLL const std::string_view label_normal_frag; -extern AX_DLL const std::string_view label_distanceNormal_frag; -extern AX_DLL const std::string_view labelOutline_frag; -extern AX_DLL const std::string_view labelDistanceFieldGlow_frag; -extern AX_DLL const std::string_view positionColorLengthTexture_vert; -extern AX_DLL const std::string_view positionColorLengthTexture_frag; -extern AX_DLL const std::string_view positionColorTextureAsPointsize_vert; -extern AX_DLL const std::string_view position_vert; -extern AX_DLL const std::string_view layer_radialGradient_frag; -extern AX_DLL const std::string_view grayScale_frag; -extern AX_DLL const std::string_view positionUColor_vert; -extern AX_DLL const std::string_view dualSampler_frag; -extern AX_DLL const std::string_view dualSampler_gray_frag; -extern AX_DLL const std::string_view cameraClear_vert; -extern AX_DLL const std::string_view cameraClear_frag; +extern AX_DLL const char* positionColor_vert; +extern AX_DLL const char* positionColor_frag; +extern AX_DLL const char* positionTexture_vert; +extern AX_DLL const char* positionTexture_frag; +extern AX_DLL const char* positionTextureColor_vert; +extern AX_DLL const char* positionTextureColor_frag; +extern AX_DLL const char* positionTextureColorAlphaTest_frag; +extern AX_DLL const char* label_normal_frag; +extern AX_DLL const char* label_distanceNormal_frag; +extern AX_DLL const char* labelOutline_frag; +extern AX_DLL const char* labelDistanceFieldGlow_frag; +extern AX_DLL const char* lineColor3D_frag; +extern AX_DLL const char* lineColor3D_vert; +extern AX_DLL const char* positionColorLengthTexture_vert; +extern AX_DLL const char* positionColorLengthTexture_frag; +extern AX_DLL const char* positionColorTextureAsPointsize_vert; +extern AX_DLL const char* position_vert; +extern AX_DLL const char* layer_radialGradient_frag; +extern AX_DLL const char* grayScale_frag; +extern AX_DLL const char* positionUColor_vert; +extern AX_DLL const char* dualSampler_frag; +extern AX_DLL const char* dualSampler_gray_frag; +extern AX_DLL const char* cameraClear_vert; +extern AX_DLL const char* cameraClear_frag; -extern AX_DLL const std::string_view quadTexture_frag; -extern AX_DLL const std::string_view quadTexture_vert; -extern AX_DLL const std::string_view quadColor_frag; -extern AX_DLL const std::string_view quadColor_vert; +extern AX_DLL const char* CC3D_color_frag; +extern AX_DLL const char* CC3D_colorNormal_frag; +extern AX_DLL const char* CC3D_colorNormalTexture_frag; +extern AX_DLL const char* CC3D_colorTexture_frag; +extern AX_DLL const char* CC3D_particleTexture_frag; +extern AX_DLL const char* CC3D_particleColor_frag; +extern AX_DLL const char* CC3D_particle_vert; +extern AX_DLL const char* CC3D_positionNormalTexture_vert; +extern AX_DLL const char* CC3D_skinPositionNormalTexture_vert; +extern AX_DLL const char* CC3D_positionTexture_vert; +extern AX_DLL const char* CC3D_skinPositionTexture_vert; +extern AX_DLL const char* CC3D_skybox_frag; +extern AX_DLL const char* CC3D_skybox_vert; +extern AX_DLL const char* CC3D_terrain_frag; +extern AX_DLL const char* CC3D_terrain_vert; -extern AX_DLL const std::string_view hsv_frag; -extern AX_DLL const std::string_view dualSampler_hsv_frag; +extern AX_DLL const char* CC2D_quadTexture_frag; +extern AX_DLL const char* CC2D_quadTexture_vert; +extern AX_DLL const char* CC2D_quadColor_frag; +extern AX_DLL const char* CC2D_quadColor_vert; -extern AX_DLL const std::string_view videoTextureYUY2_frag; -extern AX_DLL const std::string_view videoTextureNV12_frag; -extern AX_DLL const std::string_view videoTextureBGRA_frag; +extern AX_DLL const char* hsv_frag; +extern AX_DLL const char* dualSampler_hsv_frag; -/* below is 3d shaders */ -extern AX_DLL const std::string_view lineColor3D_frag; -extern AX_DLL const std::string_view lineColor3D_vert; -extern AX_DLL const std::string_view color_frag; -extern AX_DLL const std::string_view colorNormal_frag; -extern AX_DLL const std::string_view colorNormalTexture_frag; -extern AX_DLL const std::string_view colorTexture_frag; -extern AX_DLL const std::string_view particleTexture_frag; -extern AX_DLL const std::string_view particleColor_frag; -extern AX_DLL const std::string_view particle_vert; -extern AX_DLL const std::string_view positionNormalTexture_vert; -extern AX_DLL const std::string_view skinPositionNormalTexture_vert; -extern AX_DLL const std::string_view positionTexture3D_vert; -extern AX_DLL const std::string_view skinPositionTexture_vert; -extern AX_DLL const std::string_view skybox_frag; -extern AX_DLL const std::string_view skybox_vert; -extern AX_DLL const std::string_view terrain_frag; -extern AX_DLL const std::string_view terrain_vert; +extern AX_DLL const char* videoTextureYUY2_frag; +extern AX_DLL const char* videoTextureNV12_frag; +extern AX_DLL const char* videoTextureBGRA_frag; NS_AX_END /** end of support group diff --git a/core/renderer/backend/ProgramManager.cpp b/core/renderer/backend/ProgramManager.cpp index 3a1bc985f5..de05a4a0fa 100644 --- a/core/renderer/backend/ProgramManager.cpp +++ b/core/renderer/backend/ProgramManager.cpp @@ -53,8 +53,8 @@ std::string getShaderMacrosForLight() ProgramManager* ProgramManager::_sharedProgramManager = nullptr; Program* ProgramManager::newProgram(std::string_view vertShaderSource, - std::string_view fragShaderSource, - std::function fnSetupLayout) + std::string_view fragShaderSource, + std::function fnSetupLayout) { auto program = Device::getInstance()->newProgram(vertShaderSource, fragShaderSource); if (program) @@ -227,82 +227,84 @@ void VertexLayoutHelper::setupTerrain3D(Program* program) bool ProgramManager::init() { - registerProgramFactoryByName(ProgramType::POSITION_TEXTURE_COLOR, positionTextureColor_vert, positionTextureColor_frag, + registerProgramFactory(ProgramType::POSITION_TEXTURE_COLOR, positionTextureColor_vert, positionTextureColor_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::DUAL_SAMPLER, positionTextureColor_vert, dualSampler_frag, + registerProgramFactory(ProgramType::DUAL_SAMPLER, positionTextureColor_vert, dualSampler_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::LABEL_DISTANCE_NORMAL, positionTextureColor_vert, label_distanceNormal_frag, + registerProgramFactory(ProgramType::LABEL_DISTANCE_NORMAL, positionTextureColor_vert, label_distanceNormal_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::LABEL_NORMAL, positionTextureColor_vert, label_normal_frag, + registerProgramFactory(ProgramType::LABEL_NORMAL, positionTextureColor_vert, label_normal_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::LABLE_OUTLINE, positionTextureColor_vert, labelOutline_frag, + registerProgramFactory(ProgramType::LABLE_OUTLINE, positionTextureColor_vert, labelOutline_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::LABLE_DISTANCEFIELD_GLOW, positionTextureColor_vert, + registerProgramFactory(ProgramType::LABLE_DISTANCEFIELD_GLOW, positionTextureColor_vert, labelDistanceFieldGlow_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::POSITION_COLOR_LENGTH_TEXTURE, positionColorLengthTexture_vert, + registerProgramFactory(ProgramType::POSITION_COLOR_LENGTH_TEXTURE, positionColorLengthTexture_vert, positionColorLengthTexture_frag, VertexLayoutHelper::setupDrawNode); - registerProgramFactoryByName(ProgramType::POSITION_COLOR_TEXTURE_AS_POINTSIZE, positionColorTextureAsPointsize_vert, + registerProgramFactory(ProgramType::POSITION_COLOR_TEXTURE_AS_POINTSIZE, positionColorTextureAsPointsize_vert, positionColor_frag, VertexLayoutHelper::setupDrawNode); - registerProgramFactoryByName(ProgramType::POSITION_COLOR, positionColor_vert, positionColor_frag, + registerProgramFactory(ProgramType::POSITION_COLOR, positionColor_vert, positionColor_frag, VertexLayoutHelper::setupPosColor); - registerProgramFactoryByName(ProgramType::LAYER_RADIA_GRADIENT, position_vert, layer_radialGradient_frag, + registerProgramFactory(ProgramType::LAYER_RADIA_GRADIENT, position_vert, layer_radialGradient_frag, VertexLayoutHelper::setupPos); - registerProgramFactoryByName(ProgramType::POSITION_TEXTURE, positionTexture_vert, positionTexture_frag, + registerProgramFactory(ProgramType::POSITION_TEXTURE, positionTexture_vert, positionTexture_frag, VertexLayoutHelper::setupTexture); - registerProgramFactoryByName(ProgramType::POSITION_TEXTURE_COLOR_ALPHA_TEST, positionTextureColor_vert, + registerProgramFactory(ProgramType::POSITION_TEXTURE_COLOR_ALPHA_TEST, positionTextureColor_vert, positionTextureColorAlphaTest_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::POSITION_UCOLOR, positionUColor_vert, positionColor_frag, + registerProgramFactory(ProgramType::POSITION_UCOLOR, positionUColor_vert, positionColor_frag, VertexLayoutHelper::setupPos); - registerProgramFactoryByName(ProgramType::DUAL_SAMPLER_GRAY, positionTextureColor_vert, dualSampler_gray_frag, + registerProgramFactory(ProgramType::DUAL_SAMPLER_GRAY, positionTextureColor_vert, dualSampler_gray_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::GRAY_SCALE, positionTextureColor_vert, grayScale_frag, + registerProgramFactory(ProgramType::GRAY_SCALE, positionTextureColor_vert, grayScale_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::LINE_COLOR_3D, lineColor3D_vert, lineColor3D_frag, + registerProgramFactory(ProgramType::LINE_COLOR_3D, lineColor3D_vert, lineColor3D_frag, VertexLayoutHelper::setupDrawNode3D); - registerProgramFactoryByName(ProgramType::CAMERA_CLEAR, cameraClear_vert, cameraClear_frag, + registerProgramFactory(ProgramType::CAMERA_CLEAR, cameraClear_vert, cameraClear_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::SKYBOX_3D, skybox_vert, skybox_frag, VertexLayoutHelper::setupSkyBox); - registerProgramFactoryByName(ProgramType::SKINPOSITION_TEXTURE_3D, skinPositionTexture_vert, colorTexture_frag, + registerProgramFactory(ProgramType::SKYBOX_3D, CC3D_skybox_vert, CC3D_skybox_frag, VertexLayoutHelper::setupSkyBox); + registerProgramFactory(ProgramType::SKINPOSITION_TEXTURE_3D, CC3D_skinPositionTexture_vert, CC3D_colorTexture_frag, VertexLayoutHelper::setupDummy); auto lightDef = getShaderMacrosForLight(); - registerProgramFactoryByName(ProgramType::SKINPOSITION_NORMAL_TEXTURE_3D, skinPositionNormalTexture_vert, - colorNormalTexture_frag, VertexLayoutHelper::setupDummy, lightDef); - registerProgramFactoryByName(ProgramType::POSITION_NORMAL_TEXTURE_3D, positionNormalTexture_vert, - colorNormalTexture_frag, VertexLayoutHelper::setupDummy, lightDef); - registerProgramFactoryByName(ProgramType::POSITION_TEXTURE_3D, positionTexture3D_vert, colorTexture_frag, + registerProgramFactory(ProgramType::SKINPOSITION_NORMAL_TEXTURE_3D, lightDef + CC3D_skinPositionNormalTexture_vert, + lightDef + CC3D_colorNormalTexture_frag, VertexLayoutHelper::setupDummy); + registerProgramFactory(ProgramType::POSITION_NORMAL_TEXTURE_3D, lightDef + CC3D_positionNormalTexture_vert, + lightDef + CC3D_colorNormalTexture_frag, VertexLayoutHelper::setupDummy); + registerProgramFactory(ProgramType::POSITION_TEXTURE_3D, CC3D_positionTexture_vert, CC3D_colorTexture_frag, VertexLayoutHelper::setupDummy); - registerProgramFactoryByName(ProgramType::POSITION_3D, positionTexture3D_vert, color_frag, + registerProgramFactory(ProgramType::POSITION_3D, CC3D_positionTexture_vert, CC3D_color_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::POSITION_NORMAL_3D, positionNormalTexture_vert, colorNormal_frag, - VertexLayoutHelper::setupDummy, lightDef); - std::string lightNormMapDef = lightDef; - lightNormMapDef += "\n#define USE_NORMAL_MAPPING 1 \n"sv; - registerProgramFactoryByName(ProgramType::POSITION_BUMPEDNORMAL_TEXTURE_3D, - positionNormalTexture_vert, - colorNormalTexture_frag, VertexLayoutHelper::setupDummy, lightNormMapDef); - registerProgramFactoryByName(ProgramType::SKINPOSITION_BUMPEDNORMAL_TEXTURE_3D, - skinPositionNormalTexture_vert, - colorNormalTexture_frag, VertexLayoutHelper::setupDummy, lightNormMapDef); - registerProgramFactoryByName(ProgramType::TERRAIN_3D, terrain_vert, terrain_frag, + registerProgramFactory(ProgramType::POSITION_NORMAL_3D, lightDef + CC3D_positionNormalTexture_vert, + lightDef + CC3D_colorNormal_frag, VertexLayoutHelper::setupDummy); + const char* normalMapDef = "\n#define USE_NORMAL_MAPPING 1 \n"; + registerProgramFactory(ProgramType::POSITION_BUMPEDNORMAL_TEXTURE_3D, + lightDef + normalMapDef + CC3D_positionNormalTexture_vert, + lightDef + normalMapDef + CC3D_colorNormalTexture_frag, VertexLayoutHelper::setupDummy); + registerProgramFactory(ProgramType::SKINPOSITION_BUMPEDNORMAL_TEXTURE_3D, + lightDef + normalMapDef + CC3D_skinPositionNormalTexture_vert, + lightDef + normalMapDef + CC3D_colorNormalTexture_frag, VertexLayoutHelper::setupDummy); + registerProgramFactory(ProgramType::TERRAIN_3D, CC3D_terrain_vert, CC3D_terrain_frag, VertexLayoutHelper::setupTerrain3D); - registerProgramFactoryByName(ProgramType::PARTICLE_TEXTURE_3D, particle_vert, particleTexture_frag, + registerProgramFactory(ProgramType::PARTICLE_TEXTURE_3D, CC3D_particle_vert, CC3D_particleTexture_frag, VertexLayoutHelper::setupPU3D); - registerProgramFactoryByName(ProgramType::PARTICLE_COLOR_3D, particle_vert, particleColor_frag, + registerProgramFactory(ProgramType::PARTICLE_COLOR_3D, CC3D_particle_vert, CC3D_particleColor_frag, VertexLayoutHelper::setupPU3D); - registerProgramFactoryByName(ProgramType::QUAD_COLOR_2D, quadColor_vert, quadColor_frag, + registerProgramFactory(ProgramType::QUAD_COLOR_2D, CC2D_quadColor_vert, CC2D_quadColor_frag, VertexLayoutHelper::setupDummy); - registerProgramFactoryByName(ProgramType::QUAD_TEXTURE_2D, quadTexture_vert, quadTexture_frag, + registerProgramFactory(ProgramType::QUAD_TEXTURE_2D, CC2D_quadTexture_vert, CC2D_quadTexture_frag, VertexLayoutHelper::setupDummy); - registerProgramFactoryByName(ProgramType::HSV, positionTextureColor_vert, hsv_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::HSV_DUAL_SAMPLER, positionTextureColor_vert, dualSampler_hsv_frag, + registerProgramFactory(ProgramType::HSV, positionTextureColor_vert, hsv_frag, VertexLayoutHelper::setupSprite); + registerProgramFactory(ProgramType::HSV_DUAL_SAMPLER, positionTextureColor_vert, dualSampler_hsv_frag, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::VIDEO_TEXTURE_YUY2, positionTextureColor_vert, - std::string{videoTextureYUY2_frag}, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::VIDEO_TEXTURE_NV12, positionTextureColor_vert, - std::string{videoTextureNV12_frag}, VertexLayoutHelper::setupSprite); - registerProgramFactoryByName(ProgramType::VIDEO_TEXTURE_BGR32, positionTextureColor_vert, - std::string{videoTextureBGRA_frag}, VertexLayoutHelper::setupSprite); + registerProgramFactory(ProgramType::VIDEO_TEXTURE_YUY2, positionTextureColor_vert, + std::string{videoTextureYUY2_frag}, + VertexLayoutHelper::setupSprite); + registerProgramFactory(ProgramType::VIDEO_TEXTURE_NV12, positionTextureColor_vert, + std::string{videoTextureNV12_frag}, + VertexLayoutHelper::setupSprite); + registerProgramFactory(ProgramType::VIDEO_TEXTURE_BGR32, positionTextureColor_vert, + std::string{videoTextureBGRA_frag}, + VertexLayoutHelper::setupSprite); // The builtin dual sampler shader registry ProgramStateRegistry::getInstance()->registerProgram(ProgramType::POSITION_TEXTURE_COLOR, @@ -361,49 +363,38 @@ Program* ProgramManager::addProgram(uint32_t internalType) const } void ProgramManager::registerCustomProgramFactory(uint32_t type, - std::string_view vsName, - std::string_view fsName, - std::function fnSetupLayout) + std::string vertShaderSource, + std::string fragShaderSource, + std::function fnSetupLayout) { auto internalType = ProgramType::CUSTOM_PROGRAM | type; - registerProgramFactoryByName(internalType, vsName, fsName, - std::move(fnSetupLayout), ""); + registerProgramFactory(internalType, std::move(vertShaderSource), std::move(fragShaderSource), + std::move(fnSetupLayout)); } -void ProgramManager::registerProgramFactoryByName(uint32_t internalType, - std::string_view vertShaderName, - std::string_view fragShaderName, - std::function fnSetupLayout, - std::string_view defines) +void ProgramManager::registerProgramFactory(uint32_t internalType, + std::string&& vertShaderSource, + std::string&& fragShaderSource, + std::function fnSetupLayout) { - auto loadShaderFunc = [vsName = std::string{vertShaderName}, fsName = std::string{fragShaderName}, - setupLayout = std::move(fnSetupLayout), defines = std::string{defines}]() mutable { - auto fileUtils = FileUtils::getInstance(); - auto vertFile = fileUtils->fullPathForFilename(vsName); - auto fragFile = fileUtils->fullPathForFilename(fsName); - auto vertSource = fileUtils->getStringFromFile(vertFile); - auto fragSource = fileUtils->getStringFromFile(fragFile); - if (!defines.empty()) - { - vertSource.insert(0, defines); - fragSource.insert(0, defines); - } - auto program = backend::Device::getInstance()->newProgram(vertSource, fragSource); + auto constructProgram = [vsrc = std::move(vertShaderSource), fsrc = std::move(fragShaderSource), + setupLayout = std::move(fnSetupLayout)]() { + auto program = backend::Device::getInstance()->newProgram(vsrc, fsrc); setupLayout(program); return program; }; if (internalType < ProgramType::BUILTIN_COUNT) { - _builtinFactories[internalType] = loadShaderFunc; + _builtinFactories[internalType] = constructProgram; } else { auto it = _customFactories.find(internalType); if (it == _customFactories.end()) - _customFactories.emplace(internalType, loadShaderFunc); + _customFactories.emplace(internalType, constructProgram); else - it->second = loadShaderFunc; + it->second = constructProgram; } } diff --git a/core/renderer/backend/ProgramManager.h b/core/renderer/backend/ProgramManager.h index 6e82fb82c6..02700d6b5a 100644 --- a/core/renderer/backend/ProgramManager.h +++ b/core/renderer/backend/ProgramManager.h @@ -63,8 +63,8 @@ class AX_DLL ProgramManager : public Ref public: /** new progrma with vertexLayout setup support, user should use this API */ static Program* newProgram(std::string_view vertShaderSource, - std::string_view fragShaderSource, - std::function fnSetupLayout = VertexLayoutHelper::setupDummy); + std::string_view fragShaderSource, + std::function fnSetupLayout = VertexLayoutHelper::setupDummy); /** returns the shared instance */ static ProgramManager* getInstance(); @@ -80,9 +80,9 @@ public: // register custom program create factory void registerCustomProgramFactory(uint32_t type, - std::string_view vsName, - std::string_view fsName, - std::function fnSetupLayout = VertexLayoutHelper::setupDummy); + std::string vertShaderSource, + std::string fragShaderSource, + std::function fnSetupLayout = VertexLayoutHelper::setupDummy); /** * Remove a program object from cache. @@ -109,37 +109,36 @@ protected: */ bool init(); - void registerProgramFactoryByName(uint32_t internalType, - std::string_view vsName, - std::string_view fsName, - std::function fnSetupLayout, - std::string_view defines = ""sv); + void registerProgramFactory(uint32_t internalType, + std::string&& vertShaderSource, + std::string&& fragShaderSource, + std::function fnSetupLayout); Program* addProgram(uint32_t internalType) const; std::function _builtinFactories[(int)backend::ProgramType::BUILTIN_COUNT]; std::unordered_map> _customFactories; mutable std::unordered_map _cachedPrograms; ///< The cached program object. - static ProgramManager* _sharedProgramManager; ///< A shared instance of the program cache. + static ProgramManager* _sharedProgramManager; ///< A shared instance of the program cache. }; -using ProgramCache = ProgramManager; // for compatible +using ProgramCache = ProgramManager; // for compatible // end of _backend group /// @} NS_AX_BACKEND_END /** - * @alias some feq use types to namespace ax - */ +* @alias some feq use types to namespace ax +*/ NS_AX_BEGIN -using ProgramType = ::ax::backend::ProgramType; -using Program = ::ax::backend::Program; -using VertexLayout = ::ax::backend::VertexLayout; +using ProgramType = ::ax::backend::ProgramType; +using Program = ::ax::backend::Program; +using VertexLayout = ::ax::backend::VertexLayout; using VertexLayoutHelper = ::ax::backend::VertexLayoutHelper; -using ProgramManager = ::ax::backend::ProgramManager; -using ProgramRegistry = ::ax::backend::ProgramStateRegistry; +using ProgramManager = ::ax::backend::ProgramManager; +using ProgramRegistry = ::ax::backend::ProgramStateRegistry; NS_AX_END diff --git a/core/renderer/backend/ProgramState.cpp b/core/renderer/backend/ProgramState.cpp index af0adacc4c..27f4286608 100644 --- a/core/renderer/backend/ProgramState.cpp +++ b/core/renderer/backend/ProgramState.cpp @@ -33,7 +33,10 @@ #include #include "xxhash.h" -#include "glslcc/sgs-spec.h" + +#ifdef AX_USE_METAL +# include "glsl_optimizer.h" +#endif NS_AX_BACKEND_BEGIN @@ -301,13 +304,12 @@ void ProgramState::convertAndCopyUniformData(const backend::UniformInfo& uniform std::size_t srcSize, void* buffer) { - // The type is glslcc FOURCC ID - auto basicType = uniformInfo.type; + auto basicType = static_cast(uniformInfo.type); int offset = 0; switch (basicType) { - case SGS_VERTEXFORMAT_FLOAT: + case kGlslTypeFloat: { if (uniformInfo.isMatrix) { @@ -337,21 +339,21 @@ void ProgramState::convertAndCopyUniformData(const backend::UniformInfo& uniform } break; } -// case kGlslTypeBool: -// { -// bool b4[4]; -// for (int i = 0; i < uniformInfo.count; i++) -// { -// if (offset >= srcSize) -// break; -// -// convertbVec3TobVec4((bool*)((uint8_t*)srcData + offset), b4); -// memcpy((uint8_t*)buffer + uniformInfo.location + i * sizeof(b4), b4, sizeof(b4)); -// offset += BVEC3_SIZE; -// } -// break; -// } - case SGS_VERTEXFORMAT_INT: + case kGlslTypeBool: + { + bool b4[4]; + for (int i = 0; i < uniformInfo.count; i++) + { + if (offset >= srcSize) + break; + + convertbVec3TobVec4((bool*)((uint8_t*)srcData + offset), b4); + memcpy((uint8_t*)buffer + uniformInfo.location + i * sizeof(b4), b4, sizeof(b4)); + offset += BVEC3_SIZE; + } + break; + } + case kGlslTypeInt: { int i4[4]; for (int i = 0; i < uniformInfo.count; i++) diff --git a/core/renderer/backend/metal/CommandBufferMTL.mm b/core/renderer/backend/metal/CommandBufferMTL.mm index 1f32955215..6dcdc8d232 100644 --- a/core/renderer/backend/metal/CommandBufferMTL.mm +++ b/core/renderer/backend/metal/CommandBufferMTL.mm @@ -270,7 +270,7 @@ void CommandBufferMTL::setWinding(Winding winding) void CommandBufferMTL::setVertexBuffer(Buffer* buffer) { // Vertex buffer is bound in index 0. - [_mtlRenderEncoder setVertexBuffer:static_cast(buffer)->getMTLBuffer() offset:0 atIndex:DeviceMTL::DEFAULT_ATTRIBS_BINDING_INDEX]; + [_mtlRenderEncoder setVertexBuffer:static_cast(buffer)->getMTLBuffer() offset:0 atIndex:0]; } void CommandBufferMTL::setProgramState(ProgramState* programState) @@ -483,21 +483,20 @@ void CommandBufferMTL::setUniformBuffer() const for (auto& cb : callbackUniforms) cb.second(_programState, cb.first); - // Uniform buffer: glsl-optimizer is bound to index 1, glslcc: bound to 0 - constexpr int bindingIndex = DeviceMTL::VBO_BINDING_INDEX_START; + // Uniform buffer is bound to index 1. std::size_t bufferSize = 0; char* vertexBuffer = nullptr; _programState->getVertexUniformBuffer(&vertexBuffer, bufferSize); if (vertexBuffer) { - [_mtlRenderEncoder setVertexBytes:vertexBuffer length:bufferSize atIndex:bindingIndex]; + [_mtlRenderEncoder setVertexBytes:vertexBuffer length:bufferSize atIndex:1]; } char* fragmentBuffer = nullptr; _programState->getFragmentUniformBuffer(&fragmentBuffer, bufferSize); if (fragmentBuffer) { - [_mtlRenderEncoder setFragmentBytes:fragmentBuffer length:bufferSize atIndex:bindingIndex]; + [_mtlRenderEncoder setFragmentBytes:fragmentBuffer length:bufferSize atIndex:1]; } } } diff --git a/core/renderer/backend/metal/DeviceMTL.h b/core/renderer/backend/metal/DeviceMTL.h index 77b901f738..33b3f3d1b3 100644 --- a/core/renderer/backend/metal/DeviceMTL.h +++ b/core/renderer/backend/metal/DeviceMTL.h @@ -41,15 +41,6 @@ NS_AX_BACKEND_BEGIN class DeviceMTL : public Device { public: - /* The max vertex attribs, it's not how many device supports which may be lower. */ - static constexpr uint32_t MAX_VERTEX_ATTRIBS = 16; - - /* The vertex data buffers binding index start, the glslcc(SPIRV-Cross) compiled MSL uniform buffer index=0 */ - static constexpr uint32_t VBO_BINDING_INDEX_START = 0; - - /* The default attribs binding index */ - static constexpr uint32_t DEFAULT_ATTRIBS_BINDING_INDEX = VBO_BINDING_INDEX_START + MAX_VERTEX_ATTRIBS; - /** * Set CAMetalLayer. * @param metalLayer A CAMetalLayer object. diff --git a/core/renderer/backend/metal/ProgramMTL.mm b/core/renderer/backend/metal/ProgramMTL.mm index 1f94232ddb..a4225373ff 100644 --- a/core/renderer/backend/metal/ProgramMTL.mm +++ b/core/renderer/backend/metal/ProgramMTL.mm @@ -25,19 +25,20 @@ #include "ProgramMTL.h" #include "ShaderModuleMTL.h" #include "base/Macros.h" -#include "DeviceMTL.h" NS_AX_BACKEND_BEGIN namespace { -// constexpr std::string_view metalSpecificDefine = "#define METAL\n"sv; +constexpr std::string_view metalSpecificDefine = "#define METAL\n"sv; } ProgramMTL::ProgramMTL(std::string_view vertexShader, std::string_view fragmentShader) : Program(vertexShader, fragmentShader) { _vertexShader = static_cast(ShaderCache::newVertexShaderModule(vertexShader)); - _fragmentShader = static_cast(ShaderCache::newFragmentShaderModule(fragmentShader)); + std::string combinedSource{metalSpecificDefine}; + combinedSource += fragmentShader; + _fragmentShader = static_cast(ShaderCache::newFragmentShaderModule(std::move(combinedSource))); AX_SAFE_RETAIN(_vertexShader); AX_SAFE_RETAIN(_fragmentShader); diff --git a/core/renderer/backend/metal/RenderPipelineMTL.mm b/core/renderer/backend/metal/RenderPipelineMTL.mm index daa404475a..75de259a39 100644 --- a/core/renderer/backend/metal/RenderPipelineMTL.mm +++ b/core/renderer/backend/metal/RenderPipelineMTL.mm @@ -249,29 +249,24 @@ RenderPipelineMTL::~RenderPipelineMTL() void RenderPipelineMTL::setVertexLayout(MTLRenderPipelineDescriptor* mtlDescriptor, const PipelineDescriptor& descriptor) { + int vertexIndex = 0; auto vertexLayout = descriptor.programState->getVertexLayout(); if (!vertexLayout->isValid()) return; - int stride = vertexLayout->getStride(); - auto vertexDesc = mtlDescriptor.vertexDescriptor; - vertexDesc.layouts[DeviceMTL::DEFAULT_ATTRIBS_BINDING_INDEX].stride = stride; - vertexDesc.layouts[DeviceMTL::DEFAULT_ATTRIBS_BINDING_INDEX].stepFunction = + mtlDescriptor.vertexDescriptor.layouts[vertexIndex].stride = vertexLayout->getStride(); + mtlDescriptor.vertexDescriptor.layouts[vertexIndex].stepFunction = toMTLVertexStepFunction(vertexLayout->getVertexStepMode()); const auto& attributes = vertexLayout->getAttributes(); - - for (const auto& it : attributes) { auto attribute = it.second; - - vertexDesc.attributes[attribute.index].format = + mtlDescriptor.vertexDescriptor.attributes[attribute.index].format = toMTLVertexFormat(attribute.format, attribute.needToBeNormallized); - vertexDesc.attributes[attribute.index].offset = attribute.offset; + mtlDescriptor.vertexDescriptor.attributes[attribute.index].offset = attribute.offset; // Buffer index will always be 0; - vertexDesc.attributes[attribute.index].bufferIndex = DeviceMTL::DEFAULT_ATTRIBS_BINDING_INDEX; - + mtlDescriptor.vertexDescriptor.attributes[attribute.index].bufferIndex = 0; } } diff --git a/core/renderer/backend/metal/ShaderModuleMTL.h b/core/renderer/backend/metal/ShaderModuleMTL.h index af82217290..c5c1398ea2 100644 --- a/core/renderer/backend/metal/ShaderModuleMTL.h +++ b/core/renderer/backend/metal/ShaderModuleMTL.h @@ -26,21 +26,21 @@ #include "../ShaderModule.h" #include "../Types.h" -#include + #include #include #include #include #import +struct glslopt_shader; + NS_AX_BACKEND_BEGIN /** * @addtogroup _metal * @{ */ -struct SLCReflectContext; - /** * To Create a vertex or fragment shader. */ @@ -120,9 +120,9 @@ public: inline std::size_t getUniformBufferSize() const { return _uniformBufferSize; } private: - void parseAttibute(SLCReflectContext* context); - void parseUniform(SLCReflectContext* context); - void parseTexture(SLCReflectContext* context); + void parseAttibute(id mtlDevice, glslopt_shader* shader); + void parseUniform(id mtlDevice, glslopt_shader* shader); + void parseTexture(id mtlDevice, glslopt_shader* shader); void setBuiltinUniformLocation(); void setBuiltinAttributeLocation(); diff --git a/core/renderer/backend/metal/ShaderModuleMTL.mm b/core/renderer/backend/metal/ShaderModuleMTL.mm index 0a32c3d751..29ddf237ad 100644 --- a/core/renderer/backend/metal/ShaderModuleMTL.mm +++ b/core/renderer/backend/metal/ShaderModuleMTL.mm @@ -25,107 +25,44 @@ #include "ShaderModuleMTL.h" #include "DeviceMTL.h" -#include "yasio/ibstream.hpp" -#include "yasio/sz.hpp" - -#include "glslcc/sgs-spec.h" +#include "glsl_optimizer.h" NS_AX_BACKEND_BEGIN -struct SLCReflectContext { - sgs_chunk_refl* refl; - yasio::fast_ibstream_view* data; -}; - ShaderModuleMTL::ShaderModuleMTL(id mtlDevice, ShaderStage stage, std::string_view source) : ShaderModule(stage) { - yasio::fast_ibstream_view ibs(source.data(), source.length()); - uint32_t fourccId = ibs.read(); - if(fourccId != SGS_CHUNK) { + // Convert GLSL shader to metal shader + // TODO: don't crreate/destroy ctx every time. + glslopt_ctx* ctx = glslopt_initialize(kGlslTargetMetal); + glslopt_shader_type shaderType = stage == ShaderStage::VERTEX ? kGlslOptShaderVertex : kGlslOptShaderFragment; + glslopt_shader* glslShader = glslopt_optimize(ctx, shaderType, source.data(), 0); + if (!glslShader) + { + NSLog(@"Can not translate GLSL shader to metal shader:"); + NSLog(@"%s", source.data()); + return; + } + + const char* metalShader = glslopt_get_output(glslShader); + if (!metalShader) + { + NSLog(@"Can not get metal shader:"); + NSLog(@"%s", source.data()); + NSLog(@"%s", glslopt_get_log(glslShader)); + glslopt_cleanup(ctx); assert(false); return; } - auto sgs_size = ibs.read(); // always 0, doesn't matter - struct sgs_chunk chunk; - ibs.read_bytes(&chunk, static_cast(sizeof(chunk))); - - std::string_view mslCode; - - do { - fourccId = ibs.read(); - if(fourccId != SGS_CHUNK_STAG) { - assert(false); - return; // error - } - auto stage_size = ibs.read(); // stage_size - auto stage_id = ibs.read(); // stage_id - ShaderStage ref_stage = (ShaderStage)-1; - if (stage_id == SGS_STAGE_VERTEX) - ref_stage = ShaderStage::VERTEX; - else if(stage_id == SGS_STAGE_FRAGMENT) - ref_stage = ShaderStage::FRAGMENT; - - assert(ref_stage == stage); - - int code_size = 0; - fourccId = ibs.read(); - if (fourccId == SGS_CHUNK_CODE) { - code_size = ibs.read(); - mslCode = ibs.read_bytes(code_size); - } - else if(fourccId == SGS_CHUNK_DATA) { - code_size = ibs.read(); - mslCode = ibs.read_bytes(code_size); - } - else { - // no text or binary code chunk - assert(false); - } - - sgs_chunk_refl refl; - size_t refl_size = 0; - if(!ibs.eof()) { // try read reflect info - fourccId = ibs.read(); - if(fourccId == SGS_CHUNK_REFL) { - /* - REFL: Reflection data for the shader stage - struct sgs_chunk_refl: reflection data header - struct sgs_refl_input[]: array of vertex-shader input attributes (see sgs_chunk_refl for number of inputs) - struct sgs_refl_uniformbuffer[]: array of uniform buffer objects (see sgs_chunk_refl for number of uniform buffers) - struct sgs_refl_texture[]: array of texture objects (see sgs_chunk_refl for number of textures) - struct sgs_refl_texture[]: array of storage image objects (see sgs_chunk_refl for number of storage images) - struct sgs_refl_buffer[]: array of storage buffer objects (see sgs_chunk_refl for number of storage buffers) - */ - refl_size = ibs.read(); - ibs.read_bytes(&refl, static_cast(sizeof(refl))); - - SLCReflectContext context{&refl, &ibs}; - - // refl_inputs - parseAttibute(&context); - - // refl_uniformbuffers - parseUniform(&context); - - // refl_textures - parseTexture(&context); - - // refl_storage_images: ignore - ibs.advance(refl.num_storage_images * sizeof(sgs_refl_texture)); - - // refl_storage_buffers: ignore - ibs.advance(refl.num_storage_buffers * sizeof(sgs_refl_buffer)); - } - else { - ibs.advance(-4); // move readptr back 4 bytes - } - } - assert(ibs.eof()); - } while(false); // iterator stages, current only 1 stage - - auto metalShader = mslCode.data(); + // NSLog(@"%s", metalShader); + + parseAttibute(mtlDevice, glslShader); + parseUniform(mtlDevice, glslShader); + parseTexture(mtlDevice, glslShader); + setBuiltinUniformLocation(); + setBuiltinAttributeLocation(); + NSString* shader = [NSString stringWithUTF8String:metalShader]; NSError* error; id library = [mtlDevice newLibraryWithSource:shader options:nil error:&error]; @@ -133,42 +70,27 @@ ShaderModuleMTL::ShaderModuleMTL(id mtlDevice, ShaderStage stage, std { NSLog(@"Can not compile metal shader: %@", error); NSLog(@"%s", metalShader); + NSLog(@"%s", glslopt_get_log(glslShader)); + glslopt_shader_delete(glslShader); + glslopt_cleanup(ctx); assert(false); return; } - _mtlFunction = [library newFunctionWithName:@"main0"]; - + if (ShaderStage::VERTEX == stage) + _mtlFunction = [library newFunctionWithName:@"xlatMtlMain1"]; + else + _mtlFunction = [library newFunctionWithName:@"xlatMtlMain2"]; if (!_mtlFunction) { NSLog(@"metal shader is ---------------"); NSLog(@"%s", metalShader); - // NSLog(@"%s", glslopt_get_log(glslShader)); + NSLog(@"%s", glslopt_get_log(glslShader)); assert(false); } - - /* - === attrib: a_position, location: 0 - === attrib: a_color, location: 1 - === attrib: a_texCoord, location: 2 - */ - auto vertexAttribs = [_mtlFunction vertexAttributes]; - for (MTLVertexAttribute* attrib in vertexAttribs) { - std::string attribName = [[attrib name] UTF8String]; - int index = static_cast([attrib attributeIndex]); - - auto& attrinfo = _attributeInfo[attribName]; - - // !!!Fix attrib location due to glslcc reorder attribs, but reflect info not sync - if (index != attrinfo.location) { - attrinfo.location = index; - ax::print("=== Fix attrib: %s, location from %d to %d", attribName.c_str(), (int)attrinfo.location, index); - } - } - - setBuiltinUniformLocation(); - setBuiltinAttributeLocation(); + glslopt_shader_delete(glslShader); + glslopt_cleanup(ctx); [library release]; } @@ -177,60 +99,64 @@ ShaderModuleMTL::~ShaderModuleMTL() [_mtlFunction release]; } -void ShaderModuleMTL::parseAttibute(SLCReflectContext* context) +void ShaderModuleMTL::parseAttibute(id mtlDevice, glslopt_shader* shader) { - for(int i = 0; i < context->refl->num_inputs; ++i) { - sgs_refl_input attrib{0}; - context->data->read_bytes(&attrib, sizeof(attrib)); - + const int attributeCount = glslopt_shader_get_input_count(shader); + for (int i = 0; i < attributeCount; i++) + { + const char* parName; + glslopt_basic_type parType; + glslopt_precision parPrec; + int parVecSize, parMatSize, parArrSize, location; + glslopt_shader_get_input_desc(shader, i, &parName, &parType, &parPrec, &parVecSize, &parMatSize, &parArrSize, + &location); + AttributeBindInfo attributeInfo; - attributeInfo.attributeName = attrib.name; - attributeInfo.location = attrib.loc; - _attributeInfo[attributeInfo.attributeName] = attributeInfo; + attributeInfo.attributeName = parName; + attributeInfo.location = location; + _attributeInfo[parName] = attributeInfo; } } -void ShaderModuleMTL::parseUniform(SLCReflectContext* context) +void ShaderModuleMTL::parseUniform(id mtlDevice, glslopt_shader* shader) { - _uniformBufferSize = 0; - for(int i = 0; i < context->refl->num_uniform_buffers; ++i) { - sgs_refl_ub ub{0}; - context->data->read_bytes(&ub, sizeof(ub)); - for(int k = 0; k < ub.num_members; ++k) { - sgs_refl_ub_member ubm {0}; - context->data->read_bytes(&ubm, sizeof(ubm)); - auto location = YASIO_SZ_ALIGN(ubm.offset, 16); // align offset - auto alignedSize = YASIO_SZ_ALIGN(ubm.size_bytes, 16); // align sizeBytes - UniformInfo uniform; - uniform.count = ubm.array_size; - uniform.location = location; - uniform.isArray = ubm.array_size > 1; - uniform.size = ubm.size_bytes; // ubm.size_bytes; // nextLocation - location; - uniform.bufferOffset = location; - uniform.needConvert = (ubm.format == SGS_VERTEXFORMAT_FLOAT3) ? true : false; - uniform.type = // static_cast(parType); - uniform.isMatrix = ubm.format == SGS_VERTEXFORMAT_MAT4 || ubm.format == SGS_VERTEXFORMAT_MAT3 || ubm.format == SGS_VERTEXFORMAT_MAT34 || ubm.format == SGS_VERTEXFORMAT_MAT43; - _uniformInfos[ubm.name] = uniform; - _activeUniformInfos[location] = uniform; - - if (_maxLocation < location) - _maxLocation = (location + 1); - - _uniformBufferSize += alignedSize; + const int uniformCount = glslopt_shader_get_uniform_count(shader); + _uniformBufferSize = glslopt_shader_get_uniform_total_size(shader); + + for (int i = 0; i < uniformCount; ++i) + { + int nextLocation = -1; + const char* parName; + glslopt_basic_type parType; + glslopt_precision parPrec; + int parVecSize, parMatSize, parArrSize, location; + if (i + 1 < uniformCount) + { + glslopt_shader_get_uniform_desc(shader, i + 1, &parName, &parType, &parPrec, &parVecSize, &parMatSize, + &parArrSize, &location); + nextLocation = location; + } + else + { + nextLocation = static_cast(_uniformBufferSize); } - } -} -void ShaderModuleMTL::parseTexture(SLCReflectContext* context) -{ - for(int i = 0; i < context->refl->num_textures; ++i) { - sgs_refl_texture texinfo {0}; - context->data->read_bytes(&texinfo, sizeof(texinfo)); + glslopt_shader_get_uniform_desc(shader, i, &parName, &parType, &parPrec, &parVecSize, &parMatSize, &parArrSize, + &location); + + parArrSize = (parArrSize > 0) ? parArrSize : 1; UniformInfo uniform; - uniform.count = -1; - uniform.location = texinfo.binding; - uniform.isArray = texinfo.is_array; - _uniformInfos[texinfo.name] = uniform; + uniform.count = parArrSize; + uniform.location = location; + uniform.isArray = parArrSize; + uniform.size = nextLocation - location; + uniform.bufferOffset = location; + uniform.needConvert = (parVecSize == 3) ? true : false; + uniform.type = static_cast(parType); + uniform.isMatrix = (parMatSize > 1) ? true : false; + _uniformInfos[parName] = uniform; + _activeUniformInfos[location] = uniform; + _maxLocation = _maxLocation < location ? (location + 1) : _maxLocation; } } @@ -342,5 +268,24 @@ void ShaderModuleMTL::setBuiltinAttributeLocation() } } +void ShaderModuleMTL::parseTexture(id mtlDevice, glslopt_shader* shader) +{ + const int textureCount = glslopt_shader_get_texture_count(shader); + for (int i = 0; i < textureCount; ++i) + { + const char* parName; + glslopt_basic_type parType; + glslopt_precision parPrec; + int parVecSize, parMatSize, parArrSize, location; + glslopt_shader_get_texture_desc(shader, i, &parName, &parType, &parPrec, &parVecSize, &parMatSize, &parArrSize, + &location); + + UniformInfo uniform; + uniform.count = parArrSize; + uniform.location = location; + uniform.isArray = parArrSize > 0; + _uniformInfos[parName] = uniform; + } +} NS_AX_BACKEND_END diff --git a/core/renderer/backend/opengl/ProgramGL.cpp b/core/renderer/backend/opengl/ProgramGL.cpp index d8256b70d6..e11a10930d 100644 --- a/core/renderer/backend/opengl/ProgramGL.cpp +++ b/core/renderer/backend/opengl/ProgramGL.cpp @@ -35,11 +35,24 @@ NS_AX_BACKEND_BEGIN +namespace +{ +static const std::string SHADER_PREDEFINE = "#version 100\n precision highp float;\n precision highp int;\n"; +} + ProgramGL::ProgramGL(std::string_view vertexShader, std::string_view fragmentShader) : Program(vertexShader, fragmentShader) { +#if defined(AX_USE_GLES) + // some device required manually specify the precision qualifiers for vertex shader. + _vertexShaderModule = + static_cast(ShaderCache::newVertexShaderModule(SHADER_PREDEFINE + _vertexShader)); + _fragmentShaderModule = + static_cast(ShaderCache::newFragmentShaderModule(SHADER_PREDEFINE + _fragmentShader)); +#else _vertexShaderModule = static_cast(ShaderCache::newVertexShaderModule(_vertexShader)); _fragmentShaderModule = static_cast(ShaderCache::newFragmentShaderModule(_fragmentShader)); +#endif AX_SAFE_RETAIN(_vertexShaderModule); AX_SAFE_RETAIN(_fragmentShaderModule); diff --git a/core/renderer/shaders/3D_particle.frag b/core/renderer/shaders/3D_particle.frag index 9977992898..111893ae3b 100644 --- a/core/renderer/shaders/3D_particle.frag +++ b/core/renderer/shaders/3D_particle.frag @@ -29,8 +29,8 @@ const char* CC3D_particleTexture_frag = R"( varying mediump vec2 TextureCoordOut; varying mediump vec4 ColorOut; #else -varying vec2 TextureCoordOut; varying vec4 ColorOut; +varying vec2 TextureCoordOut; #endif uniform vec4 u_color; diff --git a/core/renderer/shaders/3D_positionNormalTexture.vert b/core/renderer/shaders/3D_positionNormalTexture.vert index 5d84a94ab1..d7e1f5ff8e 100644 --- a/core/renderer/shaders/3D_positionNormalTexture.vert +++ b/core/renderer/shaders/3D_positionNormalTexture.vert @@ -144,6 +144,8 @@ void main(void) const char* CC3D_skinPositionNormalTexture_vert = R"( + + #ifdef USE_NORMAL_MAPPING #if (MAX_DIRECTIONAL_LIGHT_NUM > 0) uniform vec3 u_DirLightSourceDirection[MAX_DIRECTIONAL_LIGHT_NUM]; diff --git a/setup.ps1 b/setup.ps1 index 7c6ff89dbb..eb70a6a8fb 100644 --- a/setup.ps1 +++ b/setup.ps1 @@ -105,21 +105,4 @@ if ($IsLinux) { } } -if ($IsWin) { - $myProcess = [System.Diagnostics.Process]::GetCurrentProcess() - $parentProcess = $myProcess.Parent - if (!$parentProcess) { - $myPID = $myProcess.Id - $instance = Get-WmiObject Win32_Process -Filter "ProcessId = $myPID" - $parentProcess = Get-Process -Id $instance.ParentProcessID - } - $parentProcessName = $parentProcess.ProcessName - if ($parentProcessName -like "explorer") { - b1k_print "setup successfully, press any key to exit . . ." -NoNewline - cmd /c pause 1>$null - exit 0 - } -} - -b1k_print 'setup successfully.' - +$b1k.pause("setup successfully") diff --git a/templates/cpp-template-default/Source/HelloWorldScene.cpp b/templates/cpp-template-default/Source/HelloWorldScene.cpp index 55408cb326..02b734b9a0 100644 --- a/templates/cpp-template-default/Source/HelloWorldScene.cpp +++ b/templates/cpp-template-default/Source/HelloWorldScene.cpp @@ -116,6 +116,7 @@ bool HelloWorld::init() // add the label as a child to this layer this->addChild(label, 1); } + // add "HelloWorld" splash screen" auto sprite = Sprite::create("HelloWorld.png"sv); if (sprite == nullptr) diff --git a/tests/cpp-tests/Source/AppDelegate.cpp b/tests/cpp-tests/Source/AppDelegate.cpp index 886870e454..394d2101f4 100644 --- a/tests/cpp-tests/Source/AppDelegate.cpp +++ b/tests/cpp-tests/Source/AppDelegate.cpp @@ -88,7 +88,7 @@ bool AppDelegate::applicationDidFinishLaunching() auto screenSize = glView->getFrameSize(); auto fileUtils = FileUtils::getInstance(); - std::vector searchPaths = fileUtils->getSearchPaths(); + std::vector searchPaths; if (screenSize.height > 320) { diff --git a/tests/cpp-tests/Source/NewRendererTest/NewRendererTest.cpp b/tests/cpp-tests/Source/NewRendererTest/NewRendererTest.cpp index 1d77c63552..d54000146c 100644 --- a/tests/cpp-tests/Source/NewRendererTest/NewRendererTest.cpp +++ b/tests/cpp-tests/Source/NewRendererTest/NewRendererTest.cpp @@ -76,11 +76,11 @@ NewRendererTests::NewRendererTests() { auto programManager = ProgramManager::getInstance(); programManager->registerCustomProgramFactory(CustomProgramType::BLUR, positionTextureColor_vert, - "example_Blur_fs"sv, + FileUtils::getInstance()->getStringFromFile("Shaders/example_Blur.fsh"), VertexLayoutHelper::setupSprite); programManager->registerCustomProgramFactory( CustomProgramType::SEPIA, positionTextureColor_vert, - "example_Sepia_fs"sv, + FileUtils::getInstance()->getStringFromFile("Shaders/example_Sepia.fsh"), VertexLayoutHelper::setupSprite); ADD_TEST_CASE(NewSpriteTest); diff --git a/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.cpp b/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.cpp index 2d524c7ee7..9d0a8832d1 100644 --- a/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.cpp +++ b/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.cpp @@ -34,6 +34,32 @@ TextureCacheTests::TextureCacheTests() TextureCacheTest::TextureCacheTest() : _numberOfSprites(20), _numberOfLoadedSprites(0) { +} + +TextureCacheTest::~TextureCacheTest() +{ + auto* cache = Director::getInstance()->getTextureCache(); + cache->unbindAllImageAsync(); +} + +void TextureCacheTest::loadingCallBack(ax::Texture2D* texture) +{ + ++_numberOfLoadedSprites; + char tmp[10]; + sprintf(tmp, "%%%d", (int)(((float)_numberOfLoadedSprites / _numberOfSprites) * 100)); + _labelPercent->setString(tmp); + + if (_numberOfLoadedSprites == _numberOfSprites) + { + this->removeChild(_labelLoading, true); + this->removeChild(_labelPercent, true); + addSprite(); + } +} + +void TextureCacheTest::onEnter() +{ + TestCase::onEnter(); auto size = Director::getInstance()->getWinSize(); _labelLoading = Label::createWithTTF("loading...", "fonts/arial.ttf", 15); @@ -88,21 +114,6 @@ TextureCacheTest::TextureCacheTest() : _numberOfSprites(20), _numberOfLoadedSpri AX_CALLBACK_1(TextureCacheTest::loadingCallBack, this)); } -void TextureCacheTest::loadingCallBack(ax::Texture2D* texture) -{ - ++_numberOfLoadedSprites; - char tmp[10]; - sprintf(tmp, "%%%d", (int)(((float)_numberOfLoadedSprites / _numberOfSprites) * 100)); - _labelPercent->setString(tmp); - - if (_numberOfLoadedSprites == _numberOfSprites) - { - this->removeChild(_labelLoading, true); - this->removeChild(_labelPercent, true); - addSprite(); - } -} - void TextureCacheTest::addSprite() { auto size = Director::getInstance()->getWinSize(); @@ -173,6 +184,18 @@ void TextureCacheTest::addSprite() TextureCacheUnbindTest::TextureCacheUnbindTest() { +} + +TextureCacheUnbindTest::~TextureCacheUnbindTest() +{ + auto* cache = Director::getInstance()->getTextureCache(); + cache->unbindAllImageAsync(); +} + +void TextureCacheUnbindTest::onEnter() +{ + TestCase::onEnter(); + auto size = Director::getInstance()->getWinSize(); Label* nothing = Label::createWithTTF("There should be\nnothing below", "fonts/arial.ttf", 15); diff --git a/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.h b/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.h index 1455951fe4..9aa61639d0 100644 --- a/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.h +++ b/tests/cpp-tests/Source/TextureCacheTest/TextureCacheTest.h @@ -36,11 +36,13 @@ public: CREATE_FUNC(TextureCacheTest); TextureCacheTest(); + ~TextureCacheTest() override; void addSprite(); void loadingCallBack(ax::Texture2D* texture); - virtual float getDuration() const override { return 3.5f; } + float getDuration() const override { return 3.5f; } + void onEnter() override; private: ax::Label* _labelLoading; @@ -55,6 +57,9 @@ public: CREATE_FUNC(TextureCacheUnbindTest); TextureCacheUnbindTest(); + ~TextureCacheUnbindTest() override; + + void onEnter() override; private: void textureLoadedA(ax::Texture2D* texture);