Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
Clear All
new posts

    Problem with Timeline using DateField type

    SmartClient Version: v10.0p_2015-02-09/Pro Deployment (built 2015-02-09)

    I have some problems with a Timeline that uses DataSourceDateField for startDate and endDate instead of DataSourceDateTimeField

    When using only Date and not DateTime, an event that starts today and end today will take up the entire day in the Timeline (Which is exactly what I want), but this logic does not persist to drag resizing. If I resize an event to fill the entire day of today, it will have end date tomorrow instead. (See attached picture)


    Another problem is that some events overlap if one event has the same start date as the other event's end date (See attached picture)

    Testcase based on the DataBound Timeline example in the showcase.
    Code:
    	public Timeline getTimeline()
    	{
    		DataSource eventDS = new DataSource();  
            DataSourceSequenceField eventIdField = new DataSourceSequenceField("eventId");  
            eventIdField.setPrimaryKey(true); 
            
            DataSourceTextField nameField = new DataSourceTextField("name");  
            DataSourceTextField descField = new DataSourceTextField("description");  
            DataSourceDateField startDateField = new DataSourceDateField("startDate");  
            DataSourceDateField endDateField = new DataSourceDateField("endDate");  
            DataSourceTextField laneField = new DataSourceTextField("lane");  
      
            eventDS.setFields(eventIdField, nameField, descField, startDateField, endDateField);  
            eventDS.setClientOnly(true);  
            eventDS.setTestData(TimelineData.getRecords());  
      
            Timeline calendar = new Timeline();  
            calendar.setHeight(451);
            calendar.setEventSnapGap(60 * 24);
            calendar.setLaneEventPadding(3);
            calendar.setStartDate(new Date());
            calendar.setData(TimelineData.getRecords());  
            calendar.setLanes(TimelineLaneData.getRecords());  
            calendar.setCanEditLane(true);  
            calendar.setShowEventDescriptions(false);
            calendar.setDisableWeekends(false);
            calendar.setLaneFields(new ListGridField[]{ new ListGridField("title", "Developer", 120)});  
              
            calendar.setDataSource(eventDS);  
            calendar.setAutoFetchData(true);  
    		
            HeaderLevel headerLevel = new HeaderLevel(TimeUnit.DAY);
            headerLevel.setTitleFormatter(new HeaderLevelTitleCustomizer() {
                @Override
                public String getTitle(HeaderLevel headerLevel, Date startDate, Date endDate, String defaultValue, Calendar calendar) {
                    DateTimeFormat fmt = DateTimeFormat.getFormat("d/M");
                    return fmt.format(startDate);
                }
            });
            calendar.setResolution(new HeaderLevel[] {new HeaderLevel(TimeUnit.WEEK), headerLevel}, TimeUnit.DAY, 21, null);
    		
            return calendar;
    	}
    	
    	public static class TimelineData {  
    		  
    	    private static CalendarEvent[] records;  
    	    private static Date today = new Date();  
    	    private static int year = today.getYear();  
    	    private static int month = today.getMonth();  
    	    private static int start = today.getDate();  
    	  
    	    public TimelineData() {  
    	    }  
    	    public static CalendarEvent[] getRecords() {  
    	        if (records == null) {  
    	            records = getNewRecords();  
    	        }  
    	        return records;  
    	    }
    	    public static CalendarEvent[] getNewRecords() {
    	        return new CalendarEvent[]{
    	                new CalendarEvent(1, "One Day", "", DateUtil.getLogicalDateOnly(new Date(year, month, start)), DateUtil.getLogicalDateOnly(new Date(year, month, start )), "charlesMadigen"),  
    	                new CalendarEvent(2, "Two Days", "", DateUtil.getLogicalDateOnly(new Date(year, month, start)), DateUtil.getLogicalDateOnly(new Date(year, month, start + 1)), "tamaraKane"),  
    	                new CalendarEvent(3, "Three Days", "", DateUtil.getLogicalDateOnly(new Date(year, month, start)), DateUtil.getLogicalDateOnly(new Date(year, month, start + 2)), "darcyFeeney"),
    	                new CalendarEvent(4, "Test", "", DateUtil.getLogicalDateOnly(new Date(year, month, start+ 2)), DateUtil.getLogicalDateOnly(new Date(year, month, start + 6)), "darcyFeeney")    
    	        };  
    	    }  
    	}
    	
    	public static class TimelineLaneData {  
    		  
    	    private static Lane[] records;  
    	  
    	    public static Lane[] getRecords() {  
    	        if (records == null) {  
    	            records = getNewRecords();  
    	        }  
    	        return records;  
    	    }  
    	  
    	    public TimelineLaneData() {  
    	    }  
    	  
    	    public static Lane[] getNewRecords() {  
    	        Lane[] lanes = new Lane[]{  
    	            getLane("charlesMadigen", "Charles Madigen", "Managers"),  
    	            getLane("tamaraKane", "Tamara Kane", "Developers"),  
    	            getLane("darcyFeeney", "Darcy Feeney", "Managers")
    	        };  
    	        return lanes;  
    	    }  
    	      
    	    private static Lane getLane(String name, String title, String devGroup) {  
    	        Lane lane = new Lane(name, title);  
    	        lane.setAttribute("devGroup", devGroup);  
    	        return lane;  
    	    }  
    	}
    Attached Files

    #2
    Calendar views, including Timelines, do not support logical dates, so you'll have to use Datetime fields in your DataSource.

    Comment


      #3
      Okay, I'm now using DateTimeFields but I am stiil seeing some overlap in special cases.

      In the test case I'm loading 4 events into the timeline. The 2 events "test 3" and "Test 4" start on the same date but for some reason "test 4" overlaps "Test 3". (See attached)

      Code:
      	public Timeline getTimeline()
      	{
      		DataSource eventDS = new DataSource();  
              DataSourceSequenceField eventIdField = new DataSourceSequenceField("eventId");  
              eventIdField.setPrimaryKey(true); 
              
              DataSourceTextField nameField = new DataSourceTextField("name");  
              DataSourceTextField descField = new DataSourceTextField("description");  
              DataSourceDateTimeField startDateField = new DataSourceDateTimeField("startDate");  
              DataSourceDateTimeField endDateField = new DataSourceDateTimeField("endDate");  
              DataSourceTextField laneField = new DataSourceTextField("lane");  
        
              eventDS.setFields(eventIdField, nameField, descField, startDateField, endDateField);  
              eventDS.setClientOnly(true);  
              eventDS.setTestData(TimelineData.getRecords());  
        
              Timeline calendar = new Timeline();  
              calendar.setHeight(451);
              calendar.setLaneEventPadding(3);
              calendar.setStartDate(new Date());
              calendar.setData(TimelineData.getRecords());  
              calendar.setLanes(TimelineLaneData.getRecords());  
              calendar.setCanEditLane(true);  
              calendar.setShowEventDescriptions(false);
              calendar.setDisableWeekends(false);
              calendar.setLaneFields(new ListGridField[]{ new ListGridField("title", "Developer", 120)});  
                
              calendar.setDataSource(eventDS);  
              calendar.setAutoFetchData(true);  
      		
              HeaderLevel headerLevel = new HeaderLevel(TimeUnit.DAY);
              headerLevel.setTitleFormatter(new HeaderLevelTitleCustomizer() {
                  @Override
                  public String getTitle(HeaderLevel headerLevel, Date startDate, Date endDate, String defaultValue, Calendar calendar) {
                      DateTimeFormat fmt = DateTimeFormat.getFormat("d/M");
                      return fmt.format(startDate);
                  }
              });
              calendar.setResolution(new HeaderLevel[] {new HeaderLevel(TimeUnit.WEEK), headerLevel}, TimeUnit.DAY, 21, null);
      		
              return calendar;
      	}
      	
      	public static class TimelineData {  
      		  
      	    private static CalendarEvent[] records;  
      	    private static Date today = new Date();  
      	    private static int year = today.getYear();  
      	    private static int month = today.getMonth();  
      	    private static int start = today.getDate();  
      	  
      	    public TimelineData() {  
      	    }  
      	    public static CalendarEvent[] getRecords() {  
      	        if (records == null) {  
      	            records = getNewRecords();  
      	        }  
      	        return records;  
      	    }
      	    public static CalendarEvent[] getNewRecords() {
      	        return new CalendarEvent[]{
      	                new CalendarEvent(1, "Test 1", "", new Date(year, month, start), new Date(year, month, start + 3), "charlesMadigen"),  
      	                new CalendarEvent(2, "Test 2", "", new Date(year, month, start + 2), new Date(year, month, start + 8), "charlesMadigen"),  
      	                new CalendarEvent(3, "Test 3", "", new Date(year, month, start + 4), new Date(year, month, start + 10), "charlesMadigen"),
      	                new CalendarEvent(4, "Test 4", "", new Date(year, month, start + 4), new Date(year, month, start + 6), "charlesMadigen")    
      	        };  
      	    }  
      	}
      	
      	public static class TimelineLaneData {  
      		  
      	    private static Lane[] records;  
      	  
      	    public static Lane[] getRecords() {  
      	        if (records == null) {  
      	            records = getNewRecords();  
      	        }  
      	        return records;  
      	    }  
      	  
      	    public TimelineLaneData() {  
      	    }  
      	  
      	    public static Lane[] getNewRecords() {  
      	        Lane[] lanes = new Lane[]{  
      	            getLane("charlesMadigen", "Charles Madigen", "Managers"),  
      	            getLane("tamaraKane", "Tamara Kane", "Developers"),  
      	            getLane("darcyFeeney", "Darcy Feeney", "Managers")
      	        };  
      	        return lanes;  
      	    }  
      	      
      	    private static Lane getLane(String name, String title, String devGroup) {  
      	        Lane lane = new Lane(name, title);  
      	        lane.setAttribute("devGroup", devGroup);  
      	        return lane;  
      	    }  
      	}
      Attached Files

      Comment


        #4
        A quick note that we do see this overlapping issue in testing and it's under investigation - we'll update here when it's been fixed.

        Comment


          #5
          We've fixed the logic around calculating complex overlap patterns for events, and you should see it working as expected in builds dated February 21 and later.

          Let us know if you spot any other edge-cases once you have a build with the fix.

          Comment


            #6
            SmartClient Version: v10.0p_2015-02-21/Pro Deployment (built 2015-02-21)

            I may have found another edge-case.

            If I try to add an event that begins before the the beginning of the timeline, and ends after the end of the timeline, I get an error.

            Error in the Results tab of the developer console:
            Code:
            13:13:21.820:TMR1:WARN:Log:TypeError: _7 is undefined
            Stack from error.stack:
                CalendarView.adjustDimensionsForOverlap() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:138
                CalendarView.sizeEventCanvas() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:136
                CalendarView.addEvent() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:195
                CalendarView.refreshVisibleEvents() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:178
                CalendarView.refreshEvents() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:210
                Calendar.refreshSelectedView() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:392
                Calendar.dataChanged() @ forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER:392
                anonymous() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:77
                thunk() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:324
                observation() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:321
                ResultSet._doneChangingData() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1910
                ResultSet._handleNewData() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1873
                isc.A.fetchRemoteDataReply() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1859
                [c]Class.fireCallback() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:290
                [c]Class.fireCallback() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:358
                DataSource.fireResponseCallbacks() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:731
                DataSource._completeResponseProcessing() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:728
                DataSource._handleClientOnlyReply/_6() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:589
                DataSource._handleClientOnlyReply() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:590
                [c]Class.fireCallback() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:290
                [c]Class.fireCallback() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:358
                anonymous() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1675
                unnamed() @ http://127.0.0.1:9876/forecast/D6824B9231049D799DAB675DEDFEA184.cache.js:98805
                [c]RPCManager.fireReplyCallbacks() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1682
                [c]RPCManager.performOperationReply() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1673
                RPCManager._performTransactionReply() @ forecast/sc/modules/ISC_DataBinding.js?version=#BUILD_NUMBER:1653
                [c]Class.fireCallback() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:290
                Timer._fireTimeout() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:1291
                Timer.setTimeout/_6<() @ forecast/sc/modules/ISC_Core.js?version=#BUILD_NUMBER:1289
            
            13:13:21.822:TMR1:WARN:Log:Uncaught JavaScript exception: TypeError: _7 is undefined in http://127.0.0.1:8888/forecast/sc/modules/ISC_Calendar.js?version=#BUILD_NUMBER, line 138

            Test Case:
            Code:
            	public Timeline getTimeline()
            	{
            		DataSource eventDS = new DataSource();  
                    DataSourceSequenceField eventIdField = new DataSourceSequenceField("eventId");  
                    eventIdField.setPrimaryKey(true); 
                    
                    DataSourceTextField nameField = new DataSourceTextField("name");  
                    DataSourceTextField descField = new DataSourceTextField("description");  
                    DataSourceDateTimeField startDateField = new DataSourceDateTimeField("startDate");  
                    DataSourceDateTimeField endDateField = new DataSourceDateTimeField("endDate");  
                    DataSourceTextField laneField = new DataSourceTextField("lane");  
              
                    eventDS.setFields(eventIdField, nameField, descField, startDateField, endDateField, laneField);  
                    eventDS.setClientOnly(true);  
                    eventDS.setTestData(TimelineData.getRecords());  
              
                    Timeline calendar = new Timeline();  
                    calendar.setHeight(451);
                    calendar.setLaneEventPadding(3);
                    calendar.setStartDate(new Date());
                    calendar.setLanes(TimelineLaneData.getRecords());  
                    calendar.setCanEditLane(true);  
                    calendar.setShowEventDescriptions(false);
                    calendar.setDisableWeekends(false);
                    calendar.setLaneFields(new ListGridField[]{ new ListGridField("title", "Developer", 120)});  
                      
                    calendar.setDataSource(eventDS);  
                    calendar.setAutoFetchData(true);  
            		
                    HeaderLevel headerLevel = new HeaderLevel(TimeUnit.DAY);
                    headerLevel.setTitleFormatter(new HeaderLevelTitleCustomizer() {
                        @Override
                        public String getTitle(HeaderLevel headerLevel, Date startDate, Date endDate, String defaultValue, Calendar calendar) {
                            DateTimeFormat fmt = DateTimeFormat.getFormat("d/M");
                            return fmt.format(startDate);
                        }
                    });
                    calendar.setResolution(new HeaderLevel[] {new HeaderLevel(TimeUnit.WEEK), headerLevel}, TimeUnit.DAY, 21, null);
            		
                    return calendar;
            	}
            	
            	public static class TimelineData {  
            		  
            	    private static CalendarEvent[] records;  
            	    private static Date today = new Date();  
            	    private static int year = today.getYear();  
            	    private static int month = today.getMonth();  
            	    private static int start = today.getDate();  
            	  
            	    public TimelineData() {  
            	    }  
            	    public static CalendarEvent[] getRecords() {  
            	        if (records == null) {  
            	            records = getNewRecords();  
            	        }  
            	        return records;  
            	    }
            	    public static CalendarEvent[] getNewRecords() {
            	        return new CalendarEvent[]{
            	                new CalendarEvent(1, "Test 1", "", new Date(year, month, start - 1), new Date(year, month+2, start), "charlesMadigen"),  
            	                new CalendarEvent(2, "Test 2", "", new Date(year, month, start + 2), new Date(year, month, start + 8), "charlesMadigen"),  
            	                new CalendarEvent(3, "Test 3", "", new Date(year, month, start + 4), new Date(year, month, start + 10), "charlesMadigen"),
            	                new CalendarEvent(4, "Test 4", "", new Date(year, month, start + 4), new Date(year, month, start + 6), "charlesMadigen")    
            	        };  
            	    }  
            	}
            	
            	public static class TimelineLaneData {  
            		  
            	    private static Lane[] records;  
            	  
            	    public static Lane[] getRecords() {  
            	        if (records == null) {  
            	            records = getNewRecords();  
            	        }  
            	        return records;  
            	    }  
            	  
            	    public TimelineLaneData() {  
            	    }  
            	  
            	    public static Lane[] getNewRecords() {  
            	        Lane[] lanes = new Lane[]{  
            	            getLane("charlesMadigen", "Charles Madigen", "Managers"),  
            	            getLane("tamaraKane", "Tamara Kane", "Developers"),  
            	            getLane("darcyFeeney", "Darcy Feeney", "Managers")
            	        };  
            	        return lanes;  
            	    }  
            	      
            	    private static Lane getLane(String name, String title, String devGroup) {  
            	        Lane lane = new Lane(name, title);  
            	        lane.setAttribute("devGroup", devGroup);  
            	        return lane;  
            	    }  
            	}
            Attached Files

            Comment


              #7
              This was already fixed on March 7 - please retest with the latest from smartclient.com/builds

              Comment


                #8
                Originally posted by Isomorphic View Post
                We've fixed the logic around calculating complex overlap patterns for events, and you should see it working as expected in builds dated February 21 and later.

                Let us know if you spot any other edge-cases once you have a build with the fix.
                Hi, I think I have spotted another edge-case in the overlapping issue.

                Code:
                public Timeline getTimeline() {
                	DataSource eventDS = new DataSource();  
                	DataSourceSequenceField eventIdField = new DataSourceSequenceField("eventId");  
                	eventIdField.setPrimaryKey(true); 
                	
                	DataSourceTextField nameField = new DataSourceTextField("name");  
                	DataSourceTextField descField = new DataSourceTextField("description");  
                	DataSourceDateTimeField startDateField = new DataSourceDateTimeField("startDate");  
                	DataSourceDateTimeField endDateField = new DataSourceDateTimeField("endDate");  
                	DataSourceTextField laneField = new DataSourceTextField("lane");  
                	  
                	eventDS.setFields(eventIdField, nameField, descField, startDateField, endDateField);  
                	eventDS.setClientOnly(true);  
                	eventDS.setTestData(TimelineData.getRecords());  
                	  
                	Timeline calendar = new Timeline();  
                	calendar.setHeight(451);
                	calendar.setLaneEventPadding(3);
                	calendar.setStartDate(new Date());
                	calendar.setData(TimelineData.getRecords());  
                	calendar.setLanes(TimelineLaneData.getRecords());  
                	calendar.setCanEditLane(true);  
                	calendar.setShowEventDescriptions(false);
                	calendar.setDisableWeekends(false);
                	calendar.setLaneFields(new ListGridField[]{ new ListGridField("title", "Developer", 120)});  
                	  
                	calendar.setDataSource(eventDS);  
                	calendar.setAutoFetchData(true);  
                	
                	HeaderLevel headerLevel = new HeaderLevel(TimeUnit.DAY);
                	headerLevel.setTitleFormatter(new HeaderLevelTitleCustomizer() {
                	    @Override
                	    public String getTitle(HeaderLevel headerLevel, Date startDate, Date endDate, String defaultValue, Calendar calendar) {
                	        DateTimeFormat fmt = DateTimeFormat.getFormat("d/M");
                	        return fmt.format(startDate);
                	    }
                	});
                	calendar.setResolution(new HeaderLevel[] {new HeaderLevel(TimeUnit.WEEK), headerLevel}, TimeUnit.DAY, 21, null);
                	
                	return calendar;
                }
                
                public static class TimelineData {
                	private static CalendarEvent[] records;  
                	private static Date today = new Date();  
                	private static int year = today.getYear();  
                	private static int month = today.getMonth();  
                	private static int start = today.getDate();  
                  
                	public TimelineData() {  
                    }
                    
                	public static CalendarEvent[] getRecords() {  
                		if (records == null) {  
                		    records = getNewRecords();  
                		}  
                		return records;
                    }
                    public static CalendarEvent[] getNewRecords() {
                        return new CalendarEvent[]{
                                new CalendarEvent(1, "Test 1", "", new Date(year, month, start), new Date(year, month, start + 6), "charlesMadigen"),  
                                new CalendarEvent(2, "Test 2", "", new Date(year, month, start + 5), new Date(year, month, start + 8), "charlesMadigen"),  
                                new CalendarEvent(3, "Test 3", "", new Date(year, month, start + 6), new Date(year, month, start + 9), "charlesMadigen"),
                                new CalendarEvent(4, "Test 4", "", new Date(year, month, start + 6), new Date(year, month, start + 8), "charlesMadigen")    
                        };  
                    }
                }
                
                public static class TimelineLaneData {  
                	  
                	private static Lane[] records;  
                	
                	public static Lane[] getRecords() {  
                		if (records == null)
                			records = getNewRecords(); 
                		return records;  
                    }
                	
                    public TimelineLaneData() {  
                    }  
                    
                    public static Lane[] getNewRecords() {  
                    	Lane[] lanes = new Lane[]{  
                    			getLane("charlesMadigen", "Charles Madigen", "Managers"),  
                    			getLane("tamaraKane", "Tamara Kane", "Developers"),  
                    			getLane("darcyFeeney", "Darcy Feeney", "Managers")
                    	};  
                    	return lanes;  
                    }  
                      
                    private static Lane getLane(String name, String title, String devGroup) {  
                    	Lane lane = new Lane(name, title);  
                    	lane.setAttribute("devGroup", devGroup);  
                    	return lane;  
                    }
                }
                You can see the overlapping issue in the attached screenshot.
                Attached Files

                Comment


                  #9
                  Any progress on this?

                  Comment


                    #10
                    Sorry for the delay in addressing this - we see the issue and it's being looked into.

                    Comment

                    Working...
                    X