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

Offline-first AI framework for Flutter. Resident LLM inference, local RAG, and autonomous agents with a Material 3 Chat UI.

example/lib/main.dart

import 'package:flutter/material.dart';
import 'package:flutter_local_agent_kit/flutter_local_agent_kit.dart';

void main() {
  runApp(const LocalAgentDemo());
}

/// A comprehensive demo app showcasing the full capabilities of the Local Agent Kit.
class LocalAgentDemo extends StatelessWidget {
  const LocalAgentDemo({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      title: 'Local Agent Studio',
      theme: ThemeData(
        useMaterial3: true,
        colorScheme: ColorScheme.fromSeed(
          seedColor: const Color(0xFF6750A4),
          brightness: Brightness.dark,
        ),
      ),
      home: const AgentStudioPage(),
    );
  }
}

class AgentStudioPage extends StatefulWidget {
  const AgentStudioPage({super.key});

  @override
  State<AgentStudioPage> createState() => _AgentStudioPageState();
}

class _AgentStudioPageState extends State<AgentStudioPage> {
  final FlutterLocalAgentKit _kit = FlutterLocalAgentKit();
  
  bool _isInit = false;
  double _downloadProgress = 0.0;
  String _statusMessage = 'System Idle';
  String _activeModelName = 'Checking...';
  int _ragDocCount = 0;

  @override
  void initState() {
    super.initState();
    _bootstrap();
  }

  Future<void> _bootstrap() async {
    setState(() => _statusMessage = 'Checking model weights...');
    
    const modelId = 'llama-3.2-1b-instruct';
    final recommended = ModelManager.recommendedModels.firstWhere((m) => m.id == modelId);
    setState(() => _activeModelName = recommended.name);

    final isDownloaded = await _kit.models.isModelDownloaded(modelId);
    final modelPath = await _kit.models.getLocalPath(modelId);

    if (!isDownloaded) {
      setState(() => _statusMessage = 'Downloading ${recommended.name} (~700MB)...');
      try {
        await _kit.models.downloadModel(
          recommended,
          onProgress: (progress) => setState(() => _downloadProgress = progress),
        );
      } catch (e) {
        setState(() => _statusMessage = 'Download Failed: $e');
        return;
      }
    }

    setState(() => _statusMessage = 'Booting Native Engines...');

    try {
      await _kit.initialize(modelPath: modelPath);
      setState(() {
        _isInit = true;
        _statusMessage = 'AI Core Online';
      });
    } catch (e) {
      setState(() => _statusMessage = 'Boot Error: $e');
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Local Agent Studio', style: TextStyle(fontWeight: FontWeight.bold)),
        actions: [_buildStatusChip()],
      ),
      body: _isInit 
        ? Column(
            children: [
              _buildControlPanel(),
              const Divider(height: 1),
              Expanded(
                child: AgentChatView(
                  onMessage: (query) => _kit.runAgent(query),
                  welcomeMessage: 'I am your resident AI agent. Everything we discuss stays on this device.',
                  suggestions: const [
                    '🕵️ Who are you?',
                    '📅 What is the time?',
                    '🧮 Solve: (15 * 8) + 120',
                    '📚 How does RAG work?',
                    '🚀 Performance test',
                  ],

                ),
              ),

            ],
          )
        : _buildLoadingState(),
    );
  }

  Widget _buildControlPanel() {
    return Container(
      padding: const EdgeInsets.all(16),
      decoration: BoxDecoration(
        color: Theme.of(context).colorScheme.surfaceContainerHighest.withValues(alpha: 0.3),
      ),
      child: Row(
        children: [
          Expanded(
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.start,
              children: [
                Text('Resident LLM: $_activeModelName', style: Theme.of(context).textTheme.labelLarge),
                const SizedBox(height: 4),
                Text('RAG Knowledge: $_ragDocCount documents', style: Theme.of(context).textTheme.bodySmall),
              ],
            ),
          ),
          ElevatedButton.icon(
            onPressed: () {
              // Simulated knowledge injection for demo
              setState(() => _ragDocCount++);
              ScaffoldMessenger.of(context).showSnackBar(
                const SnackBar(content: Text('Document indexed into local vector base.')),
              );
            },
            icon: const Icon(Icons.add_link),
            label: const Text('Inject'),
          ),
        ],
      ),
    );
  }

  Widget _buildStatusChip() {
    final isError = _statusMessage.contains('Error') || _statusMessage.contains('Failed');
    return Container(
      margin: const EdgeInsets.symmetric(horizontal: 16),
      padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 4),
      decoration: BoxDecoration(
        color: isError 
            ? Colors.red.withValues(alpha: 0.2) 
            : (_isInit ? Colors.green.withValues(alpha: 0.2) : Colors.orange.withValues(alpha: 0.2)),
        borderRadius: BorderRadius.circular(20),
        border: Border.all(
          color: isError ? Colors.red : (_isInit ? Colors.green : Colors.orange),
        ),
      ),
      child: Text(
        isError ? 'ERROR' : (_isInit ? 'SECURE' : 'INITIALIZING'),
        style: TextStyle(
          color: isError ? Colors.red : (_isInit ? Colors.green : Colors.orange),
          fontSize: 12,
          fontWeight: FontWeight.bold,
        ),
      ),
    );
  }

  Widget _buildLoadingState() {
    final isError = _statusMessage.contains('Error') || _statusMessage.contains('Failed');
    
    return Center(
      child: Padding(
        padding: const EdgeInsets.all(32),
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            if (!isError) const CircularProgressIndicator(),
            if (isError) const Icon(Icons.error_outline, size: 64, color: Colors.red),
            const SizedBox(height: 24),
            Text(
              _statusMessage, 
              textAlign: TextAlign.center,
              style: Theme.of(context).textTheme.titleMedium?.copyWith(
                color: isError ? Colors.red : null,
              ),
            ),
            if (!isError && _downloadProgress > 0) ...[
              const SizedBox(height: 16),
              SizedBox(
                width: 240,
                child: LinearProgressIndicator(value: _downloadProgress, borderRadius: BorderRadius.circular(10)),
              ),
              const SizedBox(height: 8),
              Text('${(_downloadProgress * 100).toInt()}%', style: Theme.of(context).textTheme.labelSmall),
            ],
            if (isError) ...[
              const SizedBox(height: 24),
              FilledButton.icon(
                onPressed: () => _bootstrap(),
                icon: const Icon(Icons.refresh),
                label: const Text('Retry Boot Sequence'),
              ),
            ],
          ],
        ),
      ),
    );
  }
}
7
likes
0
points
471
downloads

Publisher

unverified uploader

Weekly Downloads

Offline-first AI framework for Flutter. Resident LLM inference, local RAG, and autonomous agents with a Material 3 Chat UI.

Repository (GitHub)
View/report issues

License

unknown (license)

Dependencies

dio, flutter, flutter_markdown_plus, llamadart, markdown, math_expressions, mobile_rag_engine, path, path_provider, uuid

More

Packages that depend on flutter_local_agent_kit