Я пытаюсь создать круг с определенным радиусом на земле в OpenLayers v5.Но я, кажется, не понимаю, как создать его с определенной единицей измерения, такой как метры, мили и т. Д. Аргумент радиуса в конструкторе выглядит как неуказанная единица карты, как отмечено в этой проблеме , что завершается использованием метода getMetersPerUnit
из проекции.Однако каждый раз, когда вызывается этот метод, кажется, что он всегда возвращает 1. Я также смотрел, как что-то делать с экспортом METERS_PER_UNIT
в библиотеке проекций, но, опять же, значение для метров равно 1.
Мой рисунок пытается дать хорошую отправную точку, основанную на экстенте текущего вида.Предыдущая работа использовала 1/8 бокового расстояния текущего вида.
function getRoundedEigthedDistanceBetweenPoints(coordinateA, coordinateB) {
/**
* Distance between bottom right and left corners in meters
* We want 1/8 of the distance, rounded to nearest 10?
* Why? /shrug ?♂️
*/
return (getDistanceBetweenPoints(coordinateA, coordinateB) / 8 / 10) * 10;
}
/**
* @link https://stackoverflow.com/a/28454386/168005
* @param coordA
* @param coordB
*/
function getDistanceBetweenPoints(coordA, coordB) {
return (new LineString([coordA, coordB]).getLength() * 100) / 100;
}
const [minX, _, maxX, __] = map.getView().calculateExtent();
// Since all I want is a straight line, I just give it the minX and maxX values, and zero out the "Y"s.
const startingDistance = getRoundedEigthedDistanceBetweenPoints([minX, 0], [maxX, 0]);
Учитывая вышеизложенное, я предполагал, что результат startingDistance
был в метрах.Но если я сравниваю значения моих кругов с нормальной длиной LineString, цифры немного сбиваются.
Проблема усугубляется, когда я пытаюсь изменить радиус позже по сравнению с пользовательским вводом, потому что я думал, что работаю в метрах (очевидно, это не так), поэтому я преобразую предоставленные значения в метры и устанавливаю егопрямо как радиус.
enum Units {
Meters = "m",
Miles = "mi",
Kilometers = "km",
Feet = "ft",
}
const METERS_PER_FEET = 0.3048;
const FEET_PER_MILE = 5280;
const METERS_PER_KILO = 1000;
function convertFeetToMeters(feet) {
return feet * METERS_PER_FEET;
}
function convertMilesToMeters(miles) {
return miles * METERS_PER_MILE;
}
function convertMetersToKilometers(meters) {
return meters / METERS_PER_KILO;
}
function convertUnitToMeters(unit: Units, value: number) {
switch (unit) {
case Units.Feet:
return convertFeetToMeters(value);
case Units.Miles:
return convertMilesToMeters(value);
case Units.Kilometers:
return convertKilometersToMeters(value);
default:
return value;
}
}
function updateFeature({ type, feature, unit, value }) {
/**
* Mutably make the change
*/
if (type === "radius" || type === "unit") {
// Take in the units listed in the UI and convert the value, respectively.
const computedRadius = convertUnitToMeters(unit.value, parseFloat(value));
feature.getGeometry().setRadius(computedRadius);
}
}
Я знаю, что это целое бизнес искажения Web Mercator , и использование чего-то вроде getLength
из модуля ol/sphere
преобразует радиус из уже созданного круга, но как насчет установки радиуса круга?Есть ли инструмент для этого?