Windows uygulamalarında dokunsal geri bildirim uygulama

Bu makalede, yaygın etkileşim desenleri için kod örnekleri de dahil olmak üzere InputHapticsManager API'sini kullanarak Windows uygulamanıza nasıl dokunsal geri bildirim ekleyebileceğiniz açıklanır.

Haptics'in ne zaman ve neden kullanılacağına ilişkin tasarım kılavuzu için bkz. Haptics tasarım yönergeleri.

Desteklenen cihazlar

Fare, dokunmatik yüzey ve kalem gibi giriş cihazlarında dokunsal geri bildirim desteklenir. Kullanılabilirlik modele ve üreticiye göre değişir. Haptics API'lerini çağırmadan önce her zaman çalışma zamanında destek olup olmadığını denetleyin (aşağıdaki desteğe bakın ).

Requirements

Requirement Ayrıntılar
Namespace Windows.Devices.Haptics
En düşük işletim sistemi Windows 11, SDK 10.0.28000.1721 (Mart 2026)
Hizala / Çarpıştır / Adımla / Dalga formlarını büyüt SDK 10.0.28000.1839 (Nisan 2026)
API sözleşmesi UniversalApiContract sürüm 19.0

Önceki işletim sistemi sürümlerini hedeflemek için tüm çağrıları korumak için kullanın ApiInformation.IsTypePresent (aşağıdaki koda bakın).

Destek olup olmadığını denetleyin

Api'nin kullanılabilir olduğunu ve kullanımdan önce bir dokunsal cihazın mevcut olduğunu her zaman doğrulayın. API eski işletim sistemi sürümlerinde mevcut değildir ve tüm giriş cihazları haptics'i desteklemez.

using Windows.Devices.Haptics;
using Windows.Foundation.Metadata;

// Guard against older OS versions where the API is absent.
bool apiPresent = ApiInformation.IsTypePresent("Windows.Devices.Haptics.InputHapticsManager");

// Check that a supported haptic device is connected.
bool supported = apiPresent && InputHapticsManager.IsSupported();

Dalga formunu tetikleme

Geçerli iş parçacığının giriş odağıyla ilişkili bir yönetici örneği elde etmek için UI iş parçacığında InputHapticsManager.GetForCurrentThread() çağrısını yapın. Cihaz algılama ve yönlendirme otomatik olarak işlenir; cihazları kendiniz listelemeniz gerekmez.

using Windows.Devices.Haptics;

if (supported)
{
    var mgr = InputHapticsManager.GetForCurrentThread();

    // The second parameter is a fallback waveform used if the first is
    // unsupported. Passing 0 lets the system choose a device-appropriate
    // fallback. TrySendHapticWaveform returns false if neither waveform is
    // supported; this is a non-fatal condition.
    bool sent = mgr.TrySendHapticWaveform(
        KnownSimpleHapticsControllerWaveforms.Align,
        0);
}

Önemli

GetForCurrentThread() öğesini kullanıcı arabirimi iş parçacığından (veya giriş odağına sahip iş parçacığından) çağırın. Arka plan iş parçacığından çağırmak geri bildirimi doğru cihaza yönlendirmez.

Oynatmayı durdur

Sürükleme veya etkileşim sona erdiğinde, devam eden dokunsal geri bildirim oynatımını durdurmak için TryStopFeedback çağırın.

using Windows.Devices.Haptics;

if (supported)
{
    InputHapticsManager
        .GetForCurrentThread()
        .TryStopFeedback();
}

Uygulama örneği

Nesne hizalama

Hizalama kılavuzları tasarım araçları, sunu düzenleyicileri ve diyagram oluşturma uygulamalarında yaygındır. Dokunsal geri bildirim, kullanıcıların nesnelerin yerine yerleştirildiğinde hissedebilmesi için ikinci bir kanal ekler ve böylece hizalamayı görsel olarak onaylamak için yakınlaştırma gereksinimini azaltır.

Ne zaman tetiklenecek: Hizalama kılavuzunun görünümünü tetikleyici olarak kullanın. Yakalama mantığınız bir kılavuz çizgisi gösterdiğinde, dokunsal geri bildirimi tetikleyin. Kılavuz görünmüyorsa, ateş etmeyin. Bu, dokunsal olayları görünür sistem geri bildirimleriyle sıkı bir şekilde bir arada tutar.

Yinelenenlerden kaçının: Şekil aynı anda birden çok kılavuza hizalanabilir (örneğin, sol kenar ve üst kenar). Bunu tek bir etkileşim olarak değerlendirin; etkin kılavuzları izleyin ve yalnızca yeni bir kılavuz görüntülendiğinde ateş edin.

using Windows.Devices.Haptics;

private readonly HashSet<int> _activeGuides = new();

// Call this after computing which alignment guides are currently visible.
void OnGuidesUpdated(IEnumerable<int> currentGuideIds)
{
    var currentGuides = currentGuideIds.ToHashSet();

    bool hasNewGuide = currentGuides.Except(_activeGuides).Any();

    // Update the tracked set in place (field is readonly).
    _activeGuides.Clear();
    _activeGuides.UnionWith(currentGuides);

    if (hasNewGuide && supported)
    {
        InputHapticsManager.GetForCurrentThread()
            .TrySendHapticWaveform(
                KnownSimpleHapticsControllerWaveforms.Align,
                0);
    }
}

Sliders

