动态更改FLEX中Datagrid列的宽度

发布于 2024-07-24 06:43:33 字数 164 浏览 10 评论 0原文

我们是否可以通过点击列的边框来动态改变datagrid列的宽度,以便显示太长而无法显示且需要滚动的完整字符串? 如果是这样,怎么办?

另外,我们如何确保列宽根据字符数/字符串长度动态变化; 因为很多时候数据太长而无法显示。 在显示到数据网格之前,我们可以设置列宽以考虑数据的长度吗?

Can we change the width of the datagrid column dynamically by clicking on the border of the column in order to display the complete string which is too long to be displayed and needs to be scrolled ? If so, How ?

Also, how can we ensure that the column width changes dynamically based on the number of characters / length of string; since many a times the data is too long to be displayed. Can we set the column width to take the length of data into consideration before displaying onto the datagrid ?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

薄荷→糖丶微凉 2024-07-31 06:43:33

所以我遇到了类似的问题,这就是我发现的。 如果设置:

horizontalScrollPolicy="off"

那么列宽将自动调整大小以适合 DataGrid 的宽度。 您还可以手动设置列宽,只要将滚动设置为打开或关闭并且不设置为自动即可。 我发现了一篇关于此的有趣文章, http://junleashed .wordpress.com/2008/07/10/flex-datagridcolumn-width-management/。 基本上,他手动管理列宽,然后计算滚动条是否应该打开或关闭。

So I was having a similar problem and here is what I found. If you set:

horizontalScrollPolicy="off"

Then the column widths will size automatically to fit the width of the DataGrid. You can also manually set the column widths, as long as scrolling is set to either on or off and not set to auto. I found an interesting article about this, http://junleashed.wordpress.com/2008/07/10/flex-datagridcolumn-width-management/. Basically, he manages the column widths manually, and then calculates whether the scrollbar should be on or off.

沒落の蓅哖 2024-07-31 06:43:33

这是我想到的,但对于大型数据提供商来说可能效率不高:

<?xml version="1.0" encoding="utf-8"?>
<mx:WindowedApplication xmlns:mx="http://www.adobe.com/2006/mxml"
    creationComplete="onComplete();">

    <mx:Script>
        <![CDATA[
            // imports:
            import mx.events.FlexEvent;
            import mx.core.UIComponent;
            import mx.controls.dataGridClasses.DataGridColumn;
            import mx.controls.Text;
            import mx.utils.ObjectUtil;
            import mx.controls.Label;
            import mx.collections.ArrayCollection;
            // data provider:
            [Bindable] private var dp:ArrayCollection = new ArrayCollection();

            private function onComplete():void {
                // populate data provider here
                // to avoid calcMaxLengths execution when the app is created:
                dp = new ArrayCollection(
                    [
                        { col1: "Short", col2: "Other column 1" },
                        { col1: "Some long string", col2: "Other column 2" },
                        { col1: "Short", col2: "Other column 3" },
                        { col1: "Short", col2: "Other column 4" },
                        { col1: "The longest value in this column", col2: "Other column 5" },
                        { col1: "Short", col2: "Other column 6" },
                        { col1: "Short", col2: "Other column 7" }
                    ]
                );
            }

            // this is going to be executed whenever the data provider changes:
            [Bindable("dataChange")]
            private function calcMaxLengths(input:ArrayCollection):ArrayCollection {
                // if there are items in the DP:
                if ( input.length > 0 ) {
                    // and no SPECIAL child exists:
                    if ( getChildByName("$someTempUICToRemoveAfterFinished") == null ) {
                        // create new SPECIAL child
                        // this is required to call measureText
                        // if you use custom data grid item renderer
                        // then create instance of it instead of UIComponent:
                        var uic:UIComponent = new UIComponent();
                        // do not show and do not mess with the sizes:
                        uic.includeInLayout = false;
                        uic.visible = false;
                        // name it to leverage get getChildByName method:
                        uic.name = "$someTempUICToRemoveAfterFinished";
                        // add event listener:
                        uic.addEventListener(FlexEvent.CREATION_COMPLETE, onTempUICCreated);
                        // add to parent:
                        addChild(uic);
                    }
                }
                // return an input:
                return input;
            }

            // called when SPECIAL child is created:
            private function onTempUICCreated(event:FlexEvent):void {
                // keep the ref to the SPECIAL child:
                var renderer:UIComponent = UIComponent(event.target);
                // output - this will contain max size for each column:
                var maxLengths:Object = {};
                // temp variables:
                var key:String = "";
                var i:int=0;
                // for each item in the DP:
                for ( i=0; i<dp.length; i++ ) {
                    var o:Object = dp.getItemAt(i);
                    // for each key in the DP row:
                    for ( key in o ) {
                        // if the output doesn't have current key yet create it and set to 0:
                        if ( !maxLengths.hasOwnProperty(key) ) {
                            maxLengths[key] = 0;
                        }
                        // check if it's simple object (may cause unexpected issues for Boolean):
                        if ( ObjectUtil.isSimple(o[key]) ) {
                            // measure the text:
                            var cellMetrics:TextLineMetrics = renderer.measureText(o[key]+"");
                            // and if the width is greater than longest found up to now:
                            if ( cellMetrics.width > maxLengths[key] ) {
                                // set it as the longest one:
                                maxLengths[key] = cellMetrics.width;
                            }
                        }
                    }
                }

                // apply column sizes:
                for ( key in maxLengths ) {
                    for ( i=0; i<dg.columnCount; i++ ) {
                        // if the column actually exists:
                        if ( DataGridColumn(dg.columns[i]).dataField == key ) {
                            // set size + some constant margin
                            DataGridColumn(dg.columns[i]).width = Number(maxLengths[key]) + 12;
                        }
                    }
                }
                // cleanup:
                removeChild(getChildByName("$someTempUICToRemoveAfterFinished"));
            }

        ]]>
    </mx:Script>

    <mx:DataGrid id="dg" horizontalScrollPolicy="on" dataProvider="{calcMaxLengths(dp)}" width="400">
        <mx:columns>
            <mx:DataGridColumn dataField="col1" width="40" />
            <mx:DataGridColumn dataField="col2" width="100" />
        </mx:columns>
    </mx:DataGrid>

