Project Init
How to create a new Flutter project, understand pubspec.yaml, organize your folder structure, and run the app on a device or emulator.
1. Creating a New Flutter Project
Use the flutter create command followed by your project name. Project names must be lowercase with underscores. You can also specify the organization, platform targets, and template type.
# Basic project creation
flutter create my_app
# With custom organization (used for bundle ID)
flutter create --org com.example my_app
# Target specific platforms only
flutter create --platforms android,ios my_app
# Use a specific template (app, plugin, package)
flutter create --template=app my_app
# Check Flutter environment and installed tools
flutter doctor
2. pubspec.yaml Structure
pubspec.yaml is the project manifest. It defines the app name, SDK constraints, dependencies, dev dependencies, and asset paths. All indentation must use spaces (not tabs).
name: my_app
description: A new Flutter project.
publish_to: "none" # Remove if publishing to pub.dev
version: 1.0.0+1 # version: major.minor.patch+buildNumber
environment:
sdk: ">=3.0.0 <4.0.0"
dependencies:
flutter:
sdk: flutter
cupertino_icons: ^1.0.6
http: ^1.2.1
provider: ^6.1.2
shared_preferences: ^2.2.3
go_router: ^13.2.0
dev_dependencies:
flutter_test:
sdk: flutter
flutter_lints: ^3.0.0
flutter:
uses-material-design: true
assets:
- assets/images/
- assets/icons/
fonts:
- family: Poppins
fonts:
- asset: assets/fonts/Poppins-Regular.ttf
- asset: assets/fonts/Poppins-Bold.ttf
weight: 700
3. Recommended Folder Structure
A clean folder structure keeps your codebase maintainable. Separate screens, widgets, services, models, and utilities into their own directories inside lib/.
my_app/
├── android/
├── ios/
├── assets/
│ ├── images/
│ ├── icons/
│ └── fonts/
├── lib/
│ ├── main.dart # Entry point
│ ├── app.dart # MaterialApp setup
│ ├── screens/ # Full-page screens
│ │ ├── home_screen.dart
│ │ ├── login_screen.dart
│ │ └── profile_screen.dart
│ ├── widgets/ # Reusable UI components
│ │ ├── custom_button.dart
│ │ └── custom_text_field.dart
│ ├── services/ # API calls, local storage
│ │ ├── api_service.dart
│ │ └── auth_service.dart
│ ├── models/ # Data models
│ │ └── user_model.dart
│ ├── providers/ # State management
│ │ └── auth_provider.dart
│ └── utils/ # Constants, helpers, themes
│ ├── constants.dart
│ ├── theme.dart
│ └── helpers.dart
├── test/
└── pubspec.yaml
4. main.dart & app.dart Entry Point
main.dart calls runApp() with the root widget. It's best practice to separate the MaterialApp configuration into its own app.dart file to keep things clean.
// lib/main.dart
import "package:flutter/material.dart";
import "app.dart";
void main() {
WidgetsFlutterBinding.ensureInitialized();
runApp(const MyApp());
}
// lib/app.dart
import "package:flutter/material.dart";
import "screens/home_screen.dart";
import "screens/login_screen.dart";
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: "My App",
debugShowCheckedModeBanner: false,
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.indigo),
useMaterial3: true,
),
initialRoute: "/login",
routes: {
"/login": (context) => const LoginScreen(),
"/home": (context) => const HomeScreen(),
},
);
}
}
5. Running & Building the App
Use the Flutter CLI to run on connected devices, emulators, or build release APKs/IPAs. The flutter pub get command fetches all packages listed in pubspec.yaml.
# Install dependencies
flutter pub get
# List connected devices
flutter devices
# Run on a specific device
flutter run -d emulator-5554
flutter run -d chrome # For web
# Hot reload (in terminal while running): press "r"
# Hot restart: press "R"
# Quit: press "q"
# Build release APK (Android)
flutter build apk --release
flutter build apk --split-per-abi # Smaller APKs
# Build App Bundle (for Play Store)
flutter build appbundle --release
# Build for iOS
flutter build ipa --release
# Clean build cache
flutter clean && flutter pub get