kopia lustrzana https://github.com/OpenDroneMap/WebODM
Add units tests
rodzic
9a8013d6ce
commit
e0eb7cad7e
|
@ -1,4 +1,4 @@
|
|||
import { _ } from '../classes/gettext';
|
||||
import { _ } from './gettext';
|
||||
|
||||
const units = {
|
||||
acres: {
|
||||
|
@ -47,13 +47,19 @@ const units = {
|
|||
factor: 10.7639,
|
||||
label: _('Square Feet'),
|
||||
abbr: 'ft²',
|
||||
round: 2,
|
||||
round: 2
|
||||
},
|
||||
sqmeters: {
|
||||
factor: 1,
|
||||
label: _('Square Meters'),
|
||||
abbr: 'm²',
|
||||
round: 2,
|
||||
round: 2
|
||||
},
|
||||
sqmeters: {
|
||||
factor: 0.000001,
|
||||
label: _('Square Kilometers'),
|
||||
abbr: 'km²',
|
||||
round: 5
|
||||
},
|
||||
sqmiles: {
|
||||
factor: 0.000000386102,
|
||||
|
@ -61,36 +67,68 @@ const units = {
|
|||
abbr: 'mi²',
|
||||
round: 5
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class ValueUnit{
|
||||
constructor(val, unit){
|
||||
this.val = val;
|
||||
this.unit = unit;
|
||||
}
|
||||
|
||||
toString(){
|
||||
const mul = Math.pow(10, this.unit.round);
|
||||
const rounded = (Math.round(this.val * mul) / mul).toString();
|
||||
|
||||
let withCommas = "";
|
||||
let parts = rounded.split(".");
|
||||
parts[0] = parts[0].replace(/\B(?=(\d{3})+(?!\d))/g, ",");
|
||||
withCommas = parts.join(".");
|
||||
|
||||
return `${withCommas} ${this.unit.abbr}`;
|
||||
}
|
||||
}
|
||||
|
||||
class UnitSystem{
|
||||
lengthUnit(meters){ throw new Error("Not implemented"); }
|
||||
areaUnit(sqmeters){ throw new Error("Not implemented"); }
|
||||
getName(){ throw new Error("Not implemented"); }
|
||||
|
||||
area(meters){
|
||||
|
||||
area(sqmeters){
|
||||
const unit = this.areaUnit(sqmeters);
|
||||
const val = unit.factor * sqmeters;
|
||||
return new ValueUnit(val, unit);
|
||||
}
|
||||
|
||||
length(sqmeters){
|
||||
const unit = this.lengthUnit(sqmeters);
|
||||
const v = unit.factor * sqmeters;
|
||||
return {v, s: `{v.toLocaleString()}` };
|
||||
length(meters){
|
||||
const unit = this.lengthUnit(meters);
|
||||
const val = unit.factor * meters;
|
||||
return new ValueUnit(val, unit);
|
||||
}
|
||||
};
|
||||
|
||||
class Metric extends UnitSystem{
|
||||
class MetricSystem extends UnitSystem{
|
||||
getName(){
|
||||
return _("Metric");
|
||||
}
|
||||
|
||||
lengthUnit(meters){
|
||||
if (meters < 100) return units.centimeters;
|
||||
if (meters < 1) return units.centimeters;
|
||||
else if (meters >= 1000) return units.kilometers;
|
||||
else return units.meters;
|
||||
}
|
||||
|
||||
areaUnit(sqmeters){
|
||||
return units.sqmeters; // TODO
|
||||
if (sqmeters >= 10000 && sqmeters < 1000000) return units.hectares;
|
||||
else if (sqmeters >= 1000000) return units.sqkilometers;
|
||||
return units.sqmeters;
|
||||
}
|
||||
}
|
||||
|
||||
class Imperial extends UnitSystem{
|
||||
class ImperialSystem extends UnitSystem{
|
||||
getName(){
|
||||
return _("Imperial");
|
||||
}
|
||||
|
||||
lengthUnit(meters){
|
||||
const feet = units.feet.factor * meters;
|
||||
if (feet >= 5280) return units.miles;
|
||||
|
@ -98,7 +136,7 @@ class Imperial extends UnitSystem{
|
|||
}
|
||||
|
||||
areaUnit(sqmeters){
|
||||
const sqfeet = units.sqfeet.factor * meters;
|
||||
const sqfeet = units.sqfeet.factor * sqmeters;
|
||||
if (sqfeet >= 43560 && sqfeet < 27878400) return units.acres;
|
||||
else if (sqfeet >= 27878400) return units.sqmiles;
|
||||
else return units.sqfeet;
|
||||
|
@ -106,18 +144,21 @@ class Imperial extends UnitSystem{
|
|||
}
|
||||
|
||||
const systems = {
|
||||
metric: new Metric(),
|
||||
|
||||
|
||||
// TODO
|
||||
metric: new MetricSystem(),
|
||||
imperial: new ImperialSystem()
|
||||
}
|
||||
|
||||
let a = 100;
|
||||
let S = systems.metric;
|
||||
// Expose to allow every part of the app to access this information
|
||||
function getPreferredUnitSystem(){
|
||||
return localStorage.getItem("preferred_unit_system") || "metric";
|
||||
}
|
||||
function setPreferredUnitSystem(system){
|
||||
localStorage.setItem("preferred_unit_system", system);
|
||||
}
|
||||
|
||||
|
||||
export default {
|
||||
// to be used on individual strings
|
||||
|
||||
export {
|
||||
systems,
|
||||
getPreferredUnitSystem,
|
||||
setPreferredUnitSystem
|
||||
};
|
||||
|
||||
|
|
|
@ -27,6 +27,7 @@ import '../vendor/leaflet/Leaflet.Ajax';
|
|||
import 'rbush';
|
||||
import '../vendor/leaflet/leaflet-markers-canvas';
|
||||
import { _ } from '../classes/gettext';
|
||||
import UnitSelector from './UnitSelector';
|
||||
|
||||
class Map extends React.Component {
|
||||
static defaultProps = {
|
||||
|
@ -404,6 +405,21 @@ class Map extends React.Component {
|
|||
position:'bottomleft'
|
||||
}).addTo(this.map);
|
||||
|
||||
const UnitsCtrl = Leaflet.Control.extend({
|
||||
options: {
|
||||
position: 'bottomleft'
|
||||
},
|
||||
|
||||
onAdd: function () {
|
||||
this.container = Leaflet.DomUtil.create('div', 'leaflet-control-units-selection leaflet-control');
|
||||
Leaflet.DomEvent.disableClickPropagation(this.container);
|
||||
ReactDOM.render(<UnitSelector />, this.container);
|
||||
return this.container;
|
||||
}
|
||||
});
|
||||
new UnitsCtrl().addTo(this.map);
|
||||
|
||||
|
||||
if (showBackground) {
|
||||
this.basemaps = {};
|
||||
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { systems, getPreferredUnitSystem, setPreferredUnitSystem } from '../classes/Units';
|
||||
|
||||
class UnitSelector extends React.Component {
|
||||
static propTypes = {
|
||||
|
@ -9,19 +10,22 @@ class UnitSelector extends React.Component {
|
|||
super(props);
|
||||
|
||||
this.state = {
|
||||
system: window.getPreferredUnitSystem()
|
||||
system: getPreferredUnitSystem()
|
||||
}
|
||||
|
||||
// console.log(systems.metric.length(1.01).toString());
|
||||
}
|
||||
|
||||
handleChange = e => {
|
||||
this.setState({system: e.target.value});
|
||||
window.setPreferredUnitSystem(e.target.value);
|
||||
setPreferredUnitSystem(e.target.value);
|
||||
};
|
||||
|
||||
render() {
|
||||
return (
|
||||
<select value={this.state.system} onChange={this.handleChange}>
|
||||
<option value="metric" key={}></option>
|
||||
{Object.keys(systems).map(k =>
|
||||
<option value={k} key={k}>{systems[k].getName()}</option>)}
|
||||
</select>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
import { systems } from '../../classes/Units';
|
||||
|
||||
describe('Metric system', () => {
|
||||
it('it should display units properly', () => {
|
||||
|
||||
const { metric } = systems;
|
||||
|
||||
const lengths = [
|
||||
[1, "1 m"],
|
||||
[0.01, "1 cm"],
|
||||
[0.0154, "1.5 cm"],
|
||||
[0.99, "99 cm"],
|
||||
[0.995555, "99.6 cm"],
|
||||
[1.01, "1.01 m"],
|
||||
[999, "999 m"],
|
||||
[1000, "1 km"],
|
||||
[1001, "1.001 km"],
|
||||
[1000010, "1,000.01 km"],
|
||||
[1000012.349, "1,000.01235 km"],
|
||||
];
|
||||
|
||||
lengths.forEach(l => {
|
||||
expect(metric.length(l[0]).toString()).toBe(l[1]);
|
||||
});
|
||||
|
||||
const areas = [
|
||||
[1, "1 m²"],
|
||||
[9999, "9,999 m²"],
|
||||
[10000, "1 ha"],
|
||||
[11005, "1.1005 ha"],
|
||||
[11005, "1.1005 ha"],
|
||||
[999999, "99.9999 ha"],
|
||||
[1000000, "1 km²"],
|
||||
[1000000000, "1,000 km²"]
|
||||
];
|
||||
|
||||
areas.forEach(a => {
|
||||
expect(metric.area(a[0]).toString()).toBe(a[1]);
|
||||
});
|
||||
})
|
||||
});
|
|
@ -26,14 +26,6 @@ window.React = React;
|
|||
// Expose set locale function globally
|
||||
window.setLocale = setLocale;
|
||||
|
||||
// Expose to allow every part of the app to access this information
|
||||
window.getPreferredUnitSystem = () => {
|
||||
return localStorage.getItem("preferred_unit_system") || "metric";
|
||||
};
|
||||
window.setPreferredUnitSystem = (system) => {
|
||||
localStorage.setItem("preferred_unit_system", system);
|
||||
};
|
||||
|
||||
$(function(){
|
||||
PluginsAPI.App.triggerReady();
|
||||
});
|
||||
|
|
Ładowanie…
Reference in New Issue