[Bink2] rework bridge to use FFmpeg's native Bink2 decoder instead of a C bridge (#554)

* [Bink2] rework bridge to use FFmpeg's native Bink2 decoder instead of a C bridge

* [readme] update DeS screenshot
This commit is contained in:
Berk
2026-07-23 03:06:14 +03:00
committed by GitHub
parent 559b7f0a84
commit 4191a9e12b
12 changed files with 506 additions and 756 deletions
+57 -33
View File
@@ -20,6 +20,11 @@ SPDX-License-Identifier: GPL-2.0-or-later
<!-- osx-x64 is the macOS target: the CPU backend executes guest x86-64
natively, so on Apple Silicon it runs under Rosetta 2. -->
<RuntimeIdentifiers>win-x64;linux-x64;osx-x64;osx-arm64</RuntimeIdentifiers>
<!-- A plain "dotnet publish" with no -r defaults $(RuntimeIdentifier) to
the host's own RID; see Directory.Build.props, which is where that
default actually has to live (PublishDir's RID suffix is decided
there, evaluated before this file, so a default set only here would
be too late for it). -->
<SelfContained>true</SelfContained>
<PublishSingleFile>true</PublishSingleFile>
<IncludeNativeLibrariesForSelfExtract>true</IncludeNativeLibrariesForSelfExtract>
@@ -60,7 +65,7 @@ SPDX-License-Identifier: GPL-2.0-or-later
<PropertyGroup>
<NoWarn>$(NoWarn);1591</NoWarn>
</PropertyGroup>
<ItemGroup>
<Content Include="..\..\LICENSE.txt">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
@@ -74,56 +79,75 @@ SPDX-License-Identifier: GPL-2.0-or-later
</Content>
</ItemGroup>
<!-- Keep glfw as a loose file next to the executable; every other native
<!-- Native libraries (glfw, FFmpeg) publish into a subfolder next to the
executable instead of sitting loose beside it, so the publish
directory stays uncluttered as more native deps get added. The folder
name is a fixed constant, not derived from the RID/architecture: each
publish output only ever holds one architecture's binaries anyway, so
varying the name added a class of bugs (RID resolution timing, host-OS
vs. target-RID mixups) for no benefit. Runtime code (Program.cs's
PreloadGlfw, FfmpegNativeBinkFrameSource's RootPath) uses the same
literal "plugins" folder name. -->
<PropertyGroup>
<NativeLibraryFolderName>plugins</NativeLibraryFolderName>
</PropertyGroup>
<!-- Keep glfw as a loose file in the native subfolder; every other native
library is embedded into the single-file bundle. -->
<Target Name="KeepGlfwOutsideSingleFile" AfterTargets="ComputeResolvedFilesToPublishList">
<ItemGroup>
<_GlfwPublishFiles Include="@(ResolvedFileToPublish)"
Condition="$([System.String]::Copy('%(ResolvedFileToPublish.Filename)').StartsWith('glfw')) Or $([System.String]::Copy('%(ResolvedFileToPublish.Filename)').StartsWith('libglfw'))" />
Condition="$([System.String]::Copy('%(ResolvedFileToPublish.Filename)').StartsWith('glfw')) Or $([System.String]::Copy('%(ResolvedFileToPublish.Filename)').StartsWith('libglfw'))" />
<ResolvedFileToPublish Remove="@(_GlfwPublishFiles)" />
<ResolvedFileToPublish Include="@(_GlfwPublishFiles)">
<ExcludeFromSingleFile>true</ExcludeFromSingleFile>
<RelativePath>$(NativeLibraryFolderName)/%(Filename)%(Extension)</RelativePath>
</ResolvedFileToPublish>
</ItemGroup>
</Target>
<!-- Building the Bink2 bridge (native/bink2-bridge/sharpemu_bink2_bridge.c)
requires cmake, ninja, and clang-cl (Windows) or a C compiler
(Linux/macOS); the same tools the CI runners already ship with. No
prebuilt/download fallback: anyone publishing SharpEmu is expected to
have the same toolchain, matching every other native dependency in
this repo. -->
<PropertyGroup>
<Bink2BridgeBuildDir>$(BaseIntermediateOutputPath)bink2-bridge/$(RuntimeIdentifier)</Bink2BridgeBuildDir>
<Bink2BridgeFileName Condition="$([MSBuild]::IsOSPlatform('Windows'))">sharpemu_bink2_bridge.dll</Bink2BridgeFileName>
<Bink2BridgeFileName Condition="$([MSBuild]::IsOSPlatform('Linux'))">libsharpemu_bink2_bridge.so</Bink2BridgeFileName>
<Bink2BridgeFileName Condition="$([MSBuild]::IsOSPlatform('OSX'))">libsharpemu_bink2_bridge.dylib</Bink2BridgeFileName>
<Bink2BridgeOutput>$(Bink2BridgeBuildDir)/out/$(Bink2BridgeFileName)</Bink2BridgeOutput>
<FfmpegRuntimeTag>2c92585</FfmpegRuntimeTag>
<FfmpegRuntimeDir>
$(BaseIntermediateOutputPath)ffmpeg-runtime/$(FfmpegRuntimeTag)/$(RuntimeIdentifier)</FfmpegRuntimeDir>
<FfmpegRuntimePackage Condition="'$(RuntimeIdentifier)' == 'win-x64'">ffmpeg-windows-x64.zip</FfmpegRuntimePackage>
<FfmpegRuntimePackage Condition="'$(RuntimeIdentifier)' == 'linux-x64'">ffmpeg-linux-x64.zip</FfmpegRuntimePackage>
<FfmpegRuntimePackage Condition="'$(RuntimeIdentifier)' == 'osx-x64'">ffmpeg-macos-x64.zip</FfmpegRuntimePackage>
<FfmpegRuntimePackage Condition="'$(RuntimeIdentifier)' == 'osx-arm64'">ffmpeg-macos-arm64.zip</FfmpegRuntimePackage>
<FfmpegRuntimeArchive>$(FfmpegRuntimeDir)/$(FfmpegRuntimePackage)</FfmpegRuntimeArchive>
<FfmpegRuntimeExtractDir>$(FfmpegRuntimeDir)/extracted</FfmpegRuntimeExtractDir>
</PropertyGroup>
<Target Name="BuildBink2Bridge"
BeforeTargets="ComputeResolvedFilesToPublishList"
Condition="'$(RuntimeIdentifier)' != '' And '$(Bink2BridgeFileName)' != ''">
<Exec Condition="$([MSBuild]::IsOSPlatform('Windows'))"
Command="cmake -S &quot;$(RepoRoot)native/bink2-bridge&quot; -B &quot;$(Bink2BridgeBuildDir)&quot; -G Ninja -DCMAKE_BUILD_TYPE=Release -DCMAKE_C_COMPILER=clang-cl -DSHARPEMU_TARGET_RID=$(RuntimeIdentifier)" />
<Exec Condition="!$([MSBuild]::IsOSPlatform('Windows'))"
Command="cmake -S &quot;$(RepoRoot)native/bink2-bridge&quot; -B &quot;$(Bink2BridgeBuildDir)&quot; -DCMAKE_BUILD_TYPE=Release -DSHARPEMU_TARGET_RID=$(RuntimeIdentifier)" />
<Exec Command="cmake --build &quot;$(Bink2BridgeBuildDir)&quot; --config Release" />
<Target Name="FetchFfmpegRuntime"
BeforeTargets="Publish"
Condition="'$(RuntimeIdentifier)' != '' And '$(FfmpegRuntimePackage)' != ''">
<DownloadFile
SourceUrl="https://github.com/sharpemu/ffmpeg-core/releases/download/$(FfmpegRuntimeTag)/$(FfmpegRuntimePackage)"
DestinationFolder="$(FfmpegRuntimeDir)"
Condition="!Exists('$(FfmpegRuntimeArchive)')" />
<Unzip
SourceFiles="$(FfmpegRuntimeArchive)"
DestinationFolder="$(FfmpegRuntimeExtractDir)"
Condition="!Exists('$(FfmpegRuntimeExtractDir)')" />
</Target>
<!-- Embeds the bridge into the single-file bundle (self-extracted at first
load, see Bink2MovieBridge.NativeAdapter) instead of leaving it as a
loose file next to the executable, so a downloaded release needs no
setup: the DLL is already inside SharpEmu.exe. -->
<Target Name="EmbedBink2Bridge"
AfterTargets="ComputeResolvedFilesToPublishList"
DependsOnTargets="BuildBink2Bridge"
Condition="'$(RuntimeIdentifier)' != '' And Exists('$(Bink2BridgeOutput)')">
<Target Name="PublishFfmpegRuntime"
AfterTargets="Publish"
DependsOnTargets="FetchFfmpegRuntime"
Condition="'$(RuntimeIdentifier)' != '' And '$(FfmpegRuntimePackage)' != ''">
<!-- Keyed off the target $(RuntimeIdentifier), not the host OS: publishing
e.g. linux-x64 from a Windows machine is a supported cross-publish,
and the extracted archive's own layout (bin/*.dll vs lib/*.so*) only
depends on which platform's ffmpeg-core package was fetched. -->
<ItemGroup>
<ResolvedFileToPublish Include="$(Bink2BridgeOutput)">
<RelativePath>$(Bink2BridgeFileName)</RelativePath>
</ResolvedFileToPublish>
<_FfmpegRuntimeFiles Condition="$(RuntimeIdentifier.StartsWith('win'))"
Include="$(FfmpegRuntimeExtractDir)/bin/*.dll" />
<_FfmpegRuntimeFiles Condition="!$(RuntimeIdentifier.StartsWith('win'))"
Include="$(FfmpegRuntimeExtractDir)/lib/*.so;$(FfmpegRuntimeExtractDir)/lib/*.so.*;$(FfmpegRuntimeExtractDir)/lib/*.dylib" />
</ItemGroup>
<Copy SourceFiles="@(_FfmpegRuntimeFiles)"
DestinationFolder="$(PublishDir)$(NativeLibraryFolderName)"
SkipUnchangedFiles="true" />
</Target>
</Project>