我正在使用传单开发一个反应应用程序,并且我对图层控件存在问题,特别是隐藏/显示图层的复选框功能。
要进行语境化,应用程序会在每个单选按钮选择后发出一个AJAX请求,根据所选选项填充某些图层,并使用复选框隐藏/显示这些图层。我使用jQuery BlockUI plugin来锁定地图并阻止用户操纵地图。这个插件适用于AJAX调用(正如我在文档中所期望的那样),也就是说对每个单选按钮,但当我试图在传单方法中做同样的事情时 一旦图层已经加载,锁定屏幕就会显示得晚。
在我尝试调试它时,我注意到有一些“死时间”和#39;来自点击'在复选框中,直到带有绘制多边形的图层加载。我认为这是解决方案的关键,但我尝试了很多方法来解决这个问题,但没有任何作用。
我的目标是在加载图层之前将锁定屏幕放在复选框之前,直到图层出现在地图上。
我做了an functional example of the app in CodeSandbox以防有人帮助我。任何意见/想法都应该感激不尽,我已经陷入了这个时间的浪潮中。
答案 0 :(得分:1)
嗯," 位死亡时间的根本原因' "是你显示GeoJSON data which weighs 26+MB ...
当勾选Leaflet Layers Control中的叠加复选框时,浏览器会计算渲染几秒钟(取决于客户端性能),同步,因此在此期间不会触发任何事件。如果你密切关注,你会发现即使是浏览器用户界面也没有时间显示" tick"在复选框中。
可以理解的是,您希望向用户提供一些反馈,以便他们知道他们的点击已经被考虑在内并且CPU疯狂地显示您的数据。并且还阻止他们尝试执行其他操作,这可能会使情况变得更糟......
使用标准的图层控件,遗憾的是你不能" hook"在这个过程中,在用户tick和Leaflet之间显示你的jQuery BlockUI覆盖,试图渲染你的GeoJSON数据。
但是,您有几个简单的解决方法:
"overlayadd"
和"overlayremove"
事件收听到&#34 ;人工"添加/删除你的GeoJSON组到地图,在渲染了你的BlockUI之后 :(有光数据的例子,但是看一下有大量数据的例子的帖子底部)
var map = L.map('map').setView([48.86, 2.35], 11);
// This would be actually your heavy GeoJSON Layer Group.
var polygon = L.circle([48.86, 2.35], {
radius: 2000
});
// This is an empty layer, just to feed it into the Layers Control and listen to its state.
var dummyLayer = L.featureGroup();
L.control.layers(null, {
'Dummy Layer': dummyLayer, // Use this to implement your BlockUI (see below event listeners)
'Polygon': polygon // If you add directly your heavy layer, you cannot execute code before the browser "hangs" when it renders.
}, {
collapsed: false
}).addTo(map);
map.on('overlayadd', function(event) {
var layer = event.layer;
if (layer === dummyLayer) {
$.blockUI({
message: '<h1>RENDERING crazy heavy data...</h1>'
});
// Slight delay to make sure BlockUI has time rendering the overlay.
setTimeout(() => {
polygon.addTo(map);
$.unblockUI();
}, 200);
}
});
map.on('overlayremove', function(event) {
var layer = event.layer;
if (layer === dummyLayer) {
// Slight delay for Leaflet to finish checking the Layers Control state.
// That is just an artifact due to having added polygon also to the Layers Control.
// In your case you would probably not add it to the Control,
// so you should not need such delay.
setTimeout(() => {
polygon.remove();
}, 100);
}
});
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
attribution: '© <a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
}).addTo(map);
&#13;
<link rel="stylesheet" href="https://unpkg.com/leaflet@1.3.1/dist/leaflet.css" integrity="sha512-Rksm5RenBEKSKFjgI3a41vrjkw4EVPlJ3+OiI65vTjIdo9brlAacEuKOiQ5OFh7cOI1bkDwLqdLw3Zg0cRJAAQ==" crossorigin="" />
<script src="https://unpkg.com/leaflet@1.3.1/dist/leaflet-src.js" integrity="sha512-IkGU/uDhB9u9F8k+2OsA6XXoowIhOuQL1NTgNZHY1nkURnqEGlDZq3GsfmdJdKFe1k1zOc6YU2K7qY+hF9AodA==" crossorigin=""></script>
<script src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script src="https://unpkg.com/block-ui@2.70.1/jquery.blockUI.js"></script>
<div id="map" style="height: 180px"></div>
&#13;
使用您实际繁重的GeoJSON数据进行侦察:https://plnkr.co/edit/EhoRzDaqClZ6sGgRVVPu?p=preview