Your search did not match any results.
Scheduler

Context Menu Integration

Documentation

This demo shows how to create a context menu for appointments and cells using the onAppointmentContextMenu and onCellContextMenu functions.

Copy to CodeSandBox
Apply
Reset
import React from 'react'; import Scheduler, { Resource } from 'devextreme-react/scheduler'; import ContextMenu from 'devextreme-react/context-menu'; import { data, resourcesData } from './data.js'; import { cellContextMenuItems, appointmentContextMenuItems, setResource } from './MenuItems.js'; import { AppointmentMenuTemplate } from './AppointmentTemplate.js'; const currentDate = new Date(2017, 4, 25); const views = ['day', 'month']; class App extends React.Component { constructor(props) { super(props); resourcesData.map((item) => { item.onItemClick = setResource; }); this.state = { appointmentContextMenuEvent: null, cellContextMenuEvent: null, appointmentContextMenuItems: appointmentContextMenuItems.concat(resourcesData), }; this.onAppointmentContextMenu = this.onAppointmentContextMenu.bind(this); this.onAppointmentContextMenuItemClick = this.onAppointmentContextMenuItemClick.bind(this); this.onCellContextMenu = this.onCellContextMenu.bind(this); this.onCellContextMenuItemClick = this.onCellContextMenuItemClick.bind(this); } render() { return ( <React.Fragment> <Scheduler dataSource={data} views={views} defaultCurrentView={'month'} defaultCurrentDate={currentDate} firstDayOfWeek={1} startDayHour={9} recurrenceEditMode={'series'} onAppointmentContextMenu={this.onAppointmentContextMenu} onCellContextMenu={this.onCellContextMenu} height={600} > <Resource dataSource={resourcesData} fieldExpr={'roomId'} label={'Room'} /> </Scheduler> <ContextMenu dataSource={this.state.appointmentContextMenuItems} width={200} target={'.dx-scheduler-appointment'} onItemClick={this.onAppointmentContextMenuItemClick} itemRender={AppointmentMenuTemplate} /> <ContextMenu dataSource={cellContextMenuItems} width={200} target={'.dx-scheduler-date-table-cell'} onItemClick={this.onCellContextMenuItemClick} /> </React.Fragment> ); } onAppointmentContextMenu(e) { this.setState({ appointmentContextMenuEvent: e }); } onAppointmentContextMenuItemClick(e) { if (!e.itemData.items && e.itemData.onItemClick) { e.itemData.onItemClick(this.state.appointmentContextMenuEvent, e); } } onCellContextMenu(e) { this.setState({ cellContextMenuEvent: e }); } onCellContextMenuItemClick(e) { e.itemData.onItemClick(this.state.cellContextMenuEvent); } } export default App;
import React from 'react'; export function AppointmentMenuTemplate(itemData) { return (<div> {itemData.color ? <div className={'item-badge'} style={{ backgroundColor: itemData.color }} /> : ''} {itemData.text} {itemData.text === 'New Appointment until the end of the week' ? <hr /> : ''} </div>); }
import React from 'react'; import ReactDOM from 'react-dom'; import App from './App.js'; ReactDOM.render( <App />, document.getElementById('app') );
<!DOCTYPE html> <html> <head> <title>DevExtreme Demo</title> <meta http-equiv="X-UA-Compatible" content="IE=edge" /> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0" /> <link rel="stylesheet" type="text/css" href="https://cdn3.devexpress.com/jslib/19.1.3/css/dx.common.css" /> <link rel="dx-theme" data-theme="generic.light" href="https://cdn3.devexpress.com/jslib/19.1.3/css/dx.light.css" /> <script src="https://unpkg.com/core-js@2.4.1/client/shim.min.js"></script> <script src="https://unpkg.com/systemjs@0.21.3/dist/system.js"></script> <script type="text/javascript" src="config.js"></script> <script type="text/javascript"> System.import('./index.js'); </script> </head> <body class="dx-viewport"> <div class="demo-container"> <div id="app"></div> </div> </body> </html>
.dx-menu-item-content span { margin-right: 5px; } .dx-menu-item-has-submenu .dx-icon-spinright { position: absolute; top: 7px; right: 2px; } .item-badge { text-align: center; float: left; margin-right: 12px; color: white; width: 18px; height: 18px; font-size: 19.5px; border-radius: 18px; margin-top: 2px; }
export const data = [ { text: 'Watercolor Landscape', roomId: [1], startDate: new Date(2017, 4, 1, 9, 30), endDate: new Date(2017, 4, 1, 11), recurrenceRule: 'FREQ=WEEKLY;BYDAY=TU,FR;COUNT=10' }, { text: 'Oil Painting for Beginners', roomId: [2], startDate: new Date(2017, 4, 1, 9, 30), endDate: new Date(2017, 4, 1, 11), recurrenceRule: 'FREQ=WEEKLY;BYDAY=MO,TH;COUNT=10' }, { text: 'Testing', roomId: [3], startDate: new Date(2017, 4, 1, 12, 0), endDate: new Date(2017, 4, 1, 13, 0), recurrenceRule: 'FREQ=WEEKLY;BYDAY=MO;WKST=TU;INTERVAL=2;COUNT=2' }, { text: 'Meeting of Instructors', roomId: [4], startDate: new Date(2017, 4, 1, 9, 0), endDate: new Date(2017, 4, 1, 9, 15), recurrenceRule: 'FREQ=DAILY;BYDAY=WE;UNTIL=20170601' }, { text: 'Recruiting students', roomId: [5], startDate: new Date(2017, 4, 26, 10, 0), endDate: new Date(2017, 4, 26, 11, 0), recurrenceRule: 'FREQ=YEARLY;BYWEEKNO=23', recurrenceException: '20170611T100000' }, { text: 'Final exams', roomId: [3], startDate: new Date(2017, 4, 26, 12, 0), endDate: new Date(2017, 4, 26, 13, 35), recurrenceRule: 'FREQ=YEARLY;BYWEEKNO=24;BYDAY=TH,FR' }, { text: 'Monthly Planning', roomId: [4], startDate: new Date(2017, 4, 26, 14, 30), endDate: new Date(2017, 4, 26, 15, 45), recurrenceRule: 'FREQ=MONTHLY;BYMONTHDAY=27;COUNT=1' }, { text: 'Open Day', roomId: [5], startDate: new Date(2017, 4, 1, 9, 30), endDate: new Date(2017, 4, 1, 13), recurrenceRule: 'FREQ=YEARLY;BYYEARDAY=148' } ]; export const resourcesData = [ { text: 'Room 101', id: 1, color: '#bbd806' }, { text: 'Room 102', id: 2, color: '#f34c8a' }, { text: 'Room 103', id: 3, color: '#ae7fcc' }, { text: 'Meeting room', id: 4, color: '#ff8817' }, { text: 'Conference hall', id: 5, color: '#03bb92' } ];
System.config({ transpiler: 'plugin-babel', paths: { 'npm:': 'https://unpkg.com/' }, defaultExtension: 'js', map: { 'react': 'npm:react@16/umd/react.development.js', 'react-dom': 'npm:react-dom@16/umd/react-dom.development.js', 'prop-types': 'npm:prop-types/prop-types.js', 'devextreme': 'npm:devextreme@19.1', 'devextreme-react': 'npm:devextreme-react@19.1', 'jszip': 'npm:jszip@3.1.3/dist/jszip.min.js', 'quill': 'npm:quill@1.3.6/dist/quill.js', 'devexpress-diagram': 'npm:devexpress-diagram', // SystemJS plugins 'plugin-babel': 'npm:systemjs-plugin-babel@0/plugin-babel.js', 'systemjs-babel-build': 'npm:systemjs-plugin-babel@0/systemjs-babel-browser.js' }, packages: { 'devextreme': { defaultExtension: 'js' }, 'devextreme-react': { main: 'index.js' } }, babelOptions: { sourceMaps: false, stage0: true, react: true } });