</mx:WindowedApplication>

This is what I came up with however it may not be efficient for large data providers:

<?xml version="1.0" encoding="utf-8"?>
<mx:WindowedApplication xmlns:mx="http://www.adobe.com/2006/mxml"
    creationComplete="onComplete();">

    <mx:Script>
        <![CDATA[
            // imports:
            import mx.events.FlexEvent;
            import mx.core.UIComponent;
            import mx.controls.dataGridClasses.DataGridColumn;
            import mx.controls.Text;
            import mx.utils.ObjectUtil;
            import mx.controls.Label;
            import mx.collections.ArrayCollection;
            // data provider:
            [Bindable] private var dp:ArrayCollection = new ArrayCollection();

            private function onComplete():void {
                // populate data provider here
                // to avoid calcMaxLengths execution when the app is created:
                dp = new ArrayCollection(
                    [
                        { col1: "Short", col2: "Other column 1" },
                        { col1: "Some long string", col2: "Other column 2" },
                        { col1: "Short", col2: "Other column 3" },
                        { col1: "Short", col2: "Other column 4" },
                        { col1: "The longest value in this column", col2: "Other column 5" },
                        { col1: "Short", col2: "Other column 6" },
                        { col1: "Short", col2: "Other column 7" }
                    ]
                );
            }

            // this is going to be executed whenever the data provider changes:
            [Bindable("dataChange")]
            private function calcMaxLengths(input:ArrayCollection):ArrayCollection {
                // if there are items in the DP:
                if ( input.length > 0 ) {
                    // and no SPECIAL child exists:
                    if ( getChildByName("$someTempUICToRemoveAfterFinished") == null ) {
                        // create new SPECIAL child
                        // this is required to call measureText
                        // if you use custom data grid item renderer
                        // then create instance of it instead of UIComponent:
                        var uic:UIComponent = new UIComponent();
                        // do not show and do not mess with the sizes:
                        uic.includeInLayout = false;
                        uic.visible = false;
                        // name it to leverage get getChildByName method:
                        uic.name = "$someTempUICToRemoveAfterFinished";
                        // add event listener:
                        uic.addEventListener(FlexEvent.CREATION_COMPLETE, onTempUICCreated);
                        // add to parent:
                        addChild(uic);
                    }
                }
                // return an input:
                return input;
            }

            // called when SPECIAL child is created:
            private function onTempUICCreated(event:FlexEvent):void {
                // keep the ref to the SPECIAL child:
                var renderer:UIComponent = UIComponent(event.target);
                // output - this will contain max size for each column:
                var maxLengths:Object = {};
                // temp variables:
                var key:String = "";
                var i:int=0;
                // for each item in the DP:
                for ( i=0; i<dp.length; i++ ) {
                    var o:Object = dp.getItemAt(i);
                    // for each key in the DP row:
                    for ( key in o ) {
                        // if the output doesn't have current key yet create it and set to 0:
                        if ( !maxLengths.hasOwnProperty(key) ) {
                            maxLengths[key] = 0;
                        }
                        // check if it's simple object (may cause unexpected issues for Boolean):
                        if ( ObjectUtil.isSimple(o[key]) ) {
                            // measure the text:
                            var cellMetrics:TextLineMetrics = renderer.measureText(o[key]+"");
                            // and if the width is greater than longest found up to now:
                            if ( cellMetrics.width > maxLengths[key] ) {
                                // set it as the longest one:
                                maxLengths[key] = cellMetrics.width;
                            }
                        }
                    }
                }

                // apply column sizes:
                for ( key in maxLengths ) {
                    for ( i=0; i<dg.columnCount; i++ ) {
                        // if the column actually exists:
                        if ( DataGridColumn(dg.columns[i]).dataField == key ) {
                            // set size + some constant margin
                            DataGridColumn(dg.columns[i]).width = Number(maxLengths[key]) + 12;
                        }
                    }
                }
                // cleanup:
                removeChild(getChildByName("$someTempUICToRemoveAfterFinished"));
            }

        ]]>
    </mx:Script>

    <mx:DataGrid id="dg" horizontalScrollPolicy="on" dataProvider="{calcMaxLengths(dp)}" width="400">
        <mx:columns>
            <mx:DataGridColumn dataField="col1" width="40" />
            <mx:DataGridColumn dataField="col2" width="100" />
        </mx:columns>
    </mx:DataGrid>

