new changes verison 2.0.1
@ -28,7 +28,7 @@ if (flutterVersionName == null) {
|
||||
}
|
||||
|
||||
android {
|
||||
namespace = "com.example.cheminova"
|
||||
namespace = "com.example.tm_cheminova"
|
||||
compileSdk = flutter.compileSdkVersion
|
||||
ndkVersion = flutter.ndkVersion
|
||||
|
||||
@ -39,7 +39,7 @@ android {
|
||||
|
||||
defaultConfig {
|
||||
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
|
||||
applicationId = "com.example.cheminova"
|
||||
applicationId = "com.example.tm_cheminova"
|
||||
// You can update the following values to match your application needs.
|
||||
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-gradle-build-configuration.
|
||||
minSdk = flutter.minSdkVersion
|
||||
|
@ -9,7 +9,7 @@
|
||||
"client_info": {
|
||||
"mobilesdk_app_id": "1:242950171023:android:7fdc614b0429b52445c3fa",
|
||||
"android_client_info": {
|
||||
"package_name": "com.example.cheminova"
|
||||
"package_name": "com.example.tm_cheminova"
|
||||
}
|
||||
},
|
||||
"oauth_client": [],
|
||||
|
@ -1,4 +1,5 @@
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
package="com.example.tm_cheminova">
|
||||
|
||||
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
|
||||
@ -7,7 +8,7 @@
|
||||
<application
|
||||
android:label="Territory Manager"
|
||||
android:name="${applicationName}"
|
||||
android:icon="@mipmap/ic_launcher">
|
||||
android:icon="@mipmap/launcher_icon">
|
||||
<activity
|
||||
android:name=".MainActivity"
|
||||
android:exported="true"
|
||||
|
@ -1,4 +1,4 @@
|
||||
package com.example.cheminova
|
||||
package com.example.tm_cheminova
|
||||
|
||||
import io.flutter.embedding.android.FlutterActivity
|
||||
|
||||
|
BIN
assets/app-icon-territory-manager.png
Normal file
After Width: | Height: | Size: 23 KiB |
@ -427,7 +427,7 @@
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES;
|
||||
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
@ -484,7 +484,7 @@
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES;
|
||||
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
|
@ -1,122 +1 @@
|
||||
{
|
||||
"images" : [
|
||||
{
|
||||
"size" : "20x20",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-20x20@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "20x20",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-20x20@3x.png",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"size" : "29x29",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-29x29@1x.png",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"size" : "29x29",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-29x29@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "29x29",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-29x29@3x.png",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"size" : "40x40",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-40x40@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "40x40",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-40x40@3x.png",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"size" : "60x60",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-60x60@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "60x60",
|
||||
"idiom" : "iphone",
|
||||
"filename" : "Icon-App-60x60@3x.png",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"size" : "20x20",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-20x20@1x.png",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"size" : "20x20",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-20x20@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "29x29",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-29x29@1x.png",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"size" : "29x29",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-29x29@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "40x40",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-40x40@1x.png",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"size" : "40x40",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-40x40@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "76x76",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-76x76@1x.png",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"size" : "76x76",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-76x76@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "83.5x83.5",
|
||||
"idiom" : "ipad",
|
||||
"filename" : "Icon-App-83.5x83.5@2x.png",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"size" : "1024x1024",
|
||||
"idiom" : "ios-marketing",
|
||||
"filename" : "Icon-App-1024x1024@1x.png",
|
||||
"scale" : "1x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"version" : 1,
|
||||
"author" : "xcode"
|
||||
}
|
||||
}
|
||||
{"images":[{"size":"20x20","idiom":"iphone","filename":"Icon-App-20x20@2x.png","scale":"2x"},{"size":"20x20","idiom":"iphone","filename":"Icon-App-20x20@3x.png","scale":"3x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@1x.png","scale":"1x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@2x.png","scale":"2x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@3x.png","scale":"3x"},{"size":"40x40","idiom":"iphone","filename":"Icon-App-40x40@2x.png","scale":"2x"},{"size":"40x40","idiom":"iphone","filename":"Icon-App-40x40@3x.png","scale":"3x"},{"size":"57x57","idiom":"iphone","filename":"Icon-App-57x57@1x.png","scale":"1x"},{"size":"57x57","idiom":"iphone","filename":"Icon-App-57x57@2x.png","scale":"2x"},{"size":"60x60","idiom":"iphone","filename":"Icon-App-60x60@2x.png","scale":"2x"},{"size":"60x60","idiom":"iphone","filename":"Icon-App-60x60@3x.png","scale":"3x"},{"size":"20x20","idiom":"ipad","filename":"Icon-App-20x20@1x.png","scale":"1x"},{"size":"20x20","idiom":"ipad","filename":"Icon-App-20x20@2x.png","scale":"2x"},{"size":"29x29","idiom":"ipad","filename":"Icon-App-29x29@1x.png","scale":"1x"},{"size":"29x29","idiom":"ipad","filename":"Icon-App-29x29@2x.png","scale":"2x"},{"size":"40x40","idiom":"ipad","filename":"Icon-App-40x40@1x.png","scale":"1x"},{"size":"40x40","idiom":"ipad","filename":"Icon-App-40x40@2x.png","scale":"2x"},{"size":"50x50","idiom":"ipad","filename":"Icon-App-50x50@1x.png","scale":"1x"},{"size":"50x50","idiom":"ipad","filename":"Icon-App-50x50@2x.png","scale":"2x"},{"size":"72x72","idiom":"ipad","filename":"Icon-App-72x72@1x.png","scale":"1x"},{"size":"72x72","idiom":"ipad","filename":"Icon-App-72x72@2x.png","scale":"2x"},{"size":"76x76","idiom":"ipad","filename":"Icon-App-76x76@1x.png","scale":"1x"},{"size":"76x76","idiom":"ipad","filename":"Icon-App-76x76@2x.png","scale":"2x"},{"size":"83.5x83.5","idiom":"ipad","filename":"Icon-App-83.5x83.5@2x.png","scale":"2x"},{"size":"1024x1024","idiom":"ios-marketing","filename":"Icon-App-1024x1024@1x.png","scale":"1x"}],"info":{"version":1,"author":"xcode"}}
|
Before Width: | Height: | Size: 11 KiB After Width: | Height: | Size: 225 KiB |
Before Width: | Height: | Size: 295 B After Width: | Height: | Size: 795 B |
Before Width: | Height: | Size: 406 B After Width: | Height: | Size: 2.2 KiB |
Before Width: | Height: | Size: 450 B After Width: | Height: | Size: 4.1 KiB |
Before Width: | Height: | Size: 282 B After Width: | Height: | Size: 1.4 KiB |
Before Width: | Height: | Size: 462 B After Width: | Height: | Size: 3.9 KiB |
Before Width: | Height: | Size: 704 B After Width: | Height: | Size: 7.3 KiB |
Before Width: | Height: | Size: 406 B After Width: | Height: | Size: 2.2 KiB |
Before Width: | Height: | Size: 586 B After Width: | Height: | Size: 6.5 KiB |
Before Width: | Height: | Size: 862 B After Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 862 B After Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 1.6 KiB After Width: | Height: | Size: 21 KiB |
Before Width: | Height: | Size: 762 B After Width: | Height: | Size: 5.9 KiB |
Before Width: | Height: | Size: 1.2 KiB After Width: | Height: | Size: 17 KiB |
Before Width: | Height: | Size: 1.4 KiB After Width: | Height: | Size: 19 KiB |
@ -63,7 +63,7 @@ class DefaultFirebaseOptions {
|
||||
messagingSenderId: '242950171023',
|
||||
projectId: 'cheminova-1fcf0',
|
||||
storageBucket: 'cheminova-1fcf0.appspot.com',
|
||||
iosBundleId: 'com.example.cheminova',
|
||||
iosBundleId: 'com.example.tm_cheminova',
|
||||
);
|
||||
|
||||
}
|
@ -24,33 +24,54 @@ class AddSalesProvider with ChangeNotifier {
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
// Future<void> getTask() async {
|
||||
// setLoading(true);
|
||||
// try {
|
||||
// Response response = await _apiClient.get(ApiUrls.salesTaskUrl);
|
||||
// setLoading(false);
|
||||
// if (response.statusCode == 200) {
|
||||
// final data = SalesTaskResponse.fromJson(response.data);
|
||||
// tasksList = data.products ?? [];
|
||||
// notifyListeners();
|
||||
// }
|
||||
// } catch (e) {
|
||||
// String error = "Something went wrong";
|
||||
// if (e is DioException) {
|
||||
// error = e.response!.data['message'] ?? "Something went wrong";
|
||||
// }
|
||||
// ScaffoldMessenger.of(
|
||||
// navigatorKey.currentContext!,
|
||||
// ).showSnackBar(
|
||||
// SnackBar(
|
||||
// content: Text(
|
||||
// error,
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// setLoading(false);
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
Future<void> getTask() async {
|
||||
setLoading(true);
|
||||
try {
|
||||
Response response = await _apiClient.get(ApiUrls.salesTaskUrl);
|
||||
setLoading(false);
|
||||
bool moreDataAvailable = true;
|
||||
int page = 1;
|
||||
|
||||
// Loop to fetch all pages
|
||||
while (moreDataAvailable) {
|
||||
Response response = await _apiClient.get(
|
||||
'${ApiUrls.salesTaskUrl}?page=$page');
|
||||
if (response.statusCode == 200) {
|
||||
// productResponse = ProductResponse.fromJson(response.data);
|
||||
final data = SalesTaskResponse.fromJson(response.data);
|
||||
tasksList = data.products ?? [];
|
||||
notifyListeners();
|
||||
}
|
||||
} catch (e) {
|
||||
String error = "Something went wrong";
|
||||
if (e is DioException) {
|
||||
error = e.response!.data['message'] ?? "Something went wrong";
|
||||
}
|
||||
ScaffoldMessenger.of(
|
||||
navigatorKey.currentContext!,
|
||||
).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
error,
|
||||
),
|
||||
),
|
||||
);
|
||||
setLoading(false);
|
||||
tasksList.addAll(data.products ?? []); // Add new products to the list
|
||||
moreDataAvailable = data.totalPages! > page;
|
||||
page++;
|
||||
notifyListeners(); // Notify listeners to update the UI with the new product list
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void filterProducts(String val) {
|
||||
tasksList = tasksList.where((element) {
|
||||
|
@ -10,7 +10,7 @@ import '../services/api_urls.dart';
|
||||
|
||||
class NotificationProvider extends ChangeNotifier {
|
||||
NotificationProvider() {
|
||||
getNotification();
|
||||
// getNotification();
|
||||
}
|
||||
|
||||
final _apiClient = ApiClient();
|
||||
@ -41,24 +41,44 @@ class NotificationProvider extends ChangeNotifier {
|
||||
void setDate(String date) {
|
||||
_selectedDate = date;
|
||||
notifyListeners();
|
||||
getNotification();
|
||||
//getNotification();
|
||||
}
|
||||
|
||||
Future<void> getNotification() async {
|
||||
clearLists();
|
||||
// Future<void> getNotification() async {
|
||||
// clearLists();
|
||||
// setLoading(true);
|
||||
// try {
|
||||
// Response response = await _apiClient
|
||||
// .get('${ApiUrls.notificationUrl}?Date=$_selectedDate');
|
||||
// setLoading(false);
|
||||
// if (response.statusCode == 200) {
|
||||
// final data = NotificationListResponse.fromJson(response.data);
|
||||
// notificationList = data.notifications ?? [];
|
||||
// notifyListeners();
|
||||
// }
|
||||
// } catch (e) {
|
||||
// setLoading(false);
|
||||
// }
|
||||
// }
|
||||
|
||||
Future<void> getNotification(String date) async {
|
||||
if (date.isEmpty) return; // Invalid call ko prevent karein
|
||||
final String url = "${ApiUrls.notificationUrl}?Date=$date";
|
||||
|
||||
setLoading(true);
|
||||
try {
|
||||
Response response = await _apiClient
|
||||
.get('${ApiUrls.notificationUrl}?Date=$_selectedDate');
|
||||
setLoading(false);
|
||||
Response response = await _apiClient.get(url);
|
||||
if (response.statusCode == 200) {
|
||||
final data = NotificationListResponse.fromJson(response.data);
|
||||
notificationList = data.notifications ?? [];
|
||||
notifyListeners();
|
||||
} else {
|
||||
notificationList = [];
|
||||
}
|
||||
} catch (e) {
|
||||
setLoading(false);
|
||||
notificationList = [];
|
||||
}
|
||||
setLoading(false);
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
Future<void> getAnnouncement(int page, int rowsPerPage) async {
|
||||
|
@ -7,7 +7,7 @@ import 'package:flutter/material.dart';
|
||||
|
||||
class ProductProvider extends ChangeNotifier {
|
||||
ProductProvider() {
|
||||
getProducts();
|
||||
getProducts(1);
|
||||
}
|
||||
|
||||
final _apiClient = ApiClient();
|
||||
@ -26,34 +26,71 @@ class ProductProvider extends ChangeNotifier {
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
Future<void> getProducts() async {
|
||||
setLoading(true);
|
||||
// Future<List<Product>?> getProducts(int page) async {
|
||||
// setLoading(true);
|
||||
// try {
|
||||
// Response response = await _apiClient.get("${ApiUrls.getProducts}?page=$page");
|
||||
// setLoading(false);
|
||||
// if (response.statusCode == 200) {
|
||||
// productResponse = ProductResponse.fromJson(response.data);
|
||||
// productList = productResponse!.products;
|
||||
// //notifyListeners();
|
||||
// }
|
||||
// } catch (e) {
|
||||
// setLoading(false);
|
||||
// String error = "Something went wrong";
|
||||
// if (e is DioException) {
|
||||
// error = e.response!.data['message'] ?? "Something went wrong";
|
||||
// }
|
||||
// ScaffoldMessenger.of(
|
||||
// navigatorKey.currentContext!,
|
||||
// ).showSnackBar(
|
||||
// SnackBar(
|
||||
// content: Text(
|
||||
// error,
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
Future<void> getProducts(int page) async {
|
||||
// if (_isLoading) return; // Prevent duplicate requests
|
||||
// setLoading(true);
|
||||
try {
|
||||
Response response = await _apiClient.get(ApiUrls.getProducts);
|
||||
setLoading(false);
|
||||
Response response = await _apiClient.get("${ApiUrls.getProducts}?page=$page");
|
||||
if (response.statusCode == 200) {
|
||||
productResponse = ProductResponse.fromJson(response.data);
|
||||
productList = productResponse!.products;
|
||||
notifyListeners();
|
||||
final newProductResponse = ProductResponse.fromJson(response.data);
|
||||
if (newProductResponse.products.isNotEmpty) {
|
||||
// if (page == 6) {
|
||||
// // Clear the list if it's the first page
|
||||
// productList = newProductResponse.products;
|
||||
// } else {
|
||||
// Append new products for subsequent pages
|
||||
productList.addAll(newProductResponse.products);
|
||||
}
|
||||
// _isLoading = false;
|
||||
// notifyListeners();
|
||||
// }
|
||||
}
|
||||
} catch (e) {
|
||||
setLoading(false);
|
||||
String error = "Something went wrong";
|
||||
if (e is DioException) {
|
||||
error = e.response!.data['message'] ?? "Something went wrong";
|
||||
error = e.response?.data['message'] ?? "Something went wrong";
|
||||
}
|
||||
ScaffoldMessenger.of(
|
||||
navigatorKey.currentContext!,
|
||||
).showSnackBar(
|
||||
ScaffoldMessenger.of(navigatorKey.currentContext!).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
error,
|
||||
),
|
||||
content: Text(error),
|
||||
),
|
||||
);
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
Future<bool> submitSelectedProducts(
|
||||
String addedFor, String addedForId) async {
|
||||
setLoading(true);
|
||||
@ -99,3 +136,125 @@ class ProductProvider extends ChangeNotifier {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
// import 'package:cheminova/constants/constant.dart';
|
||||
// import 'package:cheminova/models/product_model.dart';
|
||||
// import 'package:cheminova/services/api_client.dart';
|
||||
// import 'package:cheminova/services/api_urls.dart';
|
||||
// import 'package:dio/dio.dart';
|
||||
// import 'package:flutter/material.dart';
|
||||
//
|
||||
// class ProductProvider extends ChangeNotifier {
|
||||
// ProductProvider() {
|
||||
// // Initialize with the first page of products
|
||||
// getProducts(1);
|
||||
// }
|
||||
//
|
||||
// final _apiClient = ApiClient();
|
||||
// ProductResponse? productResponse; // To parse and store API response
|
||||
// List<Product> productList = []; // Main list of products
|
||||
// final List<Product> _selectedProducts = []; // For user-selected products
|
||||
//
|
||||
// bool _isLoading = false;
|
||||
// bool _hasMoreData = true; // Track if more data is available
|
||||
//
|
||||
// bool get isLoading => _isLoading;
|
||||
// bool get hasMoreData => _hasMoreData;
|
||||
//
|
||||
// List<Product> get selectedProducts => _selectedProducts;
|
||||
//
|
||||
// void setLoading(bool loading) {
|
||||
// _isLoading = loading;
|
||||
// notifyListeners();
|
||||
// }
|
||||
//
|
||||
// Future<void> getProducts(int page) async {
|
||||
// if (_isLoading || !_hasMoreData) return; // Prevent duplicate requests
|
||||
// setLoading(true);
|
||||
//
|
||||
// try {
|
||||
// final String url = "${ApiUrls.getProducts}?page=$page";
|
||||
// Response response = await _apiClient.get(url);
|
||||
//
|
||||
// if (response.statusCode == 200) {
|
||||
// productResponse = ProductResponse.fromJson(response.data);
|
||||
//
|
||||
// if (productResponse!.products.isNotEmpty) {
|
||||
//
|
||||
// selectedProducts.addAll(productResponse!.products);
|
||||
// // if (page <= productResponse!.totalPages) {
|
||||
// // // Replace the list if fetching the first page
|
||||
// // productList = productResponse!.products;
|
||||
// // } else {
|
||||
// // // Append new products for subsequent pages
|
||||
// // productList.addAll(productResponse!.products);
|
||||
// // }
|
||||
// notifyListeners();
|
||||
// } else {
|
||||
// // No more products to load
|
||||
// _hasMoreData = false;
|
||||
// }
|
||||
// }
|
||||
// } catch (e) {
|
||||
// String error = "Something went wrong";
|
||||
// if (e is DioException) {
|
||||
// error = e.response?.data['message'] ?? "Something went wrong";
|
||||
// }
|
||||
// ScaffoldMessenger.of(
|
||||
// navigatorKey.currentContext!,
|
||||
// ).showSnackBar(
|
||||
// SnackBar(
|
||||
// content: Text(error),
|
||||
// ),
|
||||
// );
|
||||
// } finally {
|
||||
// setLoading(false);
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// Future<bool> submitSelectedProducts(String addedFor, String addedForId) async {
|
||||
// setLoading(true);
|
||||
//
|
||||
// try {
|
||||
// final data = {
|
||||
// "products": selectedProducts.map((product) {
|
||||
// return {
|
||||
// "SKU": product.SKU,
|
||||
// "ProductName": product.name,
|
||||
// "Sale": product.sale,
|
||||
// "Inventory": product.inventory,
|
||||
// "productid": product.id,
|
||||
// };
|
||||
// }).toList(),
|
||||
// "addedFor": addedFor,
|
||||
// "addedForId": addedForId,
|
||||
// };
|
||||
//
|
||||
// Response response =
|
||||
// await _apiClient.post(ApiUrls.submitProducts, data: data);
|
||||
//
|
||||
// if (response.statusCode == 201) {
|
||||
// return true;
|
||||
// } else {
|
||||
// return false;
|
||||
// }
|
||||
// } catch (e) {
|
||||
// String error = "Something went wrong";
|
||||
// if (e is DioException) {
|
||||
// error = e.response?.data['message'] ?? "Something went wrong";
|
||||
// }
|
||||
// ScaffoldMessenger.of(
|
||||
// navigatorKey.currentContext!,
|
||||
// ).showSnackBar(
|
||||
// SnackBar(
|
||||
// content: Text(error),
|
||||
// ),
|
||||
// );
|
||||
// return false;
|
||||
// } finally {
|
||||
// setLoading(false);
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
@ -10,6 +10,9 @@ import 'package:cheminova/widgets/common_elevated_button.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
|
||||
|
||||
|
||||
|
||||
class AddProductsScreen extends StatefulWidget {
|
||||
final PdRdResponseModel distributor;
|
||||
final String distributorType;
|
||||
@ -26,20 +29,100 @@ class AddProductsScreen extends StatefulWidget {
|
||||
class _AddProductsScreenState extends State<AddProductsScreen> {
|
||||
List<Product> filteredProducts = [];
|
||||
final searchController = TextEditingController();
|
||||
final ScrollController scrollController = ScrollController();
|
||||
late ProductProvider provider;
|
||||
|
||||
int currentpage = 1;
|
||||
bool hasMoreData = true; // To track if more data is available
|
||||
bool isLoading = false; // To track loading state
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
provider = Provider.of<ProductProvider>(context, listen: false);
|
||||
loadProducts();
|
||||
|
||||
scrollController.addListener(() {
|
||||
if (scrollController.position.pixels ==
|
||||
scrollController.position.maxScrollExtent) {
|
||||
loadProducts();
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// Future<void> loadProducts() async {
|
||||
// // provider = Provider.of<ProductProvider>(context, listen: false);
|
||||
// await provider.getProducts(currentpage);
|
||||
// setState(() {
|
||||
// //provider.selectedProducts.clear();
|
||||
// // isLoading = true;
|
||||
// currentpage++;
|
||||
// filteredProducts = provider.productList;
|
||||
// });
|
||||
// }
|
||||
|
||||
|
||||
// Future<void> loadProducts() async {
|
||||
// if (isLoading || !hasMoreData) return; // Prevent multiple simultaneous calls
|
||||
//
|
||||
// setState(() {
|
||||
// isLoading = true; // Show loading state
|
||||
// });
|
||||
//
|
||||
// // Fetch products from the provider
|
||||
// await provider.getProducts(currentpage);
|
||||
//
|
||||
// setState(() {
|
||||
// final newProducts = provider.productList;
|
||||
//
|
||||
// // Add only unique products to the list
|
||||
// for (var product in newProducts) {
|
||||
// if (!filteredProducts.any((p) => p.id == product.id)) {
|
||||
// filteredProducts.add(product);
|
||||
//
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// // Check if more data is available
|
||||
// hasMoreData = newProducts.isNotEmpty;
|
||||
//
|
||||
// isLoading = false; // Remove loading state
|
||||
// currentpage++;
|
||||
// });
|
||||
// }
|
||||
|
||||
|
||||
Future<void> loadProducts() async {
|
||||
provider = Provider.of<ProductProvider>(context, listen: false);
|
||||
await provider.getProducts();
|
||||
if (isLoading || !hasMoreData) return; // Prevent duplicate API calls
|
||||
setState(() {
|
||||
provider.selectedProducts.clear();
|
||||
filteredProducts = provider.productList;
|
||||
isLoading = true;
|
||||
});
|
||||
|
||||
// Fetch products
|
||||
await provider.getProducts(currentpage);
|
||||
|
||||
setState(() {
|
||||
final newProducts = provider.productList;
|
||||
|
||||
// Add only unique products to filteredProducts
|
||||
for (var product in newProducts) {
|
||||
if (!filteredProducts.any((p) => p.id == product.id)) {
|
||||
filteredProducts.add(product);
|
||||
}
|
||||
}
|
||||
|
||||
currentpage++;
|
||||
isLoading = false;
|
||||
|
||||
// If no new products are returned, stop further API calls
|
||||
if (newProducts.isEmpty) {
|
||||
hasMoreData = false;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@ -149,9 +232,19 @@ class _AddProductsScreenState extends State<AddProductsScreen> {
|
||||
),
|
||||
Expanded(
|
||||
child: ListView.builder(
|
||||
controller: scrollController,
|
||||
itemCount:
|
||||
filteredProducts.length,
|
||||
filteredProducts.length +(isLoading ? 1 : 0),
|
||||
itemBuilder: (context, index) {
|
||||
if (index == filteredProducts.length) {
|
||||
// Show a loading indicator while fetching more products
|
||||
return const Center(
|
||||
child: Padding(
|
||||
padding: EdgeInsets.all(16.0),
|
||||
child: CircularProgressIndicator(),
|
||||
),
|
||||
);
|
||||
}
|
||||
bool isAlreadySelected =
|
||||
provider.selectedProducts
|
||||
.contains(
|
||||
@ -261,6 +354,306 @@ class _AddProductsScreenState extends State<AddProductsScreen> {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// class AddProductsScreen extends StatefulWidget {
|
||||
// final PdRdResponseModel distributor;
|
||||
// final String distributorType;
|
||||
// const AddProductsScreen({
|
||||
// super.key,
|
||||
// required this.distributor,
|
||||
// required this.distributorType,
|
||||
// });
|
||||
//
|
||||
// @override
|
||||
// State<AddProductsScreen> createState() => _AddProductsScreenState();
|
||||
// }
|
||||
|
||||
|
||||
// class _AddProductsScreenState extends State<AddProductsScreen> {
|
||||
// List<Product> filteredProducts = [];
|
||||
// final searchController = TextEditingController();
|
||||
// late ProductProvider provider;
|
||||
// int currentPage = 1;
|
||||
// bool isLoadingMore = false;
|
||||
// bool hasMoreProducts = true;
|
||||
// final ScrollController scrollController = ScrollController();
|
||||
//
|
||||
// @override
|
||||
// void initState() {
|
||||
// super.initState();
|
||||
// provider = Provider.of<ProductProvider>(context, listen: false);
|
||||
// // loadProducts();
|
||||
//
|
||||
// provider.getProducts(currentPage);
|
||||
// scrollController.addListener(() {
|
||||
// if (scrollController.position.pixels == scrollController.position.maxScrollExtent) {
|
||||
// // Load the next page when reaching the bottom
|
||||
// currentPage++;
|
||||
// provider.getProducts(currentPage);
|
||||
// }
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// Future<void> loadProducts() async {
|
||||
// await provider.getProducts(currentPage);
|
||||
//
|
||||
// setState(() {
|
||||
// filteredProducts = provider.productList;
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// Future<void> loadMoreProducts() async {
|
||||
// setState(() {
|
||||
// isLoadingMore = true;
|
||||
// });
|
||||
//
|
||||
// currentPage++;
|
||||
// await provider.getProducts(currentPage);
|
||||
//
|
||||
// setState(() {
|
||||
// // Check if more products were fetched
|
||||
// if (provider.productList.isEmpty) {
|
||||
// hasMoreProducts = false; // No more products to load
|
||||
// } else {
|
||||
// filteredProducts.addAll(provider.productList);
|
||||
// }
|
||||
// isLoadingMore = false;
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// void filterProducts(String query) {
|
||||
// setState(() {
|
||||
// filteredProducts = provider.productList.where((product) {
|
||||
// final productNameLower = product.name.toLowerCase();
|
||||
// final productSkuLower = product.SKU.toLowerCase();
|
||||
// final searchLower = query.toLowerCase();
|
||||
//
|
||||
// return productNameLower.contains(searchLower) ||
|
||||
// productSkuLower.contains(searchLower);
|
||||
// }).toList();
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// @override
|
||||
// Widget build(BuildContext context) {
|
||||
// return CommonBackground(
|
||||
// child: Scaffold(
|
||||
// backgroundColor: Colors.transparent,
|
||||
// appBar: CommonAppBar(
|
||||
// actions: [
|
||||
// IconButton(
|
||||
// onPressed: () {
|
||||
// Navigator.pop(context);
|
||||
// },
|
||||
// icon: Image.asset('assets/Back_attendance.png'),
|
||||
// padding: const EdgeInsets.only(right: 20),
|
||||
// ),
|
||||
// ],
|
||||
// title: Text(
|
||||
// widget.distributor.name!.capitalize(),
|
||||
// style: const TextStyle(
|
||||
// fontSize: 20,
|
||||
// color: Colors.black,
|
||||
// fontWeight: FontWeight.w400,
|
||||
// fontFamily: 'Anek',
|
||||
// ),
|
||||
// ),
|
||||
// backgroundColor: Colors.transparent,
|
||||
// elevation: 0,
|
||||
// ),
|
||||
// drawer: const CommonDrawer(),
|
||||
// body: Consumer<ProductProvider>(
|
||||
// builder: (context, provider, child) {
|
||||
// if (provider.isLoading && provider.productList.isEmpty) {
|
||||
// return const Center(child: CircularProgressIndicator());
|
||||
// }
|
||||
//
|
||||
// return Stack(
|
||||
// children: [
|
||||
// Column(
|
||||
// children: [
|
||||
// if (provider.selectedProducts.isNotEmpty)
|
||||
// Expanded(
|
||||
// child: ListView.builder(
|
||||
// //controller: scrollController,
|
||||
// itemCount: filteredProducts.length , // Add 1 for the loading indicator
|
||||
// itemBuilder: (context, index) {
|
||||
// final product = provider.productList[index];
|
||||
// if (index < filteredProducts.length) {
|
||||
// return ProductBlock(index: index);
|
||||
// } else if (isLoadingMore) {
|
||||
// return const Center(
|
||||
// child: Padding(
|
||||
// padding: EdgeInsets.all(16.0),
|
||||
// child: CircularProgressIndicator(),
|
||||
// ),
|
||||
// );
|
||||
// } else {
|
||||
// return const SizedBox(); // Empty widget when no more products to load
|
||||
// }
|
||||
// },
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
// Align(
|
||||
// alignment: provider.selectedProducts.isEmpty
|
||||
// ? Alignment.center
|
||||
// : Alignment.bottomCenter,
|
||||
// child: Padding(
|
||||
// padding: const EdgeInsets.all(16.0),
|
||||
// child: Column(
|
||||
// mainAxisSize: MainAxisSize.min,
|
||||
// children: [
|
||||
// FloatingActionButton.extended(
|
||||
// onPressed: () {
|
||||
// showModalBottomSheet(
|
||||
// isScrollControlled: true,
|
||||
// constraints: BoxConstraints(
|
||||
// maxHeight:
|
||||
// MediaQuery.of(context).size.height * 0.9,
|
||||
// ),
|
||||
// context: context,
|
||||
// builder: (BuildContext context) {
|
||||
// return Consumer<ProductProvider>(
|
||||
// builder: (context, value, child) =>
|
||||
// StatefulBuilder(
|
||||
// builder: (context, setState) {
|
||||
// return Column(
|
||||
// children: [
|
||||
// Padding(
|
||||
// padding: const EdgeInsets.all(18.0),
|
||||
// child: TextField(
|
||||
// controller: searchController,
|
||||
// decoration: const InputDecoration(
|
||||
// labelText:
|
||||
// 'Search by name or SKU',
|
||||
// border: OutlineInputBorder(),
|
||||
// prefixIcon: Icon(Icons.search),
|
||||
// ),
|
||||
// onChanged: (value) {
|
||||
// filterProducts(value);
|
||||
// setState(() {});
|
||||
// },
|
||||
// ),
|
||||
// ),
|
||||
// Expanded(
|
||||
// child: ListView.builder(
|
||||
// controller: scrollController,
|
||||
// itemCount: provider.productList.length,
|
||||
// itemBuilder: (context, index) {
|
||||
// final product = provider.productList[index];
|
||||
// bool isAlreadySelected = provider
|
||||
// .selectedProducts
|
||||
// .contains(
|
||||
// product);
|
||||
// return Card(
|
||||
// child: ListTile(
|
||||
// title: Text(
|
||||
// product
|
||||
// .name
|
||||
// .capitalize(),
|
||||
// style: TextStyle(
|
||||
// color: isAlreadySelected
|
||||
// ? Colors.grey
|
||||
// : Colors.black,
|
||||
// ),
|
||||
// ),
|
||||
// subtitle: Text(
|
||||
// product.SKU,
|
||||
// style: TextStyle(
|
||||
// color: isAlreadySelected
|
||||
// ? Colors.grey
|
||||
// : Colors.black,
|
||||
// ),
|
||||
// ),
|
||||
// onTap: isAlreadySelected
|
||||
// ? null
|
||||
// : () {
|
||||
// setState(() {
|
||||
// provider
|
||||
// .selectedProducts
|
||||
// .add(
|
||||
// product);
|
||||
// });
|
||||
// Navigator.pop(
|
||||
// context);
|
||||
// },
|
||||
// ),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// );
|
||||
// },
|
||||
// ).whenComplete(() {
|
||||
// setState(() {});
|
||||
// });
|
||||
// },
|
||||
// backgroundColor: Colors.white,
|
||||
// icon: const Icon(Icons.add, color: Colors.black),
|
||||
// label: const Text(
|
||||
// 'Add Products',
|
||||
// style: TextStyle(color: Colors.black),
|
||||
// ),
|
||||
// ),
|
||||
// if (provider.selectedProducts.isNotEmpty) ...[
|
||||
// const SizedBox(height: 16.0),
|
||||
// CommonElevatedButton(
|
||||
// borderRadius: 30,
|
||||
// width: double.infinity,
|
||||
// height: kToolbarHeight - 10,
|
||||
// text: 'SUBMIT',
|
||||
// backgroundColor: const Color(0xff004791),
|
||||
// onPressed: () {
|
||||
// provider
|
||||
// .submitSelectedProducts(
|
||||
// (widget.distributorType ==
|
||||
// 'Principal Distributor')
|
||||
// ? 'PrincipalDistributor'
|
||||
// : 'RetailDistributor',
|
||||
// widget.distributor.id!)
|
||||
// .then((value) {
|
||||
// if (value) {
|
||||
// Navigator.push(
|
||||
// context,
|
||||
// MaterialPageRoute(
|
||||
// builder: (context) =>
|
||||
// const DataSubmitSuccessfull(),
|
||||
// ),
|
||||
// );
|
||||
// } else {
|
||||
// ScaffoldMessenger.of(context).showSnackBar(
|
||||
// const SnackBar(
|
||||
// content: Text("Insufficient stock"),
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// });
|
||||
// },
|
||||
// ),
|
||||
// ],
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class ProductBlock extends StatefulWidget {
|
||||
final int index;
|
||||
|
||||
@ -354,3 +747,96 @@ class _ProductBlockState extends State<ProductBlock> {
|
||||
);
|
||||
}
|
||||
}
|
||||
// class ProductBlock extends StatefulWidget {
|
||||
// final int index;
|
||||
//
|
||||
// const ProductBlock({super.key, required this.index});
|
||||
//
|
||||
// @override
|
||||
// State<ProductBlock> createState() => _ProductBlockState();
|
||||
// }
|
||||
//
|
||||
// class _ProductBlockState extends State<ProductBlock> {
|
||||
// final saleController = TextEditingController();
|
||||
// final inventoryController = TextEditingController();
|
||||
// String? errorMessage;
|
||||
// late ProductProvider provider;
|
||||
//
|
||||
// @override
|
||||
// void initState() {
|
||||
// super.initState();
|
||||
// provider = Provider.of<ProductProvider>(context, listen: false);
|
||||
// }
|
||||
//
|
||||
// bool validateInput() {
|
||||
// setState(() {
|
||||
// if (saleController.text.isNotEmpty &&
|
||||
// inventoryController.text.isNotEmpty) {
|
||||
// // Check if both inputs are valid integers
|
||||
// try {
|
||||
// int.parse(saleController.text);
|
||||
// int.parse(inventoryController.text);
|
||||
// } catch (e) {
|
||||
// // Handle the case where input is not a valid integer
|
||||
// errorMessage = 'Please enter valid integer values for both fields';
|
||||
// }
|
||||
// } else {
|
||||
// errorMessage = null;
|
||||
// }
|
||||
// });
|
||||
// return errorMessage == null;
|
||||
// }
|
||||
//
|
||||
// @override
|
||||
// Widget build(BuildContext context) {
|
||||
// return Card(
|
||||
// // color: !widget.product.isPurchased ? Colors.white54 : Colors.white,
|
||||
// color: Colors.white,
|
||||
// margin: const EdgeInsets.all(8),
|
||||
// child: Padding(
|
||||
// padding: const EdgeInsets.all(16),
|
||||
// child: Column(
|
||||
// crossAxisAlignment: CrossAxisAlignment.start,
|
||||
// children: [
|
||||
// Text(
|
||||
// 'Product: ${provider.productList[widget.index].name.capitalize()}',
|
||||
// style: const TextStyle(fontSize: 16)),
|
||||
// Text('SKU: ${provider.productList[widget.index].SKU}',
|
||||
// style: const TextStyle(fontSize: 15)),
|
||||
// const SizedBox(height: 8),
|
||||
// TextField(
|
||||
// controller: saleController,
|
||||
// decoration: const InputDecoration(labelText: 'Sale'),
|
||||
// keyboardType: TextInputType.number,
|
||||
// // enabled: widget.product.isPurchased,
|
||||
// enabled: true,
|
||||
// onChanged: (_) => validateInput()
|
||||
// ? provider.productList[widget.index].sale =
|
||||
// int.parse(saleController.text)
|
||||
// : null,
|
||||
// ),
|
||||
// TextField(
|
||||
// controller: inventoryController,
|
||||
// decoration: const InputDecoration(labelText: 'Inventory'),
|
||||
// keyboardType: TextInputType.number,
|
||||
// // enabled: widget.product.isPurchased,
|
||||
// enabled: true,
|
||||
// onChanged: (_) => validateInput()
|
||||
// ? provider.productList[widget.index].inventory =
|
||||
// int.parse(inventoryController.text)
|
||||
// : null,
|
||||
// ),
|
||||
// if (errorMessage != null)
|
||||
// Padding(
|
||||
// padding: const EdgeInsets.only(top: 8.0),
|
||||
// child: Text(
|
||||
// errorMessage!,
|
||||
// style: const TextStyle(color: Colors.red),
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
|
@ -173,15 +173,15 @@ class _HomePageState extends State<HomePage> {
|
||||
Expanded(
|
||||
child: _buildCustomCard('Update\nSales Data\n', '',
|
||||
onTap: () {
|
||||
Navigator.push(
|
||||
context,
|
||||
MaterialPageRoute(
|
||||
builder: (context) =>
|
||||
const SelectDistributerScreen(
|
||||
task: "Update Sales",
|
||||
),
|
||||
),
|
||||
);
|
||||
// Navigator.push(
|
||||
// context,
|
||||
// MaterialPageRoute(
|
||||
// builder: (context) =>
|
||||
// const SelectDistributerScreen(
|
||||
// task: "Update Sales",
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
}),
|
||||
),
|
||||
],
|
||||
|
@ -7,6 +7,8 @@ import 'package:cheminova/widgets/common_elevated_button.dart';
|
||||
import 'package:intl/intl.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
|
||||
import '../models/notification_list_response.dart';
|
||||
|
||||
class NotificationScreen extends StatefulWidget {
|
||||
const NotificationScreen({super.key});
|
||||
|
||||
@ -23,16 +25,33 @@ class NotificationScreenState extends State<NotificationScreen> {
|
||||
super.initState();
|
||||
}
|
||||
|
||||
// Future<void> _selectDate(BuildContext context) async {
|
||||
// final provider = context.read<NotificationProvider>();
|
||||
// final dateSelected = await showDatePicker(
|
||||
// context: context,
|
||||
// initialDate: DateTime.now(),
|
||||
// firstDate: DateTime(2000),
|
||||
// lastDate: DateTime(2025),
|
||||
// );
|
||||
// if (dateSelected != null) {
|
||||
// provider.setDate(DateFormat('dd/MM/yyyy').format(dateSelected));
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
Future<void> _selectDate(BuildContext context) async {
|
||||
final provider = context.read<NotificationProvider>();
|
||||
final dateSelected = await showDatePicker(
|
||||
DateTime? selectedDate = await showDatePicker(
|
||||
context: context,
|
||||
initialDate: DateTime.now(),
|
||||
firstDate: DateTime(2000),
|
||||
lastDate: DateTime(2025),
|
||||
firstDate: DateTime(2020), // Adjust the start date as needed
|
||||
lastDate: DateTime.now(),
|
||||
);
|
||||
if (dateSelected != null) {
|
||||
provider.setDate(DateFormat('dd/MM/yyyy').format(dateSelected));
|
||||
|
||||
if (selectedDate != null) {
|
||||
// Format the date to dd/MM/yyyy
|
||||
String formattedDate = DateFormat('dd/MM/yyyy').format(selectedDate);
|
||||
// Call the API with the selected date
|
||||
_notificationProvider.getNotification(formattedDate);
|
||||
}
|
||||
}
|
||||
|
||||
@ -61,41 +80,79 @@ class NotificationScreenState extends State<NotificationScreen> {
|
||||
fontFamily: 'Anek')),
|
||||
backgroundColor: Colors.transparent,
|
||||
elevation: 0,
|
||||
),
|
||||
drawer: const CommonDrawer(),
|
||||
body: Consumer<NotificationProvider>(
|
||||
builder: (context, value, child) => value.isLoading
|
||||
? const Center(child: CircularProgressIndicator())
|
||||
: Column(
|
||||
children: [
|
||||
Container(
|
||||
margin: const EdgeInsets.all(10),
|
||||
padding: const EdgeInsets.symmetric(horizontal: 10),
|
||||
decoration: const BoxDecoration(
|
||||
color: Colors.white,
|
||||
borderRadius: BorderRadius.all(Radius.circular(10)),
|
||||
),
|
||||
child: Row(
|
||||
// mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
value.selectedDate,
|
||||
),
|
||||
IconButton(
|
||||
bottom: PreferredSize(
|
||||
preferredSize: Size.fromHeight(80),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16.0),
|
||||
child: TextButton(
|
||||
onPressed: () {
|
||||
_selectDate(context);
|
||||
},
|
||||
child:
|
||||
Row(
|
||||
children: [
|
||||
Text("Select Date: ",style: TextStyle(fontWeight: FontWeight.bold,fontSize: 18),),
|
||||
IconButton(
|
||||
icon: const Icon(Icons.calendar_today),
|
||||
onPressed: () {
|
||||
_selectDate(context);
|
||||
},
|
||||
icon: const Icon(Icons.calendar_month),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
MyListView(value: value),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
drawer: const CommonDrawer(),
|
||||
body:
|
||||
// Consumer<NotificationProvider>(
|
||||
// // builder: (context, value, child) => value.isLoading
|
||||
// // ? const Center(child: CircularProgressIndicator())
|
||||
// // : Column(
|
||||
// // children: [
|
||||
// // Container(
|
||||
// // margin: const EdgeInsets.all(10),
|
||||
// // padding: const EdgeInsets.symmetric(horizontal: 10),
|
||||
// // decoration: const BoxDecoration(
|
||||
// // color: Colors.white,
|
||||
// // borderRadius: BorderRadius.all(Radius.circular(10)),
|
||||
// // ),
|
||||
// // child: Row(
|
||||
// // // mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
// // mainAxisAlignment: MainAxisAlignment.center,
|
||||
// // children: [
|
||||
// // Text(
|
||||
// // value.selectedDate,
|
||||
// // ),
|
||||
// // IconButton(
|
||||
// // onPressed: () {
|
||||
// // _selectDate(context);
|
||||
// // },
|
||||
// // icon: const Icon(Icons.calendar_month),
|
||||
// // ),
|
||||
// // ],
|
||||
// // ),
|
||||
// // ),
|
||||
// // MyListView(value: value),
|
||||
// // ],
|
||||
// // ),
|
||||
// // ),
|
||||
|
||||
Consumer<NotificationProvider>(
|
||||
builder: (context, value, child) {
|
||||
if (value.isLoading) {
|
||||
return const Center(child: CircularProgressIndicator());
|
||||
} else if (value.notificationList.isEmpty) {
|
||||
// Handle empty notification list
|
||||
return const Center(child: Text("No notifications available"));
|
||||
} else {
|
||||
// Show the notification list once data is fetched
|
||||
return MyListView(value: value);
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
@ -125,38 +182,95 @@ class MyListView extends StatelessWidget {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Expanded(
|
||||
child: (value.notificationList.isEmpty)
|
||||
? const Center(
|
||||
child: Text(
|
||||
'No notifications for selected date',
|
||||
style: TextStyle(fontSize: 20, color: Colors.white),
|
||||
),
|
||||
)
|
||||
: ListView.builder(
|
||||
|
||||
|
||||
Map<String, List<Notifications>> groupedNotifications = {};
|
||||
|
||||
// Iterate over the notification list and group by formatted date
|
||||
for (var notification in value.notificationList) {
|
||||
String date = DateFormat("dd MMM yyyy").format(DateTime.parse(notification.createdAt ?? ''));
|
||||
if (!groupedNotifications.containsKey(date)) {
|
||||
groupedNotifications[date] = [];
|
||||
}
|
||||
groupedNotifications[date]!.add(notification);
|
||||
}
|
||||
if (groupedNotifications.isEmpty) {
|
||||
return const Center(child: Text("No notifications available"));
|
||||
}
|
||||
|
||||
return
|
||||
// Expanded(
|
||||
// child: (value.notificationList.isEmpty)
|
||||
// ? const Center(
|
||||
// child: Text(
|
||||
// 'No notifications available',
|
||||
// style: TextStyle(fontSize: 20, color: Colors.white),
|
||||
// ),
|
||||
// )
|
||||
// ListView.builder(
|
||||
// padding: const EdgeInsets.only(top: 15),
|
||||
// itemCount: value.notificationList.length,
|
||||
// itemBuilder: (context, index) {
|
||||
// return Padding(
|
||||
// padding:
|
||||
// const EdgeInsets.only(bottom: 10, left: 10, right: 10),
|
||||
// child: Padding(
|
||||
// padding: const EdgeInsets.only(bottom: 10),
|
||||
// child: ExpansionTile(
|
||||
// collapsedBackgroundColor: Colors.white,
|
||||
// backgroundColor: Colors.white,
|
||||
// trailing: const SizedBox.shrink(),
|
||||
// title: Text(
|
||||
// value.notificationList[index].title ?? '',
|
||||
// style: const TextStyle(
|
||||
// fontSize: 17, fontWeight: FontWeight.w500),
|
||||
// ),
|
||||
// subtitle: Text(value.notificationList[index].msg ?? ''),
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// },
|
||||
//
|
||||
// );
|
||||
|
||||
ListView.builder(
|
||||
padding: const EdgeInsets.only(top: 15),
|
||||
itemCount: value.notificationList.length,
|
||||
itemCount: groupedNotifications.length, // Number of date groups
|
||||
itemBuilder: (context, index) {
|
||||
String date = groupedNotifications.keys.elementAt(index);
|
||||
List<Notifications> notificationsForDate = groupedNotifications[date]!;
|
||||
|
||||
return Padding(
|
||||
padding:
|
||||
const EdgeInsets.only(bottom: 10, left: 10, right: 10),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(bottom: 10, left: 10, right: 10),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
// Display the date for each group of notifications
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 8.0),
|
||||
child: Text(
|
||||
date,
|
||||
style: const TextStyle(fontSize: 16, fontWeight: FontWeight.bold),
|
||||
),
|
||||
),
|
||||
// Display each notification in an expandable tile
|
||||
...notificationsForDate.map((item) => Padding(
|
||||
padding: const EdgeInsets.only(bottom: 10),
|
||||
child: ExpansionTile(
|
||||
collapsedBackgroundColor: Colors.white,
|
||||
backgroundColor: Colors.white,
|
||||
trailing: const SizedBox.shrink(),
|
||||
trailing: const SizedBox.shrink(), // Remove trailing icon
|
||||
title: Text(
|
||||
value.notificationList[index].title ?? '',
|
||||
style: const TextStyle(
|
||||
fontSize: 17, fontWeight: FontWeight.w500),
|
||||
item.title ?? '',
|
||||
style: const TextStyle(fontSize: 17, fontWeight: FontWeight.w500),
|
||||
),
|
||||
subtitle: Text(value.notificationList[index].msg ?? ''),
|
||||
subtitle: Text(item.msg ?? ''),
|
||||
),
|
||||
)),
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ import 'package:flutter/material.dart';
|
||||
class CommonAppBar extends StatelessWidget implements PreferredSizeWidget {
|
||||
final Widget title;
|
||||
final List<Widget>? actions;
|
||||
final TabBar? bottom;
|
||||
final PreferredSizeWidget? bottom;
|
||||
|
||||
const CommonAppBar({super.key, required this.title, this.actions, required Color backgroundColor, required int elevation, this.bottom});
|
||||
|
||||
@ -24,6 +24,8 @@ class CommonAppBar extends StatelessWidget implements PreferredSizeWidget {
|
||||
actions: actions);
|
||||
}
|
||||
|
||||
// @override
|
||||
// Size get preferredSize => const Size.fromHeight(kToolbarHeight);
|
||||
@override
|
||||
Size get preferredSize => const Size.fromHeight(kToolbarHeight);
|
||||
Size get preferredSize => Size.fromHeight(kToolbarHeight + (bottom?.preferredSize.height ?? 0));
|
||||
}
|
||||
|
@ -1,22 +1,180 @@
|
||||
// import 'package:cheminova/provider/user_provider.dart';
|
||||
// import 'package:cheminova/screens/change_password_screen.dart';
|
||||
// import 'package:cheminova/screens/home_screen.dart';
|
||||
// import 'package:cheminova/screens/login_screen.dart';
|
||||
// import 'package:cheminova/screens/profile_screen.dart';
|
||||
// import 'package:flutter/material.dart';
|
||||
// import 'package:provider/provider.dart';
|
||||
//
|
||||
// class CommonDrawer extends StatelessWidget {
|
||||
// const CommonDrawer({super.key});
|
||||
//
|
||||
// @override
|
||||
// Widget build(BuildContext context) {
|
||||
// return Drawer(
|
||||
// child: ListView(
|
||||
// padding: EdgeInsets.zero,
|
||||
// children: <Widget>[
|
||||
// SizedBox(
|
||||
// height: 150,
|
||||
// child: DrawerHeader(
|
||||
// decoration: const BoxDecoration(
|
||||
// color: Colors.black87,
|
||||
// ),
|
||||
// child: Consumer<UserProvider>(
|
||||
// builder: (context, userProvider, child) {
|
||||
// if (userProvider.isLoading) {
|
||||
// return const Center(child: CircularProgressIndicator());
|
||||
// } else if (userProvider.user != null) {
|
||||
// return Column(
|
||||
// crossAxisAlignment: CrossAxisAlignment.start,
|
||||
// mainAxisAlignment: MainAxisAlignment.start,
|
||||
// children: [
|
||||
// Text(
|
||||
// userProvider.user!.name,
|
||||
// style: const TextStyle(
|
||||
// color: Colors.white,
|
||||
// fontSize: 18,
|
||||
// ),
|
||||
// ),
|
||||
// Text(
|
||||
// userProvider.user!.uniqueId,
|
||||
// style: const TextStyle(
|
||||
// color: Colors.white,
|
||||
// fontSize: 20,
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// );
|
||||
// } else {
|
||||
// return const Text(
|
||||
// 'No User Data',
|
||||
// style: TextStyle(
|
||||
// color: Colors.white,
|
||||
// fontSize: 18,
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// },
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// ListTile(
|
||||
// leading: const Icon(Icons.home),
|
||||
// title: const Text('Home'),
|
||||
// onTap: () {
|
||||
// Navigator.pushReplacement(
|
||||
// context,
|
||||
// MaterialPageRoute(builder: (context) => const HomePage()),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ListTile(
|
||||
// leading: const Icon(Icons.account_circle),
|
||||
// title: const Text('Profile'),
|
||||
// onTap: () {
|
||||
// Navigator.push(
|
||||
// context,
|
||||
// MaterialPageRoute(
|
||||
// builder: (context) {
|
||||
// return const ProfileScreen();
|
||||
// },
|
||||
// ),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ListTile(
|
||||
// leading: const Icon(Icons.settings),
|
||||
// title: const Text('Change Password'),
|
||||
// onTap: () {
|
||||
// Navigator.push(
|
||||
// context,
|
||||
// MaterialPageRoute(
|
||||
// builder: (context) => const ChangePasswordPage()),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ListTile(
|
||||
// leading: const Icon(Icons.exit_to_app),
|
||||
// title: const Text('Logout'),
|
||||
// onTap: () {
|
||||
// WidgetsBinding.instance.addPostFrameCallback((_) {
|
||||
// Provider.of<UserProvider>(context, listen: false)
|
||||
// .clearUserProfile();
|
||||
// });
|
||||
// Navigator.pushReplacement(
|
||||
// context,
|
||||
// MaterialPageRoute(builder: (context) => const LoginPage()),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
//
|
||||
//
|
||||
// SizedBox(
|
||||
// height: 700,
|
||||
// child: Padding(
|
||||
// padding: const EdgeInsets.all(8.0),
|
||||
// child: Center(
|
||||
// child: Text(
|
||||
// 'Version 2.0.0',
|
||||
// style: TextStyle(color: Colors.grey[600], fontSize: 12),
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
//
|
||||
// ],
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
|
||||
import 'package:cheminova/provider/user_provider.dart';
|
||||
import 'package:cheminova/screens/change_password_screen.dart';
|
||||
import 'package:cheminova/screens/home_screen.dart';
|
||||
import 'package:cheminova/screens/login_screen.dart';
|
||||
import 'package:cheminova/screens/profile_screen.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:package_info_plus/package_info_plus.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
|
||||
class CommonDrawer extends StatelessWidget {
|
||||
class CommonDrawer extends StatefulWidget {
|
||||
const CommonDrawer({super.key});
|
||||
|
||||
@override
|
||||
State<CommonDrawer> createState() => _CommonDrawerState();
|
||||
}
|
||||
|
||||
class _CommonDrawerState extends State<CommonDrawer> {
|
||||
|
||||
|
||||
String _appVersion = '';
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
_getAppVersion();
|
||||
}
|
||||
|
||||
Future<void> _getAppVersion() async {
|
||||
PackageInfo packageInfo = await PackageInfo.fromPlatform(
|
||||
|
||||
);
|
||||
setState(() {
|
||||
_appVersion = packageInfo.version; // 1.0.0
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Drawer(
|
||||
child: ListView(
|
||||
padding: EdgeInsets.zero,
|
||||
child: Column(
|
||||
children: <Widget>[
|
||||
SizedBox(
|
||||
height: 150,
|
||||
width:double.infinity,
|
||||
child: DrawerHeader(
|
||||
decoration: const BoxDecoration(
|
||||
color: Colors.black87,
|
||||
@ -108,6 +266,14 @@ class CommonDrawer extends StatelessWidget {
|
||||
);
|
||||
},
|
||||
),
|
||||
const Spacer(), // Push the version text to the bottom
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16.0),
|
||||
child: Text(
|
||||
'Version: $_appVersion',
|
||||
style: TextStyle(color: Colors.grey[600], fontSize: 12),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
|
@ -14,6 +14,7 @@ import firebase_messaging
|
||||
import flutter_local_notifications
|
||||
import flutter_secure_storage_macos
|
||||
import geolocator_apple
|
||||
import package_info_plus
|
||||
import path_provider_foundation
|
||||
import syncfusion_pdfviewer_macos
|
||||
import url_launcher_macos
|
||||
@ -28,6 +29,7 @@ func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
|
||||
FlutterLocalNotificationsPlugin.register(with: registry.registrar(forPlugin: "FlutterLocalNotificationsPlugin"))
|
||||
FlutterSecureStoragePlugin.register(with: registry.registrar(forPlugin: "FlutterSecureStoragePlugin"))
|
||||
GeolocatorPlugin.register(with: registry.registrar(forPlugin: "GeolocatorPlugin"))
|
||||
FPPPackageInfoPlusPlugin.register(with: registry.registrar(forPlugin: "FPPPackageInfoPlusPlugin"))
|
||||
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
|
||||
SyncfusionFlutterPdfViewerPlugin.register(with: registry.registrar(forPlugin: "SyncfusionFlutterPdfViewerPlugin"))
|
||||
UrlLauncherPlugin.register(with: registry.registrar(forPlugin: "UrlLauncherPlugin"))
|
||||
|
240
pubspec.lock
@ -25,6 +25,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.4.1"
|
||||
archive:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: archive
|
||||
sha256: "6199c74e3db4fbfbd04f66d739e72fe11c8a8957d5f219f1f4482dbde6420b5a"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.2"
|
||||
args:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -49,70 +57,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.1"
|
||||
build:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: build
|
||||
sha256: "80184af8b6cb3e5c1c4ec6d8544d27711700bc3e6d2efad04238c7b5290889f0"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.1"
|
||||
build_config:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: build_config
|
||||
sha256: bf80fcfb46a29945b423bd9aad884590fb1dc69b330a4d4700cac476af1708d1
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.1"
|
||||
build_daemon:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: build_daemon
|
||||
sha256: "79b2aef6ac2ed00046867ed354c88778c9c0f029df8a20fe10b5436826721ef9"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.2"
|
||||
build_resolvers:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: build_resolvers
|
||||
sha256: "339086358431fa15d7eca8b6a36e5d783728cf025e559b834f4609a1fcfb7b0a"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.2"
|
||||
build_runner:
|
||||
dependency: "direct dev"
|
||||
description:
|
||||
name: build_runner
|
||||
sha256: "644dc98a0f179b872f612d3eb627924b578897c629788e858157fa5e704ca0c7"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.11"
|
||||
build_runner_core:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: build_runner_core
|
||||
sha256: e3c79f69a64bdfcd8a776a3c28db4eb6e3fb5356d013ae5eb2e52007706d5dbe
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "7.3.1"
|
||||
built_collection:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: built_collection
|
||||
sha256: "376e3dd27b51ea877c28d525560790aee2e6fbb5f20e2f85d5081027d94e2100"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "5.1.1"
|
||||
built_value:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: built_value
|
||||
sha256: c7913a9737ee4007efedaffc968c049fd0f3d0e49109e778edc10de9426005cb
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "8.9.2"
|
||||
characters:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -129,6 +73,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.0.3"
|
||||
cli_util:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: cli_util
|
||||
sha256: ff6785f7e9e3c38ac98b2fb035701789de90154024a75b6cb926445e83197d1c
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.4.2"
|
||||
clock:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -137,14 +89,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.1"
|
||||
code_builder:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: code_builder
|
||||
sha256: f692079e25e7869c14132d39f223f8eec9830eb76131925143b2129c4bb01b37
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.10.0"
|
||||
collection:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -430,22 +374,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "5.6.0"
|
||||
flutter_gen_runner:
|
||||
flutter_launcher_icons:
|
||||
dependency: "direct dev"
|
||||
description:
|
||||
name: flutter_gen_runner
|
||||
sha256: "931b03f77c164df0a4815aac0efc619a6ac8ec4cada55025119fca4894dada90"
|
||||
name: flutter_launcher_icons
|
||||
sha256: bfa04787c85d80ecb3f8777bde5fc10c3de809240c48fa061a2c2bf15ea5211c
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "5.6.0"
|
||||
flutter_lints:
|
||||
dependency: "direct dev"
|
||||
description:
|
||||
name: flutter_lints
|
||||
sha256: "3f41d009ba7172d5ff9be5f6e6e6abb4300e263aab8866d2a0842ed2a70f8f0c"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.0"
|
||||
version: "0.14.3"
|
||||
flutter_local_notifications:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -544,14 +480,6 @@ packages:
|
||||
description: flutter
|
||||
source: sdk
|
||||
version: "0.0.0"
|
||||
frontend_server_client:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: frontend_server_client
|
||||
sha256: f64a0333a82f30b0cca061bc3d143813a486dc086b574bfb233b7c1372427694
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.0"
|
||||
geocoding:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -640,14 +568,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.2"
|
||||
graphs:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: graphs
|
||||
sha256: "741bbf84165310a68ff28fe9e727332eef1407342fca52759cb21ad8177bb8d0"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.3.2"
|
||||
hashcodes:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -664,14 +584,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.2.2"
|
||||
http_multi_server:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: http_multi_server
|
||||
sha256: "97486f20f9c2f7be8f514851703d0119c3596d14ea63227af6f7a481ef2b2f8b"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.2.1"
|
||||
http_parser:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -680,6 +592,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.2"
|
||||
image:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: image
|
||||
sha256: "8346ad4b5173924b5ddddab782fc7d8a6300178c8b1dc427775405a01701c4a6"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.5.2"
|
||||
image_picker:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -760,14 +680,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.19.0"
|
||||
io:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: io
|
||||
sha256: "2ec25704aba361659e10e3e5f5d672068d332fc8ac516421d483a11e5cbd061e"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.4"
|
||||
js:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -808,22 +720,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.1"
|
||||
lints:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: lints
|
||||
sha256: "976c774dd944a42e83e2467f4cc670daef7eed6295b10b36ae8c85bcbf828235"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.0"
|
||||
logging:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: logging
|
||||
sha256: "623a88c9594aa774443aa3eb2d41807a48486b5613e67599fb4c41c0ad47c340"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.2.0"
|
||||
matcher:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -872,6 +768,22 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.0"
|
||||
package_info_plus:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: package_info_plus
|
||||
sha256: "739e0a5c3c4055152520fa321d0645ee98e932718b4c8efeeb51451968fe0790"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "8.1.3"
|
||||
package_info_plus_platform_interface:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: package_info_plus_platform_interface
|
||||
sha256: a5ef9986efc7bf772f2696183a3992615baa76c1ffb1189318dd8803778fb05b
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.2"
|
||||
path:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1016,14 +928,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.8"
|
||||
pool:
|
||||
posix:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: pool
|
||||
sha256: "20fe868b6314b322ea036ba325e6fc0711a22948856475e2c2b6306e8ab39c2a"
|
||||
name: posix
|
||||
sha256: a0117dc2167805aa9125b82eee515cc891819bac2f538c83646d355b16f58b9a
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.5.1"
|
||||
version: "6.0.1"
|
||||
pretty_dio_logger:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -1048,14 +960,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.4"
|
||||
pubspec_parse:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: pubspec_parse
|
||||
sha256: c799b721d79eb6ee6fa56f00c04b472dcd44a30d258fac2174a6ec57302678f8
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.3.0"
|
||||
searchfield:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -1064,22 +968,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.9"
|
||||
shelf:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: shelf
|
||||
sha256: ad29c505aee705f41a4d8963641f91ac4cee3c8fad5947e033390a7bd8180fa4
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.4.1"
|
||||
shelf_web_socket:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: shelf_web_socket
|
||||
sha256: "073c147238594ecd0d193f3456a5fe91c4b0abbcc68bf5cd95b36c4e194ac611"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.0.0"
|
||||
simple_gesture_detector:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1125,14 +1013,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.2"
|
||||
stream_transform:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: stream_transform
|
||||
sha256: "14a00e794c7c11aa145a170587321aedce29769c08d7f58b1d141da75e3b1c6f"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.0"
|
||||
string_scanner:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1245,14 +1125,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.9.4"
|
||||
timing:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: timing
|
||||
sha256: "70a3b636575d4163c477e6de42f247a23b315ae20e86442bebe32d3cabf61c32"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.1"
|
||||
typed_data:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1397,22 +1269,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.5.1"
|
||||
web_socket:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: web_socket
|
||||
sha256: "3c12d96c0c9a4eec095246debcea7b86c0324f22df69893d538fcc6f1b8cce83"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.1.6"
|
||||
web_socket_channel:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: web_socket_channel
|
||||
sha256: "9f187088ed104edd8662ca07af4b124465893caf063ba29758f97af57e61da8f"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.1"
|
||||
win32:
|
||||
dependency: transitive
|
||||
description:
|
||||
|
10
pubspec.yaml
@ -16,7 +16,7 @@ publish_to: 'none' # Remove this line if you wish to publish to pub.dev
|
||||
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
||||
# In Windows, build-name is used as the major, minor, and patch parts
|
||||
# of the product and file versions while build-number is used as the build suffix.
|
||||
version: 1.0.0+1
|
||||
version: 2.0.1+1
|
||||
|
||||
environment:
|
||||
sdk: '>=3.4.3 <4.0.0'
|
||||
@ -52,10 +52,18 @@ dependencies:
|
||||
firebase_analytics: ^11.2.1
|
||||
searchfield: ^1.0.9
|
||||
syncfusion_flutter_pdfviewer: ^26.2.11
|
||||
package_info_plus: ^8.1.3
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
sdk: flutter
|
||||
flutter_launcher_icons: ^0.14.3
|
||||
|
||||
|
||||
flutter_launcher_icons:
|
||||
android: "launcher_icon"
|
||||
ios: true
|
||||
image_path: "assets/app-icon-territory-manager.png"
|
||||
|
||||
flutter_lints: ^4.0.0
|
||||
build_runner:
|
||||
|