독도 광고 모금 캠페인

'Custom ArrayCollection'에 해당되는 글 1건

  1. 2008.10.08 [펌] Flex CookBook - Paged ArrayCollection by 이현호

우리 회사에서는 아예 페이징에 대한 컴포넌트를 만들어서 값을 던질수 있게 했는데 이것도 역시 방법이 되겠네요..

ADN FLEX COOKBOOK에 올라온 내용입니다.

COOKBOOK 가보실려면 여기 로 가보세요.

Paged ArrayCollection

by PeterMolgaard on October 6, 2008 Avg Rating 2.5 (2)   |   Log in to rate post.

Tagged with ActionScript

Problem Summary

ArrayCollection does not support paging

Solution Summary

Adding properties such as "pageSize", "numberOfPages" and "lengthTotal" to the existing ArrayCollection and implementing a filterfunction supporting paging gives a simple pagination addition to the existing ArrayCollection class.

Explanation

Yesterday one of the developers in my company had the need for a PagedArrayCollection. A quick search on Google revealed only this implementation, which turned out to be buggy so I decided to implement one myself.

I designed an interface called IPagedCollection which in combination with an extension of the existing mx.collections.ArrayCollection implementation would do the job.

Only hurdle was the need to override addItemAt and removeItemAt as the autoUpdate doesn’t seem to work when a filterFunction is employed. I will look in to this phenomena, but as for now a call to refresh after inserting or removing does the job nicely.

The code itself is quite simple, I have also created a small demo-application which illustrates the use of the collection.

Live Demo

Download of Sources

**
* Copyright(c) 2008 HelloGroup A/S, some rights reserved.
* Your reuse is governed by the Creative Commons Attribution 3.0 Denmark License
**/
package com.hello.collections
{
    public interface IPagedArrayCollection
    {
        function get currentPage() : Number;
        function set currentPage( value:Number ) : void;
        function get numberOfPages() : Number;
        function get pageSize() : Number;
        function set pageSize( value:Number ) : void;
        function get lengthTotal() : Number;
    }
}

/**
* Copyright(c) 2008 HelloGroup A/S, some rights reserved.
* Your reuse is governed by the Creative Commons Attribution 3.0 Denmark License
*
* Known Issues:
* - When the collection changes in size or pagesize, the currentPage is not updated.
*   This is a problem if currentPage is set to a higher value than in the new collection.
**/
package com.hello.collections
{
    import mx.collections.ArrayCollection;
    import mx.events.CollectionEvent;

    public class PagedArrayCollection extends ArrayCollection implements IPagedArrayCollection
    {
        private var _currentPage:Number = 1;
        private var _numberOfPages:Number = 1;
        private var _pageSize:Number = 10;
        
        public function PagedArrayCollection( source:Array=null )
        {
            super( source );
            filterFunction = filterData;
            addEventListener( CollectionEvent.COLLECTION_CHANGE, onChange );
        }  

        /**
        * Adds an item to the collection at the specified index.
        *
        * @param item Item to be added
        * @param index Index of the item to be added
        *
        * Note: Needs to be overridden in order to trigger refresh.
        *        AddItem eventually calls this function so its not needed to override addItem
        **/
        override public function addItemAt( item:Object, index:int ) : void
        {
            super.addItemAt( item, index );
            refresh();
        }

        /**
        * Removes the item from the collection at the specified index
        *
        * @param index Index of the item to be removed
        * @return The item removed
        *
        * Note: Needs to be overridden in order to trigger refresh
        **/
        override public function removeItemAt( index:int ) : Object
        {
            var removedItem:Object = super.removeItemAt( index );
            refresh();
            return removedItem;
        }

        protected function onChange( event:CollectionEvent ) : void
        {
            if( _numberOfPages != numberOfPages )
            {
                _numberOfPages = numberOfPages;
                onPagingChange( PagedCollectionEventKind.NUMBEROFPAGES_CHANGE );
            }
        }
        
        protected function onPagingChange( kind:String ) : void
        {
            dispatchEvent( new CollectionEvent( CollectionEvent.COLLECTION_CHANGE, false, false, kind ) );
        }  

        [ChangeEvent("collectionChange")]
        public function get currentPage() : Number
        {
            return _currentPage;
        }
        
        public function set currentPage( value:Number ) : void
        {
            _currentPage = value;
            refresh();
            onPagingChange( PagedCollectionEventKind.CURRENTPAGE_CHANGE );
        }

        [ChangeEvent("collectionChange")]
        public function get numberOfPages() : Number
        {
            var result:Number = source.length / pageSize;
            result = Math.ceil( result );
            return result;
        }
        
        [ChangeEvent("collectionChange")]
        public function get pageSize() : Number
        {
            return _pageSize;
        }
        
        public function set pageSize( value:Number ) : void
        {
            _pageSize = value;
            refresh();
            onPagingChange( PagedCollectionEventKind.PAGESIZE_CHANGE );
        }

        [ChangeEvent("collectionChange")]
        public function get lengthTotal() : Number
        {
            return source.length;
        }

        private function filterData( item:Object ) : Boolean
        {
            var dataWindowCeiling:Number = pageSize * currentPage;
            var dataWindowFloor:Number = dataWindowCeiling - pageSize;
            
            var itemIndex:Number = getItemIndex( item );
            var result:Boolean = dataWindowFloor <= itemIndex && itemIndex < dataWindowCeiling;
            
            return result;
        }
    }
}

