mirror of https://github.com/Ryujinx/Ryujinx.git
Compare commits
4 Commits
fd46ff18b0
...
090ac1a703
Author | SHA1 | Date |
---|---|---|
Willi Schinmeyer | 090ac1a703 | |
jhorv | 73f985d27c | |
Willi Schinmeyer | ede3f0f5b8 | |
Willi Schinmeyer | 30d7253e26 |
|
@ -3,6 +3,7 @@ namespace Ryujinx.Common.Configuration.Hid
|
||||||
public class LeftJoyconCommonConfig<TButton>
|
public class LeftJoyconCommonConfig<TButton>
|
||||||
{
|
{
|
||||||
public TButton ButtonMinus { get; set; }
|
public TButton ButtonMinus { get; set; }
|
||||||
|
public TButton ButtonScreenshot { get; set; }
|
||||||
public TButton ButtonL { get; set; }
|
public TButton ButtonL { get; set; }
|
||||||
public TButton ButtonZl { get; set; }
|
public TButton ButtonZl { get; set; }
|
||||||
public TButton ButtonSl { get; set; }
|
public TButton ButtonSl { get; set; }
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
using System.Buffers;
|
using Ryujinx.Common.Memory;
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.GAL
|
namespace Ryujinx.Graphics.GAL
|
||||||
{
|
{
|
||||||
|
@ -18,30 +18,30 @@ namespace Ryujinx.Graphics.GAL
|
||||||
PinnedSpan<byte> GetData(int layer, int level);
|
PinnedSpan<byte> GetData(int layer, int level);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sets the texture data. The data passed as a <see cref="IMemoryOwner{Byte}" /> will be disposed when
|
/// Sets the texture data. The data passed as a <see cref="MemoryOwner{Byte}" /> will be disposed when
|
||||||
/// the operation completes.
|
/// the operation completes.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="data">Texture data bytes</param>
|
/// <param name="data">Texture data bytes</param>
|
||||||
void SetData(IMemoryOwner<byte> data);
|
void SetData(MemoryOwner<byte> data);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sets the texture data. The data passed as a <see cref="IMemoryOwner{Byte}" /> will be disposed when
|
/// Sets the texture data. The data passed as a <see cref="MemoryOwner{Byte}" /> will be disposed when
|
||||||
/// the operation completes.
|
/// the operation completes.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="data">Texture data bytes</param>
|
/// <param name="data">Texture data bytes</param>
|
||||||
/// <param name="layer">Target layer</param>
|
/// <param name="layer">Target layer</param>
|
||||||
/// <param name="level">Target level</param>
|
/// <param name="level">Target level</param>
|
||||||
void SetData(IMemoryOwner<byte> data, int layer, int level);
|
void SetData(MemoryOwner<byte> data, int layer, int level);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sets the texture data. The data passed as a <see cref="IMemoryOwner{Byte}" /> will be disposed when
|
/// Sets the texture data. The data passed as a <see cref="MemoryOwner{Byte}" /> will be disposed when
|
||||||
/// the operation completes.
|
/// the operation completes.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="data">Texture data bytes</param>
|
/// <param name="data">Texture data bytes</param>
|
||||||
/// <param name="layer">Target layer</param>
|
/// <param name="layer">Target layer</param>
|
||||||
/// <param name="level">Target level</param>
|
/// <param name="level">Target level</param>
|
||||||
/// <param name="region">Target sub-region of the texture to update</param>
|
/// <param name="region">Target sub-region of the texture to update</param>
|
||||||
void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region);
|
void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region);
|
||||||
|
|
||||||
void SetStorage(BufferRange buffer);
|
void SetStorage(BufferRange buffer);
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
|
@ -8,9 +8,9 @@ namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
public readonly CommandType CommandType => CommandType.TextureSetData;
|
public readonly CommandType CommandType => CommandType.TextureSetData;
|
||||||
private TableRef<ThreadedTexture> _texture;
|
private TableRef<ThreadedTexture> _texture;
|
||||||
private TableRef<IMemoryOwner<byte>> _data;
|
private TableRef<MemoryOwner<byte>> _data;
|
||||||
|
|
||||||
public void Set(TableRef<ThreadedTexture> texture, TableRef<IMemoryOwner<byte>> data)
|
public void Set(TableRef<ThreadedTexture> texture, TableRef<MemoryOwner<byte>> data)
|
||||||
{
|
{
|
||||||
_texture = texture;
|
_texture = texture;
|
||||||
_data = data;
|
_data = data;
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
|
@ -8,11 +8,11 @@ namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
public readonly CommandType CommandType => CommandType.TextureSetDataSlice;
|
public readonly CommandType CommandType => CommandType.TextureSetDataSlice;
|
||||||
private TableRef<ThreadedTexture> _texture;
|
private TableRef<ThreadedTexture> _texture;
|
||||||
private TableRef<IMemoryOwner<byte>> _data;
|
private TableRef<MemoryOwner<byte>> _data;
|
||||||
private int _layer;
|
private int _layer;
|
||||||
private int _level;
|
private int _level;
|
||||||
|
|
||||||
public void Set(TableRef<ThreadedTexture> texture, TableRef<IMemoryOwner<byte>> data, int layer, int level)
|
public void Set(TableRef<ThreadedTexture> texture, TableRef<MemoryOwner<byte>> data, int layer, int level)
|
||||||
{
|
{
|
||||||
_texture = texture;
|
_texture = texture;
|
||||||
_data = data;
|
_data = data;
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
using Ryujinx.Graphics.GAL.Multithreading.Resources;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
|
@ -8,12 +8,12 @@ namespace Ryujinx.Graphics.GAL.Multithreading.Commands.Texture
|
||||||
{
|
{
|
||||||
public readonly CommandType CommandType => CommandType.TextureSetDataSliceRegion;
|
public readonly CommandType CommandType => CommandType.TextureSetDataSliceRegion;
|
||||||
private TableRef<ThreadedTexture> _texture;
|
private TableRef<ThreadedTexture> _texture;
|
||||||
private TableRef<IMemoryOwner<byte>> _data;
|
private TableRef<MemoryOwner<byte>> _data;
|
||||||
private int _layer;
|
private int _layer;
|
||||||
private int _level;
|
private int _level;
|
||||||
private Rectangle<int> _region;
|
private Rectangle<int> _region;
|
||||||
|
|
||||||
public void Set(TableRef<ThreadedTexture> texture, TableRef<IMemoryOwner<byte>> data, int layer, int level, Rectangle<int> region)
|
public void Set(TableRef<ThreadedTexture> texture, TableRef<MemoryOwner<byte>> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
_texture = texture;
|
_texture = texture;
|
||||||
_data = data;
|
_data = data;
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Commands.Texture;
|
using Ryujinx.Graphics.GAL.Multithreading.Commands.Texture;
|
||||||
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
using Ryujinx.Graphics.GAL.Multithreading.Model;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.GAL.Multithreading.Resources
|
namespace Ryujinx.Graphics.GAL.Multithreading.Resources
|
||||||
{
|
{
|
||||||
|
@ -111,21 +111,21 @@ namespace Ryujinx.Graphics.GAL.Multithreading.Resources
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
_renderer.New<TextureSetDataCommand>().Set(Ref(this), Ref(data));
|
_renderer.New<TextureSetDataCommand>().Set(Ref(this), Ref(data));
|
||||||
_renderer.QueueCommand();
|
_renderer.QueueCommand();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
_renderer.New<TextureSetDataSliceCommand>().Set(Ref(this), Ref(data), layer, level);
|
_renderer.New<TextureSetDataSliceCommand>().Set(Ref(this), Ref(data), layer, level);
|
||||||
_renderer.QueueCommand();
|
_renderer.QueueCommand();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
_renderer.New<TextureSetDataSliceRegionCommand>().Set(Ref(this), Ref(data), layer, level, region);
|
_renderer.New<TextureSetDataSliceRegionCommand>().Set(Ref(this), Ref(data), layer, level, region);
|
||||||
_renderer.QueueCommand();
|
_renderer.QueueCommand();
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
using Ryujinx.Common;
|
using Ryujinx.Common;
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.Device;
|
using Ryujinx.Graphics.Device;
|
||||||
using Ryujinx.Graphics.Gpu.Engine.Threed;
|
using Ryujinx.Graphics.Gpu.Engine.Threed;
|
||||||
using Ryujinx.Graphics.Gpu.Memory;
|
using Ryujinx.Graphics.Gpu.Memory;
|
||||||
using Ryujinx.Graphics.Texture;
|
using Ryujinx.Graphics.Texture;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Runtime.CompilerServices;
|
using System.Runtime.CompilerServices;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
@ -353,7 +353,7 @@ namespace Ryujinx.Graphics.Gpu.Engine.Dma
|
||||||
|
|
||||||
if (target != null)
|
if (target != null)
|
||||||
{
|
{
|
||||||
IMemoryOwner<byte> data;
|
MemoryOwner<byte> data;
|
||||||
if (srcLinear)
|
if (srcLinear)
|
||||||
{
|
{
|
||||||
data = LayoutConverter.ConvertLinearStridedToLinear(
|
data = LayoutConverter.ConvertLinearStridedToLinear(
|
||||||
|
|
|
@ -7,7 +7,6 @@ using Ryujinx.Graphics.Texture.Astc;
|
||||||
using Ryujinx.Memory;
|
using Ryujinx.Memory;
|
||||||
using Ryujinx.Memory.Range;
|
using Ryujinx.Memory.Range;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
@ -662,7 +661,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
IMemoryOwner<byte> result = ConvertToHostCompatibleFormat(data);
|
MemoryOwner<byte> result = ConvertToHostCompatibleFormat(data);
|
||||||
|
|
||||||
if (ScaleFactor != 1f && AllowScaledSetData())
|
if (ScaleFactor != 1f && AllowScaledSetData())
|
||||||
{
|
{
|
||||||
|
@ -685,7 +684,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
/// Uploads new texture data to the host GPU.
|
/// Uploads new texture data to the host GPU.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="data">New data</param>
|
/// <param name="data">New data</param>
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
BlacklistScale();
|
BlacklistScale();
|
||||||
|
|
||||||
|
@ -704,7 +703,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
/// <param name="data">New data</param>
|
/// <param name="data">New data</param>
|
||||||
/// <param name="layer">Target layer</param>
|
/// <param name="layer">Target layer</param>
|
||||||
/// <param name="level">Target level</param>
|
/// <param name="level">Target level</param>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
BlacklistScale();
|
BlacklistScale();
|
||||||
|
|
||||||
|
@ -722,7 +721,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
/// <param name="layer">Target layer</param>
|
/// <param name="layer">Target layer</param>
|
||||||
/// <param name="level">Target level</param>
|
/// <param name="level">Target level</param>
|
||||||
/// <param name="region">Target sub-region of the texture to update</param>
|
/// <param name="region">Target sub-region of the texture to update</param>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
BlacklistScale();
|
BlacklistScale();
|
||||||
|
|
||||||
|
@ -740,7 +739,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
/// <param name="level">Mip level to convert</param>
|
/// <param name="level">Mip level to convert</param>
|
||||||
/// <param name="single">True to convert a single slice</param>
|
/// <param name="single">True to convert a single slice</param>
|
||||||
/// <returns>Converted data</returns>
|
/// <returns>Converted data</returns>
|
||||||
public IMemoryOwner<byte> ConvertToHostCompatibleFormat(ReadOnlySpan<byte> data, int level = 0, bool single = false)
|
public MemoryOwner<byte> ConvertToHostCompatibleFormat(ReadOnlySpan<byte> data, int level = 0, bool single = false)
|
||||||
{
|
{
|
||||||
int width = Info.Width;
|
int width = Info.Width;
|
||||||
int height = Info.Height;
|
int height = Info.Height;
|
||||||
|
@ -755,7 +754,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
|
|
||||||
int sliceDepth = single ? 1 : depth;
|
int sliceDepth = single ? 1 : depth;
|
||||||
|
|
||||||
IMemoryOwner<byte> linear;
|
MemoryOwner<byte> linear;
|
||||||
|
|
||||||
if (Info.IsLinear)
|
if (Info.IsLinear)
|
||||||
{
|
{
|
||||||
|
@ -788,7 +787,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
data);
|
data);
|
||||||
}
|
}
|
||||||
|
|
||||||
IMemoryOwner<byte> result = linear;
|
MemoryOwner<byte> result = linear;
|
||||||
|
|
||||||
// Handle compressed cases not supported by the host:
|
// Handle compressed cases not supported by the host:
|
||||||
// - ASTC is usually not supported on desktop cards.
|
// - ASTC is usually not supported on desktop cards.
|
||||||
|
@ -832,19 +831,19 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
case Format.Etc2RgbaUnorm:
|
case Format.Etc2RgbaUnorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return ETC2Decoder.DecodeRgba(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return ETC2Decoder.DecodeRgba(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
case Format.Etc2RgbPtaSrgb:
|
case Format.Etc2RgbPtaSrgb:
|
||||||
case Format.Etc2RgbPtaUnorm:
|
case Format.Etc2RgbPtaUnorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return ETC2Decoder.DecodePta(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return ETC2Decoder.DecodePta(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
case Format.Etc2RgbSrgb:
|
case Format.Etc2RgbSrgb:
|
||||||
case Format.Etc2RgbUnorm:
|
case Format.Etc2RgbUnorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return ETC2Decoder.DecodeRgb(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return ETC2Decoder.DecodeRgb(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -856,43 +855,43 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
case Format.Bc1RgbaUnorm:
|
case Format.Bc1RgbaUnorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC1(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return BCnDecoder.DecodeBC1(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
case Format.Bc2Srgb:
|
case Format.Bc2Srgb:
|
||||||
case Format.Bc2Unorm:
|
case Format.Bc2Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC2(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return BCnDecoder.DecodeBC2(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
case Format.Bc3Srgb:
|
case Format.Bc3Srgb:
|
||||||
case Format.Bc3Unorm:
|
case Format.Bc3Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC3(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return BCnDecoder.DecodeBC3(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
case Format.Bc4Snorm:
|
case Format.Bc4Snorm:
|
||||||
case Format.Bc4Unorm:
|
case Format.Bc4Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC4(result.Memory.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc4Snorm);
|
return BCnDecoder.DecodeBC4(result.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc4Snorm);
|
||||||
}
|
}
|
||||||
case Format.Bc5Snorm:
|
case Format.Bc5Snorm:
|
||||||
case Format.Bc5Unorm:
|
case Format.Bc5Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC5(result.Memory.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc5Snorm);
|
return BCnDecoder.DecodeBC5(result.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc5Snorm);
|
||||||
}
|
}
|
||||||
case Format.Bc6HSfloat:
|
case Format.Bc6HSfloat:
|
||||||
case Format.Bc6HUfloat:
|
case Format.Bc6HUfloat:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC6(result.Memory.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc6HSfloat);
|
return BCnDecoder.DecodeBC6(result.Span, width, height, sliceDepth, levels, layers, Format == Format.Bc6HSfloat);
|
||||||
}
|
}
|
||||||
case Format.Bc7Srgb:
|
case Format.Bc7Srgb:
|
||||||
case Format.Bc7Unorm:
|
case Format.Bc7Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return BCnDecoder.DecodeBC7(result.Memory.Span, width, height, sliceDepth, levels, layers);
|
return BCnDecoder.DecodeBC7(result.Span, width, height, sliceDepth, levels, layers);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -900,7 +899,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
{
|
{
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
var converted = PixelConverter.ConvertR4G4ToR4G4B4A4(result.Memory.Span, width);
|
var converted = PixelConverter.ConvertR4G4ToR4G4B4A4(result.Span, width);
|
||||||
|
|
||||||
if (_context.Capabilities.SupportsR4G4B4A4Format)
|
if (_context.Capabilities.SupportsR4G4B4A4Format)
|
||||||
{
|
{
|
||||||
|
@ -910,7 +909,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
{
|
{
|
||||||
using (converted)
|
using (converted)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(converted.Memory.Span, width);
|
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(converted.Span, width);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -921,7 +920,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
{
|
{
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(result.Memory.Span, width);
|
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(result.Span, width);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -933,24 +932,24 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
case Format.R5G6B5Unorm:
|
case Format.R5G6B5Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertR5G6B5ToR8G8B8A8(result.Memory.Span, width);
|
return PixelConverter.ConvertR5G6B5ToR8G8B8A8(result.Span, width);
|
||||||
}
|
}
|
||||||
case Format.B5G5R5A1Unorm:
|
case Format.B5G5R5A1Unorm:
|
||||||
case Format.R5G5B5X1Unorm:
|
case Format.R5G5B5X1Unorm:
|
||||||
case Format.R5G5B5A1Unorm:
|
case Format.R5G5B5A1Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertR5G5B5ToR8G8B8A8(result.Memory.Span, width, Format == Format.R5G5B5X1Unorm);
|
return PixelConverter.ConvertR5G5B5ToR8G8B8A8(result.Span, width, Format == Format.R5G5B5X1Unorm);
|
||||||
}
|
}
|
||||||
case Format.A1B5G5R5Unorm:
|
case Format.A1B5G5R5Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertA1B5G5R5ToR8G8B8A8(result.Memory.Span, width);
|
return PixelConverter.ConvertA1B5G5R5ToR8G8B8A8(result.Span, width);
|
||||||
}
|
}
|
||||||
case Format.R4G4B4A4Unorm:
|
case Format.R4G4B4A4Unorm:
|
||||||
using (result)
|
using (result)
|
||||||
{
|
{
|
||||||
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(result.Memory.Span, width);
|
return PixelConverter.ConvertR4G4B4A4ToR8G8B8A8(result.Span, width);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL;
|
using Ryujinx.Graphics.GAL;
|
||||||
using Ryujinx.Graphics.Gpu.Memory;
|
using Ryujinx.Graphics.Gpu.Memory;
|
||||||
using Ryujinx.Graphics.Texture;
|
using Ryujinx.Graphics.Texture;
|
||||||
|
@ -5,7 +6,6 @@ using Ryujinx.Memory;
|
||||||
using Ryujinx.Memory.Range;
|
using Ryujinx.Memory.Range;
|
||||||
using Ryujinx.Memory.Tracking;
|
using Ryujinx.Memory.Tracking;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Runtime.CompilerServices;
|
using System.Runtime.CompilerServices;
|
||||||
|
|
||||||
|
@ -445,7 +445,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
|
|
||||||
ReadOnlySpan<byte> data = dataSpan[(offset - spanBase)..];
|
ReadOnlySpan<byte> data = dataSpan[(offset - spanBase)..];
|
||||||
|
|
||||||
IMemoryOwner<byte> result = Storage.ConvertToHostCompatibleFormat(data, info.BaseLevel + level, true);
|
MemoryOwner<byte> result = Storage.ConvertToHostCompatibleFormat(data, info.BaseLevel + level, true);
|
||||||
|
|
||||||
Storage.SetData(result, info.BaseLayer + layer, info.BaseLevel + level);
|
Storage.SetData(result, info.BaseLayer + layer, info.BaseLevel + level);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
using OpenTK.Graphics.OpenGL;
|
using OpenTK.Graphics.OpenGL;
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL;
|
using Ryujinx.Graphics.GAL;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.OpenGL.Image
|
namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
{
|
{
|
||||||
|
@ -55,9 +55,9 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
var dataSpan = data.Memory.Span;
|
var dataSpan = data.Span;
|
||||||
|
|
||||||
Buffer.SetData(_buffer, _bufferOffset, dataSpan[..Math.Min(dataSpan.Length, _bufferSize)]);
|
Buffer.SetData(_buffer, _bufferOffset, dataSpan[..Math.Min(dataSpan.Length, _bufferSize)]);
|
||||||
|
|
||||||
|
@ -65,13 +65,13 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
throw new NotSupportedException();
|
throw new NotSupportedException();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
throw new NotSupportedException();
|
throw new NotSupportedException();
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
using OpenTK.Graphics.OpenGL;
|
using OpenTK.Graphics.OpenGL;
|
||||||
using Ryujinx.Common;
|
using Ryujinx.Common;
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL;
|
using Ryujinx.Graphics.GAL;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
|
|
||||||
namespace Ryujinx.Graphics.OpenGL.Image
|
namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
|
@ -448,13 +448,13 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
using (data = EnsureDataFormat(data))
|
using (data = EnsureDataFormat(data))
|
||||||
{
|
{
|
||||||
unsafe
|
unsafe
|
||||||
{
|
{
|
||||||
var dataSpan = data.Memory.Span;
|
var dataSpan = data.Span;
|
||||||
fixed (byte* ptr = dataSpan)
|
fixed (byte* ptr = dataSpan)
|
||||||
{
|
{
|
||||||
ReadFrom((IntPtr)ptr, dataSpan.Length);
|
ReadFrom((IntPtr)ptr, dataSpan.Length);
|
||||||
|
@ -463,13 +463,13 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
using (data = EnsureDataFormat(data))
|
using (data = EnsureDataFormat(data))
|
||||||
{
|
{
|
||||||
unsafe
|
unsafe
|
||||||
{
|
{
|
||||||
fixed (byte* ptr = data.Memory.Span)
|
fixed (byte* ptr = data.Span)
|
||||||
{
|
{
|
||||||
int width = Math.Max(Info.Width >> level, 1);
|
int width = Math.Max(Info.Width >> level, 1);
|
||||||
int height = Math.Max(Info.Height >> level, 1);
|
int height = Math.Max(Info.Height >> level, 1);
|
||||||
|
@ -480,7 +480,7 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
using (data = EnsureDataFormat(data))
|
using (data = EnsureDataFormat(data))
|
||||||
{
|
{
|
||||||
|
@ -489,7 +489,7 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
|
|
||||||
unsafe
|
unsafe
|
||||||
{
|
{
|
||||||
fixed (byte* ptr = data.Memory.Span)
|
fixed (byte* ptr = data.Span)
|
||||||
{
|
{
|
||||||
ReadFrom2D(
|
ReadFrom2D(
|
||||||
(IntPtr)ptr,
|
(IntPtr)ptr,
|
||||||
|
@ -522,13 +522,13 @@ namespace Ryujinx.Graphics.OpenGL.Image
|
||||||
ReadFrom2D(data, layer, level, x, y, width, height, mipSize);
|
ReadFrom2D(data, layer, level, x, y, width, height, mipSize);
|
||||||
}
|
}
|
||||||
|
|
||||||
private IMemoryOwner<byte> EnsureDataFormat(IMemoryOwner<byte> data)
|
private MemoryOwner<byte> EnsureDataFormat(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
if (Format == Format.S8UintD24Unorm)
|
if (Format == Format.S8UintD24Unorm)
|
||||||
{
|
{
|
||||||
using (data)
|
using (data)
|
||||||
{
|
{
|
||||||
return FormatConverter.ConvertS8D24ToD24S8(data.Memory.Span);
|
return FormatConverter.ConvertS8D24ToD24S8(data.Span);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL;
|
using Ryujinx.Graphics.GAL;
|
||||||
using Silk.NET.Vulkan;
|
using Silk.NET.Vulkan;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using Format = Ryujinx.Graphics.GAL.Format;
|
using Format = Ryujinx.Graphics.GAL.Format;
|
||||||
using VkFormat = Silk.NET.Vulkan.Format;
|
using VkFormat = Silk.NET.Vulkan.Format;
|
||||||
|
@ -84,20 +84,20 @@ namespace Ryujinx.Graphics.Vulkan
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
_gd.SetBufferData(_bufferHandle, _offset, data.Memory.Span);
|
_gd.SetBufferData(_bufferHandle, _offset, data.Span);
|
||||||
data.Dispose();
|
data.Dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
throw new NotSupportedException();
|
throw new NotSupportedException();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
throw new NotSupportedException();
|
throw new NotSupportedException();
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using Ryujinx.Graphics.GAL;
|
using Ryujinx.Graphics.GAL;
|
||||||
using Silk.NET.Vulkan;
|
using Silk.NET.Vulkan;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
|
@ -746,23 +746,23 @@ namespace Ryujinx.Graphics.Vulkan
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data)
|
public void SetData(MemoryOwner<byte> data)
|
||||||
{
|
{
|
||||||
SetData(data.Memory.Span, 0, 0, Info.GetLayers(), Info.Levels, singleSlice: false);
|
SetData(data.Span, 0, 0, Info.GetLayers(), Info.Levels, singleSlice: false);
|
||||||
data.Dispose();
|
data.Dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level)
|
public void SetData(MemoryOwner<byte> data, int layer, int level)
|
||||||
{
|
{
|
||||||
SetData(data.Memory.Span, layer, level, 1, 1, singleSlice: true);
|
SetData(data.Span, layer, level, 1, 1, singleSlice: true);
|
||||||
data.Dispose();
|
data.Dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc/>
|
/// <inheritdoc/>
|
||||||
public void SetData(IMemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
public void SetData(MemoryOwner<byte> data, int layer, int level, Rectangle<int> region)
|
||||||
{
|
{
|
||||||
SetData(data.Memory.Span, layer, level, 1, 1, singleSlice: true, region);
|
SetData(data.Span, layer, level, 1, 1, singleSlice: true, region);
|
||||||
data.Dispose();
|
data.Dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -166,6 +166,7 @@ namespace Ryujinx.Input.GTK3
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
||||||
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Misc1, (Key)_configuration.LeftJoycon.ButtonScreenshot));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
||||||
|
|
|
@ -15,6 +15,7 @@ using Ryujinx.UI.Common.Helper;
|
||||||
using Ryujinx.UI.Widgets;
|
using Ryujinx.UI.Widgets;
|
||||||
using SkiaSharp;
|
using SkiaSharp;
|
||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
@ -73,11 +74,14 @@ namespace Ryujinx.UI
|
||||||
private HideCursorMode _hideCursorMode;
|
private HideCursorMode _hideCursorMode;
|
||||||
private readonly InputManager _inputManager;
|
private readonly InputManager _inputManager;
|
||||||
private readonly IKeyboard _keyboardInterface;
|
private readonly IKeyboard _keyboardInterface;
|
||||||
|
private readonly List<IGamepad> _gamepadInterfaces;
|
||||||
private readonly GraphicsDebugLevel _glLogLevel;
|
private readonly GraphicsDebugLevel _glLogLevel;
|
||||||
private string _gpuBackendName;
|
private string _gpuBackendName;
|
||||||
private string _gpuDriverName;
|
private string _gpuDriverName;
|
||||||
private bool _isMouseInClient;
|
private bool _isMouseInClient;
|
||||||
|
|
||||||
|
private int _gamepadsChanged; // use atomically via Interlocked
|
||||||
|
|
||||||
public RendererWidgetBase(InputManager inputManager, GraphicsDebugLevel glLogLevel)
|
public RendererWidgetBase(InputManager inputManager, GraphicsDebugLevel glLogLevel)
|
||||||
{
|
{
|
||||||
var mouseDriver = new GTK3MouseDriver(this);
|
var mouseDriver = new GTK3MouseDriver(this);
|
||||||
|
@ -88,6 +92,13 @@ namespace Ryujinx.UI
|
||||||
TouchScreenManager = _inputManager.CreateTouchScreenManager();
|
TouchScreenManager = _inputManager.CreateTouchScreenManager();
|
||||||
_keyboardInterface = (IKeyboard)_inputManager.KeyboardDriver.GetGamepad("0");
|
_keyboardInterface = (IKeyboard)_inputManager.KeyboardDriver.GetGamepad("0");
|
||||||
|
|
||||||
|
_gamepadInterfaces = new List<IGamepad>();
|
||||||
|
|
||||||
|
_inputManager.GamepadDriver.OnGamepadConnected += GamepadConnected;
|
||||||
|
_inputManager.GamepadDriver.OnGamepadDisconnected += GamepadDisconnected;
|
||||||
|
|
||||||
|
RefreshGamepads();
|
||||||
|
|
||||||
WaitEvent = new ManualResetEvent(false);
|
WaitEvent = new ManualResetEvent(false);
|
||||||
|
|
||||||
_glLogLevel = glLogLevel;
|
_glLogLevel = glLogLevel;
|
||||||
|
@ -649,6 +660,11 @@ namespace Ryujinx.UI
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (Interlocked.Exchange(ref _gamepadsChanged, 0) == 1)
|
||||||
|
{
|
||||||
|
RefreshGamepads();
|
||||||
|
}
|
||||||
|
|
||||||
NpadManager.Update(ConfigurationState.Instance.Graphics.AspectRatio.Value.ToFloat());
|
NpadManager.Update(ConfigurationState.Instance.Graphics.AspectRatio.Value.ToFloat());
|
||||||
|
|
||||||
if ((Toplevel as MainWindow).IsFocused)
|
if ((Toplevel as MainWindow).IsFocused)
|
||||||
|
@ -767,7 +783,8 @@ namespace Ryujinx.UI
|
||||||
state |= KeyboardHotkeyState.ToggleVSync;
|
state |= KeyboardHotkeyState.ToggleVSync;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_keyboardInterface.IsPressed((Key)ConfigurationState.Instance.Hid.Hotkeys.Value.Screenshot))
|
if (_keyboardInterface.IsPressed((Key)ConfigurationState.Instance.Hid.Hotkeys.Value.Screenshot) ||
|
||||||
|
ButtonPressedOnAnyGamepad(GamepadButtonInputId.Misc1))
|
||||||
{
|
{
|
||||||
state |= KeyboardHotkeyState.Screenshot;
|
state |= KeyboardHotkeyState.Screenshot;
|
||||||
}
|
}
|
||||||
|
@ -809,5 +826,37 @@ namespace Ryujinx.UI
|
||||||
|
|
||||||
return state;
|
return state;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void GamepadConnected(string id)
|
||||||
|
{
|
||||||
|
Interlocked.Exchange(ref _gamepadsChanged, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void GamepadDisconnected(string id)
|
||||||
|
{
|
||||||
|
Interlocked.Exchange(ref _gamepadsChanged, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void RefreshGamepads()
|
||||||
|
{
|
||||||
|
_gamepadInterfaces.Clear();
|
||||||
|
|
||||||
|
foreach (string id in _inputManager.GamepadDriver.GamepadsIds)
|
||||||
|
{
|
||||||
|
_gamepadInterfaces.Add(_inputManager.GamepadDriver.GetGamepad(id));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool ButtonPressedOnAnyGamepad(GamepadButtonInputId button)
|
||||||
|
{
|
||||||
|
foreach (IGamepad gamepad in _gamepadInterfaces)
|
||||||
|
{
|
||||||
|
if (gamepad.IsPressed(button))
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -84,6 +84,7 @@ namespace Ryujinx.UI.Windows
|
||||||
[GUI] ToggleButton _dpadLeft;
|
[GUI] ToggleButton _dpadLeft;
|
||||||
[GUI] ToggleButton _dpadRight;
|
[GUI] ToggleButton _dpadRight;
|
||||||
[GUI] ToggleButton _minus;
|
[GUI] ToggleButton _minus;
|
||||||
|
[GUI] ToggleButton _screenshot;
|
||||||
[GUI] ToggleButton _l;
|
[GUI] ToggleButton _l;
|
||||||
[GUI] ToggleButton _zL;
|
[GUI] ToggleButton _zL;
|
||||||
[GUI] ToggleButton _rStick;
|
[GUI] ToggleButton _rStick;
|
||||||
|
@ -165,6 +166,7 @@ namespace Ryujinx.UI.Windows
|
||||||
_dpadLeft.Clicked += Button_Pressed;
|
_dpadLeft.Clicked += Button_Pressed;
|
||||||
_dpadRight.Clicked += Button_Pressed;
|
_dpadRight.Clicked += Button_Pressed;
|
||||||
_minus.Clicked += Button_Pressed;
|
_minus.Clicked += Button_Pressed;
|
||||||
|
_screenshot.Clicked += Button_Pressed;
|
||||||
_l.Clicked += Button_Pressed;
|
_l.Clicked += Button_Pressed;
|
||||||
_zL.Clicked += Button_Pressed;
|
_zL.Clicked += Button_Pressed;
|
||||||
_lSl.Clicked += Button_Pressed;
|
_lSl.Clicked += Button_Pressed;
|
||||||
|
@ -400,6 +402,7 @@ namespace Ryujinx.UI.Windows
|
||||||
_dpadLeft.Label = "Unbound";
|
_dpadLeft.Label = "Unbound";
|
||||||
_dpadRight.Label = "Unbound";
|
_dpadRight.Label = "Unbound";
|
||||||
_minus.Label = "Unbound";
|
_minus.Label = "Unbound";
|
||||||
|
_screenshot.Label = "Unbound";
|
||||||
_l.Label = "Unbound";
|
_l.Label = "Unbound";
|
||||||
_zL.Label = "Unbound";
|
_zL.Label = "Unbound";
|
||||||
_lSl.Label = "Unbound";
|
_lSl.Label = "Unbound";
|
||||||
|
@ -460,6 +463,7 @@ namespace Ryujinx.UI.Windows
|
||||||
_dpadLeft.Label = keyboardConfig.LeftJoycon.DpadLeft.ToString();
|
_dpadLeft.Label = keyboardConfig.LeftJoycon.DpadLeft.ToString();
|
||||||
_dpadRight.Label = keyboardConfig.LeftJoycon.DpadRight.ToString();
|
_dpadRight.Label = keyboardConfig.LeftJoycon.DpadRight.ToString();
|
||||||
_minus.Label = keyboardConfig.LeftJoycon.ButtonMinus.ToString();
|
_minus.Label = keyboardConfig.LeftJoycon.ButtonMinus.ToString();
|
||||||
|
_screenshot.Label = keyboardConfig.LeftJoycon.ButtonScreenshot.ToString();
|
||||||
_l.Label = keyboardConfig.LeftJoycon.ButtonL.ToString();
|
_l.Label = keyboardConfig.LeftJoycon.ButtonL.ToString();
|
||||||
_zL.Label = keyboardConfig.LeftJoycon.ButtonZl.ToString();
|
_zL.Label = keyboardConfig.LeftJoycon.ButtonZl.ToString();
|
||||||
_lSl.Label = keyboardConfig.LeftJoycon.ButtonSl.ToString();
|
_lSl.Label = keyboardConfig.LeftJoycon.ButtonSl.ToString();
|
||||||
|
@ -498,6 +502,7 @@ namespace Ryujinx.UI.Windows
|
||||||
_dpadLeft.Label = controllerConfig.LeftJoycon.DpadLeft.ToString();
|
_dpadLeft.Label = controllerConfig.LeftJoycon.DpadLeft.ToString();
|
||||||
_dpadRight.Label = controllerConfig.LeftJoycon.DpadRight.ToString();
|
_dpadRight.Label = controllerConfig.LeftJoycon.DpadRight.ToString();
|
||||||
_minus.Label = controllerConfig.LeftJoycon.ButtonMinus.ToString();
|
_minus.Label = controllerConfig.LeftJoycon.ButtonMinus.ToString();
|
||||||
|
_screenshot.Label = controllerConfig.LeftJoycon.ButtonScreenshot.ToString();
|
||||||
_l.Label = controllerConfig.LeftJoycon.ButtonL.ToString();
|
_l.Label = controllerConfig.LeftJoycon.ButtonL.ToString();
|
||||||
_zL.Label = controllerConfig.LeftJoycon.ButtonZl.ToString();
|
_zL.Label = controllerConfig.LeftJoycon.ButtonZl.ToString();
|
||||||
_lSl.Label = controllerConfig.LeftJoycon.ButtonSl.ToString();
|
_lSl.Label = controllerConfig.LeftJoycon.ButtonSl.ToString();
|
||||||
|
@ -566,6 +571,7 @@ namespace Ryujinx.UI.Windows
|
||||||
Enum.TryParse(_dpadLeft.Label, out Key lDPadLeft);
|
Enum.TryParse(_dpadLeft.Label, out Key lDPadLeft);
|
||||||
Enum.TryParse(_dpadRight.Label, out Key lDPadRight);
|
Enum.TryParse(_dpadRight.Label, out Key lDPadRight);
|
||||||
Enum.TryParse(_minus.Label, out Key lButtonMinus);
|
Enum.TryParse(_minus.Label, out Key lButtonMinus);
|
||||||
|
Enum.TryParse(_screenshot.Label, out Key lButtonScreenshot);
|
||||||
Enum.TryParse(_l.Label, out Key lButtonL);
|
Enum.TryParse(_l.Label, out Key lButtonL);
|
||||||
Enum.TryParse(_zL.Label, out Key lButtonZl);
|
Enum.TryParse(_zL.Label, out Key lButtonZl);
|
||||||
Enum.TryParse(_lSl.Label, out Key lButtonSl);
|
Enum.TryParse(_lSl.Label, out Key lButtonSl);
|
||||||
|
@ -597,6 +603,7 @@ namespace Ryujinx.UI.Windows
|
||||||
LeftJoycon = new LeftJoyconCommonConfig<Key>
|
LeftJoycon = new LeftJoyconCommonConfig<Key>
|
||||||
{
|
{
|
||||||
ButtonMinus = lButtonMinus,
|
ButtonMinus = lButtonMinus,
|
||||||
|
ButtonScreenshot = lButtonScreenshot,
|
||||||
ButtonL = lButtonL,
|
ButtonL = lButtonL,
|
||||||
ButtonZl = lButtonZl,
|
ButtonZl = lButtonZl,
|
||||||
ButtonSl = lButtonSl,
|
ButtonSl = lButtonSl,
|
||||||
|
@ -643,6 +650,7 @@ namespace Ryujinx.UI.Windows
|
||||||
Enum.TryParse(_lStick.Label, out ConfigStickInputId lStick);
|
Enum.TryParse(_lStick.Label, out ConfigStickInputId lStick);
|
||||||
Enum.TryParse(_lStickButton.Label, out ConfigGamepadInputId lStickButton);
|
Enum.TryParse(_lStickButton.Label, out ConfigGamepadInputId lStickButton);
|
||||||
Enum.TryParse(_minus.Label, out ConfigGamepadInputId lButtonMinus);
|
Enum.TryParse(_minus.Label, out ConfigGamepadInputId lButtonMinus);
|
||||||
|
Enum.TryParse(_screenshot.Label, out ConfigGamepadInputId lButtonScreenshot);
|
||||||
Enum.TryParse(_l.Label, out ConfigGamepadInputId lButtonL);
|
Enum.TryParse(_l.Label, out ConfigGamepadInputId lButtonL);
|
||||||
Enum.TryParse(_zL.Label, out ConfigGamepadInputId lButtonZl);
|
Enum.TryParse(_zL.Label, out ConfigGamepadInputId lButtonZl);
|
||||||
Enum.TryParse(_lSl.Label, out ConfigGamepadInputId lButtonSl);
|
Enum.TryParse(_lSl.Label, out ConfigGamepadInputId lButtonSl);
|
||||||
|
@ -710,6 +718,7 @@ namespace Ryujinx.UI.Windows
|
||||||
LeftJoycon = new LeftJoyconCommonConfig<ConfigGamepadInputId>
|
LeftJoycon = new LeftJoyconCommonConfig<ConfigGamepadInputId>
|
||||||
{
|
{
|
||||||
ButtonMinus = lButtonMinus,
|
ButtonMinus = lButtonMinus,
|
||||||
|
ButtonScreenshot = lButtonScreenshot,
|
||||||
ButtonL = lButtonL,
|
ButtonL = lButtonL,
|
||||||
ButtonZl = lButtonZl,
|
ButtonZl = lButtonZl,
|
||||||
ButtonSl = lButtonSl,
|
ButtonSl = lButtonSl,
|
||||||
|
@ -997,6 +1006,7 @@ namespace Ryujinx.UI.Windows
|
||||||
DpadLeft = Key.Left,
|
DpadLeft = Key.Left,
|
||||||
DpadRight = Key.Right,
|
DpadRight = Key.Right,
|
||||||
ButtonMinus = Key.Minus,
|
ButtonMinus = Key.Minus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard already has a default screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonL = Key.E,
|
ButtonL = Key.E,
|
||||||
ButtonZl = Key.Q,
|
ButtonZl = Key.Q,
|
||||||
ButtonSl = Key.Unbound,
|
ButtonSl = Key.Unbound,
|
||||||
|
@ -1057,6 +1067,7 @@ namespace Ryujinx.UI.Windows
|
||||||
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
||||||
DpadRight = ConfigGamepadInputId.DpadRight,
|
DpadRight = ConfigGamepadInputId.DpadRight,
|
||||||
ButtonMinus = ConfigGamepadInputId.Minus,
|
ButtonMinus = ConfigGamepadInputId.Minus,
|
||||||
|
ButtonScreenshot = ConfigGamepadInputId.Misc1,
|
||||||
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
||||||
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
||||||
ButtonSl = ConfigGamepadInputId.Unbound,
|
ButtonSl = ConfigGamepadInputId.Unbound,
|
||||||
|
|
|
@ -475,6 +475,31 @@
|
||||||
<property name="top_attach">4</property>
|
<property name="top_attach">4</property>
|
||||||
</packing>
|
</packing>
|
||||||
</child>
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkLabel">
|
||||||
|
<property name="width_request">80</property>
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Screenshot</property>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">6</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkToggleButton" id="_screenshot">
|
||||||
|
<property name="label" translatable="yes"> </property>
|
||||||
|
<property name="width_request">70</property>
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="receives_default">True</property>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">1</property>
|
||||||
|
<property name="top_attach">6</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="expand">False</property>
|
<property name="expand">False</property>
|
||||||
|
|
|
@ -14,7 +14,7 @@ namespace Ryujinx.HLE.HOS.Services.SurfaceFlinger
|
||||||
{
|
{
|
||||||
private readonly MemoryOwner<byte> _rawDataOwner;
|
private readonly MemoryOwner<byte> _rawDataOwner;
|
||||||
|
|
||||||
private Span<byte> Raw => _rawDataOwner.Memory.Span;
|
private Span<byte> Raw => _rawDataOwner.Span;
|
||||||
|
|
||||||
private ref ParcelHeader Header => ref MemoryMarshal.Cast<byte, ParcelHeader>(Raw)[0];
|
private ref ParcelHeader Header => ref MemoryMarshal.Cast<byte, ParcelHeader>(Raw)[0];
|
||||||
|
|
||||||
|
|
|
@ -161,6 +161,7 @@ namespace Ryujinx.Headless.SDL2
|
||||||
DpadLeft = Key.Left,
|
DpadLeft = Key.Left,
|
||||||
DpadRight = Key.Right,
|
DpadRight = Key.Right,
|
||||||
ButtonMinus = Key.Minus,
|
ButtonMinus = Key.Minus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard already has a default screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonL = Key.E,
|
ButtonL = Key.E,
|
||||||
ButtonZl = Key.Q,
|
ButtonZl = Key.Q,
|
||||||
ButtonSl = Key.Unbound,
|
ButtonSl = Key.Unbound,
|
||||||
|
@ -221,6 +222,7 @@ namespace Ryujinx.Headless.SDL2
|
||||||
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
||||||
DpadRight = ConfigGamepadInputId.DpadRight,
|
DpadRight = ConfigGamepadInputId.DpadRight,
|
||||||
ButtonMinus = ConfigGamepadInputId.Minus,
|
ButtonMinus = ConfigGamepadInputId.Minus,
|
||||||
|
ButtonScreenshot = ConfigGamepadInputId.Misc1,
|
||||||
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
||||||
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
||||||
ButtonSl = ConfigGamepadInputId.Unbound,
|
ButtonSl = ConfigGamepadInputId.Unbound,
|
||||||
|
|
|
@ -244,6 +244,7 @@ namespace Ryujinx.Input.SDL2
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (GamepadButtonInputId)_configuration.LeftJoycon.DpadLeft));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (GamepadButtonInputId)_configuration.LeftJoycon.DpadLeft));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (GamepadButtonInputId)_configuration.LeftJoycon.DpadRight));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (GamepadButtonInputId)_configuration.LeftJoycon.DpadRight));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonMinus));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonMinus));
|
||||||
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Misc1, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonScreenshot));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonL));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonL));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonZl));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonZl));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonSr));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (GamepadButtonInputId)_configuration.LeftJoycon.ButtonSr));
|
||||||
|
|
|
@ -372,6 +372,7 @@ namespace Ryujinx.Input.SDL2
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
||||||
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Misc1, (Key)_configuration.LeftJoycon.ButtonScreenshot));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
|
using Ryujinx.Common.Memory;
|
||||||
using System;
|
using System;
|
||||||
using System.Buffers;
|
|
||||||
|
|
||||||
namespace Ryujinx.Memory
|
namespace Ryujinx.Memory
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Ryujinx.Memory
|
||||||
{
|
{
|
||||||
private readonly IWritableBlock _block;
|
private readonly IWritableBlock _block;
|
||||||
private readonly ulong _va;
|
private readonly ulong _va;
|
||||||
private readonly IMemoryOwner<byte> _memoryOwner;
|
private readonly MemoryOwner<byte> _memoryOwner;
|
||||||
private readonly bool _tracked;
|
private readonly bool _tracked;
|
||||||
|
|
||||||
private bool NeedsWriteback => _block != null;
|
private bool NeedsWriteback => _block != null;
|
||||||
|
@ -22,7 +22,7 @@ namespace Ryujinx.Memory
|
||||||
Memory = memory;
|
Memory = memory;
|
||||||
}
|
}
|
||||||
|
|
||||||
public WritableRegion(IWritableBlock block, ulong va, IMemoryOwner<byte> memoryOwner, bool tracked = false)
|
public WritableRegion(IWritableBlock block, ulong va, MemoryOwner<byte> memoryOwner, bool tracked = false)
|
||||||
: this(block, va, memoryOwner.Memory, tracked)
|
: this(block, va, memoryOwner.Memory, tracked)
|
||||||
{
|
{
|
||||||
_memoryOwner = memoryOwner;
|
_memoryOwner = memoryOwner;
|
||||||
|
|
|
@ -888,6 +888,7 @@ namespace Ryujinx.UI.Common.Configuration
|
||||||
DpadLeft = Key.Left,
|
DpadLeft = Key.Left,
|
||||||
DpadRight = Key.Right,
|
DpadRight = Key.Right,
|
||||||
ButtonMinus = Key.Minus,
|
ButtonMinus = Key.Minus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard already has a default screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonL = Key.E,
|
ButtonL = Key.E,
|
||||||
ButtonZl = Key.Q,
|
ButtonZl = Key.Q,
|
||||||
ButtonSl = Key.Unbound,
|
ButtonSl = Key.Unbound,
|
||||||
|
@ -1117,6 +1118,7 @@ namespace Ryujinx.UI.Common.Configuration
|
||||||
DpadLeft = Key.Left,
|
DpadLeft = Key.Left,
|
||||||
DpadRight = Key.Right,
|
DpadRight = Key.Right,
|
||||||
ButtonMinus = Key.Minus,
|
ButtonMinus = Key.Minus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard already has a default screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonL = Key.E,
|
ButtonL = Key.E,
|
||||||
ButtonZl = Key.Q,
|
ButtonZl = Key.Q,
|
||||||
ButtonSl = Key.Unbound,
|
ButtonSl = Key.Unbound,
|
||||||
|
|
|
@ -82,6 +82,7 @@ namespace Ryujinx.Ava
|
||||||
|
|
||||||
private readonly MainWindowViewModel _viewModel;
|
private readonly MainWindowViewModel _viewModel;
|
||||||
private readonly IKeyboard _keyboardInterface;
|
private readonly IKeyboard _keyboardInterface;
|
||||||
|
private readonly List<IGamepad> _gamepadInterfaces;
|
||||||
private readonly TopLevel _topLevel;
|
private readonly TopLevel _topLevel;
|
||||||
public RendererHost RendererHost;
|
public RendererHost RendererHost;
|
||||||
|
|
||||||
|
@ -89,6 +90,8 @@ namespace Ryujinx.Ava
|
||||||
private float _newVolume;
|
private float _newVolume;
|
||||||
private KeyboardHotkeyState _prevHotkeyState;
|
private KeyboardHotkeyState _prevHotkeyState;
|
||||||
|
|
||||||
|
private int _gamepadsChanged; // use atomically via Interlocked
|
||||||
|
|
||||||
private long _lastCursorMoveTime;
|
private long _lastCursorMoveTime;
|
||||||
private bool _isCursorInRenderer = true;
|
private bool _isCursorInRenderer = true;
|
||||||
private bool _ignoreCursorState = false;
|
private bool _ignoreCursorState = false;
|
||||||
|
@ -160,6 +163,13 @@ namespace Ryujinx.Ava
|
||||||
|
|
||||||
_keyboardInterface = (IKeyboard)_inputManager.KeyboardDriver.GetGamepad("0");
|
_keyboardInterface = (IKeyboard)_inputManager.KeyboardDriver.GetGamepad("0");
|
||||||
|
|
||||||
|
_gamepadInterfaces = new List<IGamepad>();
|
||||||
|
|
||||||
|
_inputManager.GamepadDriver.OnGamepadConnected += GamepadConnected;
|
||||||
|
_inputManager.GamepadDriver.OnGamepadDisconnected += GamepadDisconnected;
|
||||||
|
|
||||||
|
RefreshGamepads();
|
||||||
|
|
||||||
NpadManager = _inputManager.CreateNpadManager();
|
NpadManager = _inputManager.CreateNpadManager();
|
||||||
TouchScreenManager = _inputManager.CreateTouchScreenManager();
|
TouchScreenManager = _inputManager.CreateTouchScreenManager();
|
||||||
ApplicationPath = applicationPath;
|
ApplicationPath = applicationPath;
|
||||||
|
@ -1103,6 +1113,11 @@ namespace Ryujinx.Ava
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (Interlocked.Exchange(ref _gamepadsChanged, 0) == 1)
|
||||||
|
{
|
||||||
|
RefreshGamepads();
|
||||||
|
}
|
||||||
|
|
||||||
NpadManager.Update(ConfigurationState.Instance.Graphics.AspectRatio.Value.ToFloat());
|
NpadManager.Update(ConfigurationState.Instance.Graphics.AspectRatio.Value.ToFloat());
|
||||||
|
|
||||||
if (_viewModel.IsActive)
|
if (_viewModel.IsActive)
|
||||||
|
@ -1241,7 +1256,8 @@ namespace Ryujinx.Ava
|
||||||
{
|
{
|
||||||
state = KeyboardHotkeyState.ToggleVSync;
|
state = KeyboardHotkeyState.ToggleVSync;
|
||||||
}
|
}
|
||||||
else if (_keyboardInterface.IsPressed((Key)ConfigurationState.Instance.Hid.Hotkeys.Value.Screenshot))
|
else if (_keyboardInterface.IsPressed((Key)ConfigurationState.Instance.Hid.Hotkeys.Value.Screenshot) ||
|
||||||
|
ButtonPressedOnAnyGamepad(GamepadButtonInputId.Misc1))
|
||||||
{
|
{
|
||||||
state = KeyboardHotkeyState.Screenshot;
|
state = KeyboardHotkeyState.Screenshot;
|
||||||
}
|
}
|
||||||
|
@ -1276,5 +1292,37 @@ namespace Ryujinx.Ava
|
||||||
|
|
||||||
return state;
|
return state;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void GamepadConnected(string id)
|
||||||
|
{
|
||||||
|
Interlocked.Exchange(ref _gamepadsChanged, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void GamepadDisconnected(string id)
|
||||||
|
{
|
||||||
|
Interlocked.Exchange(ref _gamepadsChanged, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void RefreshGamepads()
|
||||||
|
{
|
||||||
|
_gamepadInterfaces.Clear();
|
||||||
|
|
||||||
|
foreach (string id in _inputManager.GamepadDriver.GamepadsIds)
|
||||||
|
{
|
||||||
|
_gamepadInterfaces.Add(_inputManager.GamepadDriver.GetGamepad(id));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool ButtonPressedOnAnyGamepad(GamepadButtonInputId button)
|
||||||
|
{
|
||||||
|
foreach (IGamepad gamepad in _gamepadInterfaces)
|
||||||
|
{
|
||||||
|
if (gamepad.IsPressed(button))
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -233,6 +233,8 @@
|
||||||
"ControllerSettingsDPadDown": "Runter",
|
"ControllerSettingsDPadDown": "Runter",
|
||||||
"ControllerSettingsDPadLeft": "Links",
|
"ControllerSettingsDPadLeft": "Links",
|
||||||
"ControllerSettingsDPadRight": "Rechts",
|
"ControllerSettingsDPadRight": "Rechts",
|
||||||
|
"ControllerSettingsRawScreenshot": "Unbearbeiteter Screenshot",
|
||||||
|
"ControllerSettingsRawScreenshotTooltip": "Macht ein Bildschirmfoto ohne Wasserzeichen etc.",
|
||||||
"ControllerSettingsStickButton": "Button",
|
"ControllerSettingsStickButton": "Button",
|
||||||
"ControllerSettingsStickUp": "Hoch",
|
"ControllerSettingsStickUp": "Hoch",
|
||||||
"ControllerSettingsStickDown": "Runter",
|
"ControllerSettingsStickDown": "Runter",
|
||||||
|
|
|
@ -234,6 +234,8 @@
|
||||||
"ControllerSettingsDPadDown": "Down",
|
"ControllerSettingsDPadDown": "Down",
|
||||||
"ControllerSettingsDPadLeft": "Left",
|
"ControllerSettingsDPadLeft": "Left",
|
||||||
"ControllerSettingsDPadRight": "Right",
|
"ControllerSettingsDPadRight": "Right",
|
||||||
|
"ControllerSettingsRawScreenshot": "Raw Screenshot",
|
||||||
|
"ControllerSettingsRawScreenshotTooltip": "Takes a screenshot without any watermarks etc.",
|
||||||
"ControllerSettingsStickButton": "Button",
|
"ControllerSettingsStickButton": "Button",
|
||||||
"ControllerSettingsStickUp": "Up",
|
"ControllerSettingsStickUp": "Up",
|
||||||
"ControllerSettingsStickDown": "Down",
|
"ControllerSettingsStickDown": "Down",
|
||||||
|
|
|
@ -128,6 +128,7 @@ namespace Ryujinx.Ava.Input
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadLeft, (Key)_configuration.LeftJoycon.DpadLeft));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.DpadRight, (Key)_configuration.LeftJoycon.DpadRight));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Minus, (Key)_configuration.LeftJoycon.ButtonMinus));
|
||||||
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.Misc1, (Key)_configuration.LeftJoycon.ButtonScreenshot));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftShoulder, (Key)_configuration.LeftJoycon.ButtonL));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.LeftTrigger, (Key)_configuration.LeftJoycon.ButtonZl));
|
||||||
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
_buttonsUserMapping.Add(new ButtonMappingEntry(GamepadButtonInputId.SingleRightTrigger0, (Key)_configuration.LeftJoycon.ButtonSr));
|
||||||
|
|
|
@ -178,6 +178,17 @@ namespace Ryujinx.Ava.UI.Models.Input
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private GamepadInputId _buttonScreenshot;
|
||||||
|
public GamepadInputId ButtonScreenshot
|
||||||
|
{
|
||||||
|
get => _buttonScreenshot;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_buttonScreenshot = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private GamepadInputId _buttonL;
|
private GamepadInputId _buttonL;
|
||||||
public GamepadInputId ButtonL
|
public GamepadInputId ButtonL
|
||||||
{
|
{
|
||||||
|
@ -440,6 +451,7 @@ namespace Ryujinx.Ava.UI.Models.Input
|
||||||
DpadRight = controllerInput.LeftJoycon.DpadRight;
|
DpadRight = controllerInput.LeftJoycon.DpadRight;
|
||||||
ButtonL = controllerInput.LeftJoycon.ButtonL;
|
ButtonL = controllerInput.LeftJoycon.ButtonL;
|
||||||
ButtonMinus = controllerInput.LeftJoycon.ButtonMinus;
|
ButtonMinus = controllerInput.LeftJoycon.ButtonMinus;
|
||||||
|
ButtonScreenshot = controllerInput.LeftJoycon.ButtonScreenshot;
|
||||||
LeftButtonSl = controllerInput.LeftJoycon.ButtonSl;
|
LeftButtonSl = controllerInput.LeftJoycon.ButtonSl;
|
||||||
LeftButtonSr = controllerInput.LeftJoycon.ButtonSr;
|
LeftButtonSr = controllerInput.LeftJoycon.ButtonSr;
|
||||||
ButtonZl = controllerInput.LeftJoycon.ButtonZl;
|
ButtonZl = controllerInput.LeftJoycon.ButtonZl;
|
||||||
|
@ -502,6 +514,7 @@ namespace Ryujinx.Ava.UI.Models.Input
|
||||||
DpadRight = DpadRight,
|
DpadRight = DpadRight,
|
||||||
ButtonL = ButtonL,
|
ButtonL = ButtonL,
|
||||||
ButtonMinus = ButtonMinus,
|
ButtonMinus = ButtonMinus,
|
||||||
|
ButtonScreenshot = ButtonScreenshot,
|
||||||
ButtonSl = LeftButtonSl,
|
ButtonSl = LeftButtonSl,
|
||||||
ButtonSr = LeftButtonSr,
|
ButtonSr = LeftButtonSr,
|
||||||
ButtonZl = ButtonZl,
|
ButtonZl = ButtonZl,
|
||||||
|
|
|
@ -381,6 +381,7 @@ namespace Ryujinx.Ava.UI.Models.Input
|
||||||
DpadRight = DpadRight,
|
DpadRight = DpadRight,
|
||||||
ButtonL = ButtonL,
|
ButtonL = ButtonL,
|
||||||
ButtonMinus = ButtonMinus,
|
ButtonMinus = ButtonMinus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonZl = ButtonZl,
|
ButtonZl = ButtonZl,
|
||||||
ButtonSl = LeftButtonSl,
|
ButtonSl = LeftButtonSl,
|
||||||
ButtonSr = LeftButtonSr,
|
ButtonSr = LeftButtonSr,
|
||||||
|
|
|
@ -545,6 +545,7 @@ namespace Ryujinx.Ava.UI.ViewModels.Input
|
||||||
DpadLeft = Key.Left,
|
DpadLeft = Key.Left,
|
||||||
DpadRight = Key.Right,
|
DpadRight = Key.Right,
|
||||||
ButtonMinus = Key.Minus,
|
ButtonMinus = Key.Minus,
|
||||||
|
ButtonScreenshot = Key.Unbound, // keyboard already has a default screenshot configured via ConfigurationState.Hid.Hotkeys.Screenshot, so no gamepad mapping needed
|
||||||
ButtonL = Key.E,
|
ButtonL = Key.E,
|
||||||
ButtonZl = Key.Q,
|
ButtonZl = Key.Q,
|
||||||
ButtonSl = Key.Unbound,
|
ButtonSl = Key.Unbound,
|
||||||
|
@ -605,6 +606,7 @@ namespace Ryujinx.Ava.UI.ViewModels.Input
|
||||||
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
DpadLeft = ConfigGamepadInputId.DpadLeft,
|
||||||
DpadRight = ConfigGamepadInputId.DpadRight,
|
DpadRight = ConfigGamepadInputId.DpadRight,
|
||||||
ButtonMinus = ConfigGamepadInputId.Minus,
|
ButtonMinus = ConfigGamepadInputId.Minus,
|
||||||
|
ButtonScreenshot = ConfigGamepadInputId.Misc1,
|
||||||
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
ButtonL = ConfigGamepadInputId.LeftShoulder,
|
||||||
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
ButtonZl = ConfigGamepadInputId.LeftTrigger,
|
||||||
ButtonSl = ConfigGamepadInputId.Unbound,
|
ButtonSl = ConfigGamepadInputId.Unbound,
|
||||||
|
|
|
@ -311,6 +311,36 @@
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</Border>
|
</Border>
|
||||||
|
<!-- Screenshot -->
|
||||||
|
<Border
|
||||||
|
BorderBrush="{DynamicResource ThemeControlBorderColor}"
|
||||||
|
BorderThickness="1"
|
||||||
|
IsVisible="{Binding IsLeft}"
|
||||||
|
Margin="0,5,0,0"
|
||||||
|
CornerRadius="5">
|
||||||
|
<StackPanel
|
||||||
|
Margin="10"
|
||||||
|
Orientation="Vertical">
|
||||||
|
<!-- Raw Screenshot -->
|
||||||
|
<StackPanel
|
||||||
|
Margin="0,0,0,4"
|
||||||
|
Orientation="Horizontal">
|
||||||
|
<TextBlock
|
||||||
|
Margin="0,0,10,0"
|
||||||
|
Width="120"
|
||||||
|
HorizontalAlignment="Center"
|
||||||
|
VerticalAlignment="Center"
|
||||||
|
Text="{locale:Locale ControllerSettingsRawScreenshot}"
|
||||||
|
ToolTip.Tip="{locale:Locale ControllerSettingsRawScreenshotTooltip}"
|
||||||
|
TextAlignment="Center" />
|
||||||
|
<ToggleButton Name="ButtonScreenshot">
|
||||||
|
<TextBlock
|
||||||
|
Text="{Binding Config.ButtonScreenshot, Converter={StaticResource Key}}"
|
||||||
|
TextAlignment="Center" />
|
||||||
|
</ToggleButton>
|
||||||
|
</StackPanel>
|
||||||
|
</StackPanel>
|
||||||
|
</Border>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
<!-- Triggers & Side Buttons -->
|
<!-- Triggers & Side Buttons -->
|
||||||
<StackPanel
|
<StackPanel
|
||||||
|
|
|
@ -84,6 +84,9 @@ namespace Ryujinx.Ava.UI.Views.Input
|
||||||
case "ButtonMinus":
|
case "ButtonMinus":
|
||||||
viewModel.Config.ButtonMinus = buttonValue.AsHidType<GamepadInputId>();
|
viewModel.Config.ButtonMinus = buttonValue.AsHidType<GamepadInputId>();
|
||||||
break;
|
break;
|
||||||
|
case "ButtonScreenshot":
|
||||||
|
viewModel.Config.ButtonScreenshot = buttonValue.AsHidType<GamepadInputId>();
|
||||||
|
break;
|
||||||
case "LeftStickButton":
|
case "LeftStickButton":
|
||||||
viewModel.Config.LeftStickButton = buttonValue.AsHidType<GamepadInputId>();
|
viewModel.Config.LeftStickButton = buttonValue.AsHidType<GamepadInputId>();
|
||||||
break;
|
break;
|
||||||
|
|
Loading…
Reference in New Issue