0
votes

It seems like a trivial task to do but I'm still unable to accomplish it. I'm building an application with ExtJS 5 and I have a panel with an image component on it. The panel has to resize (shrinkWrap : true) to the original size of the image. The problem is that when the layout manager is calculating the size of the panel, the image isn't yet loaded completely so it's size is 0,0. I tried to add different listeners like afterrender, render, boxready and practically all of the rest but nothing seems to work fo me - the image size is always equals to 0. I also tried to bind the sizes of the two components as you'll see in the code below, but this doesn't worked either. If i configure the boxready event with a delay of 1 second the image size is finally computed and I can call updateLayout() but this is a very unreliable solution because the image is loaded from remote server and I'm unable to predict the exact time of server response. I know that at some point of the application lifecycle the image is loaded and I need to find which event is being fired in order to resize my panel.

Example code

Ext.application({   name   : 'MyApp',

    launch : function() {
        /* 
         * I was hoping that taking the image out of the panel 
         * will 'force' it to be created earlier.
         */
        var img = Ext.create('Ext.Img', {
            src : 'img.jpg',
            reference : 'bgimg',
            publishes : {
                width : true,
                height: true
            }
            listeners : {
                boxready : { fn : 'imgReady', scope : this, delay : 100 }
            }
        });

        Ext.create('Ext.Panel', {
            renderTo : Ext.get('extjs-content'),

            width : 1000,
            height: 700,

            defaults : {
                border : true
            },

            layout : 'border',

            items : [{
                region : 'north',
                height : 80,
            }, {
                region : 'east',
                width : 200,
                collapsible : true
            }, {
                region : 'center',
                autoScroll : true,
                items : [{
                    /*
                     * This is the container of the image. Please note that
                     * I need it to preserve its absolute layout.
                     */
                    id : 'canvas',
                    layout : 'absolute',
                    shrinkWrap : true,
//                  bind : {
//                      width : '{bgimg.width}',
//                      height: '{bgimg.height}'
//                  },
                    items : [img]
                }]
            }]
        });
    },

    /*
     * If I call this with delay of 1000ms the image size is 'ready'
     * otherwise it is 0, 0.
     */
    imgReady : function(img) {
        console.log('Image size: %o', img.getSize());
        Ext.ComponentQuery.query('#canvas')[0].updateLayout();
    }
});
1

1 Answers

2
votes

You can track when the image is loaded with the load event of the img element.

var img = Ext.create('Ext.Img', {
        src : 'img.jpg',
        reference : 'bgimg',
        publishes : {
            width : true,
            height: true
        },
        listeners : {
            load : {
               element : 'el',
               fn : 'imgReady'
            }
        }
    });