Premium support for our pure JavaScript UI components


Post by gorakh.nath »

Hi team,
The tool tip that is coming on dragging of task from grid is not showing the clock icon how we can show it? so that view will be consistence between tool tip showing when hovering inside scheduler and on dragging task from grid.
I attached two screenshot in which one is showing the clock icon on hover inside the calendar and another its not showing clock icon on dragging task form grid.
My Drag.js file code is:-

import { DragHelper, DomHelper, Rectangle, WidgetHelper, StringHelper, DateHelper, Tooltip } from '@bryntum/schedulerpro/schedulerpro.umd';
import { moment } from '../../../utilities/moment';
import {DRAG_PAST_DATE_ERROR_MSG, WORKFLOW_UPDATE_ERROR, TECHNICIAN_OVERLAP_TASK_ERROR, CUSTOM_ERROR_KEY} from "../utills";
import { getLodash } from '../../../utilities/lodash';
import { ActionDispatcher } from '../../../uibuilder/Actions/ActionDispatcher';
import { SetPageContext }
  from '../../../uibuilder/ActionType/pageConfig/SetPageContext';

export default class Drag extends DragHelper {
  static get defaultConfig () {
    return {
      // Don't drag the actual row element, clone it
      cloneTarget: true,
      mode: 'translateXY',
      // Only allow drops on the schedule area
      dropTargetSelector: '.b-timeline-subgrid',
      // Only allow drag of row elements inside on the unplanned grid
      targetSelector: '.b-grid-row:not(.b-group-row)'
    };
  }

  construct (config) {
    const me = this;

super.construct(config);

me.on({
  dragstart: me.onTaskDragStart,
  drag: me.onTaskDrag,
  drop: me.onTaskDrop,
  thisObj: me
});
  }

