import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import 'dart:convert';
class SimpleApiClient extends StatefulWidget {
@override
_SimpleApiClientState createState() => _SimpleApiClientState();
}
class _SimpleApiClientState extends State<SimpleApiClient> {
List<String> items = [];
bool isLoading = false;
final TextEditingController controller = TextEditingController();
@override
void initState() {
super.initState();
fetchItems();
}
Future<void> fetchItems() async {
setState(() {
isLoading = true;
});
try {
final response = await http.get(Uri.parse('https://jsonplaceholder.typicode.com/posts'));
if (response.statusCode == 200) {
final List<dynamic> data = json.decode(response.body);
setState(() {
items = data.map((item) => item['title'] as String).toList();
});
} else {
setState(() {
items = [];
});
}
} catch (e) {
setState(() {
items = [];
});
} finally {
setState(() {
isLoading = false;
});
}
}
Future<void> addItem(String newItem) async {
if (newItem.isEmpty) return;
setState(() {
isLoading = true;
});
try {
final response = await http.post(
Uri.parse('https://jsonplaceholder.typicode.com/posts'),
headers: {'Content-Type': 'application/json; charset=UTF-8'},
body: json.encode({'title': newItem, 'body': '', 'userId': 1}),
);
if (response.statusCode == 201) {
setState(() {
items.insert(0, newItem);
controller.clear();
});
}
} catch (e) {
// Could show error message here
} finally {
setState(() {
isLoading = false;
});
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('Simple API Client')),
body: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
children: [
Expanded(
child: isLoading
? Center(child: CircularProgressIndicator())
: items.isEmpty
? Center(child: Text('No items found.'))
: ListView.builder(
itemCount: items.length,
itemBuilder: (context, index) {
return ListTile(title: Text(items[index]));
},
),
),
TextField(
controller: controller,
decoration: InputDecoration(labelText: 'New Item'),
),
SizedBox(height: 10),
ElevatedButton(
onPressed: isLoading
? null
: () {
addItem(controller.text.trim());
},
child: Text('Add Item'),
),
],
),
),
);
}
}
This Flutter app uses the http package to make network requests.
When the screen opens, fetchItems() sends a GET request to a public API and extracts the titles from the JSON response to show as a list.
The user can type a new item name in the TextField and tap the 'Add Item' button. This triggers addItem(), which sends a POST request with the new item data.
While waiting for the network, a loading spinner shows. After a successful POST, the new item is added to the top of the list and the input clears.
This simple example shows how to handle GET and POST requests, update UI state, and manage user input in Flutter.