melhorar o navigation e o separar controlls e widgetes e pages

main
230404 2025-12-03 10:31:47 +00:00
parent e16191fa9d
commit dc3a7840bb
11 changed files with 545 additions and 473 deletions

View File

@ -1,15 +0,0 @@
import 'dart:async';
class HomeController {
Future<void> loadHomeData() async {
await Future.delayed(const Duration(milliseconds: 500));
}
void refreshData() {
loadHomeData();
}
List<String> getFilterOptions() {
return ['Últimos 7 dias', 'Últimos 30 dias', 'Temporada completa'];
}
}

View File

@ -1,173 +1,215 @@
import 'package:flutter/material.dart';
import 'widgets/player_stat_card.dart';
import 'widgets/wins_losses_chart.dart';
import 'widgets/recent_game_card.dart';
import 'widgets/game_highlights.dart';
import 'widgets/bottom_nav_bar.dart';
import '../controllers/home_controller.dart';
class Home extends StatefulWidget {
const Home({super.key});
@override
State<Home> createState() => _HomeState();
}
class _HomeState extends State<Home> {
final HomeController _controller = HomeController();
int _currentIndex = 0;
@override
void initState() {
super.initState();
_controller.loadHomeData();
}
class HomeScreen extends StatelessWidget {
const HomeScreen({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.white,
appBar: AppBar(
title: const Text(
'Home',
style: TextStyle(
fontSize: 24,
fontWeight: FontWeight.bold,
color: Colors.black,
title: const Text('PlayMaker'),
backgroundColor: Colors.orange,
foregroundColor: Colors.white,
),
),
backgroundColor: Colors.white,
elevation: 0,
centerTitle: true,
),
body: Padding(
padding: const EdgeInsets.symmetric(horizontal: 16.0),
child: SingleChildScrollView(
body: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(40.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
// Team Header
Padding(
padding: const EdgeInsets.only(top: 8.0, bottom: 16.0),
child: Text(
'TEAM A',
// Título
const Text(
'PLAYMAKER',
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.w600,
color: Colors.grey[700],
fontSize: 32,
fontWeight: FontWeight.bold,
color: Colors.orange,
letterSpacing: 2,
),
),
const SizedBox(height: 40),
// Botão PRINCIPAL para iniciar jogo
SizedBox(
width: double.infinity,
height: 250,
child: ElevatedButton(
onPressed: () {
// Navegar para tela de novo jogo
print('Iniciar novo jogo!');
// Navigator.push(context, MaterialPageRoute(
// builder: (context) => NovoJogoScreen()
// ));
},
style: ElevatedButton.styleFrom(
backgroundColor: Colors.orange,
foregroundColor: Colors.white,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(25),
),
elevation: 10,
shadowColor: Colors.orange.withOpacity(0.5),
),
child: const Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Icon(
Icons.sports_basketball,
size: 80,
color: Colors.white,
),
SizedBox(height: 20),
Text(
'NOVO JOGO',
style: TextStyle(
fontSize: 38,
fontWeight: FontWeight.w900,
color: Colors.white,
letterSpacing: 2,
),
),
],
),
),
),
// Best Players Section
const SizedBox(height: 40),
// Texto explicativo
const Text(
'Melhores Jogadores',
'Toque para iniciar uma nova partida',
style: TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: Colors.black,
color: Colors.grey,
fontStyle: FontStyle.italic,
),
),
const SizedBox(height: 12),
// Player Stats Cards
Row(
children: [
Expanded(
child: PlayerStatCard(
title: 'Mais Pontos',
playerName: 'Michael Jordan',
statValue: '34.5',
statType: 'PPG',
icon: Icons.sports_basketball,
color: Colors.blue,
),
),
const SizedBox(width: 12),
Expanded(
child: PlayerStatCard(
title: 'Mais Assistências',
playerName: 'Magic Johnson',
statValue: '12.8',
statType: 'APG',
icon: Icons.share,
color: Colors.green,
),
),
const SizedBox(width: 12),
Expanded(
child: PlayerStatCard(
title: 'Mais Rebotes',
playerName: 'Dennis Rodman',
statValue: '15.3',
statType: 'RPG',
icon: Icons.vertical_align_center,
const SizedBox(height: 50),
// Seção de opções rápidas
const Text(
'Acesso Rápido',
style: TextStyle(
fontSize: 22,
fontWeight: FontWeight.bold,
color: Colors.orange,
),
),
],
),
const SizedBox(height: 24),
// Wins vs Losses
WinsLossesChart(
wins: 12,
losses: 5,
totalGames: 17,
),
const SizedBox(height: 24),
// Recent History
const Text(
'Histórico Recente',
style: TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: Colors.black,
),
),
const SizedBox(height: 12),
RecentGameCard(
teamA: 'TEAM A',
teamB: 'TEAM B',
scoreA: 91,
scoreB: 88,
quarter: '',
timeLeft: '10:00',
date: '13/06/25',
),
const SizedBox(height: 24),
// Game Highlights
const Text(
'Destaques do Jogo',
style: TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: Colors.black,
),
),
const SizedBox(height: 12),
GameHighlights(
players: [
PlayerHighlight(name: 'Fred', stat: '13,0 rebotes'),
PlayerHighlight(name: 'Afonso', stat: '20,0 pontos'),
],
),
const SizedBox(height: 20),
// Grid de opções
GridView.count(
shrinkWrap: true,
physics: const NeverScrollableScrollPhysics(),
crossAxisCount: 2,
childAspectRatio: 1.3,
mainAxisSpacing: 20,
crossAxisSpacing: 20,
children: [
// Estatísticas
_buildQuickOption(
icon: Icons.insights,
title: 'Estatísticas',
subtitle: 'Ver desempenho',
color: Colors.green,
onTap: () {
print('Ver estatísticas');
// Pode navegar para estatísticas ou mudar para índice 3 no navigation
},
),
// Equipas
_buildQuickOption(
icon: Icons.people,
title: 'Minhas Equipas',
subtitle: 'Gerir equipas',
color: Colors.blue,
onTap: () {
print('Ver equipas');
// Pode navegar para equipas ou mudar para índice 2 no navigation
},
),
// Histórico
_buildQuickOption(
icon: Icons.history,
title: 'Histórico',
subtitle: 'Jogos anteriores',
color: Colors.purple,
onTap: () {
print('Ver histórico');
},
),
// Configurações
_buildQuickOption(
icon: Icons.settings,
title: 'Configurações',
subtitle: 'Ajustar app',
color: Colors.grey,
onTap: () {
print('Abrir configurações');
},
),
],
),
],
),
),
),
bottomNavigationBar: BottomNavBar(
currentIndex: _currentIndex,
onTap: (index) {
setState(() {
_currentIndex = index;
});
},
);
}
// Widget para construir opções rápidas
Widget _buildQuickOption({
required IconData icon,
required String title,
required String subtitle,
required Color color,
required VoidCallback onTap,
}) {
return Card(
elevation: 5,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(15),
),
child: InkWell(
borderRadius: BorderRadius.circular(15),
onTap: onTap,
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Icon(
icon,
size: 40,
color: color,
),
const SizedBox(height: 10),
Text(
title,
style: TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: color,
),
textAlign: TextAlign.center,
),
const SizedBox(height: 5),
Text(
subtitle,
style: const TextStyle(
fontSize: 12,
color: Colors.grey,
),
textAlign: TextAlign.center,
),
],
),
),
),
);
}