Haptics, geri bildirimleri anlamlı konumlara sabitleyerek kaydırıcı etkileşimlerini geliştirir. Geri bildirimleri her zaman kullanıcının anlayabileceği görünür işaretçilere (değer çizgileri, adlandırılmış değerler veya aralık sınırları) bağlayın.

Ne zaman tetiklenmeli: Başparmak her bir işareti geçtiğinde dokunsal geri bildirimi tetikleyin. Tik sesleri arasında kesintisiz geri bildirim kullanmaktan kaçının; bu dikkat dağıtıcı olabilir.

using Windows.Devices.Haptics;

double _previousValue;
const double TickInterval = 25.0;

void OnSliderValueChanged(double newValue)
{
    int previousTick = (int)(_previousValue / TickInterval);
    int currentTick  = (int)(newValue       / TickInterval);

    if (currentTick != previousTick && supported)
    {
        InputHapticsManager.GetForCurrentThread()
            .TrySendHapticWaveform(
                KnownSimpleHapticsControllerWaveforms.Step,
                0);
    }

    _previousValue = newValue;
}

Deneyimi iyileştirme: Kullanıcıların aralık içinde nerede olduklarını anlamalarına yardımcı olmak için kaydırıcı konumuna göre dokunsal yoğunluğu ölçeklendirin. TrySendHapticWaveformForPlayCount ile 0.0 arasında açıkça belirtilmiş bir yoğunluk değerini kabul eden 1.0'ı kullanın.

void OnSliderValueChangedWithIntensity(double newValue, double maxValue)
{
    int previousTick = (int)(_previousValue / TickInterval);
    int currentTick  = (int)(newValue       / TickInterval);

    if (currentTick != previousTick && supported)
    {
        double intensity = newValue / maxValue; // Scale 0.0–1.0

        InputHapticsManager.GetForCurrentThread()
            .TrySendHapticWaveformForPlayCount(
                KnownSimpleHapticsControllerWaveforms.Step,
                0,          // fallback waveform
                intensity,
                1,          // playCount
                TimeSpan.Zero);
    }

    _previousValue = newValue;
}

Sürükleme etkileşimleri ve niyet algılama

Sürükleme sırasında, bir nesne sayfa merkezi, kılavuzlar ve diğer nesneler gibi birçok hizalama sınırını geçebilir. Her geçişte haptiklerin tetiklenmesi, özellikle de hassas olmaya çalışmak yerine yeniden konumlandırılırken hızlı hareketlerde kullanıcıları bunaltabilir.

Geri bildirimi, yalnızca kullanıcı kasıtlı olarak hizalanmaya çalıştığında tetiklemek için niyet algılama kullanın; kullanıcı yalnızca oradan geçerken değil.

Yaklaşım 1: Hız filtresi

İmleç hızla hareket ederken haptik geri bildirimi bastırın; geri bildirimi daha yavaş ve daha kontrollü hareketler için ayırın.

  • Sinyali kararlı hale getir. Giriş türlerine, DPI ayarlarına ve ekran yapılandırmalarına bağlı olarak tutarsız sonuçlar verebilen ham imleç delta değerlerini kullanmaktan kaçının. Sinyali normalleştirin ve düzeltin.
  • Bir eşiği dikkatle seçin. Farklı cihazlarda, giriş türlerinde, görüntü ölçeklerinde ve çok ekranlı kurulumlarda doğrulama yapın.

Yaklaşım 2: Süreölçer ayırma

Bir nesne bir tetikleyici bölgesine girdiğinde kısa bir süreölçer başlatın (50 ms makul bir başlangıç noktasıdır). Nesne, zamanlayıcı süresi dolduğunda hâlâ bölgedeyse bunun kasıtlı olduğunu kabul edin ve dokunsal geri bildirimi tetikleyin. Nesne, zamanlayıcı tetiklenmeden önce yoluna devam ederse geri bildirimi engelleyin.

  • Uygulanması daha kolaydır ve hız filtrelemeden daha kararlı davranışlar üretme eğilimindedir.
  • 50 ms gecikme, kasıtlı hizalamayı hızlı geçişten ayırt etmek için yeterlidir ve fark edilebilir gecikme eşiğinin altında kalır.
using System;
using Microsoft.UI.Xaml;
using Windows.Devices.Haptics;

private DispatcherTimer? _alignTimer;

void OnObjectEnteredAlignmentZone()
{
    _alignTimer?.Stop();
    _alignTimer = new DispatcherTimer { Interval = TimeSpan.FromMilliseconds(50) };
    _alignTimer.Tick += (_, _) =>
    {
        _alignTimer.Stop();
        if (supported)
        {
            InputHapticsManager.GetForCurrentThread()
                .TrySendHapticWaveform(
                    KnownSimpleHapticsControllerWaveforms.Align,
                    0);
        }
    };
    _alignTimer.Start();
}

void OnObjectLeftAlignmentZone()
{
    _alignTimer?.Stop();
}

İkisi arasında seçim

Hız filtresi Süreölçer kaldırma
Nasıl çalışır Reaktif— hareketi gerçek zamanlı olarak ölçer Tahmine dayalı— amacı onaylamak için kısa süre bekler
Hissedin Daha doğrudan hissedilebilir Biraz gecikmiş, ancak daha tutarlı
İnce ayar çabası Daha yüksek— dikkatli kalibrasyon gerektirir Daha düşük— tek bir gecikme değeri genellikle yeterlidir
için önerilir Yüksek oranda yanıt veren geri bildirim gerektiren uygulamalar Çoğu uygulama; iyi varsayılan başlangıç noktası