This is a migrated thread and some comments may be shown as answers.

RadSplitter tracking size changes of the browser window

8 Answers 326 Views
Splitter
This is a migrated thread and some comments may be shown as answers.
tmlipinski
Top achievements
Rank 1
tmlipinski asked on 13 Aug 2009, 01:53 PM
Hi,
My goal is to design such a functionality:
- there is a RadSplitter on the form filling almost 100% of the window
- I don't want to fill exactly 100% using radSplitter.Height = 100% - I want to have some margin outside the RadSplitter and I don't want to set body's margin to 0
- resizing the browser's window should force proper resizing of the RadSplitter
The idea of the solution is:
- RadSplitter.Width = 100%
- RadSplitter.Height is calculated - initially in Page_Load
- window size changes are caught by body.onresize event and sent to the codebehind via Ajax Request where the RadSplitter's height is recalculated
It's not important how the height is calculated; it works and it is not a problem.
I'm not sure if it is the easiest and most effective but it works - as long as we talk about the height.

The problem is that the RadSplitter's width doesn't want to be 100% after Ajax Request: it just remains unchanged; precisely: gets 100% and then - back to the previous width. When Ajax Request is switched off - width behaves as expected: it is 100% all the time.

Well, I've done some other experiment: I've replaced RadSplitter with a pure "div". And this pure div works as expected - tracks al the window size changes perfectly.
So, what can be the problem with the RadSplitter? I can prepare a simple project on demand..

Regards
Tomasz

8 Answers, 1 is accepted

Sort by
0
Tsvetie
Telerik team
answered on 14 Aug 2009, 08:58 AM
Hi Tomasz,
I noticed that you are using an old version of the Telerik.Web.UI assembly and I think we had such a problem in one of our previous versions. Could you please download our latest internal build from your Client.Net account and test your page against it? In case you continue to have problems, it would be best if you could open a new support ticket and send us a working project that demonstrates them.

Sincerely yours,
Tsvetie
the Telerik team

Instantly find answers to your questions on the new Telerik Support Portal.
Check out the tips for optimizing your support resource searches.
0
tmlipinski
Top achievements
Rank 1
answered on 14 Aug 2009, 01:45 PM
Hi,
I'm using 2009.2.701.20 version of Telerik.Web.UI.
I've just fixed the problem. The reason is my too little knowledge of RadSplitter's principles ;-) As I understand now, when a splitter is verical (as in my example):
- all its panes are adjusted vertically to the splitters height
- splitter's width is adjusted to the total width of all panes
So, in my case I must change the splitter's height (as I've been doing) and the panes' total width (for example adjust the width of the rightmost pane). I've corrected my example and it works fine (i.e. as expected :-) )
In a horizontal splitter case, the width of the splitter and the height of one of panes should be adjusted.

I'm sorry for making mess here :-(

Regards
Tomasz
0
Waleed Seada
Top achievements
Rank 2
answered on 25 Nov 2009, 07:07 AM
Hello Tomasz ,

Can you help me add the same functionality to my spliter as well.

I need to make the splitter almost 100% of the IE ... How to ...

Thanks in advance.
Waleed
0
Waleed Seada
Top achievements
Rank 2
answered on 25 Nov 2009, 07:54 AM
0
tmlipinski
Top achievements
Rank 1
answered on 25 Nov 2009, 09:08 AM
Hi,

The solution, you have found , requires the splitter to be 100% of the window - in both directions. It is not always possible. The principles of my solution are:
- the splitter has absolute sizes (in pixels)
- its initial sizes are calculated server side assuming the window has some arbitrary sizes
- just after page load, the splitter sizes are changed (client side) as if the window were resized form these assumed sizes to the real, current sizes
- since then, the splitter tracks sizes of the window using the onresize event

I can put the detailed code here but earlier than on Friday.