</mx:WindowedApplication>
缘字诀 2024-07-31 06:43:33

我最近遇到了同样的问题,我发现的唯一解决方案是使用自定义函数来优化 DataGrid 的列宽度,如建议的 此处

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml">
<mx:Script>
<![CDATA[
import mx.core.UITextField;
import mx.controls.dataGridClasses.DataGridItemRenderer;

public function optimiseGridColumns(dg:DataGrid):void {
                        var dgCol:DataGridColumn;
                        var renderer:UITextField;
                        var tf:TextFormat;
                        var col:int;

                        if (dg.columnCount > 0 && dg.dataProvider != null) {
                        // initialize widths array
                               var widths:Array = new Array (dg.columnCount);
                                for (col = 0; col < widths.length; ++col) {
                                        widths[col] = -1;
                                }

                        // go through each data item in the grid, estimate
                        // the width of the text in pixels
                                for each (var item:Object in dg.dataProvider) {
                                        for (col = 0; col < widths.length; ++col) {
                                                renderer = new DataGridItemRenderer();
                                                // Must add to datagrid as child so that it inherits
                                                // properties essential for text width estimation,
                                                // such as font size
                                                dg.addChild(renderer);

                                                dgCol = dg.columns[col] as DataGridColumn;
                                                renderer.text = dgCol.itemToLabel(item);
                                                widths[col] = Math.max(renderer.measuredWidth + 10,widths[col]);

                                                // remove renderer from datagrid when we're done
                                                dg.removeChild(renderer);
                                        }
                                }

                                // go through headers in the grid, estimate the width of
                                // the text in pixels, assuming the text is bold
                                for (col = 0; col < widths.length; ++col) {
                                        // it's ok to reuse renderer, but I chose not
                                        // to for safety reasons. Optimize if needed.
                                        renderer = new DataGridItemRenderer();

                                        // Must add to datagrid as child so that it inherits
                                        // properties essential for text width estimation,
                                        // such as font size
                                        dg.addChild(renderer);

                                        dgCol = dg.columns[col] as DataGridColumn;
                                        renderer.text = dgCol.headerText;

                                        tf = renderer.getTextFormat();
                                        tf.bold = true;
                                        renderer.setTextFormat (tf);

                                        widths[col] = Math.max(renderer.measuredWidth + 25, widths[col]);

                                        // remove renderer from datagrid when we're done
                                        dg.removeChild(renderer);
                                }

                                // set width of columns to determined values
                                for (col = 0; col < widths.length; ++col)
                                {
                                        if (widths[col] != -1)
                                        {
                                                dg.columns[col].width = widths[col];
                                        }
                                }
                        }
                } 

]]>
</mx:Script>
    <mx:XMLList id="employees">
        <employee>
            <name>Christina Coenraets</name>
            <phone>555-219-2270</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
        <employee>
            <name>Joanne Wall</name>
            <phone>555-219-2012</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
        <employee>
            <name>Maurice Smith</name>
            <phone>555-219-2012</phone>
            <email>[email protected]</email>
            <active>false</active>
        </employee>
        <employee>
            <name>Mary Jones</name>
            <phone>555-219-2000</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
    </mx:XMLList>
        <mx:DataGrid id="dg1" width="100%" height="100%" rowCount="5" dataProvider="{employees}" creationComplete="optimiseGridColumns(dg1)">
            <mx:columns>
                <mx:DataGridColumn dataField="name" headerText="Name"/>
                <mx:DataGridColumn dataField="phone" headerText="Phone"/>
                <mx:DataGridColumn dataField="email" headerText="Email"/>
            </mx:columns>
        </mx:DataGrid>