/**
* Copyright(c) 2008 HelloGroup A/S, some rights reserved.
* Your reuse is governed by the Creative Commons Attribution 3.0 Denmark License
**/
package com.hello.collections
{
    public class PagedCollectionEventKind
    {
        public static const CURRENTPAGE_CHANGE:String = "currentPageChange";
        public static const PAGESIZE_CHANGE:String = "pageSizeChange";
        public static const NUMBEROFPAGES_CHANGE:String = "numberOfPagesChange";
    }
}


This is the small demo-application which illustrates and validates that the collection works.

<?xml version="1.0" encoding="utf-8"?>
<mx:Application
    xmlns:mx="http://www.adobe.com/2006/mxml"
    layout="vertical"
    initialize="onInitialize(event)"
    creationComplete="onCreationComplete(event)">

    <mx:HBox width="100%">
        <mx:Label text="Key:" />
        <mx:TextInput id="keyInput" text="NEW KEY" />
        <mx:Label text="Value:" />
        <mx:TextInput id="valueInput" text="NEW VALUE" />
        <mx:Button id="addButton" label="Add Item" />
        <mx:Button id="removeButton" label="Remove Item" enabled="{ grid.selectedItem != null }" />
        <mx:Label text="Set PageSize:" />
        <mx:ComboBox id="pageSizeSelector" dataProvider="{ [ 5, 10, 25] }" selectedIndex="1" change="{ collection.pageSize = Number( pageSizeSelector.value ) }" />
    </mx:HBox>
    
    <mx:DataGrid id="grid" dataProvider="{ collection }" width="100%" height="100%" />
    
    <mx:HBox>
        <mx:Label text="Count: { collection.length } ({ collection.lengthTotal })" />
        <mx:Label text="( { collection.currentPage }/{ collection.numberOfPages } )" />
        <mx:Label text="PageSize: { collection.pageSize }" />
        <mx:Button label="Previous" enabled="{ collection.currentPage > 1 }" click="{ collection.currentPage-- }" />
        <mx:Button label="Next" enabled="{ collection.numberOfPages > collection.currentPage }" click="{ collection.currentPage++ }" />
    </mx:HBox>  

    <mx:Script>
    <![CDATA[
    
    import mx.events.CollectionEvent;
    import mx.events.FlexEvent;
    import com.hello.collections.PagedArrayCollection;

    [Bindable]
    private var collection:PagedArrayCollection;
    
    private function onInitialize( event:FlexEvent ) : void
    {
        var collection:Array = new Array();
        for( var i:Number = 1; i <= 20; i++ )
        {
            collection.push( { key:"Item_Key_"+ i, value:"Item_Value_"+ i } );
        }
        this.collection = new PagedArrayCollection( collection );
        this.collection.addEventListener( CollectionEvent.COLLECTION_CHANGE, onItemsChange );
        this.collection.refresh();
    }
        
    private function onCreationComplete( event:FlexEvent ) : void
    {
        addButton.addEventListener( MouseEvent.CLICK, addButton_Click );
        removeButton.addEventListener( MouseEvent.CLICK, removeButton_Click );
    }

    private function addButton_Click( event:MouseEvent ) : void
    {
        collection.addItem( { key:keyInput.text, value:valueInput.text } );
    }

    private function removeButton_Click( event:MouseEvent ) : void
    {
        collection.removeItemAt( collection.getItemIndex( grid.selectedItem ) );
    }

    private function onItemsChange( event:CollectionEvent ) : void
    {
        trace( event.kind +" collectionchanged" );
    }

    ]]>
    </mx:Script>
    
</mx:Application>

Posted by 이현호
,