Announcement

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

    SectionItem expand/collapse scrolls to the top of the view

    I have a dynamic form with many SectionItems in a layout with overflow set to auto. If I scroll to one of the lower sections and I do an expand or collapse, my view jumps to the top of the view.This is very annoying for the user.

    How can I prevent this?

    Here is my code:
    Code:
    isc.VLayout.create({
    	width: 320,
    	height: 150,
    	overflow:"auto",
    	members: [
    		isc.DynamicForm.create({
    		    width: 300,
    		    fields: [
    		        { defaultValue:"Item", type:"section", sectionExpanded:true,
    		        	selectOnFocus :true,
    		            itemIds: ["itemName", "description", "price"] 
    		        },
    		        { name:"itemName", type:"text", title:"Item"},
    		        { name:"description", type:"textArea", title:"Description"},
    		        { name:"price", type:"float", title:"Price", defaultValue:"low"},
    		        
    		        { defaultValue:"Stock", type:"section", sectionExpanded:false,
    		            itemIds: ["inStock", "nextShipment"]
    		        },
    		        { name:"inStock", type:"checkbox", title:"In Stock" },
    		        { name:"nextShipment", type:"date", title:"Next Shipment", useTextField:true},
    		        
    		        { defaultValue:"Stock2", type:"section", sectionExpanded:false,
    		            itemIds: ["inStock2", "nextShipment2"]
    		        },
    		        { name:"inStock2", type:"checkbox", title:"In Stock" },
    		        { name:"nextShipment2", type:"date", title:"Next Shipment", useTextField:true}
    		    ]
    		})
    ]})
    SmartClient 8.0

    #2
    Hi Zeratus,
    I noticed the same thing, imo this should be solved by Smartclient in the standard, but it isn't, so therefore I solved it myself.

    Below is some code which after expanding sets the focus to the first item in the section and also scrolls the form to the top of the sectionitem. Hope it helps.

    Code:
      
      collapseSection: function() {
        // when collapsing set the focus to the header
        this.updateAlwaysTakeSpace(false);
        this.form.setFocusItem(this);
        var ret = this.Super('collapseSection', arguments);
        return ret;
      },
      
      expandSection: function() {
        this.updateAlwaysTakeSpace(true);
    
        if (this.form.getFocusItem()) {
          this.form.getFocusItem().blurItem();
        }
    
        var ret = this.Super('expandSection', arguments);
        
        if (!this.form._preventFocusChanges) {
          // when expanding set the focus to the first focusable item     
          // set focus late to give the section time to draw and let
          // other items to loose focus/redraw
          this.delayCall('setNewFocusItemExpanding', [], 100);
          
          // NOTE: if the layout structure changes then this needs to be 
          // changed probably to see where the scrollbar is to scroll
          // the parentElement is not set initially when drawing
          if (this.form.parentElement) {
            // scroll after things have been expanded
            this.form.parentElement.delayCall('scrollTo', [null, this.getTop()], 100);    
          }
        }
    
        return ret;
      },
    
      setNewFocusItemExpanding: function(){
        var newFocusItem = null, i;
        for (i = 0; i < this.itemIds.length; i++) {
          var itemName = this.itemIds[i], item = this.form.getItem(itemName);
          // isFocusable is a method added in ob-smartclient.js
          if (item.isFocusable()) {
            newFocusItem = item;
            break;
          }
        }
        if (!newFocusItem && this.handleFocus && this.handleFocus()) {
          return;
        } else if (!newFocusItem) {
          this.focusInItem();
        } else {
          newFocusItem.focusInItem();
        }
      },

    Comment


      #3
      Hello Martin,
      Thank you for your solution. I found it very usefull, the code was clear and commented.

      In SmartClient 8.0 there are a few methods which have changed or dissapeared. Like "updateAlwaysTakeSpace" - this I couldn't find it in documentation, "setFocusItem" became "focusInItem", "isFocusable" became "canFocus". I hope this will help other people who will use this code.

      Unfortunetally, i couldn't make collapseSection to work. But! Starting from your code, here is my solution:

      Code:
      collapseSection: function() {
                  		if (this.form.parentElement) {
                  			var pos = this.form.parentElement.getScrollTop();
                  	       	        this.form.parentElement.delayCall('scrollTo', [null, pos], 100);    
                  		}
                  	    var ret = this.Super('collapseSection', arguments);
                  	    return ret;
                  	 },
      
                  	 expandSection: function() {
                  		 if (this.form.parentElement) {
                  			 var pos = this.form.parentElement.getScrollTop();
                                       //or var pos = this.getTop()
                  			 this.form.parentElement.delayCall('scrollTo', [null, pos], 100);    
                  		 }
                  		 var ret = this.Super('expandSection', arguments);
                  		 return ret;
                  	 },
      This would keep the scrollbar to the same position. What do you think?
      This solution produces some flickering in FF4.0. In Chrome or IE9 everything is smooth.

      Comment


        #4
        Hi All,
        Just a quick notification to let you know that we've added some code to the framework which should avoid this scroll-jumping behavior on expanding/collapsing SectionItems in DynamicForms. This change will be present in the next nightly build (and in the next public release, coming very soon).

        Isomorphic Software

        Comment


          #5
          Thank you Isomorphic.
          I forgot to add in my previous posts that besides the collpase/expand of a section there is also the Date type of field that triggers the scroll-jumping behavior. Setting the date in the calendar for the first time makes the scrollbar to jump. This happens only when the date is set for the first time.

          And this the code that I'm using in order to avoid this issue:
          Code:
          { name:"myfield", 
          rejectInvalidValueOnChange:true,
          validateOnChange:true, 
          useTextField:true, 
          enforceDate:true, 
          type:"date", 
          width:90,
          [b]
          changed: function(){
                  var pos = this.form.parentElement.getScrollTop();
             	this.form.parentElement.delayCall('scrollTo', [null, pos], 10);
                  }
          [/b]
          }
          Also, I hope you review your position regarding the white space at the bottom of live grids with expanding rows. It's hard for me to check the code because of the obfuscation/minimisation, but it is hard to believe that the white space is needed (as you said).

          Cheers

          Comment

          Working...
          X