View File

@ -1,15 +1,17 @@
import 'package:flutter/material.dart';
import '../widgets/login_widgets.dart';
import '../../Controllers/login_controller.dart';
import 'package:flutter/material.dart';
import 'package:playmaker/controllers/home_controller.dart';
import 'package:playmaker/pages/home.dart';
import '../widgets/login_widgets.dart';
import '../../Controllers/login_controller.dart';
class LoginPage extends StatefulWidget {
class LoginPage extends StatefulWidget {
const LoginPage({super.key});
@override
State<LoginPage> createState() => _LoginPageState();
}
}
class _LoginPageState extends State<LoginPage> {
class _LoginPageState extends State<LoginPage> {
final LoginController controller = LoginController();
@override
@ -51,10 +53,11 @@ class _LoginPageState extends State<LoginPage> {
LoginButton(
controller: controller,
onLoginSuccess: () {
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(
content: Text('Login bem-sucedido!'),
backgroundColor: Colors.green,
Navigator.pushReplacement(
context,
MaterialPageRoute(
builder: (context) => const HomeScreen(),
),
);
},
@ -76,4 +79,4 @@ class _LoginPageState extends State<LoginPage> {
),
);
}
}
}

View File

@ -1 +0,0 @@
// TODO Implement this library.

View File

@ -1 +0,0 @@
// TODO Implement this library.

View File

@ -1 +0,0 @@
// TODO Implement this library.

View File

@ -1 +0,0 @@
// TODO Implement this library.

View File

@ -1 +0,0 @@
// TODO Implement this library.

View File

@ -0,0 +1,47 @@
import 'package:flutter/material.dart';
class CustomNavBar extends StatelessWidget {
final int selectedIndex;
final Function(int) onItemSelected;
const CustomNavBar({
super.key,
required this.selectedIndex,
required this.onItemSelected,
});
@override
Widget build(BuildContext context) {
// Usar NavigationBar (Material 3) ao invés de BottomNavigationBar
return NavigationBar(
selectedIndex: selectedIndex,
onDestinationSelected: onItemSelected,
backgroundColor: Theme.of(context).colorScheme.surface,
surfaceTintColor: Theme.of(context).colorScheme.surfaceTint,
elevation: 1,
height: 70,
destinations: const [
NavigationDestination(
icon: Icon(Icons.home_outlined),
selectedIcon: Icon(Icons.home_filled),
label: 'Home',
),
NavigationDestination(
icon: Icon(Icons.sports_soccer_outlined),
selectedIcon: Icon(Icons.sports_soccer),
label: 'Jogo',
),
NavigationDestination(
icon: Icon(Icons.people_outline),
selectedIcon: Icon(Icons.people),
label: 'Equipas',
),
NavigationDestination(
icon: Icon(Icons.insights_outlined),
selectedIcon: Icon(Icons.insights),
label: 'Status',
),
],
);
}
}

View File

@ -1,7 +1,7 @@
import 'package:flutter/material.dart';
import 'package:playmaker/Controllers/login_controller.dart';
import 'package:flutter/material.dart';
import 'package:playmaker/Controllers/login_controller.dart';
class BasketTrackHeader extends StatelessWidget {
class BasketTrackHeader extends StatelessWidget {
const BasketTrackHeader({super.key});
@override
@ -47,9 +47,9 @@ class BasketTrackHeader extends StatelessWidget {
],
);
}
}
}
class LoginFormFields extends StatelessWidget {
class LoginFormFields extends StatelessWidget {
final LoginController controller;
const LoginFormFields({super.key, required this.controller});
@ -167,9 +167,9 @@ class LoginFormFields extends StatelessWidget {
],
);
}
}
}
class LoginButton extends StatelessWidget {
class LoginButton extends StatelessWidget {
final LoginController controller;
final VoidCallback onLoginSuccess;
@ -224,9 +224,9 @@ class LoginButton extends StatelessWidget {
),
);
}
}
}
class CreateAccountButton extends StatelessWidget {
class CreateAccountButton extends StatelessWidget {
const CreateAccountButton({super.key});
@override
@ -259,4 +259,4 @@ class CreateAccountButton extends StatelessWidget {
),
);
}
}
}