mirror of
https://github.com/vale981/VoiDPlugins
synced 2025-03-04 16:51:38 -05:00
Fix relative mode issues
This commit is contained in:
parent
aa6c011fd8
commit
59eed1faa5
9 changed files with 84 additions and 90 deletions
|
@ -20,13 +20,17 @@ namespace VoiDPlugins.OutputMode
|
|||
|
||||
public VMultiAbsolutePointer(TabletReference tabletReference, IVirtualScreen virtualScreen)
|
||||
{
|
||||
_instance = new VMultiInstance<AbsoluteInputReport>("VMultiAbs", new AbsoluteInputReport());
|
||||
var sharedStore = SharedStore.GetStore(tabletReference, STORE_KEY);
|
||||
if (!sharedStore.TryAdd(INSTANCE, _instance))
|
||||
_instance = sharedStore.Get<VMultiInstance<AbsoluteInputReport>>(INSTANCE);
|
||||
|
||||
_instance = sharedStore.GetOrUpdate(ABS_INSTANCE, createInstance, out _);
|
||||
_rawPointer = _instance.Pointer;
|
||||
_conversionFactor = new Vector2(32767, 32767) / new Vector2(virtualScreen.Width, virtualScreen.Height);
|
||||
|
||||
sharedStore.SetOrAdd(MODE, ABS_INSTANCE);
|
||||
|
||||
static VMultiInstance<AbsoluteInputReport> createInstance()
|
||||
{
|
||||
return new VMultiInstance<AbsoluteInputReport>("VMultiAbs", new AbsoluteInputReport());
|
||||
}
|
||||
}
|
||||
|
||||
public void SetPosition(Vector2 pos)
|
||||
|
|
|
@ -18,20 +18,22 @@ namespace VoiDPlugins.OutputMode
|
|||
|
||||
public VMultiRelativePointer(TabletReference tabletReference)
|
||||
{
|
||||
_instance = new VMultiInstance<RelativeInputReport>("VMultiRel", new RelativeInputReport());
|
||||
var sharedStore = SharedStore.GetStore(tabletReference, STORE_KEY);
|
||||
if (!sharedStore.TryAdd(INSTANCE, _instance))
|
||||
_instance = sharedStore.Get<VMultiInstance<RelativeInputReport>>(INSTANCE);
|
||||
|
||||
_instance = sharedStore.GetOrUpdate(REL_INSTANCE, createInstance, out var updated);
|
||||
_rawPointer = _instance.Pointer;
|
||||
|
||||
sharedStore.SetOrAdd(MODE, REL_INSTANCE);
|
||||
|
||||
static VMultiInstance<RelativeInputReport> createInstance()
|
||||
{
|
||||
return new VMultiInstance<RelativeInputReport>("VMultiRel", new RelativeInputReport());
|
||||
}
|
||||
}
|
||||
|
||||
public void SetPosition(Vector2 delta)
|
||||
{
|
||||
if (delta == Vector2.Zero && _prev == Vector2.Zero)
|
||||
return;
|
||||
if (_rawPointer is null)
|
||||
return;
|
||||
|
||||
delta += _error;
|
||||
_error = new Vector2(delta.X % 1, delta.Y % 1);
|
||||
|
|
|
@ -33,7 +33,9 @@ namespace VoiDPlugins.OutputMode
|
|||
{
|
||||
try
|
||||
{
|
||||
_instance = SharedStore.GetStore(tabletReference, STORE_KEY).Get<VMultiInstance>(INSTANCE);
|
||||
var sharedStore = SharedStore.GetStore(tabletReference, STORE_KEY);
|
||||
var mode = sharedStore.Get<int>(MODE);
|
||||
_instance = sharedStore.Get<VMultiInstance>(mode);
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
|
|
@ -3,6 +3,8 @@ namespace VoiDPlugins.OutputMode
|
|||
public static class VMultiModeConstants
|
||||
{
|
||||
public const string STORE_KEY = "VMultiMode";
|
||||
public const int INSTANCE = 0;
|
||||
public const int MODE = 0;
|
||||
public const int ABS_INSTANCE = 1;
|
||||
public const int REL_INSTANCE = 2;
|
||||
}
|
||||
}
|
|
@ -7,13 +7,11 @@ namespace VoiDPlugins.OutputMode
|
|||
{
|
||||
public unsafe class WinInkAbsolutePointer : WinInkBasePointer, IAbsolutePointer
|
||||
{
|
||||
private readonly Vector2 _conversionFactor;
|
||||
private Vector2 _prev;
|
||||
|
||||
public WinInkAbsolutePointer(TabletReference tabletReference, IVirtualScreen screen)
|
||||
: base("Windows Ink", tabletReference, screen)
|
||||
{
|
||||
_conversionFactor = new Vector2(32767, 32767) / new Vector2(screen.Width, screen.Height);
|
||||
}
|
||||
|
||||
public void SetPosition(Vector2 pos)
|
||||
|
@ -23,7 +21,7 @@ namespace VoiDPlugins.OutputMode
|
|||
|
||||
SetInternalPosition(pos);
|
||||
Instance.EnableButtonBit((int)WindowsInkButtonFlags.InRange);
|
||||
pos *= _conversionFactor;
|
||||
pos = Convert(pos);
|
||||
RawPointer->X = (ushort)pos.X;
|
||||
RawPointer->Y = (ushort)pos.Y;
|
||||
Dirty = true;
|
||||
|
|
|
@ -12,6 +12,7 @@ namespace VoiDPlugins.OutputMode
|
|||
{
|
||||
public unsafe abstract class WinInkBasePointer : IPressureHandler, ITiltHandler, IEraserHandler, ISynchronousPointer
|
||||
{
|
||||
private readonly Vector2 _conversionFactor;
|
||||
private readonly IVirtualScreen _screen;
|
||||
private ThinOSPointer? _osPointer;
|
||||
private Vector2 _internalPos;
|
||||
|
@ -30,20 +31,22 @@ namespace VoiDPlugins.OutputMode
|
|||
public WinInkBasePointer(string name, TabletReference tabletReference, IVirtualScreen screen)
|
||||
{
|
||||
_screen = screen;
|
||||
Instance = new VMultiInstance<DigitizerInputReport>(name, new DigitizerInputReport());
|
||||
_conversionFactor = new Vector2(32767, 32767) / new Vector2(screen.Width, screen.Height);
|
||||
SharedStore = SharedStore.GetStore(tabletReference, STORE_KEY);
|
||||
if (SharedStore.TryAdd(INSTANCE, Instance))
|
||||
Instance = SharedStore.GetOrUpdate(INSTANCE, createInstance, out var updated);
|
||||
RawPointer = Instance.Pointer;
|
||||
|
||||
if (updated)
|
||||
{
|
||||
SharedStore.TryAdd(POINTER, this);
|
||||
SharedStore.TryAdd(ERASER_STATE, false);
|
||||
SharedStore.TryAdd(MANUAL_ERASER, false);
|
||||
SharedStore.TryAdd(TIP_PRESSED, false);
|
||||
RawPointer = Instance.Pointer;
|
||||
SharedStore.SetOrAdd(POINTER, this);
|
||||
SharedStore.SetOrAdd(ERASER_STATE, false);
|
||||
SharedStore.SetOrAdd(MANUAL_ERASER, false);
|
||||
SharedStore.SetOrAdd(TIP_PRESSED, false);
|
||||
}
|
||||
else
|
||||
|
||||
VMultiInstance<DigitizerInputReport> createInstance()
|
||||
{
|
||||
Instance = SharedStore.Get<VMultiInstance<DigitizerInputReport>>(INSTANCE);
|
||||
RawPointer = Instance.Pointer;
|
||||
return new VMultiInstance<DigitizerInputReport>(name, new DigitizerInputReport());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -87,6 +90,11 @@ namespace VoiDPlugins.OutputMode
|
|||
}
|
||||
}
|
||||
|
||||
protected Vector2 Convert(Vector2 pos)
|
||||
{
|
||||
return pos * _conversionFactor;
|
||||
}
|
||||
|
||||
protected void SetInternalPosition(Vector2 pos)
|
||||
{
|
||||
_internalPos = pos;
|
||||
|
|
|
@ -21,16 +21,18 @@ namespace VoiDPlugins.OutputMode
|
|||
|
||||
public void SetPosition(Vector2 delta)
|
||||
{
|
||||
if (_prev == Vector2.Zero && delta == Vector2.Zero)
|
||||
if (delta == Vector2.Zero)
|
||||
return;
|
||||
|
||||
Instance.EnableButtonBit((int)WindowsInkButtonFlags.InRange);
|
||||
delta += _error;
|
||||
_error = new Vector2(delta.X % 1, delta.Y % 1);
|
||||
_currentPoint = Vector2.Clamp(_currentPoint + delta, Vector2.Zero, _maxPoint);
|
||||
|
||||
SetInternalPosition(_currentPoint);
|
||||
RawPointer->X = (ushort)_currentPoint.X;
|
||||
RawPointer->Y = (ushort)_currentPoint.Y;
|
||||
Instance.EnableButtonBit((int)WindowsInkButtonFlags.InRange);
|
||||
var pos = Convert(_currentPoint);
|
||||
RawPointer->X = (ushort)pos.X;
|
||||
RawPointer->Y = (ushort)pos.Y;
|
||||
Dirty = true;
|
||||
_prev = delta;
|
||||
}
|
||||
|
|
|
@ -97,7 +97,7 @@ namespace VoiDPlugins.OutputMode
|
|||
_instance.Write();
|
||||
}
|
||||
|
||||
public static void EraserStateTransition(SharedStore store, VMultiInstance instance, bool isEraser)
|
||||
internal static void EraserStateTransition(SharedStore store, VMultiInstance instance, bool isEraser)
|
||||
{
|
||||
var eraserState = store.Get<bool>(ERASER_STATE);
|
||||
if (eraserState != isEraser)
|
||||
|
|
|
@ -1,23 +1,16 @@
|
|||
using System.Collections;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.Runtime.InteropServices;
|
||||
using OpenTabletDriver.Plugin.Tablet;
|
||||
|
||||
namespace VoiDPlugins.Library.VoiD
|
||||
{
|
||||
public class SharedStore : IDictionary<int, object>
|
||||
public class SharedStore
|
||||
{
|
||||
private static readonly Dictionary<TabletReference, Dictionary<string, SharedStore>> _storeMap = new(new Comparer());
|
||||
|
||||
private readonly Dictionary<int, object> _sharedStore = new();
|
||||
|
||||
public object this[int key] { get => ((IDictionary<int, object>)_sharedStore)[key]; set => ((IDictionary<int, object>)_sharedStore)[key] = value; }
|
||||
public ICollection<int> Keys => ((IDictionary<int, object>)_sharedStore).Keys;
|
||||
public ICollection<object> Values => ((IDictionary<int, object>)_sharedStore).Values;
|
||||
public int Count => ((ICollection<KeyValuePair<int, object>>)_sharedStore).Count;
|
||||
public bool IsReadOnly => ((ICollection<KeyValuePair<int, object>>)_sharedStore).IsReadOnly;
|
||||
|
||||
public static SharedStore GetStore(TabletReference reference, string storeKey)
|
||||
{
|
||||
lock (_storeMap)
|
||||
|
@ -39,69 +32,52 @@ namespace VoiDPlugins.Library.VoiD
|
|||
return (T)_sharedStore[key];
|
||||
}
|
||||
|
||||
public T GetOrUpdate<T>(int key, Func<T> valueFactory, out bool updated)
|
||||
{
|
||||
if (_sharedStore.TryGetValue(key, out object? value) && SafeCast<T>(value) is T casted)
|
||||
{
|
||||
updated = false;
|
||||
return casted;
|
||||
}
|
||||
|
||||
var newValue = valueFactory();
|
||||
_sharedStore[key] = newValue!;
|
||||
updated = true;
|
||||
return newValue;
|
||||
}
|
||||
|
||||
public void Set<T>(int key, T value)
|
||||
{
|
||||
_sharedStore[key] = value!;
|
||||
}
|
||||
|
||||
public void Add(int key, object value)
|
||||
public void Add<T>(int key, T value)
|
||||
{
|
||||
((IDictionary<int, object>)_sharedStore).Add(key, value);
|
||||
_sharedStore.Add(key, value!);
|
||||
}
|
||||
|
||||
public bool TryAdd(int key, object value)
|
||||
public void SetOrAdd<T>(int key, T value)
|
||||
{
|
||||
return _sharedStore.TryAdd(key, value);
|
||||
if (_sharedStore.ContainsKey(key))
|
||||
{
|
||||
_sharedStore[key] = value!;
|
||||
}
|
||||
else
|
||||
{
|
||||
_sharedStore.Add(key, value!);
|
||||
}
|
||||
}
|
||||
|
||||
public void Add(KeyValuePair<int, object> item)
|
||||
private static T? SafeCast<T>(object value)
|
||||
{
|
||||
((ICollection<KeyValuePair<int, object>>)_sharedStore).Add(item);
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
((ICollection<KeyValuePair<int, object>>)_sharedStore).Clear();
|
||||
}
|
||||
|
||||
public bool Contains(KeyValuePair<int, object> item)
|
||||
{
|
||||
return ((ICollection<KeyValuePair<int, object>>)_sharedStore).Contains(item);
|
||||
}
|
||||
|
||||
public bool ContainsKey(int key)
|
||||
{
|
||||
return ((IDictionary<int, object>)_sharedStore).ContainsKey(key);
|
||||
}
|
||||
|
||||
public void CopyTo(KeyValuePair<int, object>[] array, int arrayIndex)
|
||||
{
|
||||
((ICollection<KeyValuePair<int, object>>)_sharedStore).CopyTo(array, arrayIndex);
|
||||
}
|
||||
|
||||
public IEnumerator<KeyValuePair<int, object>> GetEnumerator()
|
||||
{
|
||||
return ((IEnumerable<KeyValuePair<int, object>>)_sharedStore).GetEnumerator();
|
||||
}
|
||||
|
||||
public bool Remove(int key)
|
||||
{
|
||||
return ((IDictionary<int, object>)_sharedStore).Remove(key);
|
||||
}
|
||||
|
||||
public bool Remove(KeyValuePair<int, object> item)
|
||||
{
|
||||
return ((ICollection<KeyValuePair<int, object>>)_sharedStore).Remove(item);
|
||||
}
|
||||
|
||||
public bool TryGetValue(int key, [MaybeNullWhen(false)] out object value)
|
||||
{
|
||||
return ((IDictionary<int, object>)_sharedStore).TryGetValue(key, out value);
|
||||
}
|
||||
|
||||
IEnumerator IEnumerable.GetEnumerator()
|
||||
{
|
||||
return ((IEnumerable)_sharedStore).GetEnumerator();
|
||||
try
|
||||
{
|
||||
return (T)value;
|
||||
}
|
||||
catch
|
||||
{
|
||||
return default;
|
||||
}
|
||||
}
|
||||
|
||||
private class Comparer : IEqualityComparer<TabletReference>
|
||||
|
|
Loading…
Add table
Reference in a new issue