Skip to content

Commit

Permalink
Merge pull request #4903 from wri/develop
Browse files Browse the repository at this point in the history
Deploy [SDPT][Tree cover gain]
  • Loading branch information
willian-viana authored Dec 19, 2024
2 parents 99b6607 + 58d67d5 commit ca236a9
Show file tree
Hide file tree
Showing 36 changed files with 474 additions and 270 deletions.
5 changes: 4 additions & 1 deletion components/charts/components/pie-chart-legend/component.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,17 +31,20 @@ class PieChartLegend extends PureComponent {
>
<ul className={cx({ simple, sizeClass })}>
{data.map((item, index) => {
const PLACEHOLDER = new RegExp(`\\bPLACEHOLDER\\b`, 'g');
const label = item.label.replace(PLACEHOLDER, `and`);
const value = `${formatNumber({
num: item[config.key],
unit: item.unit ? item.unit : config.unit,
spaceUnit: item.unit !== '%' && config.unit !== 'countsK',
})}`;

return (
<li className="legend-item" key={index.toString()}>
<div className="legend-title">
<span style={{ backgroundColor: item.color }}>{}</span>
<p>
{item.label}
{label}
{sizeClass === 'x-small' && `- ${value}`}
</p>
</div>
Expand Down
10 changes: 2 additions & 8 deletions components/charts/horizontal-bar-chart/custom-tick-component.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,19 +22,13 @@ const CustomTick = ({ x, y, index, yAxisDotFill, data, settings }) => {
<text x="8" y="-16" textAnchor="start" fontSize="12px" fill="#555555">
{extLink ? (
<a href={path.href} target="_blank" rel="noopener noreferrer">
{region}
{' '}
-
{formatNumber({ num: total, unit: '%' })}
{region}: {formatNumber({ num: total, unit: '%' })}
{index === 0 ? ' are plantations' : ''}
</a>
) : (
<Link {...path}>
<a>
{region}
{' '}
-
{formatNumber({ num: total, unit: '%' })}
{region}: {formatNumber({ num: total, unit: '%' })}
{index === 0 ? ' are plantations' : ''}
</a>
</Link>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ const mapStateToProps = (
startDate,
endDate,
trimEndDate,
step,
matchLegend,
dynamicTimeline,
...props
}
Expand All @@ -28,7 +30,8 @@ const mapStateToProps = (
dynamicTimeline,
};
return {
marks: getMarks({ dates, dynamicTimeline }),
marks: getMarks({ dates, step, matchLegend, dynamicTimeline }),
step,
...props,
};
};
Expand Down
13 changes: 11 additions & 2 deletions components/map/components/legend/components/timeline/selectors.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,15 @@ import moment from 'moment';
import range from 'lodash/range';

const getDates = (state) => state.dates;
export const getMarks = createSelector(getDates, (dates) => {
const getSliderStep = (state) => state.step;
const getMatchLegend = (state) => state.matchLegend;

const getTicksStep = (numOfYears, sliderStep, matchLegend) => {
if (matchLegend && numOfYears && sliderStep) return numOfYears / sliderStep;
return (numOfYears > 6 ? 6 : numOfYears);
}

export const getMarks = createSelector(getDates, getSliderStep, getMatchLegend, (dates, sliderStep, matchLegend) => {
if (!dates) return null;
const { minDate, maxDate, dynamicTimeline = false } = dates;
const numOfYears = moment(maxDate).diff(minDate, 'years');
Expand All @@ -12,11 +20,12 @@ export const getMarks = createSelector(getDates, (dates) => {
if (!numOfYears || maxDays <= 365) return null;

const marks = {};
const ticksStep = getTicksStep(numOfYears, sliderStep, matchLegend);

let ticks = range(
0,
maxDays + 1,
maxDays / (numOfYears > 6 ? 6 : numOfYears)
maxDays / ticksStep
);

if (dynamicTimeline) {
Expand Down
69 changes: 67 additions & 2 deletions components/slider/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ export class Slider extends PureComponent {
railStyle: PropTypes.shape({}),
dotStyle: PropTypes.shape({}),
pushable: PropTypes.oneOfType([PropTypes.bool, PropTypes.number]),
disableStartHandle: PropTypes.bool,
disableEndHandle: PropTypes.bool,
playing: PropTypes.bool,
onChange: PropTypes.func,
};

static defaultProps = {
Expand All @@ -44,14 +48,39 @@ export class Slider extends PureComponent {
railStyle: { backgroundColor: '#d9d9d9' },
dotStyle: { visibility: 'hidden', border: '0px' },
pushable: true,
disableStartHandle: false,
disableEndHandle: false,
playing: false,
onChange: () => {},
};

renderHandle = (props) => {
const { formatValue, showTooltip } = this.props;
const {
formatValue,
showTooltip,
playing,
disableStartHandle,
disableEndHandle,
} = this.props;
const { value, dragging, index, ...restProps } = props;
const formattedValue = formatValue ? formatValue(value) : value;
const tooltipVisible = showTooltip ? showTooltip(index) : false;

// Start handle
if (disableStartHandle && props?.index === 0) {
return null;
}

// End handle
if (disableEndHandle && props?.index === 2) {
return null;
}

// Vertical line that indicates the current position, when playing
if (!playing && props?.index === 1) {
return null;
}

return (
<Tooltip
key={index}
Expand All @@ -68,8 +97,43 @@ export class Slider extends PureComponent {
);
};

handleOnChange = (newSliderPositions) => {
const {
value: sliderPositions,
disableStartHandle,
disableEndHandle,
onChange,
} = this.props;

// Both handles are disabled, no possible changes can be made.
if (disableStartHandle && disableEndHandle) {
return null;
}

// Start handle disabled. We allow trim and end value, but keep the start value the same.
if (disableStartHandle) {
onChange([
sliderPositions[0],
newSliderPositions[1],
newSliderPositions[2],
]);
return null;
}

// End handle disabled. We allow the start value, but keep the same trim and end value.
if (disableEndHandle) {
onChange([newSliderPositions[0], sliderPositions[1], sliderPositions[2]]);
return null;
}

// Full functionality, pass the new values along.
onChange(newSliderPositions);
return null;
};

render() {
const { customClass, range, handleStyle, value, ...rest } = this.props;
const { customClass, range, handleStyle, value, onChange, ...rest } =
this.props;

const Component = range ? Range : RCSlider;
const handleNum = Array.isArray(value) ? value.length : 1;
Expand Down Expand Up @@ -98,6 +162,7 @@ export class Slider extends PureComponent {
handle={this.renderHandle}
handleStyle={handleStyles}
value={value}
onChange={this.handleOnChange}
{...rest}
/>
</div>
Expand Down
11 changes: 10 additions & 1 deletion components/timestep/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,13 +39,15 @@ class Timestep extends PureComponent {
handleOnChange: PropTypes.func,
handleOnAfterChange: PropTypes.func,
handleOnPlay: PropTypes.func,
disableStartHandle: PropTypes.bool,
disableEndHandle: PropTypes.bool,
};

static defaultProps = {
customClass: null,
range: true,
pushable: 0,
canPlay: false,
canPlay: true,

trim: null,

Expand Down Expand Up @@ -75,6 +77,8 @@ class Timestep extends PureComponent {
handleOnChange: null,
handleOnAfterChange: null,
handleOnPlay: null,
disableStartHandle: false,
disableEndHandle: false,
};

constructor(props) {
Expand Down Expand Up @@ -462,6 +466,8 @@ class Timestep extends PureComponent {
range,
pushable,
PlayButton,
disableStartHandle,
disableEndHandle,
} = this.props;

const { playing } = this.state;
Expand All @@ -488,6 +494,9 @@ class Timestep extends PureComponent {
pushable={pushable}
onChange={this.handleOnChange}
onAfterChange={this.handleOnAfterChange}
disableStartHandle={disableStartHandle}
disableEndHandle={disableEndHandle}
playing={playing}
/>
</div>
</div>
Expand Down
11 changes: 6 additions & 5 deletions components/ui/dynamic-sentence/component.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -49,13 +49,14 @@ class DynamicSentence extends PureComponent {
}
} else {
// eslint-disable-next-line security/detect-non-literal-regexp
const regex = new RegExp(`{${p}}`, 'g');
const DYNAMIC_PARAMETERS = new RegExp(`{${p}}`, 'g');
const PLACEHOLDER = new RegExp(`\\bPLACEHOLDER\\b`, 'g'); // regex to remove the bold from the word 'and' between indicators

formattedSentence =
formattedSentence &&
formattedSentence.replace(
regex,
`<b>${translateText(param)}</b>`
);
formattedSentence
.replace(DYNAMIC_PARAMETERS, `<b>${translateText(param)}</b>`)
.replace(PLACEHOLDER, `<span class="no-bold">and</span>`);
}
}
});
Expand Down
4 changes: 4 additions & 0 deletions components/ui/dynamic-sentence/styles.scss
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@
font-size: 20px;
color: $slate;

.no-bold {
font-weight: 300 !important;
}

strong,
b,
span {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,29 @@ class WidgetSettings extends PureComponent {
/>
</div>
);

case 'baseline-select':
return (
options &&
!!options.length && (
<Dropdown
className={cx('widget-settings-selector', type)}
theme={cx('theme-select-light', {
'theme-dropdown-button': type === 'mini-select',
})}
label={label}
value={startValue}
options={options}
onChange={(change) =>
propagateChange({ [startKey]: change && change.value })}
disabled={loading}
clearable={clearable}
infoAction={metaKey ? () => handleShowInfo(metaKey) : null}
optionsAction={handleShowInfo}
optionsActionKey="metaKey"
noSelectedValue={placeholder}
/>
)
);
case 'compare-select':
return (
<div className={cx('widget-settings-selector', type)}>
Expand All @@ -120,7 +142,7 @@ class WidgetSettings extends PureComponent {
const loadingDatepicker = !startValue || !minDate || !maxDate;

return (
<div className={cx("widget-settings-selector", type)}>
<div className={cx('widget-settings-selector', type)}>
<div className="datepicker-selector">
<div>
<span className="label">From</span>
Expand All @@ -130,7 +152,7 @@ class WidgetSettings extends PureComponent {
selected={new Date(startValue)}
onChange={(change) =>
propagateChange({
[startKey]: moment(change).format("YYYY-MM-DD"),
[startKey]: moment(change).format('YYYY-MM-DD'),
})}
minDate={new Date(minDate)}
maxDate={new Date(maxDate)}
Expand All @@ -146,7 +168,7 @@ class WidgetSettings extends PureComponent {
selected={new Date(endValue)}
onChange={(change) =>
propagateChange({
[endKey]: moment(change).format("YYYY-MM-DD"),
[endKey]: moment(change).format('YYYY-MM-DD'),
})}
minDate={new Date(minDate)}
maxDate={new Date(maxDate)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@ import {
TREE_PLANTATIONS,
} from 'data/layers';

import { EuropeFAOCountries } from 'utils/fao-countries';

import getWidgetProps from './selectors';

const MIN_YEAR = 2000;

export default {
widget: 'treeCoverGainOutsidePlantations',
title: {
Expand Down Expand Up @@ -43,8 +43,16 @@ export default {
clearable: true,
blacklist: ['wdpa'],
},
{
key: 'baselineYear',
label: 'Baseline Year',
type: 'baseline-select',
startKey: 'startYear',
placeholder: MIN_YEAR,
clearable: true,
},
],
refetchKeys: ['forestType', 'landCategory'],
refetchKeys: ['forestType', 'landCategory', 'startYear'],
chartType: 'pieChart',
colors: 'gainWithinOutsidePlantations',
metaKey: 'widget_tree_cover_gain_outside_plantations',
Expand All @@ -70,24 +78,25 @@ export default {
},
sentences: {
globalInitial:
'Globally between 2000 and 2020, {gainPercent} of tree cover gain occurred outside of plantations.',
'Globally between {baselineYear} and 2020, {gainPercent} of tree cover gain occurred outside of plantations.',
globalWithIndicator:
'Globally between 2000 and 2020, {gainPercent} of tree cover gain within {indicator} occurred outside of plantations.',
'Globally between {baselineYear} and 2020, {gainPercent} of tree cover gain within {indicator} occurred outside of plantations.',
regionInitial:
'In {location} between 2000 and 2020, {gainPercent} of tree cover gain occurred outside of plantations.',
'In {location} between {baselineYear} and 2020, {gainPercent} of tree cover gain occurred outside of plantations.',
regionWithIndicator:
'In {location} between 2000 and 2020, {gainPercent} of tree cover gain within {indicator} occurred outside of plantations.',
},
blacklists: {
adm0: EuropeFAOCountries,
'In {location} between {baselineYear} and 2020, {gainPercent} of tree cover gain within {indicator} occurred outside of plantations. ',
},
settings: {
threshold: 0,
startYear: MIN_YEAR,
endYear: 2020, // reference to display the correct data on the map
},
getData: (params) => {
return getTreeCoverGainByPlantationType(params).then((response) => {
const { data } = (response && response.data) || {};

if (data?.length === 0) return null;

const totalArea = data.reduce(
(prev, curr) => prev + curr?.gain_area_ha,
0
Expand Down
Loading

0 comments on commit ca236a9

Please sign in to comment.