  /**
   * 
   * @param {object} schedulerObj : contains the scheduler object
   * @param {string} key : contains the key
   * @returns {string}: based on the key
   */
  getErrorMsg = (schedulerObj, key)=> {
    const customError= getLodash(schedulerObj.jsonDef, 'customErrorMessage');
    let errorMsg='';
    if(key){
      switch (key) {
        case CUSTOM_ERROR_KEY.TASK_OVERLAPPING_ERROR:
          errorMsg= customError?.taskOverlappingErrorMsg || TECHNICIAN_OVERLAP_TASK_ERROR;
          break;
        case CUSTOM_ERROR_KEY.WORKFLOW_UPDATE_ERROR:
          errorMsg= customError?.workflowUpdateErrorMsg || WORKFLOW_UPDATE_ERROR;
          break;
        case CUSTOM_ERROR_KEY.PAST_DATE_ERROR:
          errorMsg= customError?.pastDateErrorMsg || DRAG_PAST_DATE_ERROR_MSG;
          break;
        default:
          break;
      }
    }
    return errorMsg;
  }
  
/** * * @param {object} schedulerObj : contains scheduler object * @param {string} errorMsgKey : contains key based on that error message will come */ showErrorMsg = (schedulerObj, errorMsgKey)=> { const errorMsg= this.getErrorMsg(schedulerObj,errorMsgKey); schedulerObj.setShowAlert(true); schedulerObj.setErrorMessage(errorMsg); } /** * * @param {object} obj : contains the object value use to set the invalid of scheduler * @returns {boolean} : if valid true else false */ isContextValid = (obj)=> { let isValidContext = false; if(obj && obj.valid && Boolean(obj.date && obj.resource)){ isValidContext= true; //Now check for overlap task if allowOverlap false defined in the config if(obj && obj.schedule && !obj.schedule.allowOverlap && !obj.allowTechnicianOverlap && !obj.allowEventOverlap){ isValidContext= obj.schedule.isDateRangeAvailable(obj.startDate, obj.endDate, null, obj.resource); !isValidContext && this.showErrorMsg(obj.me, CUSTOM_ERROR_KEY.TASK_OVERLAPPING_ERROR); } } return isValidContext; } onTaskDragStart ({ context }) { const me = this, { schedule } = me, mouseX = context.clientX, proxy = context.element, task = me.grid.getRecordFromElement(context.grabbed), newSize = me.schedule.timeAxisViewModel.getDistanceForDuration(task.durationMS); // save a reference to the task so we can access it later context.task = task; // Mutate dragged element (grid row) into an event bar proxy.classList.remove('b-grid-row'); proxy.classList.add('b-sch-event-wrap'); proxy.classList.add('b-unassigned-class'); proxy.classList.add(`b-${schedule.mode}`); // proxy.innerHTML = `<i class="${task.iconCls}"></i> ${task.name}`; proxy.innerHTML = StringHelper.xss` <div class="b-sch-event b-has-content"> <div class="b-sch-event-content"> <div>${task.name}</div> <span>Duration: ${task.duration} ${task.durationUnit}</span> </div> </div> `; me.schedule.enableScrollingCloseToEdges(me.schedule.timeAxisSubGrid); if (schedule.isHorizontal) { // If the new width is narrower than the grabbed element... if (context.grabbed.offsetWidth > newSize) { const proxyRect = Rectangle.from(context.grabbed); // If the mouse is off (nearly or) the end, centre the element on the mouse if (mouseX > proxyRect.x + newSize - 20) { context.newX = context.elementStartX = context.elementX = mouseX - newSize / 2; DomHelper.setTranslateX(proxy, context.newX); } } proxy.style.width = `${newSize}px`; } else { const width = schedule.resourceColumns.columnWidth; // Always center horizontal under mouse for vertical mode context.newX = context.elementStartX = context.elementX = mouseX - width / 2; DomHelper.setTranslateX(proxy, context.newX); proxy.style.width = `${width}px`; proxy.style.height = `${newSize}px`; } // Prevent tooltips from showing while dragging schedule.element.classList.add('b-dragging-event'); if (!me.tip) { me.tip = new Tooltip({ align : 'b-t', clippedBy : [schedule.timeAxisSubGridElement, schedule.bodyContainer], forElement : context.element, cls : 'b-popup b-sch-event-tooltip' }); } } onTaskDrag ({ event, context }) { const me = this, { schedule } = me, { task } = context, coordinate = DomHelper[`getTranslate${me.schedule.isHorizontal ? 'X' : 'Y'}`](context.element), date = me.schedule.getDateFromCoordinate(coordinate, 'round', false), startDate = schedule.getDateFromCoordinate(coordinate, 'round', false), endDate = startDate && DateHelper.add(startDate, task.duration, task.durationUnit), // Coordinates required when used in vertical mode, since it does not use actual columns resource = context.target && schedule.resolveResourceRecord(context.target, [event.offsetX, event.offsetY]), // Don't allow drops anywhere, only allow drops if the drop is on the timeaxis and on top of a Resource paramObj= { valid: context.valid, date,resource}, isValid= this.isContextValid(paramObj); context.valid = isValid; // Save reference to resource so we can use it in onTaskDrop context.resource = resource; if (me.tip && context.valid) { const dateFormat = schedule.displayDateFormat, formattedStartDate = DateHelper.format(startDate, dateFormat), formattedEndDate = DateHelper.format(endDate, dateFormat); me.tip.html = ` <div class="b-sch-event-title">${task.name}</div> <div class="b-sch-tooltip-startdate">${formattedStartDate}</div> <div class="b-sch-tooltip-enddate">${formattedEndDate}</div> `; me.tip.showBy(context.element); } else { me.tip?.hide(); } } // Drop callback after a mouse up, take action and transfer the unplanned task to the real SchedulerEventStore (if it's valid) async onTaskDrop ({ context, event }) {
const me = this, { task, target, resource } = context, listCount = me.grid.data.length, { schedule } = me, coordinate = DomHelper[`getTranslate${schedule.isHorizontal ? 'X' : 'Y'}`](context.element), date = me.schedule.getDateFromCoordinate(coordinate, 'round', false), startDate = schedule.getDateFromCoordinate(coordinate, 'round', false), endDate = startDate && DateHelper.add(startDate, task.duration, task.durationUnit), paramObj= { valid: context.valid, date,resource,schedule, startDate, endDate , me, allowTechnicianOverlap: resource?.originalData?.allowTechnicianOverlap, alloweEventOverlap: task?.originalData?.alloweEventOverlap } schedule.disableScrollingCloseToEdges(me.schedule.timeAxisSubGrid); const isValid = this.isContextValid(paramObj); me.tip && me.tip?.hide(); // If drop was done in a valid location, set the startDate and transfer the task to the Scheduler event store if (isValid && context.valid && target) { const // Try resolving event record from target element, to determine if drop was on another event targetEventRecord = me.schedule.resolveEventRecord(context.target); const finalize = me.context.finalize; if(moment().isAfter(date, 'second')) { this.showErrorMsg(me,CUSTOM_ERROR_KEY.PAST_DATE_ERROR) return false; } if (date) { me.setShowAlert(false); me.setErrorMessage(''); me.showLoader(); task.startDate = startDate; task.endDate = endDate; const pageContext = new SetPageContext({task: task.data, resource: resource?.originalData }); this.dispatch(pageContext.plainAction()); const ah = new ActionDispatcher(this); ah.doAction(this.jsonDef.dropGridTaskAction); //const response = await me.submitTaskDetails({ ...task.data, resourceId: context.resource.data.id }); me.hideLoader(); // if(response === null || (response && response.errorCode)) { // this.showErrorMsg(me,CUSTOM_ERROR_KEY.WORKFLOW_UPDATE_ERROR) // return false; // } // // Remove from grid first so that the data change // // below does not fire events into the grid. // me.setTaskListCount(listCount-1); // me.grid.store.remove(task); // // task.setStartDate(date, true); // task.startDate = date; // task.resource = context.resource; // me.schedule.eventStore.add(task); } // Dropped on a scheduled event, display toast if (targetEventRecord) { WidgetHelper.toast(`Dropped on ${targetEventRecord.name}`); } finalize(); // me.context.finalize(); } else { me.abort(); } me.schedule.element.classList.remove('b-dragging-event'); } }
Attachments
Screenshot 2021-09-21 at 5.57.54 PM.png
Screenshot 2021-09-21 at 5.57.54 PM.png (883.58 KiB) Viewed 546 times
Screenshot 2021-09-21 at 5.56.14 PM.png
Screenshot 2021-09-21 at 5.56.14 PM.png (277.88 KiB) Viewed 546 times

Post by saki »

The clocks in tooltip are handled by ClockTemplate that is not currently public. I have created feature request to make it public here: https://github.com/bryntum/support/issues/3447


Post Reply