From 412c9759dfa108e59dba9b9c4fc46ea64a78f007 Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Fri, 25 Apr 2025 16:27:57 +0800 Subject: [PATCH 01/10] =?UTF-8?q?=E6=BB=A4=E9=95=9C=E6=B7=BB=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Manager/AppSettings/Filter/RLPro.meta | 8 + .../AppSettings/Filter/RLPro/RLPro_Bleed.cs | 106 +++++++++++ .../Filter/RLPro/RLPro_Bleed.cs.meta | 2 + .../Filter/RLPro/RLPro_Bleed.shader | 175 ++++++++++++++++++ .../Filter/RLPro/RLPro_Bleed.shader.meta | 9 + .../Filter/RLPro/RLPro_CRT_Aperture.shader | 144 ++++++++++++++ .../RLPro/RLPro_CRT_Aperture.shader.meta | 9 + 7 files changed, 453 insertions(+) create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro.meta create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader.meta create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro.meta new file mode 100644 index 00000000..fa0c2c14 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: b5c1ebe19e88e8840b17582b45643281 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs new file mode 100644 index 00000000..e3ab14e6 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs @@ -0,0 +1,106 @@ +using Assets.Script.AppMain.Filter; +using UnityEngine; + +namespace AxibugEmuOnline.Client.Filters +{ + [Strip(RuntimePlatform.PSP2)] + public class RLPRO_CRT : FilterEffect + { + public override string Name => nameof(RLPRO_CRT); + protected override string ShaderName => null; + + #region BleedPass_Param + public FilterParameter BleedMode = new FilterParameter(EnumBleedMode.NTSCOld3Phase); + [Range(0, 15)] + public FloatParameter BleedAmount = new FloatParameter(1f); + #endregion + #region CRTAperture_Param + [Range(0, 5)] + public FloatParameter GlowHalation = new FloatParameter(0.1f); + [Range(0, 2)] + public FloatParameter GlowDifusion = new FloatParameter(0.05f); + [Range(0, 2)] + public FloatParameter MaskColors = new FloatParameter(2.0f); + [Range(0, 1)] + public FloatParameter MaskStrength = new FloatParameter(0.3f); + [Range(0, 5)] + public FloatParameter GammaInput = new FloatParameter(2.4f); + [Range(0, 5)] + public FloatParameter GammaOutput = new FloatParameter(2.4f); + [Range(0, 2.5f)] + public FloatParameter Brightness = new FloatParameter(1.5f); + #endregion + + Material m_bleedMat; + Material m_crtApertureMat; + Material m_tvEffectMat; + + protected override void OnInit(Material renderMat) + { + m_bleedMat = new Material(Shader.Find("Filter/RLPro_Bleed")); + m_crtApertureMat = new Material(Shader.Find("Filter/RLPro_CRT_Aperture")); + } + + protected override void OnRenderer(Material renderMat, Texture src, RenderTexture result) + { + var rt1 = BleedPass(src); + var rt2 = CRT_AperturePass(rt1); + + Graphics.Blit(rt2, result); + + RenderTexture.ReleaseTemporary(rt1); + RenderTexture.ReleaseTemporary(rt2); + } + + private RenderTexture BleedPass(Texture src) + { + var rt = RenderTexture.GetTemporary(src.width, src.height); + + m_bleedMat.DisableKeyword("_NTSCOld3Phase"); + m_bleedMat.DisableKeyword("_NTSC3Phase"); + m_bleedMat.DisableKeyword("_NTSC2Phase"); + + switch (BleedMode.GetValue()) + { + case EnumBleedMode.NTSCOld3Phase: + m_bleedMat.EnableKeyword("_NTSCOld3Phase"); + break; + case EnumBleedMode.NTSC3Phase: + m_bleedMat.EnableKeyword("_NTSC3Phase"); + break; + case EnumBleedMode.NTSC2Phase: + m_bleedMat.EnableKeyword("_NTSC2Phase"); + break; + } + + m_bleedMat.SetFloat("bleedAmount", BleedAmount.GetValue()); + + Graphics.Blit(src, rt, m_bleedMat); + + return rt; + } + private RenderTexture CRT_AperturePass(Texture src) + { + var rt = RenderTexture.GetTemporary(src.width, src.height); + + m_crtApertureMat.SetFloat("GLOW_HALATION", GlowHalation.GetValue()); + m_crtApertureMat.SetFloat("GLOW_DIFFUSION", GlowDifusion.GetValue()); + m_crtApertureMat.SetFloat("MASK_COLORS", MaskColors.GetValue()); + m_crtApertureMat.SetFloat("MASK_STRENGTH", MaskStrength.GetValue()); + m_crtApertureMat.SetFloat("GAMMA_INPUT", GammaInput.GetValue()); + m_crtApertureMat.SetFloat("GAMMA_OUTPUT", GammaOutput.GetValue()); + m_crtApertureMat.SetFloat("BRIGHTNESS", Brightness.GetValue()); + + Graphics.Blit(src, rt, m_crtApertureMat); + + return rt; + } + + public enum EnumBleedMode + { + NTSCOld3Phase, + NTSC3Phase, + NTSC2Phase, + } + } +} \ No newline at end of file diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta new file mode 100644 index 00000000..1d65124b --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: fcc83c5bfa946f748811247794560a56 \ No newline at end of file diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader new file mode 100644 index 00000000..4840f8e4 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader @@ -0,0 +1,175 @@ +Shader "Filter/RLPro_Bleed" +{ + Properties + { + _MainTex ("Base (RGB)", 2D) = "white" {} + } + SubShader + { + Pass + { + CGPROGRAM + + #pragma shader_feature_local _NTSCOld3Phase _NTSC3Phase _NTSC2Phase + #pragma vertex vert_img + #pragma fragment frag + #include "UnityCG.cginc" + + sampler2D _MainTex; + float4 _MainTex_TexelSize; + float2 _iResolution; + + float bleedAmount = 1.0; + int bleedLength = 21; + + struct v2f + { + float4 pos : POSITION; + float2 uv : TEXCOORD0; + }; + + half3 rgb2yiq(half3 c) + { + return half3( + (0.2989 * c.x + 0.5959 * c.y + 0.2115 * c.z), + (0.5870 * c.x - 0.2744 * c.y - 0.5229 * c.z), + (0.1140 * c.x - 0.3216 * c.y + 0.3114 * c.z) + ); + } + + half3 yiq2rgb(half3 c) + { + return half3( + (1.0 * c.x + 1.0 * c.y + 1.0 * c.z), + (0.956 * c.x - 0.2720 * c.y - 1.1060 * c.z), + (0.6210 * c.x - 0.6474 * c.y + 1.7046 * c.z) + ); + } + + half3 t2d(float2 p) + { + half3 col = tex2D(_MainTex, p).rgb; + + return rgb2yiq(col); + } + + #define fixCoord (p - float2( 0.5 * ONE_X, 0.0)) + #define fetch_offset(offset, one_x) t2d(fixCoord + float2( (offset) * (ONE_X), 0.0)); + #define get_t2d(offset, one_x) tex2D(_MainTex, p + (offset)*(one_x)).rgb; + + float4 FragNTSCOld3Phase(v2f i) : COLOR + { + float2 uv = i.uv; + float2 p = uv; + float ONE_X = 1.0 / _ScreenParams.x; + + ONE_X *= bleedAmount; + bleedLength = 25; + float maxTexLength = 50.0; + float luma_filter[25]; luma_filter[0] = -0.000071070; luma_filter[1] = -0.000032816; luma_filter[2] = 0.000128784; luma_filter[3] = 0.000134711; luma_filter[4] = -0.000226705; luma_filter[5] = -0.000777988; luma_filter[6] = -0.000997809; luma_filter[7] = -0.000522802; luma_filter[8] = 0.000344691; luma_filter[9] = 0.000768930; luma_filter[10] = 0.000275591; luma_filter[11] = -0.000373434; luma_filter[12] = 0.000522796; luma_filter[13] = 0.003813817; luma_filter[14] = 0.007502825; luma_filter[15] = 0.006786001; luma_filter[16] = -0.002636726; luma_filter[17] = -0.019461182; luma_filter[18] = -0.033792479; luma_filter[19] = -0.029921972; luma_filter[20] = 0.005032552; luma_filter[21] = 0.071226466; luma_filter[22] = 0.151755921; luma_filter[23] = 0.218166470; luma_filter[24] = 0.243902439; + float chroma_filter[24 + 1]; chroma_filter[0] = 0.001845562; chroma_filter[1] = 0.002381606; chroma_filter[2] = 0.003040177; chroma_filter[3] = 0.003838976; chroma_filter[4] = 0.004795341; chroma_filter[5] = 0.005925312; chroma_filter[6] = 0.007242534; chroma_filter[7] = 0.008757043; chroma_filter[8] = 0.010473987; chroma_filter[9] = 0.012392365; chroma_filter[10] = 0.014503872; chroma_filter[11] = 0.016791957; chroma_filter[12] = 0.019231195; chroma_filter[13] = 0.021787070; chroma_filter[14] = 0.024416251; chroma_filter[15] = 0.027067414; chroma_filter[16] = 0.029682613; chroma_filter[17] = 0.032199202; chroma_filter[18] = 0.034552198; chroma_filter[19] = 0.036677005; chroma_filter[20] = 0.038512317; chroma_filter[21] = 0.040003044; chroma_filter[22] = 0.041103048; chroma_filter[23] = 0.041777517; chroma_filter[24] = 0.042004791; + half3 signal = half3(0.0,0.0,0.0); + half3 norm = half3(0.0,0.0,0.0); + half3 adj = half3(0.0,0.0,0.0); + int taps = bleedLength - 4; + for (int ii = 0; ii < taps % 1023; ii++) + { + float offset = float(ii); + half3 sums = fetch_offset(offset - float(taps), ONE_X) + fetch_offset(float(taps) - offset, ONE_X); + adj = half3(luma_filter[ii + 3], chroma_filter[ii], chroma_filter[ii]); + signal += sums * adj; + norm += adj; + } + adj = half3(luma_filter[taps], chroma_filter[taps], chroma_filter[taps]); + half4 col23 = tex2D(_MainTex, fixCoord); + signal += rgb2yiq(col23.rgb) * adj; + norm += adj; + signal = signal / norm; + float3 rgb = yiq2rgb(signal); + + float alpha = col23.a + (rgb.r + rgb.g + rgb.b) / 3; + return half4(rgb, alpha); + } + + float4 FragNTSC3Phase(v2f i) : COLOR + { + float2 uv = i.uv; + float2 p = uv; + float ONE_X = 1.0 / _iResolution.x; + + ONE_X *= bleedAmount; + bleedLength = 25; + float maxTexLength = 50.0; + float luma_filter[25]; luma_filter[0] = -0.000012020; luma_filter[1] = -0.000022146; luma_filter[2] = -0.000013155; luma_filter[3] = -0.000012020; luma_filter[4] = -0.000049979; luma_filter[5] = -0.000113940; luma_filter[6] = -0.000122150; luma_filter[7] = -0.000005612; luma_filter[8] = 0.000170516; luma_filter[9] = 0.000237199; luma_filter[10] = 0.000169640; luma_filter[11] = 0.000285688; luma_filter[12] = 0.000984574; luma_filter[13] = 0.002018683; luma_filter[14] = 0.002002275; luma_filter[15] = -0.000909882; luma_filter[16] = -0.007049081; luma_filter[17] = -0.013222860; luma_filter[18] = -0.012606931; luma_filter[19] = 0.002460860; luma_filter[20] = 0.035868225; luma_filter[21] = 0.084016453; luma_filter[22] = 0.135563500; luma_filter[23] = 0.175261268; luma_filter[24] = 0.190176552; + float chroma_filter[25]; chroma_filter[0] = -0.000118847; chroma_filter[1] = -0.000271306; chroma_filter[2] = -0.000502642; chroma_filter[3] = -0.000930833; chroma_filter[4] = -0.001451013; chroma_filter[5] = -0.002064744; chroma_filter[6] = -0.002700432; chroma_filter[7] = -0.003241276; chroma_filter[8] = -0.003524948; chroma_filter[9] = -0.003350284; chroma_filter[10] = -0.002491729; chroma_filter[11] = -0.000721149; chroma_filter[12] = 0.002164659; chroma_filter[13] = 0.006313635; chroma_filter[14] = 0.011789103; chroma_filter[15] = 0.018545660; chroma_filter[16] = 0.026414396; chroma_filter[17] = 0.035100710; chroma_filter[18] = 0.044196567; chroma_filter[19] = 0.053207202; chroma_filter[20] = 0.061590275; chroma_filter[21] = 0.068803602; chroma_filter[22] = 0.074356193; chroma_filter[23] = 0.077856564; chroma_filter[24] = 0.079052396; + half3 signal = half3(0.0,0.0,0.0); + half3 norm = half3(0.0,0.0,0.0); + half3 adj = half3(0.0,0.0,0.0); + int taps = bleedLength - 4; + for (int ii = 0; ii < taps % 1023; ii++) + { + float offset = float(ii); + half3 sums = fetch_offset(offset - float(taps), ONE_X) + fetch_offset(float(taps) - offset, ONE_X); + adj = half3(luma_filter[ii + 3], chroma_filter[ii], chroma_filter[ii]); + signal += sums * adj; + norm += adj; + } + adj = half3(luma_filter[taps], chroma_filter[taps], chroma_filter[taps]); + half4 col23 = tex2D(_MainTex, fixCoord); + signal += rgb2yiq(col23.rgb) * adj; + norm += adj; + signal = signal / norm; + float3 rgb = yiq2rgb(signal); + + float alpha = col23.a + (rgb.r + rgb.g + rgb.b) / 3; + return half4(rgb, alpha); + } + + float4 FragNTSC2Phase(v2f i) : COLOR + { + float2 uv = i.uv; + float2 p = uv; + float ONE_X = 1.0 / _ScreenParams.x; + + ONE_X *= bleedAmount; + bleedLength = 33; + float maxTexLength = 50.0; + float luma_filter[33]; luma_filter[0] = -0.000174844; luma_filter[1] = -0.000205844; luma_filter[2] = -0.000149453; luma_filter[3] = -0.000051693; luma_filter[4] = 0.000000000; luma_filter[5] = -0.000066171; luma_filter[6] = -0.000245058; luma_filter[7] = -0.000432928; luma_filter[8] = -0.000472644; luma_filter[9] = -0.000252236; luma_filter[10] = 0.000198929; luma_filter[11] = 0.000687058; luma_filter[12] = 0.000944112; luma_filter[13] = 0.000803467; luma_filter[14] = 0.000363199; luma_filter[15] = 0.000013422; luma_filter[16] = 0.000253402; luma_filter[17] = 0.001339461; luma_filter[18] = 0.002932972; luma_filter[19] = 0.003983485; luma_filter[20] = 0.003026683; luma_filter[21] = -0.001102056; luma_filter[22] = -0.008373026; luma_filter[23] = -0.016897700; luma_filter[24] = -0.022914480; luma_filter[25] = -0.021642347; luma_filter[26] = -0.008863273; luma_filter[27] = 0.017271957; luma_filter[28] = 0.054921920; luma_filter[29] = 0.098342579; luma_filter[30] = 0.139044281; luma_filter[31] = 0.168055832; luma_filter[32] = 0.178571429; + float chroma_filter[33]; chroma_filter[0] = 0.001384762; chroma_filter[1] = 0.001678312; chroma_filter[2] = 0.002021715; chroma_filter[3] = 0.002420562; chroma_filter[4] = 0.002880460; chroma_filter[5] = 0.003406879; chroma_filter[6] = 0.004004985; chroma_filter[7] = 0.004679445; chroma_filter[8] = 0.005434218; chroma_filter[9] = 0.006272332; chroma_filter[10] = 0.007195654; chroma_filter[11] = 0.008204665; chroma_filter[12] = 0.009298238; chroma_filter[13] = 0.010473450; chroma_filter[14] = 0.011725413; chroma_filter[15] = 0.013047155; chroma_filter[16] = 0.014429548; chroma_filter[17] = 0.015861306; chroma_filter[18] = 0.017329037; chroma_filter[19] = 0.018817382; chroma_filter[20] = 0.020309220; chroma_filter[21] = 0.021785952; chroma_filter[22] = 0.023227857; chroma_filter[23] = 0.024614500; chroma_filter[24] = 0.025925203; chroma_filter[25] = 0.027139546; chroma_filter[26] = 0.028237893; chroma_filter[27] = 0.029201910; chroma_filter[28] = 0.030015081; chroma_filter[29] = 0.030663170; chroma_filter[30] = 0.031134640; chroma_filter[31] = 0.031420995; chroma_filter[32] = 0.031517031; + half3 signal = half3(0.0,0.0,0.0); + half3 norm = half3(0.0,0.0,0.0); + half3 adj = half3(0.0,0.0,0.0); + int taps = bleedLength - 4; + for (int ii = 0; ii < taps % 1023; ii++) + { + float offset = float(ii); + half3 sums = fetch_offset(offset - float(taps), ONE_X) + fetch_offset(float(taps) - offset, ONE_X); + adj = half3(luma_filter[ii + 3], chroma_filter[ii], chroma_filter[ii]); + signal += sums * adj; + norm += adj; + } + adj = half3(luma_filter[taps], chroma_filter[taps], chroma_filter[taps]); + half4 col23 = tex2D(_MainTex, fixCoord); + signal += rgb2yiq(col23.rgb) * adj; + norm += adj; + signal = signal / norm; + float3 rgb = yiq2rgb(signal); + + float alpha = col23.a + (rgb.r + rgb.g + rgb.b) / 3; + return half4(rgb, alpha); + } + + fixed4 frag (v2f i) : SV_Target + { + #if _NTSCOld3Phase + return FragNTSCOld3Phase(i); + #elif _NTSC3Phase + return FragNTSC3Phase(i); + #else + return FragNTSC2Phase(i); + #endif + } + ENDCG + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader.meta new file mode 100644 index 00000000..d5e2b768 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.shader.meta @@ -0,0 +1,9 @@ +fileFormatVersion: 2 +guid: d7b367e99136835468184ea471e79e02 +ShaderImporter: + externalObjects: {} + defaultTextures: [] + nonModifiableTextures: [] + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader new file mode 100644 index 00000000..b5d99176 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader @@ -0,0 +1,144 @@ +Shader "Filter/RLPro_CRT_Aperture" +{ + Properties + { + _MainTex ("Base (RGB)", 2D) = "white" {} + } + SubShader + { + Pass + { + CGPROGRAM + + #pragma shader_feature_local _NTSCOld3Phase _NTSC3Phase _NTSC2Phase + #pragma vertex vert_img + #pragma fragment Frag0 + #include "UnityCG.cginc" + + #define FIX(c) max(abs(c), 1e-5) + #define saturate(c) clamp(c, 0.0, 1.0) + #define PI 3.14159265359 + + sampler2D _MainTex; + float4 _MainTex_TexelSize; + float2 _iResolution; + + float GLOW_HALATION = 0.1; + float GLOW_DIFFUSION = 0.05; + float MASK_COLORS = 2.0; + float MASK_STRENGTH = 0.3; + float GAMMA_INPUT = 2.4; + float GAMMA_OUTPUT = 2.4; + float BRIGHTNESS = 1.5; + + struct v2f + { + float4 pos : POSITION; + float2 uv : TEXCOORD0; + }; + + float mod(float x, float y) + { + return x - y * floor(x / y); + } + + float fract(float x) + { + return x - floor(x); + } + + float2 fract(float2 x) + { + return x - floor(x); + } + + float4 fract(float4 x) + { + return x - floor(x); + } + + float3 TEX2D(float2 c) + { + return pow(abs(tex2D(_MainTex, c).rgb), float3(GAMMA_INPUT, GAMMA_INPUT, GAMMA_INPUT)).xyz; + } + + float3x3 get_color_matrix(float2 co, float2 dx) + { + return float3x3(TEX2D(co - dx), TEX2D(co), TEX2D(co + dx)); + } + + float3 blur(float3x3 m, float dist, float rad) + { + float3 x = float3(dist - 1.0, dist, dist + 1.0) / rad; + float3 w = exp2(x * x * -1.0); + + return (m[0] * w.x + m[1] * w.y + m[2] * w.z) / (w.x + w.y + w.z); + } + + float3 filter_gaussian(float2 co, float2 tex_size) + { + float2 dx = float2(1.0 / tex_size.x, 0.0); + float2 dy = float2(0.0, 1.0 / tex_size.y); + float2 pix_co = co * tex_size; + float2 tex_co = (floor(pix_co) + 0.5) / tex_size; + float2 dist = (fract(pix_co) - 0.5) * -1.0; + float3x3 line0 = get_color_matrix(tex_co - dy, dx); + float3x3 line1 = get_color_matrix(tex_co, dx); + float3x3 line2 = get_color_matrix(tex_co + dy, dx); + float3x3 column = float3x3(blur(line0, dist.x, 0.5), blur(line1, dist.x, 0.5), blur(line2, dist.x, 0.5)); + return blur(column, dist.y, 0.5); + } + + float3 filter_lanczos(float2 co, float2 tex_size, float sharp) + { + tex_size.x *= sharp; + + float2 dx = float2(1.0 / tex_size.x, 0.0); + float2 pix_co = co * tex_size - float2(0.5, 0.0); + float2 tex_co = (floor(pix_co) + float2(0.5, 0.001)) / tex_size; + float2 dist = fract(pix_co); + float4 coef = PI * float4(dist.x + 1.0, dist.x, dist.x - 1.0, dist.x - 2.0); + coef = FIX(coef); + coef = 2.0 * sin(coef) * sin(coef / 2.0) / (coef * coef); + coef /= dot(coef, float4(1.0, 1.0, 1.0, 1.0)); + float4 col1 = float4(TEX2D(tex_co), 1.0); + float4 col2 = float4(TEX2D(tex_co + dx), 1.0); + float4x4 fkfk = mul(coef.x, float4x4(col1, col1, col2, col2)); + float4x4 fkfks = mul(coef.y, float4x4(col1, col1, col2, col2)); + float4x4 fkfkb = mul(coef.z, float4x4(col1, col1, col2, col2)); + return float3(fkfk[0].x, fkfk[0].y, fkfk[0].z); + } + + float3 mix(float3 x, float3 y, float3 a) { + return float3(x * (1 - a) + y * a); + } + + float3 get_mask_weight(float x) + { + float i = mod(floor(x), MASK_COLORS); + if (i == 0.0) return mix(float3(1.0, 0.0, 1.0), float3(1.0, 0.0, 0.0), MASK_COLORS - 2.0); + else if (i == 1.0) return float3(0.0, 1.0, 0.0); + else return float3(0.0, 0.0, 1.0); + } + + float4 Frag0(v2f i) : SV_Target + { + float2 pos = i.uv; + float3 col_glow = filter_gaussian(pos, _ScreenParams.xy); + float3 col_soft = filter_lanczos(pos, _ScreenParams.xy, 1); + float3 col_sharp = filter_lanczos(pos, _ScreenParams.xy, 3); + float3 col = sqrt(col_sharp * col_soft); + col_glow = saturate(col_glow - col); + col += col_glow * col_glow * GLOW_HALATION; + col = mix(col, col * get_mask_weight(pos.x) * MASK_COLORS, MASK_STRENGTH); + col += col_glow * GLOW_DIFFUSION; + col = pow(abs(col * BRIGHTNESS), float3(1.0 / GAMMA_OUTPUT, 1.0 / GAMMA_OUTPUT, 1.0 / GAMMA_OUTPUT)); + half4 col1 = tex2D(_MainTex, pos); + float fade = 1; + + return lerp(col1,float4(col, col1.a+(col.r+col.g+col.b)/3),fade); + } + ENDCG + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader.meta new file mode 100644 index 00000000..8304beb7 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_CRT_Aperture.shader.meta @@ -0,0 +1,9 @@ +fileFormatVersion: 2 +guid: f63497435389f8548ab973da8535e1b5 +ShaderImporter: + externalObjects: {} + defaultTextures: [] + nonModifiableTextures: [] + userData: + assetBundleName: + assetBundleVariant: From e8fc45b0068cd1f5c568e15f50e2b83875b1cee6 Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Sun, 27 Apr 2025 10:20:18 +0800 Subject: [PATCH 02/10] RLPro_Bleed rename to RLPRO_CRT --- .../AppSettings/Filter/RLPro/{RLPro_Bleed.cs => RLPRO_CRT.cs} | 0 .../Filter/RLPro/{RLPro_Bleed.cs.meta => RLPRO_CRT.cs.meta} | 0 2 files changed, 0 insertions(+), 0 deletions(-) rename AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/{RLPro_Bleed.cs => RLPRO_CRT.cs} (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/{RLPro_Bleed.cs.meta => RLPRO_CRT.cs.meta} (100%) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_Bleed.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs.meta From fcd64a54f6a42a4997f77d871a856e29cd73b844 Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Sun, 27 Apr 2025 15:06:42 +0800 Subject: [PATCH 03/10] =?UTF-8?q?=E5=AE=8C=E5=96=84RLPRO=5FCRT=E6=BB=A4?= =?UTF-8?q?=E9=95=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../AppSettings/Filter/RLPro/RLPRO_CRT.cs | 69 ++++++-- .../Filter/RLPro/RLPro_TV_Effect.shader | 162 ++++++++++++++++++ .../Filter/RLPro/RLPro_TV_Effect.shader.meta | 9 + 3 files changed, 230 insertions(+), 10 deletions(-) create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs index e3ab14e6..75c07baa 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs @@ -10,25 +10,37 @@ namespace AxibugEmuOnline.Client.Filters protected override string ShaderName => null; #region BleedPass_Param - public FilterParameter BleedMode = new FilterParameter(EnumBleedMode.NTSCOld3Phase); + public FilterParameter BleedMode = EnumBleedMode.NTSCOld3Phase; [Range(0, 15)] - public FloatParameter BleedAmount = new FloatParameter(1f); + public FloatParameter BleedAmount = 1f; #endregion #region CRTAperture_Param [Range(0, 5)] - public FloatParameter GlowHalation = new FloatParameter(0.1f); + public FloatParameter GlowHalation = 0.1f; [Range(0, 2)] - public FloatParameter GlowDifusion = new FloatParameter(0.05f); + public FloatParameter GlowDifusion = 0.05f; [Range(0, 2)] - public FloatParameter MaskColors = new FloatParameter(2.0f); + public FloatParameter MaskColors = 2.0f; [Range(0, 1)] - public FloatParameter MaskStrength = new FloatParameter(0.3f); + public FloatParameter MaskStrength = 0.3f; [Range(0, 5)] - public FloatParameter GammaInput = new FloatParameter(2.4f); + public FloatParameter GammaInput = 2.4f; [Range(0, 5)] - public FloatParameter GammaOutput = new FloatParameter(2.4f); + public FloatParameter GammaOutput = 2.4f; [Range(0, 2.5f)] - public FloatParameter Brightness = new FloatParameter(1.5f); + public FloatParameter Brightness = 1.5f; + #endregion + #region TV_Effect_Param + public FilterParameter WrapMode = EnumWrapMode.SimpleWrap; + public FloatParameter maskDark = 0.5f; + public FloatParameter maskLight = 1.5f; + public FloatParameter hardScan = -8.0f; + public FloatParameter hardPix = -3.0f; + public Vector2Parameter warp = new Vector2(1.0f / 32.0f, 1.0f / 24.0f); + public Vector2Parameter res; + public FloatParameter resScale; + public FloatParameter scale; + public FloatParameter fade; #endregion Material m_bleedMat; @@ -39,17 +51,20 @@ namespace AxibugEmuOnline.Client.Filters { m_bleedMat = new Material(Shader.Find("Filter/RLPro_Bleed")); m_crtApertureMat = new Material(Shader.Find("Filter/RLPro_CRT_Aperture")); + m_tvEffectMat = new Material(Shader.Find("Filter/RLPro_TV_Effect")); } protected override void OnRenderer(Material renderMat, Texture src, RenderTexture result) { var rt1 = BleedPass(src); var rt2 = CRT_AperturePass(rt1); + var rt3 = TV_Effect_Pass(rt2); - Graphics.Blit(rt2, result); + Graphics.Blit(rt3, result); RenderTexture.ReleaseTemporary(rt1); RenderTexture.ReleaseTemporary(rt2); + RenderTexture.ReleaseTemporary(rt3); } private RenderTexture BleedPass(Texture src) @@ -95,6 +110,34 @@ namespace AxibugEmuOnline.Client.Filters return rt; } + private RenderTexture TV_Effect_Pass(Texture src) + { + var rt = RenderTexture.GetTemporary(src.width, src.height); + + m_tvEffectMat.DisableKeyword("_SimpleWrap"); + m_tvEffectMat.DisableKeyword("_CubicDistortion"); + + switch (WrapMode.GetValue()) + { + case EnumWrapMode.SimpleWrap: + m_tvEffectMat.EnableKeyword("_SimpleWrap"); break; + case EnumWrapMode.CubicDistortion: + m_tvEffectMat.EnableKeyword("_CubicDistortion"); break; + } + + m_tvEffectMat.SetFloat("maskDark", maskDark.GetValue()); + m_tvEffectMat.SetFloat("maskLight", maskLight.GetValue()); + m_tvEffectMat.SetFloat("hardScan", hardScan.GetValue()); + m_tvEffectMat.SetVector("warp", warp.GetValue()); + m_tvEffectMat.SetVector("res", res.GetValue()); + m_tvEffectMat.SetFloat("resScale", resScale.GetValue()); + m_tvEffectMat.SetFloat("scale", scale.GetValue()); + m_tvEffectMat.SetFloat("fade", fade.GetValue()); + + Graphics.Blit(src, rt, m_tvEffectMat); + + return rt; + } public enum EnumBleedMode { @@ -102,5 +145,11 @@ namespace AxibugEmuOnline.Client.Filters NTSC3Phase, NTSC2Phase, } + + public enum EnumWrapMode + { + SimpleWrap, + CubicDistortion + } } } \ No newline at end of file diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader new file mode 100644 index 00000000..0be47b3d --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader @@ -0,0 +1,162 @@ +Shader "Filter/RLPro_TV_Effect" +{ + Properties + { + _MainTex ("Base (RGB)", 2D) = "white" {} + } + SubShader + { + Pass + { + CGPROGRAM + + #pragma shader_feature_local _SimpleWrap _CubicDistortion + #pragma vertex vert_img + #pragma fragment Frag + #include "UnityCG.cginc" + + sampler2D _MainTex; + float4 _MainTex_TexelSize; + float2 _iResolution; + + float maskDark = 0.5; + float maskLight = 1.5; + float hardScan = -8.0; + float hardPix = -3.0; + float2 warp = float2(1.0 / 32.0, 1.0 / 24.0); + float2 res; + float resScale; + float scale; + float fade; + + struct v2f + { + float4 pos : POSITION; + float2 uv : TEXCOORD0; + }; + + float3 Fetch(float2 pos, float2 off) + { + pos = floor(pos * res + off) / res; + return tex2Dlod(_MainTex, float4(pos.xy, 0, -16.0)).rgb; + } + + float2 Dist(float2 pos) { pos = pos * res; return -((pos - floor(pos)) - float2(0.5, 0.5)); } + float Gaus(float pos, float scale) { return exp2(scale * pos * pos); } + + float3 Horz3(float2 pos, float off) + { + float3 b = Fetch(pos, float2(-1.0, off)); + float3 c = Fetch(pos, float2(0.0, off)); + float3 d = Fetch(pos, float2(1.0, off)); + float dst = Dist(pos).x; + float scale = hardPix; + float wb = Gaus(dst - 1.0, scale); + float wc = Gaus(dst + 0.0, scale); + float wd = Gaus(dst + 1.0, scale); + return (b * wb + c * wc + d * wd) / (wb + wc + wd); + } + + float3 Horz5(float2 pos, float off) + { + float3 a = Fetch(pos, float2(-2.0, off)); + float3 b = Fetch(pos, float2(-1.0, off)); + float3 c = Fetch(pos, float2(0.0, off)); + float3 d = Fetch(pos, float2(1.0, off)); + float3 e = Fetch(pos, float2(2.0, off)); + float dst = Dist(pos).x; + float scale = hardPix; + float wa = Gaus(dst - 2.0, scale); + float wb = Gaus(dst - 1.0, scale); + float wc = Gaus(dst + 0.0, scale); + float wd = Gaus(dst + 1.0, scale); + float we = Gaus(dst + 2.0, scale); + return (a * wa + b * wb + c * wc + d * wd + e * we) / (wa + wb + wc + wd + we); + } + + float Scan(float2 pos, float off) + { + float dst = Dist(pos).y; + return Gaus(dst + off, hardScan); + } + + float3 Tri(float2 pos) + { + float3 a = Horz3(pos, -1.0); + float3 b = Horz5(pos, 0.0); + float3 c = Horz3(pos, 1.0); + float wa = Scan(pos, -1.0); + float wb = Scan(pos, 0.0); + float wc = Scan(pos, 1.0); + return a * wa + b * wb + c * wc; + } + + float2 Warp(float2 pos) + { + float2 h = pos - float2(0.5, 0.5); + float r2 = dot(h, h); + float f = 1.0 + r2 * (warp.x + warp.y * sqrt(r2)); + return f * scale * h + 0.5; + } + + float2 Warp1(float2 pos) + { + pos = pos * 2.0 - 1.0; + pos *= float2(1.0 + (pos.y * pos.y) * warp.x, 1.0 + (pos.x * pos.x) * warp.y); + return pos * scale + 0.5; + } + + float3 Mask(float2 pos) + { + pos.x += pos.y * 3.0; + float3 mask = float3(maskDark, maskDark, maskDark); + pos.x = frac(pos.x / 6.0); + if (pos.x < 0.333)mask.r = maskLight; + else if (pos.x < 0.666)mask.g = maskLight; + else mask.b = maskLight; + return mask; + } + + float4 SimpleWrapFrag(v2f i) + { + float2 uv = i.uv; + + float4 col = tex2D(_MainTex,uv); + res = _ScreenParams.xy / resScale; + float2 fragCoord = uv * _ScreenParams.xy; + float4 fragColor = 0; + float2 pos = Warp1(fragCoord.xy / _ScreenParams.xy); + fragColor.rgb = Tri(pos) * Mask(fragCoord); + fragColor.a = tex2D(_MainTex,pos).a; + + return lerp(col,fragColor,fade); + } + + float4 CubicDistortionFrag(v2f i) + { + float2 uv = i.uv; + + float4 col = tex2D(_MainTex,uv); + res = _iResolution.xy / resScale; + float2 fragCoord = uv * _ScreenParams.xy; + float4 fragColor = 0; + float2 pos = Warp(fragCoord.xy / _ScreenParams.xy); + fragColor.rgb = Tri(pos) * Mask(fragCoord); + fragColor.a = tex2D(_MainTex,pos).a; + + return lerp(col,fragColor,fade); + } + + float4 Frag(v2f i) : SV_Target + { +#if _SimpleWrap + return SimpleWrapFrag(i); +#else + return CubicDistortionFrag(i); +#endif + } + + ENDCG + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader.meta new file mode 100644 index 00000000..1aceaad1 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPro_TV_Effect.shader.meta @@ -0,0 +1,9 @@ +fileFormatVersion: 2 +guid: bef4d98671a3c524f9bfdba0d25e5991 +ShaderImporter: + externalObjects: {} + defaultTextures: [] + nonModifiableTextures: [] + userData: + assetBundleName: + assetBundleVariant: From 8fc65c2f70f5512bb2ccd06a11e725e7810d045e Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Mon, 28 Apr 2025 11:20:45 +0800 Subject: [PATCH 04/10] =?UTF-8?q?=E8=B0=83=E6=95=B4=E5=87=A0=E4=B8=AA?= =?UTF-8?q?=E5=B7=A5=E5=85=B7=E8=84=9A=E6=9C=AC=E7=9A=84=E7=9B=AE=E5=BD=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Assets/Script/AppMain/UI/Tools.meta | 8 ++++++++ .../Script/AppMain/UI/{ => Tools}/AlphaWraper.cs | 5 ++++- .../AppMain/UI/{ => Tools}/AlphaWraper.cs.meta | 0 .../UI/{ => Tools}/AutoRaycastCanvasGroup.cs | 5 ++++- .../UI/{ => Tools}/AutoRaycastCanvasGroup.cs.meta | 0 .../Script/AppMain/UI/{ => Tools}/PulseInvoker.cs | 13 ++++++++----- .../AppMain/UI/{ => Tools}/PulseInvoker.cs.meta | 0 .../Script/AppMain/UI/{ => Tools}/Selector.cs | 3 +++ .../Script/AppMain/UI/{ => Tools}/Selector.cs.meta | 0 .../Assets/Script/AppMain/UI/{ => Tools}/UITool.cs | 0 .../Script/AppMain/UI/{ => Tools}/UITool.cs.meta | 0 11 files changed, 27 insertions(+), 7 deletions(-) create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools.meta rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/AlphaWraper.cs (95%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/AlphaWraper.cs.meta (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/AutoRaycastCanvasGroup.cs (75%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/AutoRaycastCanvasGroup.cs.meta (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/PulseInvoker.cs (87%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/PulseInvoker.cs.meta (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/Selector.cs (93%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/Selector.cs.meta (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/UITool.cs (100%) rename AxibugEmuOnline.Client/Assets/Script/AppMain/UI/{ => Tools}/UITool.cs.meta (100%) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools.meta new file mode 100644 index 00000000..4f98186e --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: ac0b0e6e0769cf144a829fef3f6740b1 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AlphaWraper.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AlphaWraper.cs similarity index 95% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AlphaWraper.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AlphaWraper.cs index cc7c5174..078cb6bd 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AlphaWraper.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AlphaWraper.cs @@ -1,10 +1,13 @@ -using DG.Tweening; +using DG.Tweening; using DG.Tweening.Core; using DG.Tweening.Plugins.Options; using UnityEngine; namespace AxibugEmuOnline.Client { + /// + /// 用于指定一对CanvasGroup,做透明度切换 + /// public class AlphaWraper { private bool m_on; diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AlphaWraper.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AlphaWraper.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AlphaWraper.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AlphaWraper.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AutoRaycastCanvasGroup.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AutoRaycastCanvasGroup.cs similarity index 75% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AutoRaycastCanvasGroup.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AutoRaycastCanvasGroup.cs index 4637d7f0..df5c5afb 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AutoRaycastCanvasGroup.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AutoRaycastCanvasGroup.cs @@ -1,7 +1,10 @@ -using UnityEngine; +using UnityEngine; namespace AxibugEmuOnline.Client { + /// + /// 自动根据canvasgroup的alpha控制blocksRaycasts的开启状态 + /// [RequireComponent(typeof(CanvasGroup))] public class AutoRaycastCanvasGroup : MonoBehaviour { diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AutoRaycastCanvasGroup.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AutoRaycastCanvasGroup.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/AutoRaycastCanvasGroup.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/AutoRaycastCanvasGroup.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/PulseInvoker.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/PulseInvoker.cs similarity index 87% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/PulseInvoker.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/PulseInvoker.cs index 70209912..bbe10d62 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/PulseInvoker.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/PulseInvoker.cs @@ -1,7 +1,10 @@ -namespace AxibugEmuOnline.Client.UI -{ - using System; +using System; +namespace AxibugEmuOnline.Client.UI +{ + /// + /// 用于周期性触发回调的工具,带有触发周期和延迟触发的参数可调 + /// public class PulseInvoker { private Action _action; @@ -9,8 +12,8 @@ private float _delay; private float _elapsedTime; private bool _isActive; - private bool _isDelayed; - + private bool _isDelayed; + public PulseInvoker(Action action, float delay, float interval) { _action = action; diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/PulseInvoker.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/PulseInvoker.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/PulseInvoker.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/PulseInvoker.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Selector.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/Selector.cs similarity index 93% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Selector.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/Selector.cs index 78b9e2fc..3957b6df 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Selector.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/Selector.cs @@ -5,6 +5,9 @@ using UnityEngine; namespace AxibugEmuOnline.Client { + /// + /// 选择指示器,用于控制RectTransform在屏幕坐标上的高宽和位置同步,同时带有过度动画 + /// public class Selector : MonoBehaviour { [SerializeField] diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Selector.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/Selector.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Selector.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/Selector.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/UITool.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/UITool.cs similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/UITool.cs rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/UITool.cs diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/UITool.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/UITool.cs.meta similarity index 100% rename from AxibugEmuOnline.Client/Assets/Script/AppMain/UI/UITool.cs.meta rename to AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/UITool.cs.meta From e5f497a16344c7ba7fa42e6bc32189bf62de3b0d Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Mon, 28 Apr 2025 11:58:22 +0800 Subject: [PATCH 05/10] =?UTF-8?q?=E5=AD=98=E6=A1=A3=E4=BA=91=E5=90=8C?= =?UTF-8?q?=E6=AD=A5=E7=8A=B6=E6=80=81UI=E6=8F=90=E4=BA=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Resources/UIPrefabs/OptionUI.prefab | 392 +++++++++++++++++- .../AppMain/UI/Tools/DotweenRotation.cs | 53 +++ .../AppMain/UI/Tools/DotweenRotation.cs.meta | 2 + 3 files changed, 431 insertions(+), 16 deletions(-) create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs create mode 100644 AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/Resources/UIPrefabs/OptionUI.prefab b/AxibugEmuOnline.Client/Assets/Resources/UIPrefabs/OptionUI.prefab index 94f5a72d..232826e5 100644 --- a/AxibugEmuOnline.Client/Assets/Resources/UIPrefabs/OptionUI.prefab +++ b/AxibugEmuOnline.Client/Assets/Resources/UIPrefabs/OptionUI.prefab @@ -648,6 +648,81 @@ MonoBehaviour: m_FlexibleWidth: 1 m_FlexibleHeight: -1 m_LayoutPriority: 1 +--- !u!1 &1601163034082482360 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 2303902335643923373} + - component: {fileID: 7825136160635457043} + - component: {fileID: 2505159117998551519} + m_Layer: 5 + m_Name: Conflict + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &2303902335643923373 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 1601163034082482360} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 905458728127029103} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 50, y: 50} + m_Pivot: {x: 0, y: 0} +--- !u!222 &7825136160635457043 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 1601163034082482360} + m_CullTransparentMesh: 1 +--- !u!114 &2505159117998551519 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 1601163034082482360} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 0 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: 21300000, guid: 994c93ed03dadee49974aebf3cb5365d, type: 3} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 --- !u!1 &1731066637017514641 GameObject: m_ObjectHideFlags: 0 @@ -869,6 +944,45 @@ MonoBehaviour: m_FillOrigin: 0 m_UseSpriteMesh: 0 m_PixelsPerUnitMultiplier: 1 +--- !u!1 &2040328582144336713 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 905458728127029103} + m_Layer: 5 + m_Name: StateNode + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &905458728127029103 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2040328582144336713} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: + - {fileID: 3539783812791358836} + - {fileID: 6030618878828304669} + - {fileID: 2303902335643923373} + - {fileID: 8677023902282266940} + m_Father: {fileID: 5970282275929291192} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 1, y: 1} + m_AnchoredPosition: {x: 5, y: 5} + m_SizeDelta: {x: -10, y: -10} + m_Pivot: {x: 0.5, y: 0.5} --- !u!1 &2471254561136382013 GameObject: m_ObjectHideFlags: 0 @@ -1023,6 +1137,81 @@ MonoBehaviour: m_Icon: {fileID: 394891843266770919} ExpandFlag: {fileID: 1501213187178026014} ApplyFlag: {fileID: 3335801350916860509} +--- !u!1 &2637678715180681658 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 8677023902282266940} + - component: {fileID: 6387250980529666459} + - component: {fileID: 6242848023853370498} + m_Layer: 5 + m_Name: Synced + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &8677023902282266940 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2637678715180681658} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 905458728127029103} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 50, y: 50} + m_Pivot: {x: 0, y: 0} +--- !u!222 &6387250980529666459 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2637678715180681658} + m_CullTransparentMesh: 1 +--- !u!114 &6242848023853370498 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2637678715180681658} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 0 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: 21300000, guid: 28db37d78cad20f4397804dfa4572829, type: 3} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 --- !u!1 &2660711182228429640 GameObject: m_ObjectHideFlags: 0 @@ -1188,10 +1377,10 @@ RectTransform: m_Children: [] m_Father: {fileID: 1100500336380202360} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} - m_AnchorMin: {x: 0, y: 0} - m_AnchorMax: {x: 0, y: 0} - m_AnchoredPosition: {x: 0, y: 0} - m_SizeDelta: {x: 0, y: 0} + m_AnchorMin: {x: 0, y: 1} + m_AnchorMax: {x: 0, y: 1} + m_AnchoredPosition: {x: 170, y: -333} + m_SizeDelta: {x: 300, y: 26} m_Pivot: {x: 0.5, y: 0.5} --- !u!222 &7910447946506517051 CanvasRenderer: @@ -1253,6 +1442,97 @@ MonoBehaviour: m_EffectColor: {r: 0, g: 0, b: 0, a: 0.5} m_EffectDistance: {x: 1.5, y: -1.5} m_UseGraphicAlpha: 1 +--- !u!1 &4078965612622303339 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 6030618878828304669} + - component: {fileID: 6018890508858230420} + - component: {fileID: 1865219663044263670} + - component: {fileID: 6562970432720184454} + m_Layer: 5 + m_Name: Syncing + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &6030618878828304669 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 4078965612622303339} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 905458728127029103} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 50, y: 50} + m_Pivot: {x: 0, y: 0} +--- !u!222 &6018890508858230420 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 4078965612622303339} + m_CullTransparentMesh: 1 +--- !u!114 &1865219663044263670 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 4078965612622303339} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 0 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: 21300000, guid: c5a9535bb63e1f14f9a1528566864ab2, type: 3} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 +--- !u!114 &6562970432720184454 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 4078965612622303339} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 8707b921aaba60d45b4041e96f3542dd, type: 3} + m_Name: + m_EditorClassIdentifier: + m_duration: 2 + m_ease: 1 + m_reverseRotation: 1 --- !u!1 &4124172888520656882 GameObject: m_ObjectHideFlags: 0 @@ -1384,12 +1664,13 @@ RectTransform: - {fileID: 7389645496847632176} - {fileID: 173892651193427531} - {fileID: 8150810211498757695} + - {fileID: 905458728127029103} m_Father: {fileID: 1100500336380202360} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} - m_AnchorMin: {x: 0, y: 0} - m_AnchorMax: {x: 0, y: 0} - m_AnchoredPosition: {x: 0, y: 0} - m_SizeDelta: {x: 0, y: 0} + m_AnchorMin: {x: 0, y: 1} + m_AnchorMax: {x: 0, y: 1} + m_AnchoredPosition: {x: 170, y: -160} + m_SizeDelta: {x: 300, y: 300} m_Pivot: {x: 0.5, y: 0.5} --- !u!114 &2558056583130529771 MonoBehaviour: @@ -1522,8 +1803,8 @@ MonoBehaviour: m_Name: m_EditorClassIdentifier: m_IgnoreLayout: 1 - m_MinWidth: 300 - m_MinHeight: -1 + m_MinWidth: -1 + m_MinHeight: 1080 m_PreferredWidth: -1 m_PreferredHeight: -1 m_FlexibleWidth: -1 @@ -2743,6 +3024,81 @@ MonoBehaviour: m_EffectColor: {r: 0, g: 0, b: 0, a: 0.5} m_EffectDistance: {x: 1.5, y: -1.5} m_UseGraphicAlpha: 1 +--- !u!1 &6998836277133601669 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 3539783812791358836} + - component: {fileID: 6969397185295608833} + - component: {fileID: 5170828039250978253} + m_Layer: 5 + m_Name: Disconnect + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!224 &3539783812791358836 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6998836277133601669} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 905458728127029103} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 50, y: 50} + m_Pivot: {x: 0, y: 0} +--- !u!222 &6969397185295608833 +CanvasRenderer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6998836277133601669} + m_CullTransparentMesh: 1 +--- !u!114 &5170828039250978253 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 6998836277133601669} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3} + m_Name: + m_EditorClassIdentifier: + m_Material: {fileID: 0} + m_Color: {r: 1, g: 1, b: 1, a: 1} + m_RaycastTarget: 0 + m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0} + m_Maskable: 1 + m_OnCullStateChanged: + m_PersistentCalls: + m_Calls: [] + m_Sprite: {fileID: 21300000, guid: 630c435b903e3dc4e80038c0a531162d, type: 3} + m_Type: 0 + m_PreserveAspect: 0 + m_FillCenter: 1 + m_FillMethod: 4 + m_FillAmount: 1 + m_FillClockwise: 1 + m_FillOrigin: 0 + m_UseSpriteMesh: 0 + m_PixelsPerUnitMultiplier: 1 --- !u!1 &7099541800602849681 GameObject: m_ObjectHideFlags: 0 @@ -2760,7 +3116,7 @@ GameObject: m_Icon: {fileID: 0} m_NavMeshLayer: 0 m_StaticEditorFlags: 0 - m_IsActive: 1 + m_IsActive: 0 --- !u!224 &1100500336380202360 RectTransform: m_ObjectHideFlags: 0 @@ -2778,10 +3134,10 @@ RectTransform: - {fileID: 6878964193873653430} m_Father: {fileID: 4478785627166277610} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} - m_AnchorMin: {x: 0, y: 0} - m_AnchorMax: {x: 0, y: 0} - m_AnchoredPosition: {x: 0, y: 0} - m_SizeDelta: {x: 0, y: 0} + m_AnchorMin: {x: 0, y: 1} + m_AnchorMax: {x: 0, y: 1} + m_AnchoredPosition: {x: 165, y: -443} + m_SizeDelta: {x: 330, y: 356} m_Pivot: {x: 0.5, y: 0.5} --- !u!114 &20405450890320071 MonoBehaviour: @@ -2803,7 +3159,7 @@ MonoBehaviour: m_ChildAlignment: 0 m_Spacing: 10 m_ChildForceExpandWidth: 1 - m_ChildForceExpandHeight: 1 + m_ChildForceExpandHeight: 0 m_ChildControlWidth: 1 m_ChildControlHeight: 1 m_ChildScaleWidth: 0 @@ -2826,6 +3182,10 @@ MonoBehaviour: UI_ScreenShot: {fileID: 1024458178917207864} UI_Empty: {fileID: 8350228378118296958} UI_SavTime: {fileID: 13043593624240728} + UI_Disconnect: {fileID: 6998836277133601669} + UI_Syncing: {fileID: 4078965612622303339} + UI_Conflict: {fileID: 1601163034082482360} + UI_Synced: {fileID: 2637678715180681658} --- !u!1 &7141318786199574664 GameObject: m_ObjectHideFlags: 0 diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs new file mode 100644 index 00000000..c2a5fe28 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs @@ -0,0 +1,53 @@ +using DG.Tweening; +using DG.Tweening.Core; +using DG.Tweening.Plugins.Options; +using UnityEngine; + +namespace AxibugEmuOnline.Client.Tools +{ + public class DotweenRotation : MonoBehaviour + { + [SerializeField] + float m_duration = 1f; + [SerializeField] + Ease m_ease = Ease.Linear; + [SerializeField] + bool m_reverseRotation; + + private TweenerCore m_tween; + + void OnEnable() + { + Restart(); + } + + private void Restart() + { + if (m_tween != null) + { + m_tween.Kill(); + m_tween = null; + } + + transform.localRotation = Quaternion.identity; + m_tween = transform.DOLocalRotate(new Vector3(0, 0, 360f * (m_reverseRotation ? -1 : 1)), m_duration, RotateMode.LocalAxisAdd) + .SetEase(m_ease) + .SetLoops(-1); + m_tween.SetLink(gameObject); + } + + private void OnDisable() + { + if (m_tween != null) + { + m_tween.Kill(); + m_tween = null; + } + } + + private void OnValidate() + { + Restart(); + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs.meta b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs.meta new file mode 100644 index 00000000..39060b1f --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/Tools/DotweenRotation.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: 8707b921aaba60d45b4041e96f3542dd \ No newline at end of file From 902dc95d1980d3bcc5eeb369bd2a1ff16057c79c Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Tue, 29 Apr 2025 16:19:09 +0800 Subject: [PATCH 06/10] =?UTF-8?q?IEmuCore=E4=BB=8E=E6=8E=A5=E5=8F=A3?= =?UTF-8?q?=E4=BF=AE=E6=94=B9=E4=B8=BA=E6=8A=BD=E8=B1=A1=E7=B1=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Emulator/EssgeeEmulator/UEssgee.cs | 92 +++++++++---------- .../AppMain/Emulator/MameEmulator/UMAME.cs | 36 ++++---- .../Emulator/NesEmulator/NesEmulator.cs | 37 ++++---- .../StoicGooseEmulator/UStoicGoose.cs | 36 ++++---- .../Assets/Script/AppMain/IEmuCore.cs | 47 ++++------ .../Assets/Script/AppMain/Manager/AppEmu.cs | 8 +- .../Script/AppMain/UI/InGameUI/InGameUI.cs | 2 +- .../AppMain/UI/InGameUI/InGameUI_Scaler.cs | 2 +- .../Assets/Script/AppMain/UI/LaunchUI.cs | 2 +- .../UI/XMBTopGroupUI/ControllerInfo.cs | 2 +- .../UI/XMBTopGroupUI/ControllerInfoPanel.cs | 2 +- .../AppMain/UI/XMBTopGroupUI/XMBInfoBar.cs | 4 +- 12 files changed, 129 insertions(+), 141 deletions(-) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs index e1654a05..17ed2dca 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs @@ -1,4 +1,4 @@ -using AxibugEmuOnline.Client; +using AxibugEmuOnline.Client; using AxibugEmuOnline.Client.ClientCore; using AxibugProtobuf; using Essgee; @@ -17,19 +17,19 @@ using System.Text; using UnityEngine; using UnityEngine.UI; -public class UEssgee : MonoBehaviour, IEmuCore +public class UEssgee : IEmuCore { public static UEssgee instance; public static System.Diagnostics.Stopwatch sw = System.Diagnostics.Stopwatch.StartNew(); public static bool bInGame => instance?.emulatorHandler?.IsRunning == true ? true : false; - public RomPlatformType Platform => mPlatform; + public override RomPlatformType Platform => mPlatform; - public uint Frame => (uint)emulatorHandler.AxiEmuRunFrame; + public override uint Frame => (uint)emulatorHandler.AxiEmuRunFrame; - public Texture OutputPixel => graphicsHandler.rawBufferWarper; + public override Texture OutputPixel => graphicsHandler.rawBufferWarper; - public RawImage DrawCanvas => graphicsHandler.DrawCanvas; + public override RawImage DrawCanvas => graphicsHandler.DrawCanvas; public static bool bLogicUpdatePause { get; private set; } #region @@ -71,38 +71,38 @@ public class UEssgee : MonoBehaviour, IEmuCore } - #region EmuCoreʵ + #region EmuCore接入实现 - public object GetState() + public override object GetState() { return emulatorHandler.GetStateData(); } - public byte[] GetStateBytes() + public override byte[] GetStateBytes() { return emulatorHandler.GetStateData(); } - public void LoadState(object state) + public override void LoadState(object state) { emulatorHandler.SetStateData((byte[])state); } - public void LoadStateFromBytes(byte[] data) + public override void LoadStateFromBytes(byte[] data) { emulatorHandler.SetStateData(data); } - public void Pause() + public override void Pause() { bLogicUpdatePause = false; } - public void Resume() + public override void Resume() { bLogicUpdatePause = true; } - public MsgBool StartGame(RomFile romFile) + public override MsgBool StartGame(RomFile romFile) { mPlatform = romFile.Platform; @@ -110,7 +110,7 @@ public class UEssgee : MonoBehaviour, IEmuCore bLogicUpdatePause = true; - //浱ǰڽеϷ浵 + //保存当前正在进行的游戏存档 if (emulatorHandler != null && !emulatorHandler.IsRunning) { emulatorHandler.SaveCartridge(); @@ -119,10 +119,10 @@ public class UEssgee : MonoBehaviour, IEmuCore if (LoadAndRunCartridge(romFile.LocalFilePath)) return true; else - return "Romʧ"; + return "Rom加载失败"; } - public void Dispose() + public override void Dispose() { if (!emulatorHandler.IsRunning) { @@ -131,36 +131,36 @@ public class UEssgee : MonoBehaviour, IEmuCore ShutdownEmulation(); } - public void DoReset() + public override void DoReset() { emulatorHandler.SaveCartridge(); emulatorHandler.Reset(); } - public IControllerSetuper GetControllerSetuper() + public override IControllerSetuper GetControllerSetuper() { return mUniKeyboard.ControllerMapper; } - public bool PushEmulatorFrame() + public override bool PushEmulatorFrame() { if (!emulatorHandler.IsRunning) return false; if (!bLogicUpdatePause) return false; - //ɼ֡Input + //采集本帧Input bool bhadNext = mUniKeyboard.SampleInput(); - //δյInput,֡ƽ + //如果未收到Input数据,核心帧不推进 if (!bhadNext) return false; emulatorHandler.Update_Frame(); return true; } - public void AfterPushFrame() + public override void AfterPushFrame() { } - public void GetAudioParams(out int frequency, out int channels) + public override void GetAudioParams(out int frequency, out int channels) { frequency = soundHandler.sampleRate; channels = soundHandler.channle; @@ -169,10 +169,10 @@ public class UEssgee : MonoBehaviour, IEmuCore void InitAll(IGameMetaReources metaresources, IEssgeeIOSupport uegIO, string CustonDataDir) { - //ʼ + //初始化配置 InitAppEnvironment(CustonDataDir, uegIO); InitEmu(); - //ϸڳʼ + //细节初始化 InitializeHandlers(metaresources); } @@ -218,7 +218,7 @@ public class UEssgee : MonoBehaviour, IEmuCore if (AppEnvironment.EnableLogger) { - //TODO رDebug + //TODO 关闭Debug //Logger.Flush(); //Logger.Close(); } @@ -229,7 +229,7 @@ public class UEssgee : MonoBehaviour, IEmuCore //keysDown = new List(); } - #region ϸڳʼ + #region 细节初始化 private void InitializeHandlers(IGameMetaReources metaresources) { @@ -277,7 +277,7 @@ public class UEssgee : MonoBehaviour, IEmuCore #endregion void Dispose(bool disposing) { - //TODO ͷʱ + //TODO 释放时 //if (disposing) //{ // if (components != null) components.Dispose(); @@ -289,10 +289,10 @@ public class UEssgee : MonoBehaviour, IEmuCore //base.Dispose(disposing); } - #region + #region 配置 private static void LoadConfiguration() { - //TODO ʱü + //TODO 暂时跳过这里的配置加载 //Directory.CreateDirectory(EmuStandInfo.programDataDirectory); //if (!File.Exists(EmuStandInfo.programConfigPath) || (EmuStandInfo.Configuration = EmuStandInfo.programConfigPath.DeserializeFromFile()) == null) //{ @@ -397,12 +397,12 @@ public class UEssgee : MonoBehaviour, IEmuCore } public static void SaveConfiguration() { - //ñ + //不用保存这个配置 //EmuStandInfo.Configuration.SerializeToFile(EmuStandInfo.programConfigPath); } #endregion - #region ģ + #region 模拟器基本设置 public void SetEmuFpsLimit(bool bOpen) { @@ -427,12 +427,12 @@ public class UEssgee : MonoBehaviour, IEmuCore } #endregion - #region ģ + #region 模拟器生命周期 private void PowerOnWithoutCartridge(Type machineType) { - //TODO IsRecording?? Ҫʵ + //TODO IsRecording?? 可能需要实现 //if (soundHandler.IsRecording) // soundHandler.CancelRecording(); @@ -456,7 +456,7 @@ public class UEssgee : MonoBehaviour, IEmuCore var (machineType, romData) = CartridgeLoader.Load(fileName, "ROM image"); - //TODO IsRecording?? Ҫʵ + //TODO IsRecording?? 可能需要实现 //if (soundHandler.IsRecording) // soundHandler.CancelRecording(); @@ -481,13 +481,13 @@ public class UEssgee : MonoBehaviour, IEmuCore //toggleLayersToolStripMenuItem.Enabled = enableChannelsToolStripMenuItem.Enabled = true; - //ʼͬƽ̨İť + //初始化不同平台的按钮 mUniKeyboard.Init(emulatorHandler.emulator); emulatorHandler.Startup(); - //ʼƵ + //初始化音频 soundHandler.Initialize(); //SizeAndPositionWindow(); @@ -549,7 +549,7 @@ public class UEssgee : MonoBehaviour, IEmuCore //{ if (!AppEnvironment.TemporaryDisableCustomExceptionForm) { - //TODO debugڣ + //TODO debug窗口? //(_, ExceptionResult result, string prefix, string postfix) = ExceptionForm.GetExceptionInfo(ex); //if (result == ExceptionResult.Continue) @@ -661,7 +661,7 @@ public class UEssgee : MonoBehaviour, IEmuCore } #endregion - #region ģڲ¼ + #region 模拟器内部事件 private void EmulatorHandler_SendLogMessage(object sender, SendLogMessageEventArgs e) { @@ -699,7 +699,7 @@ public class UEssgee : MonoBehaviour, IEmuCore private void EmulatorHandler_SizeScreen(object sender, SizeScreenEventArgs e) { - //TODO ʵ ĻС + //TODO 待实现 屏幕大小 //this.CheckInvokeMethod(delegate () //{ @@ -710,7 +710,7 @@ public class UEssgee : MonoBehaviour, IEmuCore private void EmulatorHandler_ChangeViewport(object sender, ChangeViewportEventArgs e) { - //TODO ʵ + //TODO 待实现 //this.CheckInvokeMethod(delegate () //{ @@ -721,7 +721,7 @@ public class UEssgee : MonoBehaviour, IEmuCore private void EmulatorHandler_PollInput(object sender, PollInputEventArgs e) { - //TODO Inputʵ + //TODO Input实现 //e.Keyboard = mUniKeyboard.mKeyCodeCore.GetPressedKeys(); e.Keyboard.AddRange(mUniKeyboard.GetPressedKeys()); @@ -775,7 +775,7 @@ public class UEssgee : MonoBehaviour, IEmuCore /* Images, ex. GB Printer printouts */ //image.Save(filePath); - //TODO ͼ洢 + //TODO 图像存储 } else if (e.Data is byte[] raw) { @@ -801,7 +801,7 @@ public class UEssgee : MonoBehaviour, IEmuCore if (emulatorHandler.IsPaused) { - //TODO Ƶͣ + //TODO 音频暂停? //soundHandler?.ClearSampleBuffer(); } } @@ -825,7 +825,7 @@ public class UEssgee : MonoBehaviour, IEmuCore // waveHeader.FileLength += (uint)e.MixedSamples.Length; //} - //TODO Ƶ + //TODO 音频处理 //soundHandler.SubmitSamples(e.MixedSamples, e.ChannelSamples, e.MixedSamples.Length); soundHandler.SubmitSamples(e.MixedSamples, e.ChannelSamples, e.MixedSamplesLength); } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs index eaef5d52..764a1a18 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs @@ -9,7 +9,7 @@ using System.Text; using UnityEngine; using UnityEngine.UI; -public class UMAME : MonoBehaviour, IEmuCore +public class UMAME : IEmuCore { public static UMAME instance { get; private set; } public MAMEEmu emu { get; private set; } @@ -38,9 +38,9 @@ public class UMAME : MonoBehaviour, IEmuCore public string EmuDataPath { get { return App.PersistentDataPath(Platform); } } public string RomPath => EmuDataPath + "/RemoteRoms/"; public string SavePath => EmuDataPath + "/sav/"; - public RomPlatformType Platform { get { return mPlatform; } } + public override RomPlatformType Platform { get { return mPlatform; } } RomPlatformType mPlatform = RomPlatformType.Cps1; - public uint Frame => (uint)emu.currEmuFrame; + public override uint Frame => (uint)emu.currEmuFrame; void Awake() { instance = this; @@ -67,31 +67,31 @@ public class UMAME : MonoBehaviour, IEmuCore StopGame(); } #region 实现接口 - public object GetState() + public override object GetState() { return SaveState(); } - public byte[] GetStateBytes() + public override byte[] GetStateBytes() { return SaveState(); } - public void LoadState(object state) + public override void LoadState(object state) { LoadState((byte[])state); } - public void LoadStateFromBytes(byte[] data) + public override void LoadStateFromBytes(byte[] data) { LoadState(data); } - public void Pause() + public override void Pause() { bLogicUpdatePause = false; } - public void Resume() + public override void Resume() { bLogicUpdatePause = true; } - public MsgBool StartGame(RomFile romFile) + public override MsgBool StartGame(RomFile romFile) { mPlatform = romFile.Platform; mTimeSpan.InitStandTime(); @@ -100,22 +100,22 @@ public class UMAME : MonoBehaviour, IEmuCore else return "Rom加载失败"; } - public void Dispose() + public override void Dispose() { StopGame(); } - public void DoReset() + public override void DoReset() { StopGame(); LoadGame(mChangeRomName, false); } - public IControllerSetuper GetControllerSetuper() + public override IControllerSetuper GetControllerSetuper() { return mUniKeyboard.ControllerMapper; } - public void GetAudioParams(out int frequency, out int channels) + public override void GetAudioParams(out int frequency, out int channels) { mUniSoundPlayer.GetAudioParams(out frequency, out channels); } @@ -160,7 +160,7 @@ public class UMAME : MonoBehaviour, IEmuCore } } - public bool PushEmulatorFrame() + public override bool PushEmulatorFrame() { if (!bInGame) return false; if (!bLogicUpdatePause) return false; @@ -175,7 +175,7 @@ public class UMAME : MonoBehaviour, IEmuCore emu.UpdateFrame(); return true; } - public void AfterPushFrame() + public override void AfterPushFrame() { mFPS.text = ($"fpsv {mUniVideoPlayer.videoFPS.ToString("F2")} fpsa {mUniSoundPlayer.audioFPS.ToString("F2")} ,Idx:{App.roomMgr.netReplay?.mCurrClientFrameIdx},RIdx:{App.roomMgr.netReplay?.mRemoteFrameIdx},RForward:{App.roomMgr.netReplay?.mRemoteForwardCount} ,RD:{App.roomMgr.netReplay?.mRemoteForwardCount} ,D:{App.roomMgr.netReplay?.mDiffFrameCount} ,Q:{App.roomMgr.netReplay?.mNetReplayQueue.Count}"); } @@ -227,9 +227,9 @@ public class UMAME : MonoBehaviour, IEmuCore } - public Texture OutputPixel => mUniVideoPlayer.rawBufferWarper; + public override Texture OutputPixel => mUniVideoPlayer.rawBufferWarper; - public RawImage DrawCanvas => mUniVideoPlayer.DrawCanvas; + public override RawImage DrawCanvas => mUniVideoPlayer.DrawCanvas; } \ No newline at end of file diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs index 5421409f..2f318b37 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs @@ -11,7 +11,7 @@ using VirtualNes.Core.Debug; namespace AxibugEmuOnline.Client { - public class NesEmulator : MonoBehaviour, IEmuCore + public class NesEmulator : IEmuCore { public VideoProvider VideoProvider; public AudioProvider AudioProvider; @@ -35,12 +35,12 @@ namespace AxibugEmuOnline.Client AudioProvider.NesEmu = this; } - public RomPlatformType Platform => RomPlatformType.Nes; + public override RomPlatformType Platform => RomPlatformType.Nes; private CoreSupporter m_coreSupporter; /// /// 指定ROM开始游戏 /// - public MsgBool StartGame(RomFile rom) + public override MsgBool StartGame(RomFile rom) { StopGame(); @@ -63,28 +63,28 @@ namespace AxibugEmuOnline.Client } } - public void Pause() + public override void Pause() { IsPause = true; } - public void Resume() + public override void Resume() { IsPause = false; } - public void DoReset() + public override void DoReset() { NesCore.Reset(); } - public void LoadState(object state) + public override void LoadState(object state) { NesCore.LoadState((State)state); } - public object GetState() + public override object GetState() { return NesCore.GetState(); } @@ -93,7 +93,7 @@ namespace AxibugEmuOnline.Client /// 获取即时存档 /// /// - public byte[] GetStateBytes() + public override byte[] GetStateBytes() { return NesCore.GetState().ToBytes(); } @@ -104,14 +104,14 @@ namespace AxibugEmuOnline.Client /// /// - public void LoadStateFromBytes(byte[] data) + public override void LoadStateFromBytes(byte[] data) { var st = new State(); st.FromByte(data); NesCore.LoadState(st); } - public uint Frame => NesCore.FrameCount; + public override uint Frame => NesCore.FrameCount; /// /// 停止游戏 @@ -127,7 +127,7 @@ namespace AxibugEmuOnline.Client private ControllerState m_lastState; #endif //推进帧 - public bool PushEmulatorFrame() + public override bool PushEmulatorFrame() { if (NesCore == null || IsPause) return false; @@ -145,23 +145,22 @@ namespace AxibugEmuOnline.Client NesCore.pad.Sync(controlState); NesCore.EmulateFrame(true); - return true; } - public unsafe void AfterPushFrame() + public override unsafe void AfterPushFrame() { var screenBuffer = NesCore.ppu.GetScreenPtr(); VideoProvider.SetDrawData(screenBuffer); } - public IControllerSetuper GetControllerSetuper() + public override IControllerSetuper GetControllerSetuper() { return ControllerMapper; } - public void Dispose() + public override void Dispose() { StopGame(); } @@ -197,9 +196,9 @@ namespace AxibugEmuOnline.Client } #endif - public Texture OutputPixel => VideoProvider.OutputPixel; - public RawImage DrawCanvas => VideoProvider.Drawer; - public void GetAudioParams(out int frequency, out int channels) + public override Texture OutputPixel => VideoProvider.OutputPixel; + public override RawImage DrawCanvas => VideoProvider.Drawer; + public override void GetAudioParams(out int frequency, out int channels) { AudioProvider.GetAudioParams(out frequency, out channels); } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs index 37758fd7..469b7ed0 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs @@ -11,7 +11,7 @@ using UnityEngine; using UnityEngine.UI; using CartridgeMetadata = StoicGoose.Core.Cartridges.Metadata; -public class UStoicGoose : MonoBehaviour, IEmuCore +public class UStoicGoose : IEmuCore { public static UStoicGoose instance; public static System.Diagnostics.Stopwatch sw = System.Diagnostics.Stopwatch.StartNew(); @@ -49,44 +49,44 @@ public class UStoicGoose : MonoBehaviour, IEmuCore public string CurrRomName { get; private set; } #region 实现IEmuCore - public RomPlatformType Platform => mPlatform; + public override RomPlatformType Platform => mPlatform; - public uint Frame => (uint)emulatorHandler.AxiEmuRunFrame; + public override uint Frame => (uint)emulatorHandler.AxiEmuRunFrame; - public Texture OutputPixel => graphicsHandler.rawBufferWarper; + public override Texture OutputPixel => graphicsHandler.rawBufferWarper; - public RawImage DrawCanvas => graphicsHandler.DrawCanvas; - public object GetState() + public override RawImage DrawCanvas => graphicsHandler.DrawCanvas; + public override object GetState() { throw new NotImplementedException(); } - public byte[] GetStateBytes() + public override byte[] GetStateBytes() { throw new NotImplementedException(); } - public void LoadState(object state) + public override void LoadState(object state) { throw new NotImplementedException(); } - public void LoadStateFromBytes(byte[] data) + public override void LoadStateFromBytes(byte[] data) { throw new NotImplementedException(); } - public void Pause() + public override void Pause() { PauseEmulation(); } - public void Resume() + public override void Resume() { UnpauseEmulation(); } - public MsgBool StartGame(RomFile romFile) + public override MsgBool StartGame(RomFile romFile) { mPlatform = romFile.Platform; @@ -105,7 +105,7 @@ public class UStoicGoose : MonoBehaviour, IEmuCore return "Rom加载失败"; } - public void Dispose() + public override void Dispose() { //保存当前正在进行的游戏存档 if (emulatorHandler != null && !emulatorHandler.IsRunning) @@ -115,27 +115,27 @@ public class UStoicGoose : MonoBehaviour, IEmuCore EmuClose(); } - public void DoReset() + public override void DoReset() { ResetEmulation(); } - public IControllerSetuper GetControllerSetuper() + public override IControllerSetuper GetControllerSetuper() { throw new NotImplementedException(); } - public bool PushEmulatorFrame() + public override bool PushEmulatorFrame() { throw new NotImplementedException(); } - public void AfterPushFrame() + public override void AfterPushFrame() { throw new NotImplementedException(); } - public void GetAudioParams(out int frequency, out int channels) + public override void GetAudioParams(out int frequency, out int channels) { throw new NotImplementedException(); } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs index b2e721b2..37d36f94 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs @@ -4,52 +4,41 @@ using UnityEngine.UI; namespace AxibugEmuOnline.Client { - public interface IEmuCore + public abstract class IEmuCore : MonoBehaviour { - GameObject gameObject { get; } - /// 获得模拟器核心中的状态快照对象 - object GetState(); + public abstract object GetState(); /// 获得模拟器核心中的状态快照字节数据 - byte[] GetStateBytes(); + public abstract byte[] GetStateBytes(); /// 加载状态快照 /// 该对象应该来自核心的方法的返回值,或是从返回的byte数组构建 - void LoadState(object state); + public abstract void LoadState(object state); /// 加载状态快照 /// 该对象应该来自核心的返回的byte数组 - void LoadStateFromBytes(byte[] data); + public abstract void LoadStateFromBytes(byte[] data); /// 暂停核心推帧 - void Pause(); + public abstract void Pause(); /// 恢复核心推帧(从Pause状态恢复) - void Resume(); + public abstract void Resume(); /// 启动模拟器逻辑 - MsgBool StartGame(RomFile romFile); + public abstract MsgBool StartGame(RomFile romFile); /// 释放模拟器核心 - void Dispose(); + public abstract void Dispose(); /// 重置核心,通常由模拟器核心提供的功能 - void DoReset(); + public abstract void DoReset(); /// 获得模拟器核心的控制器设置器 /// - IControllerSetuper GetControllerSetuper(); + public abstract IControllerSetuper GetControllerSetuper(); /// 核心所属平台 - RomPlatformType Platform { get; } + public abstract RomPlatformType Platform { get; } /// 获取当前模拟器帧序号,在加载快照和Reset后,应当重置为0 - uint Frame { get; } + public abstract uint Frame { get; } /// 模拟器核心推帧 - bool PushEmulatorFrame(); + public abstract bool PushEmulatorFrame(); /// 模拟器核心推帧结束 - void AfterPushFrame(); - public void GetAudioParams(out int frequency, out int channels); - Texture OutputPixel { get; } - RawImage DrawCanvas { get; } - } - - public static class IEnumCoreTool - { - public static bool IsNull(this IEmuCore core) - { - if (core == null) return true; - return core.Equals(null); - } + public abstract void AfterPushFrame(); + public abstract void GetAudioParams(out int frequency, out int channels); + public abstract Texture OutputPixel { get; } + public abstract RawImage DrawCanvas { get; } } } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppEmu.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppEmu.cs index a46290aa..d53608f6 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppEmu.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppEmu.cs @@ -29,7 +29,7 @@ namespace AxibugEmuOnline.Client.Manager private void OnSelfJoinRoom() { //如果当前正在游戏中,就先结束游戏 - if (!m_emuCore.IsNull()) StopGame(); + if (m_emuCore != null) StopGame(); var roomInfo = App.roomMgr.mineRoomMiniInfo; roomInfo.FetchRomFileInRoomInfo((_, romFile) => @@ -48,7 +48,7 @@ namespace AxibugEmuOnline.Client.Manager public void BeginGame(RomFile romFile) { - if (!m_emuCore.IsNull()) return; + if (m_emuCore != null) return; switch (romFile.Platform) { @@ -120,7 +120,7 @@ namespace AxibugEmuOnline.Client.Manager public void StopGame() { - if (m_emuCore.IsNull()) return; + if (m_emuCore == null) return; m_emuCore.Dispose(); GameObject.Destroy(m_emuCore.gameObject); m_emuCore = null; @@ -133,7 +133,7 @@ namespace AxibugEmuOnline.Client.Manager public void ResetGame() { - if (m_emuCore.IsNull()) return; + if (m_emuCore == null) return; m_emuCore.DoReset(); } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI.cs index dcf73f6e..6a8b0dea 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI.cs @@ -65,7 +65,7 @@ namespace AxibugEmuOnline.Client void PushCoreFrame() { - if (Core.IsNull()) return; + if (Core == null) return; //fluash netMsg NetMsg.Instance.DequeueNesMsg(); diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI_Scaler.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI_Scaler.cs index 4c9fad7e..c53eed55 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI_Scaler.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/InGameUI/InGameUI_Scaler.cs @@ -32,7 +32,7 @@ namespace AxibugEmuOnline.Client { get { - if (m_gameUI.Core.IsNull()) return false; + if (m_gameUI.Core == null) return false; var isSetMode = App.settings.ScreenScaler.IsSetMode(m_gameUI.Core.Platform); diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/LaunchUI.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/LaunchUI.cs index 4b1e0964..a375a2ed 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/LaunchUI.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/LaunchUI.cs @@ -49,7 +49,7 @@ namespace AxibugEmuOnline.Client private void Update() { - if (CommandDispatcher.Instance.Mode == CommandListener.ScheduleType.Gaming && App.emu.Core.IsNull()) + if (CommandDispatcher.Instance.Mode == CommandListener.ScheduleType.Gaming && App.emu.Core == null) CommandDispatcher.Instance.Mode = CommandListener.ScheduleType.Normal; } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfo.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfo.cs index c7146aed..35ea2a58 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfo.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfo.cs @@ -90,7 +90,7 @@ public class ControllerInfo : MonoBehaviour } else { - if (App.emu.Core.IsNull()) + if (App.emu.Core == null) { SetDisconnect(); return; diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfoPanel.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfoPanel.cs index 02d800d1..6ea98099 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfoPanel.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/ControllerInfoPanel.cs @@ -35,7 +35,7 @@ public class ControllerInfoPanel : MonoBehaviour } else //不在房间中,直接设置 { - if (App.emu.Core.IsNull()) return; + if (App.emu.Core == null) return; var setuper = App.emu.Core.GetControllerSetuper(); if (setuper == null) return; diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/XMBInfoBar.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/XMBInfoBar.cs index f3c21da0..5cbf80f4 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/XMBInfoBar.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/UI/XMBTopGroupUI/XMBInfoBar.cs @@ -24,7 +24,7 @@ public class XMBInfoBar : MonoBehaviour private void Update() { - ControlSlotInfoNode.SetActiveEx(!App.emu.Core.IsNull()); + ControlSlotInfoNode.SetActiveEx(App.emu.Core != null); } void OnDisable() @@ -46,7 +46,7 @@ public class XMBInfoBar : MonoBehaviour ValueTuple m_lastFrameInfo; private void RefreshFps() { - if (App.emu.Core.IsNull()) + if (App.emu.Core == null) FPS.gameObject.SetActiveEx(false); else { From c7a4f1467a07e8e7d6f107986883655d8c2b68ae Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Tue, 29 Apr 2025 19:17:40 +0800 Subject: [PATCH 07/10] =?UTF-8?q?RLPRO=5FCRT=E6=BB=A4=E9=95=9C=E5=AE=8C?= =?UTF-8?q?=E5=96=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../AppSettings/Filter/RLPro/RLPRO_CRT.cs | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs index 75c07baa..393879d0 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Manager/AppSettings/Filter/RLPro/RLPRO_CRT.cs @@ -32,15 +32,21 @@ namespace AxibugEmuOnline.Client.Filters #endregion #region TV_Effect_Param public FilterParameter WrapMode = EnumWrapMode.SimpleWrap; + [Range(0f, 2f)] public FloatParameter maskDark = 0.5f; + [Range(0f, 2f)] public FloatParameter maskLight = 1.5f; + [Range(-8f, -16f)] public FloatParameter hardScan = -8.0f; + [Range(-3f, 1f)] public FloatParameter hardPix = -3.0f; - public Vector2Parameter warp = new Vector2(1.0f / 32.0f, 1.0f / 24.0f); - public Vector2Parameter res; - public FloatParameter resScale; - public FloatParameter scale; - public FloatParameter fade; + public Vector2Parameter warp = new Vector2(0.03125f, 0.04166f); + [Range(1f, 16f)] + public FloatParameter resScale = 4f; + [Range(0.5f, 5f)] + public FloatParameter scale = 1f; + [Range(0f, 1f)] + public FloatParameter fade = 1f; #endregion Material m_bleedMat; @@ -128,8 +134,8 @@ namespace AxibugEmuOnline.Client.Filters m_tvEffectMat.SetFloat("maskDark", maskDark.GetValue()); m_tvEffectMat.SetFloat("maskLight", maskLight.GetValue()); m_tvEffectMat.SetFloat("hardScan", hardScan.GetValue()); + m_tvEffectMat.SetFloat("hardPix", hardPix.GetValue()); m_tvEffectMat.SetVector("warp", warp.GetValue()); - m_tvEffectMat.SetVector("res", res.GetValue()); m_tvEffectMat.SetFloat("resScale", resScale.GetValue()); m_tvEffectMat.SetFloat("scale", scale.GetValue()); m_tvEffectMat.SetFloat("fade", fade.GetValue()); From 1ffa708e7121e605e3e6f44327997e8cef4f391f Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Tue, 29 Apr 2025 19:18:02 +0800 Subject: [PATCH 08/10] =?UTF-8?q?NesEmulator=E9=87=8D=E6=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Emulator/NesEmulator/NesEmulator.cs | 51 ++++++------ .../Assets/Script/AppMain/IEmuCore.cs | 80 ++++++++++++++++++- 2 files changed, 103 insertions(+), 28 deletions(-) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs index 2f318b37..0f706a8a 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs @@ -1,5 +1,6 @@ using AxibugEmuOnline.Client.ClientCore; using AxibugProtobuf; +using AxiReplay; using System; using System.Diagnostics; using System.Globalization; @@ -11,7 +12,7 @@ using VirtualNes.Core.Debug; namespace AxibugEmuOnline.Client { - public class NesEmulator : IEmuCore + public class NesEmulator : EmuCore { public VideoProvider VideoProvider; public AudioProvider AudioProvider; @@ -122,32 +123,31 @@ namespace AxibugEmuOnline.Client NesCore = null; } - -#if UNITY_EDITOR - private ControllerState m_lastState; -#endif //推进帧 - public override bool PushEmulatorFrame() + protected override bool OnPushEmulatorFrame(ControllerState inputData) { if (NesCore == null || IsPause) return false; - m_coreSupporter.SampleInput(NesCore.FrameCount); - var controlState = m_coreSupporter.GetControllerState(); - - //如果未收到Input数据,核心帧不推进 - if (!controlState.valid) return false; - -#if UNITY_EDITOR - if (controlState != m_lastState) App.log.Info($"[LOCALDEBUG]{NesCore.FrameCount}-->{controlState}"); - m_lastState = controlState; -#endif - - NesCore.pad.Sync(controlState); + NesCore.pad.Sync(inputData); NesCore.EmulateFrame(true); return true; } + protected override ControllerState ConvertInputDataFromNet(ReplayStep step) + { + return m_coreSupporter.FromNet(step); + } + protected override ulong InputDataToNet(ControllerState inputData) + { + return m_coreSupporter.ToNet(inputData); + } + + protected override ControllerState GetLocalInput() + { + return m_coreSupporter.GetControllerState(); + } + public override unsafe void AfterPushFrame() { @@ -164,6 +164,13 @@ namespace AxibugEmuOnline.Client { StopGame(); } + + public override Texture OutputPixel => VideoProvider.OutputPixel; + public override RawImage DrawCanvas => VideoProvider.Drawer; + public override void GetAudioParams(out int frequency, out int channels) + { + AudioProvider.GetAudioParams(out frequency, out channels); + } #if UNITY_EDITOR /// @@ -195,13 +202,5 @@ namespace AxibugEmuOnline.Client UnityEditor.AssetDatabase.SaveAssets(); } #endif - - public override Texture OutputPixel => VideoProvider.OutputPixel; - public override RawImage DrawCanvas => VideoProvider.Drawer; - public override void GetAudioParams(out int frequency, out int channels) - { - AudioProvider.GetAudioParams(out frequency, out channels); - } - } } \ No newline at end of file diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs index 37d36f94..aebf176c 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs @@ -1,9 +1,18 @@ -using AxibugProtobuf; +#pragma warning disable CS0618 // 类型或成员已过时 + +using AxibugEmuOnline.Client.ClientCore; +using AxibugProtobuf; +using AxiReplay; +using System; using UnityEngine; using UnityEngine.UI; namespace AxibugEmuOnline.Client { + /// + /// use instead + /// + [Obsolete("不可直接继承,需要继承EmuCore类型")] public abstract class IEmuCore : MonoBehaviour { /// 获得模拟器核心中的状态快照对象 @@ -33,12 +42,79 @@ namespace AxibugEmuOnline.Client public abstract RomPlatformType Platform { get; } /// 获取当前模拟器帧序号,在加载快照和Reset后,应当重置为0 public abstract uint Frame { get; } - /// 模拟器核心推帧 + public abstract bool PushEmulatorFrame(); /// 模拟器核心推帧结束 public abstract void AfterPushFrame(); public abstract void GetAudioParams(out int frequency, out int channels); public abstract Texture OutputPixel { get; } public abstract RawImage DrawCanvas { get; } + } + + public abstract class EmuCore : IEmuCore + { + public sealed override bool PushEmulatorFrame() + { + if (SampleInputData(out var inputData)) + { + return OnPushEmulatorFrame(inputData); + } + + return false; + } + + ulong m_lastTestInput; + protected bool SampleInputData(out INPUTDATA inputData) + { + bool result = false; + inputData = default(INPUTDATA); + + if (InGameUI.Instance.IsNetPlay) + { + ReplayStep replayData; + int frameDiff; + bool inputDiff; + + if (App.roomMgr.netReplay.TryGetNextFrame((int)Frame, out replayData, out frameDiff, out inputDiff)) + { + if (inputDiff) + { + App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} TryGetNextFrame remoteFrame->{App.roomMgr.netReplay.mRemoteFrameIdx} diff->{frameDiff} " + + $"frame=>{replayData.FrameStartID} InPut=>{replayData.InPut}"); + } + + inputData = ConvertInputDataFromNet(replayData); + result = true; + } + else + { + result = false; + } + + var localState = GetLocalInput(); + var rawData = InputDataToNet(localState); + if (m_lastTestInput != rawData) + { + m_lastTestInput = rawData; + App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} Input F:{App.roomMgr.netReplay.mCurrClientFrameIdx} | I:{rawData}"); + } + App.roomMgr.SendRoomSingelPlayerInput(Frame, rawData); + } + //单机模式 + else + { + inputData = GetLocalInput(); + result = true; + } + + return result; + } + + protected abstract INPUTDATA GetLocalInput(); + protected abstract INPUTDATA ConvertInputDataFromNet(ReplayStep step); + protected abstract ulong InputDataToNet(INPUTDATA inputData); + /// 模拟器核心推帧 + protected abstract bool OnPushEmulatorFrame(INPUTDATA InputData); } } +#pragma warning restore CS0618 // 类型或成员已过时 From ace77987e46615cc2c278e7e7d300ef75bac9014 Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Tue, 29 Apr 2025 19:43:02 +0800 Subject: [PATCH 09/10] =?UTF-8?q?fix=20NesEmulator=E9=87=8D=E6=9E=84?= =?UTF-8?q?=E5=90=8E=E5=A4=84=E7=90=86=E8=BE=93=E5=85=A5=E6=95=B0=E6=8D=AE?= =?UTF-8?q?bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Assets/Resources/IMPORTENT.prefab | 8 +++ .../Emulator/NesEmulator/CoreSupporter.cs | 53 ++----------------- .../Emulator/NesEmulator/NesEmulator.cs | 4 +- .../Assets/Script/AppMain/IEmuCore.cs | 5 +- .../VirtualNes.Core/Supporter/Supporter.cs | 2 - 5 files changed, 15 insertions(+), 57 deletions(-) diff --git a/AxibugEmuOnline.Client/Assets/Resources/IMPORTENT.prefab b/AxibugEmuOnline.Client/Assets/Resources/IMPORTENT.prefab index 8e7c8dc7..8be16655 100644 --- a/AxibugEmuOnline.Client/Assets/Resources/IMPORTENT.prefab +++ b/AxibugEmuOnline.Client/Assets/Resources/IMPORTENT.prefab @@ -1215,6 +1215,14 @@ PrefabInstance: propertyPath: m_AnchoredPosition.y value: 0 objectReference: {fileID: 0} + - target: {fileID: 6671307062690349520, guid: 1de15a80c8c1aa94486563740a15d91c, type: 3} + propertyPath: m_LocalRotation.w + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 6671307062690349520, guid: 1de15a80c8c1aa94486563740a15d91c, type: 3} + propertyPath: m_LocalRotation.z + value: 0 + objectReference: {fileID: 0} - target: {fileID: 6838719776118089301, guid: 1de15a80c8c1aa94486563740a15d91c, type: 3} propertyPath: m_IsActive value: 1 diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/CoreSupporter.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/CoreSupporter.cs index 4d46cac3..eec32d97 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/CoreSupporter.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/CoreSupporter.cs @@ -10,11 +10,6 @@ namespace AxibugEmuOnline.Client { public class CoreSupporter : ISupporterImpl { - private NesControllerMapper m_controllerMapper; - public CoreSupporter(NesControllerMapper conMapper) - { - m_controllerMapper = conMapper; - } public System.IO.Stream OpenRom(string fname) { @@ -95,51 +90,9 @@ namespace AxibugEmuOnline.Client { var db = Resources.Load("NES/ROMDB"); return db.GetMapperNo(rom.GetPROM_CRC(), out mapperNo); - } - - private ControllerState m_sampledState; - public ControllerState GetControllerState() - { - return m_sampledState; - } - - uint LastTestInput = 0; - public void SampleInput(uint frameIndex) - { - if (InGameUI.Instance.IsNetPlay) - { - int targetFrame; ReplayStep replayData; int frameDiff; bool inputDiff; - if (App.roomMgr.netReplay.TryGetNextFrame((int)frameIndex, out replayData, out frameDiff, out inputDiff)) - { - if (inputDiff) - { - App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} TryGetNextFrame remoteFrame->{App.roomMgr.netReplay.mRemoteFrameIdx} diff->{frameDiff} " + - $"frame=>{replayData.FrameStartID} InPut=>{replayData.InPut}"); - } - - m_sampledState = FromNet(replayData); - } - else - { - m_sampledState = default(ControllerState); - } - - var localState = m_controllerMapper.CreateState(); - var rawData = ToNet(localState); - if (LastTestInput != rawData) - { - LastTestInput = rawData; - App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} Input F:{App.roomMgr.netReplay.mCurrClientFrameIdx} | I:{rawData}"); - } - App.roomMgr.SendRoomSingelPlayerInput(frameIndex, rawData); - } - //单机模式 - else - { - m_sampledState = m_controllerMapper.CreateState(); - } - } - + } + + public ControllerState FromNet(AxiReplay.ReplayStep step) { var temp = new ServerInputSnapShot(); diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs index 0f706a8a..69cf14d7 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/NesEmulator/NesEmulator.cs @@ -45,7 +45,7 @@ namespace AxibugEmuOnline.Client { StopGame(); - m_coreSupporter = new CoreSupporter(ControllerMapper); + m_coreSupporter = new CoreSupporter(); Supporter.Setup(m_coreSupporter); Debuger.Setup(new CoreDebuger()); @@ -145,7 +145,7 @@ namespace AxibugEmuOnline.Client protected override ControllerState GetLocalInput() { - return m_coreSupporter.GetControllerState(); + return ControllerMapper.CreateState(); } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs index aebf176c..1be8dfe4 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/IEmuCore.cs @@ -99,9 +99,8 @@ namespace AxibugEmuOnline.Client App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} Input F:{App.roomMgr.netReplay.mCurrClientFrameIdx} | I:{rawData}"); } App.roomMgr.SendRoomSingelPlayerInput(Frame, rawData); - } - //单机模式 - else + } + else//单机模式 { inputData = GetLocalInput(); result = true; diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Supporter/Supporter.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Supporter/Supporter.cs index 43438ef6..20b88689 100644 --- a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Supporter/Supporter.cs +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Supporter/Supporter.cs @@ -23,7 +23,5 @@ void SaveFile(byte[] fileData, string directPath, string fileName); System.IO.Stream OpenFile(string directPath, string fileName); bool TryGetMapperNo(ROM rom, out int mapperNo); - ControllerState GetControllerState(); - void SampleInput(uint frameCount); } } \ No newline at end of file From cc57a1e0df757df8e274b4aa63d74123f2a491f9 Mon Sep 17 00:00:00 2001 From: "ALIENJACK\\alien" Date: Wed, 30 Apr 2025 15:41:20 +0800 Subject: [PATCH 10/10] =?UTF-8?q?emucore=E5=9F=BA=E7=B1=BB=E6=9B=BF?= =?UTF-8?q?=E6=8D=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Emulator/EssgeeEmulator/UEssgee.cs | 41 +++++++----- .../UEssgeeInterface/UEGKeyboard.cs | 42 +----------- .../AppMain/Emulator/MameEmulator/UMAME.cs | 46 +++++++------ .../MameEmulator/UniInterface/UniKeyboard.cs | 65 ++++--------------- .../StoicGooseEmulator/UStoicGoose.cs | 27 ++++++-- 5 files changed, 85 insertions(+), 136 deletions(-) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs index 17ed2dca..69ef9530 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgee.cs @@ -1,6 +1,7 @@ using AxibugEmuOnline.Client; using AxibugEmuOnline.Client.ClientCore; using AxibugProtobuf; +using AxiReplay; using Essgee; using Essgee.Emulation; using Essgee.Emulation.Configuration; @@ -11,13 +12,12 @@ using Essgee.Metadata; using Essgee.Utilities; using System; using System.Collections.Generic; -using System.Drawing; using System.Linq; using System.Text; using UnityEngine; using UnityEngine.UI; -public class UEssgee : IEmuCore +public class UEssgee : EmuCore { public static UEssgee instance; public static System.Diagnostics.Stopwatch sw = System.Diagnostics.Stopwatch.StartNew(); @@ -125,7 +125,7 @@ public class UEssgee : IEmuCore public override void Dispose() { if (!emulatorHandler.IsRunning) - { + { emulatorHandler.SaveCartridge(); } ShutdownEmulation(); @@ -141,21 +141,32 @@ public class UEssgee : IEmuCore { return mUniKeyboard.ControllerMapper; } - - public override bool PushEmulatorFrame() - { + protected override bool OnPushEmulatorFrame(ulong InputData) + { if (!emulatorHandler.IsRunning) return false; - if (!bLogicUpdatePause) return false; - - //采集本帧Input - bool bhadNext = mUniKeyboard.SampleInput(); - //如果未收到Input数据,核心帧不推进 - if (!bhadNext) return false; - - emulatorHandler.Update_Frame(); - return true; + if (!bLogicUpdatePause) return false; + + mUniKeyboard.SetCurrKeyArr(InputData); + emulatorHandler.Update_Frame(); + + return true; } + protected override ulong ConvertInputDataFromNet(ReplayStep step) + { + return step.InPut; + } + + protected override ulong InputDataToNet(ulong inputData) + { + return inputData; + } + + protected override ulong GetLocalInput() + { + return mUniKeyboard.DoLocalPressedKeys(); + } + public override void AfterPushFrame() { } diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgeeInterface/UEGKeyboard.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgeeInterface/UEGKeyboard.cs index 5b730853..409fee6e 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgeeInterface/UEGKeyboard.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/EssgeeEmulator/UEssgeeInterface/UEGKeyboard.cs @@ -315,45 +315,7 @@ public class UEGKeyboard : MonoBehaviour //mUniKeyboard.btnABC.Key = new long[] { (long)MotionKey.P1_BTN_1, (long)MotionKey.P1_BTN_2, (long)MotionKey.P1_BTN_3 }; } - public bool SampleInput() - { - //Net模式 - if (InGameUI.Instance.IsNetPlay) - { - bool bHadNetData = false; - int targetFrame; ReplayStep replayData; int frameDiff; bool inputDiff; - if (App.roomMgr.netReplay.TryGetNextFrame((int)UEssgee.instance.Frame, out replayData, out frameDiff, out inputDiff)) - { - if (inputDiff) - { - App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} TryGetNextFrame remoteFrame->{App.roomMgr.netReplay.mRemoteFrameIdx} diff->{frameDiff} " + - $"frame=>{replayData.FrameStartID} InPut=>{replayData.InPut}"); - } - CurrRemoteInpuAllData = replayData.InPut; - SetCurrKeyArr(CurrRemoteInpuAllData); - bHadNetData = true; - } - else//无输入 - { - CurrRemoteInpuAllData = 0; - } - - //发送本地操作 - App.roomMgr.SendRoomSingelPlayerInput(UEssgee.instance.Frame, - DoLocalPressedKeys()); - - return bHadNetData; - } - //单机模式 - else - { - ulong inputData = DoLocalPressedKeys(); - SetCurrKeyArr(inputData); - return true; - } - } - - void SetCurrKeyArr(ulong inputData) + public void SetCurrKeyArr(ulong inputData) { temp.Clear(); for (int i = 0; i < CheckList.Length; i++) @@ -368,7 +330,7 @@ public class UEGKeyboard : MonoBehaviour mCurrKey = temp.ToArray(); } - ulong DoLocalPressedKeys() + public ulong DoLocalPressedKeys() { //tempInputAllData = 0; //for (int i = 0; i < CheckList.Length; i++) diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs index 764a1a18..253836be 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UMAME.cs @@ -9,7 +9,7 @@ using System.Text; using UnityEngine; using UnityEngine.UI; -public class UMAME : IEmuCore +public class UMAME : EmuCore { public static UMAME instance { get; private set; } public MAMEEmu emu { get; private set; } @@ -95,7 +95,7 @@ public class UMAME : IEmuCore { mPlatform = romFile.Platform; mTimeSpan.InitStandTime(); - if (LoadGame(romFile.FileName, false)) + if (LoadGame(romFile.FileName)) return true; else return "Rom加载失败"; @@ -107,7 +107,7 @@ public class UMAME : IEmuCore public override void DoReset() { StopGame(); - LoadGame(mChangeRomName, false); + LoadGame(mChangeRomName); } public override IControllerSetuper GetControllerSetuper() { @@ -121,7 +121,7 @@ public class UMAME : IEmuCore } #endregion - bool LoadGame(string loadRom, bool bReplay = false) + bool LoadGame(string loadRom) { emu.ResetRomRoot(RomPath); //Application.targetFrameRate = 60; @@ -133,12 +133,6 @@ public class UMAME : IEmuCore //读取成功 if (emu.bRom) { - if (bReplay) - { - string Path = SavePath + Machine.sName + ".rp"; - mReplayReader = new ReplayReader(Path); - mUniKeyboard.SetRePlay(true); - } //读取ROM之后获得宽高初始化画面 int _width; int _height; IntPtr _framePtr; @@ -159,22 +153,32 @@ public class UMAME : IEmuCore return false; } } - - public override bool PushEmulatorFrame() + protected override bool OnPushEmulatorFrame(ulong InputData) { if (!bInGame) return false; if (!bLogicUpdatePause) return false; - //采集本帧Input - bool bhadNext = mUniKeyboard.SampleInput(); - //如果未收到Input数据,核心帧不推进 - if (!bhadNext) return false; - //放行下一帧 - //emu.UnlockNextFreme(); - //推帧 - emu.UpdateFrame(); - return true; + mUniKeyboard.SyncInput(InputData); + emu.UpdateFrame(); + + return true; } + + protected override ulong ConvertInputDataFromNet(ReplayStep step) + { + return step.InPut; + } + + protected override ulong InputDataToNet(ulong inputData) + { + return inputData; + } + + protected override ulong GetLocalInput() + { + return mUniKeyboard.DoLocalPressedKeys(); + } + public override void AfterPushFrame() { mFPS.text = ($"fpsv {mUniVideoPlayer.videoFPS.ToString("F2")} fpsa {mUniSoundPlayer.audioFPS.ToString("F2")} ,Idx:{App.roomMgr.netReplay?.mCurrClientFrameIdx},RIdx:{App.roomMgr.netReplay?.mRemoteFrameIdx},RForward:{App.roomMgr.netReplay?.mRemoteForwardCount} ,RD:{App.roomMgr.netReplay?.mRemoteForwardCount} ,D:{App.roomMgr.netReplay?.mDiffFrameCount} ,Q:{App.roomMgr.netReplay?.mNetReplayQueue.Count}"); diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UniInterface/UniKeyboard.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UniInterface/UniKeyboard.cs index 20521e68..92b63622 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UniInterface/UniKeyboard.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/MameEmulator/UniInterface/UniKeyboard.cs @@ -12,43 +12,34 @@ using UnityEngine; public class UniKeyboard : MonoBehaviour, IKeyboard { public MameControllerMapper ControllerMapper { get; private set; } - bool bReplayMode; PlayMode mPlayMode; - ReplayMode mReplayMode; void Awake() { ControllerMapper = new MameControllerMapper(); - Init(false); + Init(); } public ulong GetPressedKeys() { - ulong InputData; - if (!bReplayMode)//游玩模式(单机或联机) - return mPlayMode.GetPressedKeys(); - else//Replay模式 - return mReplayMode.GetPressedKeys(); + return mPlayMode.GetPressedKeys(); + } + public void SyncInput(ulong inputData) + { + mPlayMode.CurrLocalInpuAllData = inputData; } - public bool SampleInput() - { - if (bReplayMode) return true; - return mPlayMode.SampleInput(); + public ulong DoLocalPressedKeys() + { + return mPlayMode.DoLocalPressedKeys(); } #region - public void SetRePlay(bool IsReplay) - { - bReplayMode = IsReplay; - } - public void Init(bool IsReplay) + public void Init() { - bReplayMode = IsReplay; mPlayMode = new PlayMode(this); - mReplayMode = new ReplayMode(); } public static IEnumerable GetInputpDataToMotionKey(ulong inputdata) @@ -80,41 +71,7 @@ public class UniKeyboard : MonoBehaviour, IKeyboard return CurrLocalInpuAllData; } - public bool SampleInput() - { - //Net模式 - if (InGameUI.Instance.IsNetPlay) - { - bool bHadNetData = false; - int targetFrame; ReplayStep replayData; int frameDiff; bool inputDiff; - if (App.roomMgr.netReplay.TryGetNextFrame((int)UMAME.instance.Frame, out replayData, out frameDiff, out inputDiff)) - { - if (inputDiff) - { - App.log.Debug($"{DateTime.Now.ToString("hh:mm:ss.fff")} TryGetNextFrame remoteFrame->{App.roomMgr.netReplay.mRemoteFrameIdx} diff->{frameDiff} " + - $"frame=>{replayData.FrameStartID} InPut=>{replayData.InPut}"); - } - CurrRemoteInpuAllData = replayData.InPut; - - bHadNetData = true; - } - else//无输入 - { - CurrRemoteInpuAllData = 0; - } - //发送本地操作 - App.roomMgr.SendRoomSingelPlayerInput(UMAME.instance.Frame, DoLocalPressedKeys()); - return bHadNetData; - } - //单人模式 - else - { - DoLocalPressedKeys(); - return true; - } - } - - ulong DoLocalPressedKeys() + public ulong DoLocalPressedKeys() { ulong tempLocalInputAllData = 0; tempLocalInputAllData |= mUniKeyboard.ControllerMapper.Controller0.GetSingleAllInput(); diff --git a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs index 469b7ed0..7ec435cb 100644 --- a/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs +++ b/AxibugEmuOnline.Client/Assets/Script/AppMain/Emulator/StoicGooseEmulator/UStoicGoose.cs @@ -1,6 +1,7 @@ using AxibugEmuOnline.Client; using AxibugEmuOnline.Client.ClientCore; using AxibugProtobuf; +using AxiReplay; using StoicGoose.Common.Utilities; using StoicGoose.Core.Machines; using System; @@ -11,7 +12,7 @@ using UnityEngine; using UnityEngine.UI; using CartridgeMetadata = StoicGoose.Core.Cartridges.Metadata; -public class UStoicGoose : IEmuCore +public class UStoicGoose : EmuCore { public static UStoicGoose instance; public static System.Diagnostics.Stopwatch sw = System.Diagnostics.Stopwatch.StartNew(); @@ -124,11 +125,25 @@ public class UStoicGoose : IEmuCore { throw new NotImplementedException(); } - - public override bool PushEmulatorFrame() - { - throw new NotImplementedException(); - } + protected override bool OnPushEmulatorFrame(ulong InputData) + { + throw new NotImplementedException(); + } + + protected override ulong ConvertInputDataFromNet(ReplayStep step) + { + return step.InPut; + } + + protected override ulong InputDataToNet(ulong inputData) + { + return inputData; + } + + protected override ulong GetLocalInput() + { + throw new NotImplementedException(); + } public override void AfterPushFrame() {