Skip to content

Instantly share code, notes, and snippets.

@anoochit
Last active June 4, 2022 13:17
Show Gist options
  • Select an option

  • Save anoochit/042f4500af8af35df5c8e41298dacb29 to your computer and use it in GitHub Desktop.

Select an option

Save anoochit/042f4500af8af35df5c8e41298dacb29 to your computer and use it in GitHub Desktop.
import 'dart:developer' as dev;
import 'dart:math';
import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:flutter/material.dart';
import 'package:intl/intl.dart';
import 'package:location/location.dart';
import 'package:url_launcher/url_launcher.dart';
import '../../models/sick_model.dart';
class CalculatePage extends StatefulWidget {
const CalculatePage({Key? key}) : super(key: key);
@override
State<CalculatePage> createState() => _CalculatePageState();
}
class _CalculatePageState extends State<CalculatePage> {
double currentLat = 0.0;
double currentLng = 0.0;
List<PatienPath> listPatientPathTmp = [];
List<PatienPath> listPatientPath = [];
List<SickModel> listPatient = [];
@override
void initState() {
super.initState();
findLat1Lng1();
}
@override
void dispose() {
super.dispose();
}
List<PatienPath> buildlistPatientPathTmp(double currentLat, double currentLng) {
List<PatienPath> _listPatientPathTmp = [];
// calculate distance from current location
dev.log('patient total = ${listPatient.length}');
for (int i = 0; i < listPatient.length; i++) {
var lat1 = currentLat;
var lng1 = currentLng;
var lat2 = listPatient[i].lat;
var lng2 = listPatient[i].lng;
// calculate distance
var distance = calculateDistance(lat1, lng1, lat2, lng2);
dev.log('${listPatient[i].name} - ${listPatient[i].idCard} - $distance');
// add to temp path list
_listPatientPathTmp.add(PatienPath(docId: listPatient[i].idCard, distance: distance));
}
return _listPatientPathTmp;
}
List<SickModel> listPatientData = [];
readAllSick() async {
// read all patient to list
FirebaseFirestore.instance.collection('sick').get().then((value) {
// set data to patient list
for (var doc in value.docs) {
SickModel patient = SickModel.fromMap(doc.data());
//dev.log('name = ${patient.name}');
listPatient.add(patient);
listPatientData.add(patient);
}
dev.log('total patient ${listPatient.length}');
// calculate paths
while (listPatient.length > 0) {
// build pateint path list
if (listPatientPath.length <= 0) {
dev.log('currentLat = $currentLat, currentLng = $currentLng');
listPatientPathTmp = buildlistPatientPathTmp(currentLat, currentLng);
} else {
// get lat, lon from patial list
// dev.log('total patient = ${listPatient.length}');
// dev.log('last patient path = ${listPatientPath.last.docId}');
final item = listPatientData.firstWhere((element) => element.idCard == listPatientPath.last.docId);
dev.log('currentLat = ${item.lat}, currentLng = ${item.lng}');
listPatientPathTmp = buildlistPatientPathTmp(item.lat, item.lng);
}
// sort tmp path list
listPatientPathTmp.sort((a, b) => a.distance.compareTo(b.distance));
dev.log('shortes path is ${listPatientPathTmp.first.docId} , ${listPatientPathTmp.first.distance} ');
// set data to patient path list
listPatientPath
.add(PatienPath(docId: listPatientPathTmp.first.docId, distance: listPatientPathTmp.first.distance));
// remove patient in list patient
listPatient.removeWhere((element) => element.idCard == listPatientPathTmp.first.docId);
// remove first patient in temp
listPatientPathTmp.removeAt(0);
dev.log('list Patient Path Tmp length = ${listPatientPathTmp.length}');
// dev.log('list patient length = ${listPatient.length}');
// dev.log('list patient path length = ${listPatientPath.length}');
}
dev.log('list patient path = ${listPatientPath.length}');
setState(() {});
});
}
Future<Null> findLat1Lng1() async {
findLocationData().then((value) {
// setState(() {
currentLat = value?.latitude ?? 0.0;
currentLng = value?.longitude ?? 0.0;
dev.log('currentLat = $currentLat, currentLng = $currentLng');
readAllSick();
//});
});
}
double calculateDistance(double lat1, double lng1, double lat2, double lng2) {
double distance = 0;
var p = 0.017453292519943295;
var c = cos;
var a = 0.5 - c((lat2 - lat1) * p) / 2 + c(lat1 * p) * c(lat2 * p) * (1 - c((lng2 - lng1) * p)) / 2;
distance = 12742 * asin(sqrt(a));
return distance;
}
Future<LocationData?> findLocationData() async {
Location location = Location();
try {
return await location.getLocation();
} catch (e) {
return null;
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(),
body: (listPatientPath.isEmpty)
? Center(child: CircularProgressIndicator())
: Container(
child: ListView.builder(
itemCount: listPatientPath.length,
itemBuilder: (context, index) {
// get patient data
final patient =
listPatientData.firstWhere((element) => element.idCard == listPatientPath[index].docId);
return ListTile(
title: Text(patient.name),
);
},
),
),
);
}
}
class PatienPath {
String docId;
double distance;
PatienPath({
required this.docId,
required this.distance,
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment