diff --git a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/SettingKeys.kt b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/SettingKeys.kt index 1d6e0dcee..aca424cd9 100644 --- a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/SettingKeys.kt +++ b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/SettingKeys.kt @@ -43,6 +43,9 @@ object SettingKeys { external fun frame_limit(): String external fun turbo_limit(): String external fun texture_filter(): String + external fun antialiasing_filter(): String + external fun fsr_sharpness(): String + external fun output_scaling(): String external fun texture_sampling(): String external fun delay_game_render_thread_us(): String external fun layout_option(): String diff --git a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/model/IntSetting.kt b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/model/IntSetting.kt index eb1a880a5..c26e17abf 100644 --- a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/model/IntSetting.kt +++ b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/model/IntSetting.kt @@ -48,6 +48,9 @@ enum class IntSetting( PORTRAIT_BOTTOM_HEIGHT(SettingKeys.custom_portrait_bottom_height(),Settings.SECTION_LAYOUT,480), AUDIO_INPUT_TYPE(SettingKeys.input_type(), Settings.SECTION_AUDIO, 0), CPU_CLOCK_SPEED(SettingKeys.cpu_clock_percentage(), Settings.SECTION_CORE, 100), + ANTIALIASING_FILTER(SettingKeys.antialiasing_filter(), Settings.SECTION_RENDERER, 0), + FSR_SHARPNESS(SettingKeys.fsr_sharpness(), Settings.SECTION_RENDERER, 50), + OUTPUT_SCALING(SettingKeys.output_scaling(), Settings.SECTION_RENDERER, 2), TEXTURE_FILTER(SettingKeys.texture_filter(), Settings.SECTION_RENDERER, 0), TEXTURE_SAMPLING(SettingKeys.texture_sampling(), Settings.SECTION_RENDERER, 0), USE_FRAME_LIMIT(SettingKeys.use_frame_limit(), Settings.SECTION_RENDERER, 1), diff --git a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/ui/SettingsFragmentPresenter.kt b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/ui/SettingsFragmentPresenter.kt index 25e56517f..b11fdc1db 100644 --- a/src/android/app/src/main/java/org/citra/citra_emu/features/settings/ui/SettingsFragmentPresenter.kt +++ b/src/android/app/src/main/java/org/citra/citra_emu/features/settings/ui/SettingsFragmentPresenter.kt @@ -922,14 +922,48 @@ class SettingsFragmentPresenter(private val fragmentView: SettingsFragmentView) ) ) add( - SwitchSetting( - BooleanSetting.LINEAR_FILTERING, - R.string.linear_filtering, - R.string.linear_filtering_description, - BooleanSetting.LINEAR_FILTERING.key, - BooleanSetting.LINEAR_FILTERING.defaultValue + SingleChoiceSetting( + IntSetting.OUTPUT_SCALING, + R.string.output_scaling_name, + R.string.output_scaling_description, + R.array.outputScalingNames, + R.array.outputScalingValues, + IntSetting.OUTPUT_SCALING.key, + IntSetting.OUTPUT_SCALING.defaultValue ) ) + add( + SliderSetting( + IntSetting.FSR_SHARPNESS, + R.string.fsr_sharpness_name, + R.string.fsr_sharpness_description, + 0, + 100, + "%", + IntSetting.FSR_SHARPNESS.key, + IntSetting.FSR_SHARPNESS.defaultValue.toFloat() + ) + ) + add( + SingleChoiceSetting( + IntSetting.ANTIALIASING_FILTER, + R.string.antialiasing_filter_name, + R.string.antialiasing_filter_description, + R.array.antialiasingFilterNames, + R.array.antialiasingFilterValues, + IntSetting.ANTIALIASING_FILTER.key, + IntSetting.ANTIALIASING_FILTER.defaultValue + ) + ) +// add( +// SwitchSetting( +// BooleanSetting.LINEAR_FILTERING, +// R.string.linear_filtering, +// R.string.linear_filtering_description, +// BooleanSetting.LINEAR_FILTERING.key, +// BooleanSetting.LINEAR_FILTERING.defaultValue +// ) +// ) add( SwitchSetting( BooleanSetting.SHADERS_ACCURATE_MUL, diff --git a/src/android/app/src/main/jni/config.cpp b/src/android/app/src/main/jni/config.cpp index e0fa260c5..d3107e586 100644 --- a/src/android/app/src/main/jni/config.cpp +++ b/src/android/app/src/main/jni/config.cpp @@ -153,6 +153,9 @@ void Config::ReadValues() { ReadSetting("Renderer", Settings::values.use_disk_shader_cache); ReadSetting("Renderer", Settings::values.use_vsync); ReadSetting("Renderer", Settings::values.texture_filter); + ReadSetting("Renderer", Settings::values.output_scaling); + ReadSetting("Renderer", Settings::values.fsr_sharpness); + ReadSetting("Renderer", Settings::values.antialiasing_filter); ReadSetting("Renderer", Settings::values.texture_sampling); ReadSetting("Renderer", Settings::values.turbo_limit); // Workaround to map Android setting for enabling the frame limiter to the format Citra expects diff --git a/src/android/app/src/main/jni/default_ini.h b/src/android/app/src/main/jni/default_ini.h index ce93d0e6f..57c49dfa8 100644 --- a/src/android/app/src/main/jni/default_ini.h +++ b/src/android/app/src/main/jni/default_ini.h @@ -187,6 +187,17 @@ static const char* android_config_default_file_content = (BOOST_HANA_STRING(R"( # Loaded from shaders/anaglyph )") DECLARE_KEY(anaglyph_shader_name) BOOST_HANA_STRING(R"( +# Scaling mode for image output +# 0: Nearest, 1: Bilinear, 2 (default): Adaptive, 3: FSR 1, 4: Sharp Bilinear +)") DECLARE_KEY(output_scaling) BOOST_HANA_STRING(R"( + +# Antialiasing filter to use +# 0 (default): None, 1: FXAA, 2: SMAA +)") DECLARE_KEY(antialiasing_filter) BOOST_HANA_STRING(R"( + +# 0 - 100: Strength of FSR Sharpening. 50 (default) +)") DECLARE_KEY(fsr_sharpness) BOOST_HANA_STRING(R"( + # Whether to enable linear filtering or not # This is required for some shaders to work correctly # 0: Nearest, 1 (default): Linear diff --git a/src/android/app/src/main/res/values/arrays.xml b/src/android/app/src/main/res/values/arrays.xml index 2a08cd546..99aa8b1a7 100644 --- a/src/android/app/src/main/res/values/arrays.xml +++ b/src/android/app/src/main/res/values/arrays.xml @@ -297,6 +297,34 @@ 5 + + @string/nearest + @string/bilinear + @string/adaptive + @string/fsr + @string/sharpbilinear + + + + 0 + 1 + 2 + 3 + 4 + + + + @string/none + @string/fxaa + @string/smaa + + + + 0 + 1 + 2 + + @string/game_controlled @string/nearest_neighbor diff --git a/src/android/app/src/main/res/values/strings.xml b/src/android/app/src/main/res/values/strings.xml index 08e927081..5077c8203 100644 --- a/src/android/app/src/main/res/values/strings.xml +++ b/src/android/app/src/main/res/values/strings.xml @@ -262,6 +262,12 @@ Scales the screens with an integer multiplier of the original 3DS screen. For layouts with two different screen sizes, the largest screen is integer-scaled. Texture Filter Enhances the visuals of applications by applying a filter to textures. The supported filters are Anime4K Ultrafast, Bicubic, ScaleForce, xBRZ freescale, and MMPX. + Antialiasing Filter + Reduces the amount of aliasing, resulting in smoother edges. FXAA is extremely lightweight but more aggressive and lower quality. SMAA is heavier but is higher quality and more selective with the edges it smooths. + Output Scaling + The method by which the game output is scaled to the screen. Nearest doesn\'t smooth visuals but causes uneven pixels at non-integer ratios. Bilinear smooths visuals but may cause aliasing when downscaling. Adaptive uses bilinear for upscaling, but uses area sampling to downscale without creating aliasing. FSR 1 is an upscaler which allows sharpening and allows better visuals without increasing the internal resolution. This should be used with antialiasing and a minimum internal resolution of 2x Native. Sharp Bilinear looks similar to nearest but is slightly smoothed to prevent uneven pixels at non-integer ratios. + FSR Sharpness + Specifies the strength of the sharpening pass when using FSR Delay Game Render Thread Delay the game render thread when it submits data to the GPU. Helps with performance issues in the (very few) applications with dynamic framerates. Advanced @@ -764,6 +770,18 @@ xBRZ MMPX + + Nearest + Bilinear + Adaptive + AMD FSR 1 + Sharp Bilinear + + + + FXAA + SMAA + Game Controlled Nearest Neighbor