Skip to content

Overview

  • File: lib/views/contacts_page.dart

The ContactsPage is a Flutter widget that manages the contacts list in the HVC Mobile application. It provides functionality for viewing, searching, and interacting with contacts, including initiating calls, chats, and managing favorites.

Class Structure

Class Definition

dart
class ContactsPage extends StatefulWidget {
  static const String routeName = '/ContactsPage';
  ContactsPage({Key? key}) : super(key: key);

  @override
  _ContactsPageState createState() => _ContactsPageState();
}

Controllers

dart
final ContactsController contactsController = Get.find();
final MeetingsController meetingsController = Get.find();
final RealTimeController realTimeController = Get.find();
final MessagesController messagesController = Get.find();

State Variables

dart
final TextEditingController searchCtrl = TextEditingController();

Dependencies

Required Packages

  • flutter/material.dart - Core Flutter UI components
  • get/get.dart - State management and routing
  • infinite_scroll_pagination - Infinite scrolling functionality
  • permission_handler - Permission management

Internal Dependencies

  • contacts_controller.dart - Contact management logic
  • meetings_controller.dart - Meeting management
  • messages_controller.dart - Message handling
  • real_time_controller.dart - Real-time communication
  • hlk_helpers/ - Custom helper utilities
  • models/ - Data models
  • shared/ - Shared constants and configurations
  • widgets/ - Custom widgets

State Management

Initialization

dart
@override
void initState() {
  super.initState();
  if (contactsController.contacts.isEmpty) contactsController.fetchPage(1);
}

Reactive State

dart
Obx(() => contactsController.loadingContacts.value
    ? const Center(child: CircularProgressIndicator())
    : Column(...))

Contact Management

Contact Selection

dart
void onItemSelected(Contact contact, bool isSelected) {
  setState(() {
    contact.isSelected = isSelected;
    if (isSelected) {
      contactsController.selected.add(contact);
    } else {
      contactsController.selected.remove(contact);
    }
  });
}

Contact Actions

  1. Start Chat
dart
Future<void> goToChat(Contact contact) async {
  UserData user = UserData.fromMap(userData);
  final res = await realTimeController.callSendMessage(
    content: '',
    contentType: 'text',
    user: user,
    contacts: [contact.id],
  );

  if (res != null) {
    messagesController.selectedGroupId.value = res.groupId;
    messagesController.reloadMessages();
    messagesController.getMessagesOnline(groupId: res.groupId);
    Get.to(ContactMessageDetailsPage(
      contact: contact,
      isForMessage: false,
    ));
    if (contact.isGroup) contactsController.getGroupUsers(contact.id);
    messagesController.getChatListOnline();
  }
}
  1. Make Call
dart
callHandler: () async {
  UserData user = UserData.fromMap(userData);
  contactsController.selected.add(contact);

  final callDto = InitCallDto(
    from: user.userId,
    fromName: user.name,
    targets: [contact.id],
    title: 'Meeting with ${user.name}',
    source: 'Mobile',
    platform: Platform.isIOS ? 'iOS' : 'Android',
  );

  await validatePermission(
    Permission.camera,
    () async => await validatePermission(
      Permission.microphone,
      () async {
        await realTimeController.makeCall(
          callDto,
          contact.name,
          true,
          contact.isGroup,
        );
      }
    )
  );
  contactsController.releaseSelections();
}
  1. Toggle Favorite
dart
makeFavoriteHandler: () async {
  await contactsController.makeContactFavorite(
    contact.id,
    !contact.favourite,
  );
}

UI Components

dart
if (contactsController.showSearchBox.value)
  Padding(
    padding: const EdgeInsets.only(left: 24, right: 12, top: 10),
    child: Row(
      children: [
        Expanded(
          child: TextFormField(
            controller: searchCtrl,
            validator: requiredValidator,
            decoration: getInputDecoration('Search Contact', false),
          ),
        ),
        IconButton(
          onPressed: () async {
            setState(() {
              contactsController.showSearchBox.value = false;
              contactsController.name.value = searchCtrl.text;
            });
            await contactsController.reload();
            searchCtrl.clear();
          },
          icon: const Icon(Icons.search),
        ),
      ],
    ),
  )

Contact List

dart
PagedListView<int, Contact>(
  pagingController: contactsController.pagingController,
  builderDelegate: PagedChildBuilderDelegate<Contact>(
    itemBuilder: (context, contact, index) => ContactItem(...),
    noItemsFoundIndicatorBuilder: (context) => NoItemLoader(...),
  ),
)

Contact Item

dart
ContactItem(
  callHandler: () async { ... },
  contact: contactsController.contacts.elementAt(index),
  onSelected: (newVal) => onItemSelected(contact, newVal!),
  onTapHandler: () async => await goToChat(contact),
  messageHandler: () async => await goToChat(contact),
  makeFavoriteHandler: () async { ... },
)

Search Functionality

Search Implementation

dart
onPressed: () async {
  setState(() {
    contactsController.showSearchBox.value = false;
    contactsController.name.value = searchCtrl.text;
  });
  await contactsController.reload();
  searchCtrl.clear();
}

Search Box Toggle

dart
if (contactsController.showSearchBox.value)
  // Show search box
else
  // Hide search box

Communication Features

Chat Initialization

  1. Create message
  2. Set group ID
  3. Load messages
  4. Navigate to chat page
  5. Load group users (if group chat)
  6. Update chat list

Call Initialization

  1. Create call DTO
  2. Validate permissions
  3. Initiate call
  4. Release selections

Released under the MIT License.