0

i have data from API that contains 400++K data, when I search some data, it works but only shows the data that is on page 1this API contain 10 data per page

this is my controller, i want to search data based on noCtplan and partNo

import 'dart:async';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import '../../../data/repositories/wi_repository.dart';
import '../models/kode_proyek.dart';
import '../models/wi.dart';
import 'kode_proyek_controller.dart';

class WiController extends GetxController {
  final WiRepository _wiRepository = WiRepository();
  final KodeProyekController _kodeProyekController =
      Get.put(KodeProyekController());

  var allWi = <Wi>[].obs;
  var proyekDetails = <String, KodeProyek>{}.obs;
  var isLoading = false.obs;
  var filteredWi = <Wi>[].obs;
  var currentPage = 1.obs;
  var totalPages = 1.obs;
  TextEditingController searchTextController = TextEditingController();
  Timer? _debounce;

  Future<void> getWi({int page = 1}) async {
    try {
      isLoading.value = true;
      var response = await _wiRepository.fetchWi(page: page);
      var wiData = response['items'] as List<Wi>;
      var totalPageCount = response['totalPages'];

      if (page == 1) {
        allWi.assignAll(wiData);
      } else {
        allWi.addAll(wiData);
      }

      await _kodeProyekController.fetchAndMatchProyekDetails(wiData);
      _kodeProyekController.proyekDetails.forEach((key, value) {
        if (key != null) {
          proyekDetails[key] = value;
        }
      });
      filteredWi.assignAll(allWi);

      totalPages.value = totalPageCount;
    } catch (e) {
      if (kDebugMode) print(e.toString());
    } finally {
      isLoading.value = false;
    }
  }

  void loadMoreWi() async {
    if (currentPage.value < totalPages.value) {
      currentPage.value++;
      await getWi(page: currentPage.value);
    }
  }

  void filterWi(String query) {
    if (_debounce?.isActive ?? false) _debounce?.cancel();
    _debounce = Timer(const Duration(milliseconds: 300), () {
      if (query.isEmpty) {
        filteredWi.assignAll(allWi);
      } else {
        var filtered = allWi.where((wi) {
          var partNo = wi.partNo?.toLowerCase() ?? '';
          var noCtplan = wi.noCtplan?.toLowerCase() ?? '';
          return partNo.contains(query.toLowerCase()) ||
              noCtplan.contains(query.toLowerCase());
        }).toList();
        filteredWi.assignAll(filtered);
      }
    });
  }

  void clearSearch() {
    searchTextController.clear();
    filteredWi.assignAll(allWi);
  }

  @override
  void onInit() {
    super.onInit();
    getWi();
  }
}

repository

import 'package:get/get.dart';
import '../../features/wi/models/wi.dart';
import '../../utils/http/http_client.dart';

class WiRepository extends GetConnect {
  Future<Map<String, dynamic>> fetchWi({int page = 1}) async {
    var url = 'wi-data.php?page=$page';
    final response = await WHttpHelper.get(url);

    final data = {
      'currentPage': response['currentPage'],
      'totalPages': response['totalPages'],
      'items': (response['items'] as List).map((e) => Wi.fromJson(e)).toList(),
    };
    return data;
  }

  Future<Map<String, dynamic>> searchWi(String query) async {
    var url = 'wi-data.php?search=$query';
    final response = await WHttpHelper.get(url);

    final data = {
      'currentPage': response['currentPage'],
      'totalPages': response['totalPages'],
      'items': (response['items'] as List).map((e) => Wi.fromJson(e)).toList(),
    };
    return data;
  }
}

and this is my screen page

import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import '../../../../common/styles/spacing_styles.dart';
import '../../../../common/widgets/shadow_search_form.dart';
import '../../../../utils/constants/colors.dart';
import '../../../../utils/constants/sizes.dart';
import '../../../../utils/devices/device_utility.dart';
import '../../controllers/wi_controller.dart';
import 'search.wi_widget/ticket_widget.dart';

class SearchWi extends StatelessWidget {
  const SearchWi({super.key});

  @override
  Widget build(BuildContext context) {
    final WiController state = Get.put(WiController());
    final TextEditingController searchTextController = state.searchTextController;

    final ScrollController scrollController = ScrollController();
    scrollController.addListener(() {
      if (scrollController.position.pixels == scrollController.position.maxScrollExtent) {
        state.loadMoreWi();
      }
    });

    return Scaffold(
      appBar: AppBar(
        backgroundColor: WColors.light,
        title: ShadowSearchForm(
          onSearch: (value) {
            state.filterWi(value);
          },
          controller: searchTextController,
          focusColor: WColors.primary,
          hasBoxShadow: false,
          readOnly: false,
          height: 40,
          showCursor: true,
        ),
      ),
      backgroundColor: WColors.light,
      body: GestureDetector(
        onTap: () {
          WDeviceUtils.hideKeyboard(context);
        },
        child: Obx(() {
          if (state.isLoading.value && state.allWi.isEmpty) {
            return const Center(
              child: CircularProgressIndicator(
                color: WColors.secondary,
              ),
            );
          }

          // Log data untuk debugging
          if (kDebugMode) {
            print('Displaying data: ${state.filteredWi}');
          }

          return ListView.builder(
            controller: scrollController,
            itemCount: state.filteredWi.length + (state.currentPage.value < state.totalPages.value ? 1 : 0),
            itemBuilder: (context, index) {
              if (index < state.filteredWi.length) {
                return Padding(
                  padding: WSpacingStyle.ticketPadding,
                  child: TicketWidget(index: index),
                );
              } else {
                return const Padding(
                  padding: EdgeInsets.all(WSizes.defaultSpace),
                  child: Center(
                    child: CircularProgressIndicator(
                      color: WColors.secondary,
                    ),
                  ),
                );
              }
            },
          );
        }),
      ),
    );
  }
}

the problem is, can't load data in another page

only show loading, i've waited 1 hour to make sure

1 Answer 1

0

Try with this package: ts_paginated_list

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.