• ListCell Animation in ListView


    After a long time I am back again with new stuffs. I have seen that JavaFX has got so many demand nowadays. Lots of people are requesting for something new something wow effect. In the same way one of my colleagues told me what if we have listview got some effects on scrolling the list. I got some dig around JavaFX Animation API and did some animation with ListCell but I thought it would be great if I share my works to you guys.

    First We got to revamp what is the Listcell. ListCell are designed for making user to display text content in list format. But we can override these and make our own like displaying images,shapes and other controls as well.

    ListCell inherits the character of Labeled so in default ListCell only displays the text content.If you want some control in your listcell other than label then there are some bunch of cellfactory in javafx.scene.control.cell package.

    Every ListCell are being rendered according to the cellFactory implementation so you are free to implement your own cellFactory to make the listcell even more customizable. I had posted about TableCell customization which utilizes use of cellFactory (TableView Cell Modify)

    Lets roll with the ListCell customization.

    ——————————————————————————————————————————————————————

    public class AnimatedListCell<T> extends AbstractAnimatedListCell<T> {
    
        //... other codes ...     
        /**
         * Get cellfactory of AbstractAnimatedListCell for ListView
         *
         * @param type
         * @return
         */
        public static Callback<ListView<String>, ListCell<String>> forListView(final AnimationType... type) {
            return new Callback<ListView<String>, ListCell<String>>() {
                @Override
                public ListCell<String> call(
                        ListView<String> p) {
                    return new AnimatedListCell<>(new DefaultStringConverter(), type);
                }
            };
        }
    
        /**
         * Get cellfactory of AbstractAnimatedListCell for ListView with StringConverter
         *
         * @param <T>
         * @param sc
         * @param type
         * @return
         */
        public static <T extends Object> Callback<ListView<T>, ListCell<T>> forListView(
                final StringConverter<T> sc, final AnimationType... type) {
            return new Callback<ListView<T>, ListCell<T>>() {
                @Override
                public ListCell<T> call(
                        ListView<T> p) {
                    return new AnimatedListCell<>(sc, type);
                }
            };
    
    
        }
    
        /**
         * For getting the KeyFrames of specific AnimationType
         *
         * @param types
         * @return
         */
        @Override
        protected KeyFrame[] getKeyFrames(AnimationType[] types) {
            if (types == null) {
                return null;
            }
            KeyFrame[] frames = null;
            for (AnimationType type : types) {
                switch (type) {
                    case FADE_OUT:
                        frames = anim.getFadeOut(frames);
                        break;
                    case FLAP_RIGHT:
                        frames = anim.getFlapRight(frames);
                        break;
                    case FLATTERN_OUT:
                        frames = anim.getFlatternOut(frames);
                        break;
                    case FLY_FROM_DOWN:
                        frames = anim.getFlyFromDown(frames);
                        break;
                    case FLY_FROM_UP:
                        frames = anim.getFlyFromUp(frames);
                        break;
                    case ROTATE_RIGHT:
                        frames = anim.getRotateYRight(frames);
                        break;
                    case SPEED_LEFT:
                        frames = anim.getSpeedLeft(frames);
                        break;
                    case SPEED_RIGHT:
                        frames = anim.getSpeedRight(frames);
                        break;
                    case TRANSITION_DOWN:
                        frames = anim.getTransitionDown(frames);
                        break;
                    case TRANSITION_LEFT:
                        frames = anim.getTransitionLeft(frames);
                        break;
                    case TRANSITION_RIGHT:
                        frames = anim.getTransitionRight(frames);
                        break;
                    case TRANSITION_TOP:
                        frames = anim.getTransitionTop(frames);
                        break;
                    case ZOOM_IN:
                        frames = anim.getZoomIn(0, frames);
                        break;
                    case POP_OUT:
                        frames = anim.getPopOut(frames);
                        break;
    
                }
            }
            return frames;
    
        }
    
        @Override
        protected void updateItem(T t, boolean bln) {
            //overriding the super interface
            super.updateItem(t, bln);
    
        }
    }

    Above Class is subclass of AbstractAnimatedListCell so you can implement this in your cellFactory. Currently AbstractAnimatedListCell is subclass of ListCell which helps to make the animation possible. Now Lets directly move to the animation implementation.

    /**
     *
     * @author Narayan G. Maharjan <me@ngopal.com.np>
     */
    public class ListViewAnimation extends Application {
        ObservableList list = FXCollections.observableArrayList();
    
        ListView<String> listView;
    
        ComboBox<AnimationType> box;
    
        HBox hbox;
    
        AnchorPane root;
    
        Button btn;
    
        /**
         * For initializing Containers
         */
        public void initContainers() {
            root = new AnchorPane();
            hbox = new HBox(10);
    
            AnchorPane.setBottomAnchor(listView, 50d);
            AnchorPane.setTopAnchor(listView, 10d);
            AnchorPane.setLeftAnchor(listView, 10d);
            AnchorPane.setRightAnchor(listView, 10d);
            AnchorPane.setBottomAnchor(hbox, 10d);
            AnchorPane.setLeftAnchor(hbox, 10d);
        }
    
        /**
         * For initializing controls
         */
        public void initControls() {
            listView = new ListView<>();
            listView.setCellFactory(AnimatedListCell.forListView(AnimationType.ROTATE_RIGHT, AnimationType.FADE_OUT));
    
    
            box = new ComboBox<>();
            box.valueProperty().addListener(new ChangeListener<AnimationType>() {
                @Override
                public void changed(
                        ObservableValue<? extends AnimationType> ov, AnimationType t, AnimationType t1) {
                    if (!t1.equals(t)) {
                        listView.setCellFactory(AnimatedListCell.forListView(t1));
                    }
                }
            });
    
            btn = new Button("Add New");
            btn.setOnAction(new EventHandler<ActionEvent>() {
                @Override
                public void handle(ActionEvent event) {
                    list.add("Added New");
                }
            });
    
    
        }
    
        @Override
        public void start(Stage stage) throws Exception {
            //Loading custom fonts
            Font.loadFont(getClass().getResource("fonts/segoesc.ttf").toExternalForm(), 12);
    
            //adding values to list
            for (int i = 0; i < 10; i++) {
                list.add("" + i);
            }
    
            //Initializing Controls
            initControls();
            initContainers();
    
            //Adding Values
            listView.setItems(list);
            box.getItems().addAll(AnimationType.values());
    
            //Adding controls to container
            hbox.getChildren().addAll(new Label("Animation Type:"), box, btn);
            root.getChildren().addAll(listView, hbox);
    
            Scene scene = new Scene(root);
            scene.getStylesheets().add(getClass().getResource("css/style.css").toExternalForm());
            scene.setCamera(new PerspectiveCamera());
            stage.setTitle("List Animation!");
            stage.setScene(scene);
            stage.show();
    
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    }

    Well after implementing those Animation you can get animation instantly on list cell update . However I have added some few styling to make it even more better.

    If you want to try out yourself . Grab the source code from here:

  • 相关阅读:
    面试之求找两个数和为某个数、几个连续数等于某个数
    oracle 创建字段自增长——两种实现方式汇总
    UnityTestTools測试工具
    现代控制理论课件资料与说明
    教你轻松自己定义ViewPagerIndicator
    【Android】自己定义ListView的Adapter报空指针异常解决方法
    SICP-Exercise 1.5
    网络编程----------SOCKET编程实现简单的TCP协议
    字符串翻转
    机房收费系统重构(六)—泛型集合
  • 原文地址:https://www.cnblogs.com/cuizhf/p/3309253.html
Copyright © 2020-2023  润新知