Skip to content

Relative or Rolling Window Filter

Use relative windows for dashboards, queues, renewals, overdue work, and saved views that should move with the current date. Unlike a fixed calendar range, the saved state is an expression that resolves against the filter run’s captured reference date.

Source code
TypeScriptts
const referenceDate = formatLocalIsoDate(new Date());

grid.plugins = [AdvanceFilterPlugin];
grid.columns = [
  { prop: 'task', name: 'Task' },
  {
    prop: 'dueDate',
    name: 'Due date',
    filter: ['date', FILTER_RELATIVE_WINDOW],
  },
];
grid.filter = true;

return [
  { task: 'Earlier follow-up', dueDate: addDays(referenceDate, -8) },
  { task: 'Weekly review', dueDate: addDays(referenceDate, -6) },
  { task: 'Recent report', dueDate: addDays(referenceDate, -2) },
  { task: 'Today checklist', dueDate: referenceDate },
  { task: 'Tomorrow plan', dueDate: addDays(referenceDate, 1) },
];
import { defineCustomElements } from '@revolist/revogrid/loader';
import {
AdvanceFilterPlugin,
FILTER_RELATIVE_WINDOW,
} from '@revolist/revogrid-pro';
import '@revolist/revogrid-pro/dist/revogrid-pro.css';
defineCustomElements();
const grid = document.createElement('revo-grid');
grid.plugins = [AdvanceFilterPlugin];
grid.columns = [
{ prop: 'task', name: 'Task' },
{ prop: 'dueDate', name: 'Due', filter: ['date', FILTER_RELATIVE_WINDOW] },
];
grid.filter = true;
document.querySelector('#app')!.append(grid);
grid.source = [
{ task: 'Renew license', dueDate: '2026-08-24' },
{ task: 'Send report', dueDate: '2026-08-26' },
{ task: 'Plan launch', dueDate: '2026-09-10' },
];

Both the type and operator use the stable ID 'relativeWindow', exported as FILTER_RELATIVE_WINDOW and RELATIVE_WINDOW_OPERATOR.

Saved values are versioned expressions:

{ version: 1, mode: 'preset', preset: 'last7Days' }
{
version: 1,
mode: 'custom',
direction: 'next',
amount: 2,
unit: 'week',
rolling: false,
}

Preset IDs are last7Days, today, thisMonth, thisQuarter, yearToDate, and overdue. Custom directions are last and next; units are day, week, month, quarter, and year.

import {
RELATIVE_WINDOW_OPERATOR,
defineAdvancedFilterConfig,
} from '@revolist/revogrid-pro';
grid.filter = defineAdvancedFilterConfig({
multiFilterItems: {
dueDate: [
{
id: 1,
type: RELATIVE_WINDOW_OPERATOR,
value: { version: 1, mode: 'preset', preset: 'last7Days' },
relation: 'and',
},
],
},
});

The expression remains relative. Each filtering run captures one reference instant, so every row and date-aware condition in that run uses the same “today.”

The shortcut row and custom-window controls are independently configurable. Built-in preset IDs can be hidden, reordered, or mixed with application-specific shortcuts:

import {
createRelativeWindowStructuredFilterType,
defineAdvancedFilterConfig,
} from '@revolist/revogrid-pro';
const relativeWindow = createRelativeWindowStructuredFilterType({
locale: 'en-GB',
dateFormat: { day: '2-digit', month: 'short', year: 'numeric' },
presets: [
'today',
'thisMonth',
{
id: 'next-fortnight',
label: 'Next 14 days',
title: 'Rolling from today',
expression: {
version: 1,
mode: 'custom',
direction: 'next',
amount: 14,
unit: 'day',
rolling: true,
},
},
'overdue',
],
customWindow: {
directions: ['last', 'next'],
units: ['day', 'week', 'month'],
showRolling: true,
defaultValue: {
direction: 'next',
amount: 2,
unit: 'week',
rolling: false,
},
},
showHeading: true,
showPreview: true,
});
grid.filter = defineAdvancedFilterConfig({
structuredFilterTypes: [relativeWindow],
date: {
timezoneMode: 'organization',
organizationTimeZone: 'Europe/Lisbon',
weekStartsOn: 1,
fiscalYearStart: { month: 2, day: 1 },
},
});

Custom shortcuts do not extend or bypass the date-expression model. Each button is backed by a normal validated RelativeDateWindowExpression, and selecting it persists only that expression. Its id identifies the button; label, ariaLabel, title, and disabled control its presentation. A matching custom label is also used in the compact condition summary.

OptionBehavior
presetsOrdered built-in IDs and custom shortcuts. Use false or [] to hide the shortcut row.
customWindowCustom editor settings. Use false to hide the whole Last/Next, amount, unit, and rolling section.
customWindow.directionsAllowed direction choices: last, next, or both.
customWindow.unitsAllowed unit choices: day, week, month, quarter, and/or year.
customWindow.showRollingSet to false to hide the rolling switch and keep the configured/default rolling policy.
customWindow.defaultValueInitial direction, amount, unit, and rolling policy when no custom expression is saved.
showHeadingSet to false to hide the in-body title and description while retaining an accessible section label.
showPreviewSet to false to hide the resolved absolute-date preview.
locale, dateFormatFormat preview text only.

For example, a compact preset-only editor can omit every other section:

createRelativeWindowStructuredFilterType({
presets: ['today', 'last7Days', 'overdue'],
customWindow: false,
showHeading: false,
showPreview: false,
});

The default remains unchanged when these options are omitted: all six built-ins, the complete custom editor, rolling switch, heading, and preview are shown. Duplicate shortcut IDs or expressions and invalid custom expressions are ignored. An empty direction or unit list hides the custom editor because it cannot produce a valid expression.

locale and dateFormat affect preview text only. Timezone decides the reference civil date, weekStartsOn controls calendar-week windows, and fiscalYearStart controls quarter and year policy where applicable.

For a custom expression, amount must be an integer from 1 through 10,000. rolling: true uses a rolling duration; rolling: false resolves complete calendar units.

  • Saving the preview’s absolute { from, to } range instead of the versioned expression; that turns a moving saved view into a fixed range.
  • Omitting version: 1 or using unsupported preset, direction, or unit strings.
  • Treating last7Days as seven 24-hour durations; it is a civil-date window resolved in the column timezone.
  • Using an offset-free datetime source for date filtering without first deciding the intended timezone and source contract.
  • Assuming locale changes week start, fiscal policy, or timezone; configure those under filter.date.