</mx:Application>

I recently encountered that same issue and the only solution I found is to use a customized function that optimizes the DataGrid's columns width as suggested here:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml">
<mx:Script>
<![CDATA[
import mx.core.UITextField;
import mx.controls.dataGridClasses.DataGridItemRenderer;

public function optimiseGridColumns(dg:DataGrid):void {
                        var dgCol:DataGridColumn;
                        var renderer:UITextField;
                        var tf:TextFormat;
                        var col:int;

                        if (dg.columnCount > 0 && dg.dataProvider != null) {
                        // initialize widths array
                               var widths:Array = new Array (dg.columnCount);
                                for (col = 0; col < widths.length; ++col) {
                                        widths[col] = -1;
                                }

                        // go through each data item in the grid, estimate
                        // the width of the text in pixels
                                for each (var item:Object in dg.dataProvider) {
                                        for (col = 0; col < widths.length; ++col) {
                                                renderer = new DataGridItemRenderer();
                                                // Must add to datagrid as child so that it inherits
                                                // properties essential for text width estimation,
                                                // such as font size
                                                dg.addChild(renderer);

                                                dgCol = dg.columns[col] as DataGridColumn;
                                                renderer.text = dgCol.itemToLabel(item);
                                                widths[col] = Math.max(renderer.measuredWidth + 10,widths[col]);

                                                // remove renderer from datagrid when we're done
                                                dg.removeChild(renderer);
                                        }
                                }

                                // go through headers in the grid, estimate the width of
                                // the text in pixels, assuming the text is bold
                                for (col = 0; col < widths.length; ++col) {
                                        // it's ok to reuse renderer, but I chose not
                                        // to for safety reasons. Optimize if needed.
                                        renderer = new DataGridItemRenderer();

                                        // Must add to datagrid as child so that it inherits
                                        // properties essential for text width estimation,
                                        // such as font size
                                        dg.addChild(renderer);

                                        dgCol = dg.columns[col] as DataGridColumn;
                                        renderer.text = dgCol.headerText;

                                        tf = renderer.getTextFormat();
                                        tf.bold = true;
                                        renderer.setTextFormat (tf);

                                        widths[col] = Math.max(renderer.measuredWidth + 25, widths[col]);

                                        // remove renderer from datagrid when we're done
                                        dg.removeChild(renderer);
                                }

                                // set width of columns to determined values
                                for (col = 0; col < widths.length; ++col)
                                {
                                        if (widths[col] != -1)
                                        {
                                                dg.columns[col].width = widths[col];
                                        }
                                }
                        }
                } 

]]>
</mx:Script>
    <mx:XMLList id="employees">
        <employee>
            <name>Christina Coenraets</name>
            <phone>555-219-2270</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
        <employee>
            <name>Joanne Wall</name>
            <phone>555-219-2012</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
        <employee>
            <name>Maurice Smith</name>
            <phone>555-219-2012</phone>
            <email>[email protected]</email>
            <active>false</active>
        </employee>
        <employee>
            <name>Mary Jones</name>
            <phone>555-219-2000</phone>
            <email>[email protected]</email>
            <active>true</active>
        </employee>
    </mx:XMLList>
        <mx:DataGrid id="dg1" width="100%" height="100%" rowCount="5" dataProvider="{employees}" creationComplete="optimiseGridColumns(dg1)">
            <mx:columns>
                <mx:DataGridColumn dataField="name" headerText="Name"/>
                <mx:DataGridColumn dataField="phone" headerText="Phone"/>
                <mx:DataGridColumn dataField="email" headerText="Email"/>
            </mx:columns>
        </mx:DataGrid>

</mx:Application>
凹づ凸ル 2024-07-31 06:43:33

对于 Gridview 控件,您可以深入查看 SelectedRowStyle 属性并将 Wrap 设置为 True。

For the Gridview control, you can drill-down into the SelectedRowStyle property and set Wrap to True.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文