useValueNotifierToSignal<T> function

Signal<T> useValueNotifierToSignal<T>(
  1. ValueNotifier<T> value, {
  2. List<Object?> keys = const <Object>[],
  3. SignalOptions<T>? options,
})

Creates a new mutable Signal from a ValueNotifier and subscribes to it.

This provides interoperability with standard Flutter classes, allowing you to bridge a ValueNotifier into a fully reactive Signal container. Changes made to the ValueNotifier automatically update the signal, and changes made to the signal automatically write back to the ValueNotifier.

:::tip This enables seamless bi-directional integration when working with external packages or existing widgets that rely heavily on ValueNotifier. :::

Parameters

  • value: The ValueNotifier to bridge.
  • keys: A list of objects to watch. If any key changes, the signal is re-created.
  • debugLabel: An optional debug label.

Example

import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:signals_hooks/signals_hooks.dart';

class LegacyBridgeWidget extends HookWidget {
  const LegacyBridgeWidget({super.key});

  @override
  Widget build(BuildContext context) {
    final notifier = useValueNotifier(0);
    // Bridge the standard ValueNotifier to a fully reactive Signal
    final countSignal = useValueNotifierToSignal(notifier);

    return Column(
      children: [
        Text('ValueNotifier value: ${notifier.value}'),
        Text('Signal value: ${countSignal.value}'),
        ElevatedButton(
          onPressed: () => countSignal.value++, // Updates notifier automatically
          child: const Text('Increment Signal'),
        ),
      ],
    );
  }
}

Implementation

Signal<T> useValueNotifierToSignal<T>(
  ValueNotifier<T> value, {
  List<Object?> keys = const <Object>[],
  SignalOptions<T>? options,
}) {
  final s = useMemoized(
    () => valueNotifierToSignal(
      value,
      debugLabel: options?.name,
      autoDispose: options?.autoDispose ?? false,
    ),
    keys,
  );
  return useExistingSignal(s, keys: keys);
}