all_device_sensors 1.0.1 copy "all_device_sensors: ^1.0.1" to clipboard
all_device_sensors: ^1.0.1 copied to clipboard

A Flutter plugin to access all device sensors — accelerometer, gyroscope, magnetometer, linear acceleration, gravity, barometer, proximity, light and step counter. By Bharathwaj.

example/lib/main.dart

import 'package:flutter/material.dart';
import 'dart:async';
import 'package:all_device_sensors/all_device_sensors.dart';

void main() => runApp(const MyApp());

class MyApp extends StatelessWidget {
  const MyApp({super.key});
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Device Sensors',
      debugShowCheckedModeBanner: false,
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: const Color(0xFF1A73E8)),
        useMaterial3: true,
      ),
      home: const SensorHomePage(),
    );
  }
}

class SensorHomePage extends StatefulWidget {
  const SensorHomePage({super.key});
  @override
  State<SensorHomePage> createState() => _SensorHomePageState();
}

class _SensorHomePageState extends State<SensorHomePage>
    with SingleTickerProviderStateMixin {
  final _plugin = AllDeviceSensors();
  late TabController _tabController;

  // 3-axis
  SensorData? _accel, _gyro, _mag, _linear, _gravity;
  // single-value
  SingleSensorData? _baro, _proximity, _light, _steps;

  List<Map<String, dynamic>> _allSensors = [];
  int _sensorCount = 0;

  final List<StreamSubscription> _subs = [];

  @override
  void initState() {
    super.initState();
    _tabController = TabController(length: 4, vsync: this);
    _loadSensors();
    _startStreams();
  }

  Future<void> _loadSensors() async {
    final sensors = await _plugin.getSensors();
    setState(() {
      _allSensors = sensors.map((s) => {'name': s.name, 'vendor': s.vendor, 'type': s.type}).toList();
      _sensorCount = sensors.length;
    });
  }

  void _startStreams() {
    _subs.addAll([
      _plugin.accelerometerStream(interval: SensorInterval.ui).listen((d) => setState(() => _accel = d)),
      _plugin.gyroscopeStream(interval: SensorInterval.ui).listen((d) => setState(() => _gyro = d)),
      _plugin.magnetometerStream(interval: SensorInterval.ui).listen((d) => setState(() => _mag = d)),
      _plugin.linearAccelerationStream(interval: SensorInterval.ui).listen((d) => setState(() => _linear = d)),
      _plugin.gravityStream(interval: SensorInterval.ui).listen((d) => setState(() => _gravity = d)),
      _plugin.barometerStream().listen((d) => setState(() => _baro = d)),
      _plugin.proximityStream().listen((d) => setState(() => _proximity = d)),
      _plugin.lightStream().listen((d) => setState(() => _light = d)),
      _plugin.stepCounterStream().listen((d) => setState(() => _steps = d)),
    ]);
  }

  @override
  void dispose() {
    _tabController.dispose();
    for (final s in _subs) { s.cancel(); }
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: const Color(0xFFF5F7FA),
      appBar: AppBar(
        backgroundColor: const Color(0xFF1A73E8),
        foregroundColor: Colors.white,
        elevation: 0,
        title: const Text('Device Sensors', style: TextStyle(fontWeight: FontWeight.w600)),
        centerTitle: true,
        bottom: TabBar(
          controller: _tabController,
          indicatorColor: Colors.white,
          labelColor: Colors.white,
          unselectedLabelColor: Colors.white60,
          tabs: const [
            Tab(icon: Icon(Icons.speed),        text: 'Motion'),
            Tab(icon: Icon(Icons.sensors),      text: 'Environment'),
            Tab(icon: Icon(Icons.directions_walk), text: 'Activity'),
            Tab(icon: Icon(Icons.list_alt),     text: 'All'),
          ],
        ),
      ),
      body: Column(
        children: [
          _buildBanner(),
          Expanded(
            child: TabBarView(
              controller: _tabController,
              children: [
                _buildMotionTab(),
                _buildEnvironmentTab(),
                _buildActivityTab(),
                _buildAllSensorsTab(),
              ],
            ),
          ),
        ],
      ),
    );
  }

  // ── Banner ──────────────────────────────────────────────────────────────────

  Widget _buildBanner() {
    return Container(
      color: const Color(0xFF1A73E8),
      padding: const EdgeInsets.only(bottom: 10),
      child: Center(
        child: Text(
          '$_sensorCount sensors detected on this device',
          style: const TextStyle(color: Colors.white70, fontSize: 13),
        ),
      ),
    );
  }

  // ── Tab 1: Motion (Accel, Gyro, Mag, Linear, Gravity) ──────────────────────

  Widget _buildMotionTab() {
    return ListView(
      padding: const EdgeInsets.all(16),
      children: [
        _xyzCard('Accelerometer', Icons.speed, const Color(0xFF1A73E8),
            'Acceleration incl. gravity (m/s²)', _accel),
        _xyzCard('Gyroscope', Icons.rotate_right, const Color(0xFF34A853),
            'Rotation rate (rad/s)', _gyro),
        _xyzCard('Magnetometer', Icons.explore, const Color(0xFFEA4335),
            'Magnetic field (μT)', _mag),
        _xyzCard('Linear Acceleration', Icons.trending_up, const Color(0xFFFA7B17),
            'Acceleration excl. gravity (m/s²)', _linear),
        _xyzCard('Gravity', Icons.arrow_downward, const Color(0xFF9334E6),
            'Gravity force (m/s²)', _gravity),
      ],
    );
  }

  // ── Tab 2: Environment (Baro, Proximity, Light) ─────────────────────────────

  Widget _buildEnvironmentTab() {
    return ListView(
      padding: const EdgeInsets.all(16),
      children: [
        _singleCard('Barometer', Icons.compress, const Color(0xFF1A73E8),
            'Atmospheric pressure (hPa)', _baro, 'hPa'),
        _singleCard('Proximity', Icons.sensors, const Color(0xFF34A853),
            '0 = near  ·  1 = far', _proximity,
            _proximity != null ? (_proximity!.value == 0 ? 'Near' : 'Far') : null),
        _singleCard('Light', Icons.wb_sunny, const Color(0xFFFA7B17),
            'Ambient light level (lux)', _light, 'lux'),
      ],
    );
  }

  // ── Tab 3: Activity (Step Counter) ─────────────────────────────────────────

  Widget _buildActivityTab() {
    return ListView(
      padding: const EdgeInsets.all(16),
      children: [
        _singleCard('Step Counter', Icons.directions_walk, const Color(0xFF9334E6),
            'Steps since last reboot', _steps, 'steps'),
      ],
    );
  }

  // ── Tab 4: All Sensors list ─────────────────────────────────────────────────

  Widget _buildAllSensorsTab() {
    if (_allSensors.isEmpty) {
      return const Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            CircularProgressIndicator(color: Color(0xFF1A73E8)),
            SizedBox(height: 16),
            Text('Loading sensors...', style: TextStyle(color: Colors.grey)),
          ],
        ),
      );
    }
    return ListView.separated(
      padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 12),
      itemCount: _allSensors.length,
      separatorBuilder: (_, __) => const SizedBox(height: 8),
      itemBuilder: (context, index) {
        final s = _allSensors[index];
        return Container(
          decoration: BoxDecoration(
            color: Colors.white,
            borderRadius: BorderRadius.circular(14),
            boxShadow: [BoxShadow(color: Colors.black.withOpacity(0.04), blurRadius: 6, offset: const Offset(0, 2))],
          ),
          child: ListTile(
            contentPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 6),
            leading: Container(
              width: 42, height: 42,
              decoration: BoxDecoration(color: const Color(0xFF1A73E8).withOpacity(0.1), shape: BoxShape.circle),
              child: Center(
                child: Text('${index + 1}',
                    style: const TextStyle(color: Color(0xFF1A73E8), fontWeight: FontWeight.bold, fontSize: 14)),
              ),
            ),
            title: Text(s['name'] ?? 'Unknown',
                style: const TextStyle(fontWeight: FontWeight.w600, fontSize: 14)),
            subtitle: Text(s['vendor'] ?? '', style: const TextStyle(fontSize: 12, color: Colors.grey)),
            trailing: Container(
              padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 4),
              decoration: BoxDecoration(color: const Color(0xFFF1F3F4), borderRadius: BorderRadius.circular(20)),
              child: Text('Type ${s['type']}', style: const TextStyle(fontSize: 11, color: Colors.black54)),
            ),
          ),
        );
      },
    );
  }

  // ── Reusable widgets ────────────────────────────────────────────────────────

  Widget _xyzCard(String title, IconData icon, Color color, String subtitle, SensorData? data) {
    return Container(
      margin: const EdgeInsets.only(bottom: 12),
      padding: const EdgeInsets.all(16),
      decoration: BoxDecoration(
        color: Colors.white,
        borderRadius: BorderRadius.circular(16),
        boxShadow: [BoxShadow(color: Colors.black.withOpacity(0.05), blurRadius: 8, offset: const Offset(0, 2))],
      ),
      child: Column(
        crossAxisAlignment: CrossAxisAlignment.start,
        children: [
          Row(children: [
            Icon(icon, color: color, size: 20),
            const SizedBox(width: 8),
            Text(title, style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 15)),
            const Spacer(),
            _statusDot(data != null),
          ]),
          const SizedBox(height: 4),
          Text(subtitle, style: const TextStyle(fontSize: 12, color: Colors.grey)),
          const SizedBox(height: 12),
          Row(children: [
            _axisChip('X', data?.x, color),
            const SizedBox(width: 8),
            _axisChip('Y', data?.y, color),
            const SizedBox(width: 8),
            _axisChip('Z', data?.z, color),
          ]),
        ],
      ),
    );
  }

  Widget _singleCard(String title, IconData icon, Color color, String subtitle,
      SingleSensorData? data, String? unit) {
    return Container(
      margin: const EdgeInsets.only(bottom: 12),
      padding: const EdgeInsets.all(16),
      decoration: BoxDecoration(
        color: Colors.white,
        borderRadius: BorderRadius.circular(16),
        boxShadow: [BoxShadow(color: Colors.black.withOpacity(0.05), blurRadius: 8, offset: const Offset(0, 2))],
      ),
      child: Row(
        children: [
          Container(
            width: 48, height: 48,
            decoration: BoxDecoration(color: color.withOpacity(0.1), shape: BoxShape.circle),
            child: Icon(icon, color: color, size: 24),
          ),
          const SizedBox(width: 16),
          Expanded(
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.start,
              children: [
                Text(title, style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 15)),
                Text(subtitle, style: const TextStyle(fontSize: 12, color: Colors.grey)),
              ],
            ),
          ),
          Column(
            crossAxisAlignment: CrossAxisAlignment.end,
            children: [
              Text(
                data != null ? data.value.toStringAsFixed(1) : '--',
                style: TextStyle(fontSize: 22, fontWeight: FontWeight.bold, color: color),
              ),
              if (unit != null)
                Text(unit, style: const TextStyle(fontSize: 11, color: Colors.grey)),
            ],
          ),
        ],
      ),
    );
  }

  Widget _axisChip(String label, double? value, Color color) {
    return Expanded(
      child: Container(
        padding: const EdgeInsets.symmetric(vertical: 10),
        decoration: BoxDecoration(color: color.withOpacity(0.07), borderRadius: BorderRadius.circular(10)),
        child: Column(
          children: [
            Text(label, style: TextStyle(fontSize: 12, color: color, fontWeight: FontWeight.bold)),
            const SizedBox(height: 4),
            Text(value != null ? value.toStringAsFixed(2) : '--',
                style: const TextStyle(fontSize: 14, fontWeight: FontWeight.w600)),
          ],
        ),
      ),
    );
  }

  Widget _statusDot(bool active) {
    return Container(
      width: 8, height: 8,
      decoration: BoxDecoration(
        shape: BoxShape.circle,
        color: active ? Colors.green : Colors.grey.shade300,
      ),
    );
  }
}
0
likes
150
points
68
downloads

Documentation

API reference

Publisher

unverified uploader

Weekly Downloads

A Flutter plugin to access all device sensors — accelerometer, gyroscope, magnetometer, linear acceleration, gravity, barometer, proximity, light and step counter. By Bharathwaj.

Repository (GitHub)

Topics

#sensors #accelerometer #gyroscope #barometer #hardware

License

MIT (license)

Dependencies

flutter, plugin_platform_interface

More

Packages that depend on all_device_sensors

Packages that implement all_device_sensors