Adjustable height of window

Have you ever run in situation that your window's height was to large for your screen and you can't see the bottom and top toolbars that cause you can't save the form? Check this out!

Preparation

For this tutorial we will need a simple dummy window, that will have lots of fields, so you will not be able to see the header and bottom buttons. Go and create one, or take mine :)

BXR.window.Large = function(config) {
    config = config || {};
    Ext.applyIf(config,{
        title: 'Very large window'
        ,fields: [{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 1'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 2'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 3'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 4'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 5'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 6'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 7'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 8'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 9'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 10'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 11'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 12'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 13'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 14'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 15'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 16'
        }]
    });
    BXR.window.Large.superclass.constructor.call(this,config);
};
Ext.extend(BXR.window.Large,MODx.Window);
Ext.reg('bxr-window-large',BXR.window.Large);

There is nothing special on this window, just a lots of fields.

Resizing the window after render

Let's say we will want to resize the window when we are showing it. We will create a listener for afterRender event where we will do the resizing. Also we will create a function that will handle the resizing.

Start from the end, we will create the dummy resizing function. Insert this after Ext.extend(BXR.window.Large,MODx.Window

,{
    resizeWindow: function(){
    }
}

And also create the listener. Insert this after fields definition.

,listeners: {
    afterRender: function(){
        this.resizeWindow();
    }
}

This will call our (dummy) function for resizing window after the window is rendered.

Your code should look like this one now

BXR.window.Large = function(config) {
    config = config || {};
    Ext.applyIf(config,{
        title: 'Very large window'
        ,fields: [{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 1'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 2'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 3'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 4'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 5'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 6'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 7'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 8'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 9'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 10'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 11'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 12'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 13'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 14'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 15'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 16'
        }]
        ,listeners: {
            afterRender: function(){
                this.resizeWindow();
            }
        }
    });
    BXR.window.Large.superclass.constructor.call(this,config);
};
Ext.extend(BXR.window.Large,MODx.Window,{
    resizeWindow: function(){
    }
});
Ext.reg('bxr-window-large',BXR.window.Large);

Now when the function for resizing is called when we wanted, we will need to get height of the window and height of the top and bottom bar. Add these lines below config = config || {};

this.originalHeight = null;
this.toolsHeight = null;

And these lines above this.resizeWindow();

this.originalHeight = this.el.getHeight();
this.toolsHeight = this.originalHeight - this.body.getHeight() + 50;

What this piece of code do, is, the we first init some variables and into originalHeight we set the width of window. Into the second variable toolsHeight we will set height of the whole window and subtracts the height of window's body. This height we will increase by 50, to get some space around the window.

Now comes the funny part, we will learn our dummy resizeWindow function some stuff. Add these lines into it.

var viewHeight = Ext.getBody().getViewSize().height;
var el = this.fp.getForm().el;
if(viewHeight < this.originalHeight){
    el.setStyle('overflow-y', 'scroll');
    el.setHeight(viewHeight - this.toolsHeight);
}else{
    el.setStyle('overflow-y', 'auto');
    el.setHeight('auto');
}

So briefly, we set into viewHeight the height of your browser. That we will check if its lower that window height and if its, we will add vertical scroller and set the height of the window's body to viewHeight minus the height of tools. If the window fits the browser's height it will remove scrollbar and set height of window's body to auto adjust.

This should works fine when you open the window, but when you open the window on small screen and then move your browser's window into larger screen, it will not adjust! Fortunately, here is some more :). After BXR.window.Large.superclass.constructor.call(this,config); add this line

Ext.EventManager.onWindowResize(this.resizeWindow, this);

It will bind the resizeWindow function on event that is fired after browser is resized, cool right?

Result

BXR.window.Large = function(config) {
    config = config || {};
    this.originalHeight = null;
    this.toolsHeight = null;
    Ext.applyIf(config,{
        title: 'Very large window'
        ,fields: [{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 1'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 2'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 3'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 4'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 5'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 6'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 7'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 8'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 9'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 10'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 11'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 12'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 13'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 14'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 15'
        },{
            xtype: 'textfield'
            ,fieldLabel: 'Dummy field 16'
        }]
        ,listeners: {
            afterRender: function(){
                this.originalHeight = this.el.getHeight();
                this.toolsHeight = this.originalHeight - this.body.getHeight() + 50;
                this.resizeWindow();
            }
        }
    });
    BXR.window.Large.superclass.constructor.call(this,config);
    Ext.EventManager.onWindowResize(this.resizeWindow, this);
};
Ext.extend(BXR.window.Large,MODx.Window,{
    resizeWindow: function(){
        var viewHeight = Ext.getBody().getViewSize().height;
        var el = this.fp.getForm().el;
        if(viewHeight < this.originalHeight){
            el.setStyle('overflow-y', 'scroll');
            el.setHeight(viewHeight - this.toolsHeight);
        }else{
            el.setStyle('overflow-y', 'auto');
            el.setHeight('auto');
        }
    }
});
Ext.reg('bxr-window-large',BXR.window.Large);
Post By John Peca ExtJS, MODX