main_screen.dart

import 'package:flutter/material.dart';
import 'camera_preview_screen.dart';
import 'home_screen.dart';
import 'history_screen.dart';

class MainScreen extends StatefulWidget {
  final int initialIndex;
  const MainScreen({super.key, this.initialIndex = 1});

  @override
  State<MainScreen> createState() => _MainScreenState();
}

class _MainScreenState extends State<MainScreen> {
  late int _selectedIndex;

  final List<Widget> _pages = [
    const CameraPreviewScreen(),
    const HomeScreen(),
    HistoryScreen(),
  ];

  @override
  void initState() {
    super.initState();
    _selectedIndex = widget.initialIndex;
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: IndexedStack(
        index: _selectedIndex,
        children: _pages,
      ),
      bottomNavigationBar: Container(
        height: 80,
        decoration: const BoxDecoration(
          color: Color(0xFFCE8426),
        ),
        padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 16),
        child: Row(
          mainAxisAlignment: MainAxisAlignment.spaceAround,
          children: [
            _buildNavItem(Icons.camera_alt, 'ตัวระบุ', 0),
            _buildNavItem(Icons.home, 'หน้าหลัก', 1),
            _buildNavItem(Icons.history, 'ประวัติ', 2),
          ],
        ),
      ),
    );
  }

  Widget _buildNavItem(IconData icon, String label, int index) {
    final bool isSelected = _selectedIndex == index;

    return GestureDetector(
      onTap: () {
        setState(() {
          _selectedIndex = index;
        });
      },
      child: AnimatedContainer(
        duration: const Duration(milliseconds: 200),
        padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 6),
        decoration: isSelected
            ? BoxDecoration(
                color: const Color(0xFFFFCC80), // สีพื้นหลังเมื่อเลือก
                borderRadius: BorderRadius.circular(20),
              )
            : null,
        child: Row(
          children: [
            Icon(
              icon,
              size: 30,
              color: isSelected ? Colors.black : Colors.black54,
            ),
            const SizedBox(width: 6),
            if (isSelected)
              Text(
                label,
                style: const TextStyle(
                  color: Colors.black,
                  fontWeight: FontWeight.bold,
                ),
              ),
          ],
        ),
      ),
    );
  }
}

1. โครงสร้างคลาส

  • MainScreen เป็น StatefulWidget เพราะเราต้องเปลี่ยนหน้าจอเวลาเลือกเมนูด้านล่าง

  • initialIndex → กำหนดหน้าเริ่มต้น (default = 1 → HomeScreen)


2. _MainScreenState

  • _selectedIndex → ตัวแปรเก็บ index ของหน้า ณ ปัจจุบัน

  • _pages → list ของหน้าต่าง ๆ:

    1. CameraPreviewScreen() → หน้าใช้กล้อง

    2. HomeScreen() → หน้าแสดงข้อมูลหลัก

    3. HistoryScreen() → หน้าแสดงประวัติ


3. initState

  • กำหนด _selectedIndex ตาม initialIndex ตอนเริ่มแอป


4. Scaffold + Body

  • Scaffold → โครงสร้างหลักของหน้า

  • IndexedStack → แสดง page ตาม _selectedIndex

    • ข้อดี: หน้าอื่นยังคงอยู่ใน memory → ไม่โหลดใหม่ทุกครั้ง


5. Bottom Navigation Bar

  • เป็น Container กำหนดสีส้ม และความสูง 80

  • ใช้ Row วางปุ่ม navigation 3 ปุ่ม

  • แต่ละปุ่มสร้างด้วย _buildNavItem


6. _buildNavItem

อธิบาย:

  • GestureDetector → ตรวจจับการกดปุ่ม

  • setState() → เปลี่ยน _selectedIndex → หน้าเปลี่ยน

  • AnimatedContainer → เปลี่ยนสี/ขนาดปุ่มแบบ smooth

  • ปุ่มที่เลือก:

    • มีสีพื้นหลังสว่าง

    • Icon เป็นสีดำ

    • แสดง label

  • ปุ่มที่ไม่ได้เลือก:

    • ไม่มี background

    • Icon สีเทา

    • ไม่มี label


7. สรุปง่าย ๆ

  1. ใช้ IndexedStack แสดงหน้าต่าง ๆ ตาม _selectedIndex

  2. Bottom Navigation Bar มี 3 ปุ่ม: กล้อง, หน้าแรก, ประวัติ

  3. _buildNavItem() → สร้างปุ่ม navigation แบบสวยงาม, เลือกปุ่มมี animation และแสดง label

  4. _selectedIndex → ควบคุมหน้าและสีปุ่ม


ผลลัพธ์: แอปมี Bottom Navigation แบบสวยงาม, หน้าไม่โหลดซ้ำเมื่อเปลี่ยน, และ UI มี animation เล็ก ๆ เมื่อเลือกปุ่ม

Last updated