Best regards
Tomasz
0
Waleed Seada
Top achievements
Rank 2
answered on 25 Nov 2009, 11:06 AM
Hi Tomasz ,

Yes of course, will be of great help indeed.

thanks in advance
Waleed
0
tmlipinski
Top achievements
Rank 1
answered on 28 Nov 2009, 06:39 PM
Hi,
Here is the promised chunk of the code.
The markup is trivial - a horizontal splitter with two panes:
  <telerik:RadScriptManager ID="RadScriptManager1" runat="server">  
  </telerik:RadScriptManager> 
  <telerik:RadSplitter ID="splitterMain" runat="server" Orientation="Horizontal" Skin="Simple" 
    BorderSize="0">  
    <telerik:RadPane ID="paneUpper" runat="server" Skin="Simple" BackColor="Beige">  
    </telerik:RadPane> 
    <telerik:RadPane runat="server" ID="paneLower" Height="100px" Skin="Simple" BackColor="LightCoral">  
    </telerik:RadPane> 
  </telerik:RadSplitter> 
 
The body is set as follows:
<body style="margin: 3px; background-color: Lime;"
First, at the server side, we set the initial sizes (assuming that the window is of some arbitrary sizes):
    protected void Page_Load(object sender, EventArgs e)  
    {  
      // body margins; must be manually declared  
      int gapy = 6;  
      int gapx = 6;  
      // initial window sizes  
      int initialWidth = 800;  
      int initialHeight = 500;  
 
      int height = initialHeight - gapy;  
      int width = initialWidth - gapx;  
      // at the server side, setting the splitter's width forces adjusting the width of all panes ....  
      splitterMain.Width = new Unit(width, UnitType.Pixel);  
      // ... and setting the pane's height forces adjusting the splitter's height  
      paneUpper.Height = new Unit(height - paneLower.Height.Value, UnitType.Pixel);  
      // this is for the Horizontal orientation of the splitter; for the Vertical orientation,   
      // widths and heights must be inverted (i.e. we must set the splitter's height and pane's width)  
    }  
 
And at the client side there is some JavaScript code, that does the following:
  • at the page_load event adjust these calculated sizes to fit the real, current window sizes
  • react to the window.onresize event tracking changes of window sizes

