formless 0.1.3 copy "formless: ^0.1.3" to clipboard
formless: ^0.1.3 copied to clipboard

A Flutter package that turns any list of fields into an AI-powered conversational form. Validates answers via Groq, OpenAI, Gemini, or DeepSeek and returns a clean key->value map when all fields are collected.

Formless #

A Flutter package that turns any list of fields into an AI-powered conversational form.

Instead of a traditional form, Formless walks the user through each question one at a time in a chat UI. The LLM validates answers in natural language, asks for corrections when needed, and returns a clean key → value map when all fields are collected.

Features #

  • Chat-style UI — no traditional form widgets needed
  • Supports Groq, OpenAI, Gemini, and DeepSeek
  • Per-field validation with optional custom rules for the LLM, plus optional onValidate for your own API checks after the AI accepts an answer
  • Users can edit any previous answer by long-pressing their bubble
  • Fully themeable — bubble colors, input field, send button, and more
  • Automatic JSON retry and rate-limit backoff

Free to use #

Formless works with providers that offer a free tier — you don't need a paid plan to get started:

Provider Free tier
Groq Yes — generous free tier, very fast
Gemini Yes — free tier available
OpenAI No — pay per use
DeepSeek No — pay per use

Privacy & security #

User data is sent directly from the device to the AI provider — it never passes through any third-party server, including Formless itself. The package makes HTTP calls straight to the provider's API using the key you supply, so your users' answers stay between them and the provider you choose.

Installation #

Add to your pubspec.yaml:

dependencies:
  formless: ^0.1.3

Then run:

flutter pub get

Getting started #

You need an API key from one of the supported providers:

Provider Where to get a key
Groq https://console.groq.com
OpenAI https://platform.openai.com
Gemini https://aistudio.google.com
DeepSeek https://platform.deepseek.com

Pass the key at runtime using --dart-define — never hardcode it:

flutter run --dart-define=MY_API_KEY=your_key_here

Usage #

Minimal #

import 'package:formless/formless.dart';

Formless(
  provider: AiProvider.openAi,
  apiKey: const String.fromEnvironment('MY_API_KEY'),
  onComplete: (data) {
    // data = {'name': 'Alice', 'email': 'alice@example.com', ...}
    print(data);
  },
)

This uses the built-in default questions: name, age, email, and phone.

Custom questions #

Formless(
  provider: AiProvider.groq,
  apiKey: const String.fromEnvironment('MY_API_KEY'),
  questions: [
    QuestionsModel(
      question: 'What is your full name?',
      key: 'name',
      type: QuestionFieldType.text,
    ),
    QuestionsModel(
      question: 'What is your email address?',
      key: 'email',
      type: QuestionFieldType.email,
    ),
    QuestionsModel(
      question: 'What is your monthly income?',
      key: 'income',
      type: QuestionFieldType.numeric,
      validationMessage: 'Only accept values between 1000 and 100000',
    ),
  ],
  onComplete: (data) => print(data),
)

Post-AI validation (onValidate) #

The LLM first decides whether the answer fits the question and any validationMessage / field type. After it accepts, you can run your own validation on the user’s text — for example calling your API to check that a nickname is not already taken.

onValidate is optional on each QuestionsModel. It runs only when the AI has already accepted the answer. Return null to keep the answer, or a non-empty String to reject it; that string is shown to the user so they can try again.

QuestionsModel(
  question: 'What nickname would you like?',
  key: 'nickname',
  type: QuestionFieldType.text,
  onValidate: (answer) async {
    final taken = await myBackend.isNicknameTaken(answer);
    if (taken) {
      return 'That nickname is already taken — please choose another.';
    }
    return null;
  },
),

Use this for uniqueness checks, database rules, or any logic you control on the device or via your own services — anything the model cannot reliably verify on its own.

Custom theme #

Formless(
  provider: AiProvider.openAi,
  apiKey: const String.fromEnvironment('MY_API_KEY'),
  theme: FormlessTheme(
    userBubbleColor: Colors.blue.shade700,
    botBubbleColor: Colors.grey.shade100,
    sendButtonColor: Colors.blue.shade700,
    inputDecoration: InputDecoration(
      hintText: 'Type your answer...',
      filled: true,
      fillColor: Colors.grey.shade100,
      border: OutlineInputBorder(
        borderRadius: BorderRadius.circular(12),
      ),
    ),
  ),
  onComplete: (data) => print(data),
)

Override the model #

Formless(
  provider: AiProvider.openAi,
  apiKey: const String.fromEnvironment('MY_API_KEY'),
  model: 'gpt-4o',
  onComplete: (data) => print(data),
)

API reference #

Formless #

Parameter Type Required Description
provider AiProvider Yes Which LLM API to use
apiKey String Yes API key for the chosen provider
questions List<QuestionsModel>? No Fields to collect; defaults to name/age/email/phone
model String? No Override the provider's default model
theme FormlessTheme? No Colors and input field styling
sendIcon Widget? No Custom icon inside the send button
onComplete Function(Map<String, dynamic>)? No Called with collected data when done
onError Function(String)? No Called on network or API errors

QuestionsModel #

Parameter Type Required Description
question String Yes The question shown to the user
key String Yes Key used in the onComplete data map
type QuestionFieldType? No Drives validation rules (email, phone, numeric, etc.)
validationMessage String? No Custom rule the LLM must strictly follow
onValidate Future<String?> Function(String)? No After the AI accepts, run custom checks (e.g. API); return null or an error message for the user

FormlessTheme #

Parameter Description
userBubbleColor User message bubble background
botBubbleColor Bot message bubble background
userTextColor Text color in user bubbles
botTextColor Text color in bot bubbles
sendButtonColor Send button background
typingIndicatorColor Animated typing dots color
inputDecoration Full InputDecoration override for the text field
inputTextStyle Text style for what the user types
inputBorderColor Border color (ignored when inputDecoration is set)
inputHintText Hint text (ignored when inputDecoration is set)

License #

MIT

4
likes
0
points
237
downloads

Publisher

unverified uploader

Weekly Downloads

A Flutter package that turns any list of fields into an AI-powered conversational form. Validates answers via Groq, OpenAI, Gemini, or DeepSeek and returns a clean key->value map when all fields are collected.

Repository (GitHub)
View/report issues

Topics

#form #ai #llm #chat #validation

License

unknown (license)

Dependencies

flutter, http

More

Packages that depend on formless