[英]How to sort dynamic list items based on numerical values in Javascript
這讓我壓力山大!
正在構建一個列出多個辦公地點的應用程序。
該應用程序會選擇用戶的位置並計算他與所有辦公室之間的距離。
現在我需要根據列表與用戶的距離按升序對列表進行排序。
現在,當應用程序由 javascript 加載時,li 項目會在 ul 中動態創建。
我的應用程序連接並從 firebase 獲取各個辦公室的數據。
但是,距離是在客戶端創建的,我需要根據該距離對列表項(辦公室)進行排序。
最近的位置
<!-- Firebase App (the core Firebase SDK) is always required and must be listed first -->
<script src="https://www.gstatic.com/firebasejs/7.2.0/firebase-app.js"></script>
<!-- Add Firebase products that you want to use -->
<script src="https://www.gstatic.com/firebasejs/7.2.0/firebase-firestore.js"></script>
<div class="container">
<div class="section">
<div class="row">
<div class="all-parishes">
<ul id="all-parishes" style="padding: 0; list-style: none; ">
</ul>
</div>
</div>
</div>
<br>
<br>
</div>
<script>
//Distance Calculation
// Your web app's Firebase configuration
var firebaseConfig = {
apiKey: "AIzaSyDXtwlWjWygp_sGx9R1qk-4gDuH9ZEx9xg",
authDomain: "parish-connect.firebaseapp.com",
databaseURL: "https://parish-connect.firebaseio.com",
projectId: "parish-connect",
storageBucket: "parish-connect.appspot.com",
messagingSenderId: "304974921983",
appId: "1:304974921983:web:9ac09b834259488951ccca",
measurementId: "G-QWLPQ52Z7S"
};
// Initialize Firebase
firebase.initializeApp(firebaseConfig);
var db = firebase.firestore();
var lat1, lon1;
function getLocation() {
if (navigator.geolocation) {
navigator.geolocation.watchPosition(showPosition);
} else {
x.innerHTML = "Geolocation is not supported by this browser.";
}
}
getLocation();
function showPosition(position) {
lat1 = position.coords.latitude;
lon1 = position.coords.longitude;
console.log(lat1);
console.log(lon1);
// To do: The code below creates a dynamic list items (<li>) and prints to the
// <ul> container. I want to be able to sort the lists in ascending/descending order based on
//the distances <p class="distance">${calcDistance(doc.data().lat, doc.data().lng).toFixed(5)} km away</p>
var text = "";
db.collection("parish-ghana").onSnapshot(querySnapshot => {
querySnapshot.forEach(doc => {
text += `
<li>
<div class="card demo-card-header-pic">
<div style="background-image:url(${doc.data().pic_url})" valign="bottom" class="card-header"></div>
<div class="card-content card-content-padding">
<p class="parish-item">${doc.data().name}</p>
<p class="distance">${calcDistance(doc.data().lat, doc.data().lng).toFixed(5)} km away</p>
</div>
</div>
</li>
<hr>
`
});
document.getElementById("all-parishes").innerHTML = text;
});
}
//End to do
//When the location throws an error
function onLocationError(e) {
alert(e.message);
}
//Function to calculate distances
function calcDistance(lat2, lon2) {
function toRad(x) {
return x * Math.PI / 180;
}
var R = 6371; // km
var dLat = toRad(lat2 - lat1);
var dLon = toRad(lon2 - lon1);
var a = Math.sin(dLat / 2) * Math.sin(dLat / 2) +
Math.cos(toRad(lat1)) * Math.cos(toRad(lat2)) *
Math.sin(dLon / 2) * Math.sin(dLon / 2);
var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
var d = R * c;
return d;
}
</script>
試試下面小提琴中使用的方法。
<ul>
<li><div> apple</div></li>
<li><div> pinapple</div></li>
<li><div> mango </div></li>
<li><div> banana</div></li>
</ul>
<br>
<center>
<button>
click here
</button>
</center>
<p id = "triger_elem" style =
"text-align:center; color:green; font-size:20px; font-weight:bold;">
</p>
function Ascending_sort(a, b) {
return ($(b).find('div').text().toUpperCase()) <
($(a).find('div').text().toUpperCase()) ? 1 : -1;
}
$('button').on('click', function() {
$("ul li").sort(Ascending_sort).appendTo('ul');
$("#triger_elem").text("sorted");
});
你的問題的一個小示范
您可以先將 querySnapshot 映射到數據對象的普通數組,然后將distance
作為附加屬性添加到每個對象。 然后按該新屬性對該數組進行排序。 最后執行您已經擁有的循環(對動態表達式略有更改)。 我也將使用一個.map()
為該循環,然后.join
HTML的碎片連同<hr>
這是它的外觀:
db.collection("parish-ghana").onSnapshot(querySnapshot => {
document.getElementById("all-parishes").innerHTML = querySnapshot.docs
.map(doc => doc.data())
.map(data => ({
...data,
distance: calcDistance(data.lat, data.lng)
}))
.sort((a, b) => a.distance - b.distance)
.map(data => `
<li>
<div class="card demo-card-header-pic">
<div style="background-image:url(${data.pic_url})" valign="bottom" class="card-header"><\/div>
<div class="card-content card-content-padding">
<p class="parish-item">${data.name}<\/p>
<p class="distance">${data.distance.toFixed(5)} km away<\/p>
<\/div>
<\/div>
<\/li>
`)
.join('<hr>\n');
});
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.