The code is:

  <telerik:RadCodeBlock ID="codeBlock1" runat="server">  
    <script type="text/javascript">  
      // initial "sizes" of the window; must be the same as in the code-behind  
      var initialWidth = 800;  
      var initialHeight = 500;  
      var before;             // previous window sizes; see checkSize()  
      var inResize = false;   // whether currently inside the onresize handler  
 
      // the core function - window.onresize handler  
      function onresizeHandler() {  
        if (inResize == false) {  
          inResize = true;  
          for (i = 0; i < 2; i++) {  // the loop is just in case
            // get current window size  
            var after = checkSize();  
            if (before.height != after.height || before.width != after.width) {  // do anything when sizes are different
              var deltaW = after.width - before.width;  
              var deltaH = after.height - before.height;  
              var splitter = $find("<%= splitterMain.ClientID %>");  
              if (splitter) {  
                var paneUpper = splitter.getPaneById("<%= paneUpper.ClientID %>");  
                var paneLower = splitter.getPaneById("<%= paneLower.ClientID %>");  
                // at the client side sizes of both: splitter and its panes must be calculated - by contrast to the server side  
                if (deltaW != 0) {  
                  paneUpper.set_width(paneUpper.get_width() + deltaW);  
                  paneLower.set_width(paneUpper.get_width());  
                  splitter.set_width(paneUpper.get_width());  
                }  
                if (deltaH != 0) {  
                  paneUpper.setVarSize(paneUpper.getVarSize() + deltaH);  
                  splitter.set_height(splitter.get_height() + deltaH);  
                }  
                before = after;  
              }  
            }  
            else 
              break;  
          }  
          inResize = false;  
        }  
      }  
 
      // the main trick: this function is called in the page_load event handler and forces resizing from  
      // artificial, dummy sizes (initial*) to the current ones  
      function initialResize() {  
        before = new Object();  
        before.width = initialWidth;  
        before.height = initialHeight;  
        onresizeHandler();  
 
        // set the event handler  
        window.onresize = onresizeHandler;  
      }  
 
      // get the current widnow sizes; the first part is taken directly from:  
      // http://www.howtocreate.co.uk/tutorials/javascript/browserwindow  
      // then goes my addition: in the case of Opera browser the window height must be slightly diminished; it is  
      // experimentally adjusted for 800x600 and 1024x768 screens; for other resolutions it must be supplemented  
      // the result is returned as an object with two properties: width and height  
      function checkSize() {  
        // rozmiary wg algorytmu z sieci  
        var myWidth = 0, myHeight = 0;  
        if (typeof (window.innerWidth) == 'number') {  
          //Non-IE  
          myWidth = window.innerWidth;  
          myHeight = window.innerHeight;  
        }  
        else if (document.documentElement &&  
                 (document.documentElement.clientWidth ||  
                  document.documentElement.clientHeight)) {  
          //IE 6+ in 'standards compliant mode'  
          myWidth = document.documentElement.clientWidth;  
          myHeight = document.documentElement.clientHeight;  
        }  
        else if (document.body &&   
                 (document.body.clientWidth ||   
                  document.body.clientHeight)) {  
          //IE 4 compatible  
          myWidth = document.body.clientWidth;  
          myHeight = document.body.clientHeight;  
        }  
 
        // Opera browser case  
        var gap = 0;  
        if (navigator.appName == "Opera") {  
          switch (screen.height) {  
            case 600:  
              gap = 20;  
              break;  
            case 768:  
              gap = 14;  
              break;  
          }  
        }  
        myHeight -= gap;  
 
        var retVal = new Object();  
        retVal.width = myWidth;  
        retVal.height = myHeight;  
        return retVal;  
      }  
 
      // given a size in pixels and a delta (+/-) of the size makes a new size in pixels:  
      // '100px' + 20 = '120px'  
      function incrementSize(pSize, pDelta) {  
        var numSize = parseFloat(pSize.substring(0, pSize.length - 2));  
        if (numSize + pDelta > 0)  
          numSize += pDelta;  
        return numSize + "px";  
      }  
 
      // initialResize function is added to the page_load handler to force  
      // calling this function just after the page is loaded  
      Sys.Application.add_load(initialResize);  
    </script>  
  </telerik:RadCodeBlock> 
Try it! It's been tested under IE7, FF 3.0.5, Chrome 3.0, Opera 9.64 and Safari 4.0.4.
Some additional notes:
  • I use RadControls Q3 2009; it is important because RadSplitter Q2 2009 behaves at the client side a little bit differently: you don't need set the pane's width and the splitter's height - exactly as at the server side
  • imagine, that you have an iframe tag on the paneUpper panel and want to use the same mechanism to adjust the content of the page placed on it; under FF, Chrome, Opera and Safari you can do it without any changes; but under IE, the window placed on an iframe doesn't fire window.resize event when changing its height :-(; because of that, you cannot hook onresizehandler to the window.onresize but must call this function directly from the onresize handler of the hosting page

Uff, the post has became quite long. I hope it's clear enough. If not - ask me questions.

Good luck :-)
Regards
Tomasz

0
tmlipinski
Top achievements
Rank 1
answered on 29 Nov 2009, 04:13 PM

Post scriptum: at the client side, the splitter's width should be set in a more general way:
     splitter.set_width(splitter.get_width() + deltaW);  

Regards

Tomasz

Tags
Splitter
Asked by
tmlipinski
Top achievements
Rank 1
Answers by
Tsvetie
Telerik team
tmlipinski
Top achievements
Rank 1
Waleed Seada
Top achievements
Rank 2
Share this question
or