Package eu.hansolo.enzo.experimental.pushbutton.skin

Source Code of eu.hansolo.enzo.experimental.pushbutton.skin.PushButtonSkin

/*
* Copyright (c) 2013 by Gerrit Grunwald
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package eu.hansolo.enzo.experimental.pushbutton.skin;

import eu.hansolo.enzo.experimental.pushbutton.PushButton;
import javafx.collections.ListChangeListener;
import javafx.scene.control.Skin;
import javafx.scene.control.SkinBase;
import javafx.scene.effect.BlurType;
import javafx.scene.effect.DropShadow;
import javafx.scene.effect.InnerShadow;
import javafx.scene.layout.Background;
import javafx.scene.layout.BackgroundFill;
import javafx.scene.layout.Pane;
import javafx.scene.layout.Region;
import javafx.scene.paint.Color;


public class PushButtonSkin extends SkinBase<PushButton> implements Skin<PushButton> {
    private static final double MINIMUM_WIDTH    = 5;
    private static final double MINIMUM_HEIGHT   = 5;
    private static final double MAXIMUM_WIDTH    = 1024;
    private static final double MAXIMUM_HEIGHT   = 1024;
    private static final double PREFERRED_WIDTH  = 128;
    private static final double PREFERRED_HEIGHT = 128;
    private double              aspectRatio;
    private double              size;
    private double              width;
    private double              height;
    private Pane                pane;

    private Region              frame;
    private InnerShadow         frameInnerShadow0;
    private InnerShadow         frameInnerShadow1;

    private Region              deselected;
    private InnerShadow         deselectedInnerShadow0;
    private InnerShadow         deselectedInnerShadow1;
    private DropShadow          deselectedDropShadow;

    private Region              selected;
    private InnerShadow         selectedInnerShadow0;
    private InnerShadow         selectedInnerShadow1;
    private DropShadow          selectedDropShadow;

    private Region              icon;


    // ******************** Constructors **************************************
    public PushButtonSkin(final PushButton CONTROL) {
        super(CONTROL);
        aspectRatio  = PREFERRED_HEIGHT / PREFERRED_WIDTH;
        pane         = new Pane();
        init();
        initGraphics();
        registerListeners();
    }


    // ******************** Initialization ************************************
    private void init() {
        if (Double.compare(getSkinnable().getPrefWidth(), 0.0) <= 0 || Double.compare(getSkinnable().getPrefHeight(), 0.0) <= 0 ||
            Double.compare(getSkinnable().getWidth(), 0.0) <= 0 || Double.compare(getSkinnable().getHeight(), 0.0) <= 0) {
            if (getSkinnable().getPrefWidth() > 0 && getSkinnable().getPrefHeight() > 0) {
                getSkinnable().setPrefSize(getSkinnable().getPrefWidth(), getSkinnable().getPrefHeight());
            } else {
                getSkinnable().setPrefSize(PREFERRED_WIDTH, PREFERRED_HEIGHT);
            }
        }

        if (Double.compare(getSkinnable().getMinWidth(), 0.0) <= 0 || Double.compare(getSkinnable().getMinHeight(), 0.0) <= 0) {
            getSkinnable().setMinSize(MINIMUM_WIDTH, MINIMUM_HEIGHT);
        }

        if (Double.compare(getSkinnable().getMaxWidth(), 0.0) <= 0 || Double.compare(getSkinnable().getMaxHeight(), 0.0) <= 0) {
            getSkinnable().setMaxSize(MAXIMUM_WIDTH, MAXIMUM_HEIGHT);
        }

        if (getSkinnable().getPrefWidth() != PREFERRED_WIDTH || getSkinnable().getPrefHeight() != PREFERRED_HEIGHT) {
            aspectRatio = getSkinnable().getPrefHeight() / getSkinnable().getPrefWidth();
        }
    }

    private void initGraphics() {
        frame = new Region();
        frame.getStyleClass().setAll("frame");

        frameInnerShadow0 = new InnerShadow();
        frameInnerShadow0.setOffsetX(0);
        frameInnerShadow0.setOffsetY(1);
        frameInnerShadow0.setRadius(0);
        frameInnerShadow0.setColor(Color.web("0x333333a6"));
        frameInnerShadow0.setBlurType(BlurType.TWO_PASS_BOX);
        frameInnerShadow1 = new InnerShadow();
        frameInnerShadow1.setOffsetX(0);
        frameInnerShadow1.setOffsetY(-1);
        frameInnerShadow1.setRadius(0);
        frameInnerShadow1.setColor(Color.web("0xeeeeeea6"));
        frameInnerShadow1.setBlurType(BlurType.TWO_PASS_BOX);
        frameInnerShadow1.setInput(frameInnerShadow0);
        frame.setEffect(frameInnerShadow1);

        deselected = new Region();
        deselected.getStyleClass().setAll("deselected");

        deselectedInnerShadow0 = new InnerShadow();
        deselectedInnerShadow0.setOffsetX(0);
        deselectedInnerShadow0.setOffsetY(-1);
        deselectedInnerShadow0.setRadius(0);
        deselectedInnerShadow0.setColor(Color.web("0x4b4e52a6"));
        deselectedInnerShadow0.setBlurType(BlurType.TWO_PASS_BOX);
        deselectedInnerShadow1 = new InnerShadow();
        deselectedInnerShadow1.setOffsetX(0);
        deselectedInnerShadow1.setOffsetY(1);
        deselectedInnerShadow1.setRadius(0);
        deselectedInnerShadow1.setColor(Color.web("0xeeeeeea6"));
        deselectedInnerShadow1.setBlurType(BlurType.TWO_PASS_BOX);
        deselectedInnerShadow1.setInput(deselectedInnerShadow0);
        deselectedDropShadow = new DropShadow();
        deselectedDropShadow.setOffsetX(0);
        deselectedDropShadow.setOffsetY(3);
        deselectedDropShadow.setRadius(3.0 / 128.0 * PREFERRED_WIDTH);
        deselectedDropShadow.setColor(Color.web("0x000000a6"));
        deselectedDropShadow.setBlurType(BlurType.TWO_PASS_BOX);
        deselectedDropShadow.setInput(deselectedInnerShadow1);
        deselected.setEffect(deselectedDropShadow);

        selected = new Region();
        selected.getStyleClass().setAll("selected");

        selectedInnerShadow0 = new InnerShadow();
        selectedInnerShadow0.setOffsetX(0);
        selectedInnerShadow0.setOffsetY(-1);
        selectedInnerShadow0.setRadius(0);
        selectedInnerShadow0.setColor(Color.web("0x4b4e52a6"));
        selectedInnerShadow0.setBlurType(BlurType.TWO_PASS_BOX);
        selectedInnerShadow1 = new InnerShadow();
        selectedInnerShadow1.setOffsetX(0);
        selectedInnerShadow1.setOffsetY(1);
        selectedInnerShadow1.setRadius(0);
        selectedInnerShadow1.setColor(Color.web("0xeeeeeea6"));
        selectedInnerShadow1.setBlurType(BlurType.TWO_PASS_BOX);
        selectedInnerShadow1.setInput(selectedInnerShadow0);
        selectedDropShadow = new DropShadow();
        selectedDropShadow.setOffsetX(0);
        selectedDropShadow.setOffsetY(0);
        selectedDropShadow.setRadius(2.0 / 128.0 * PREFERRED_WIDTH);
        selectedDropShadow.setColor(Color.web("0x000000a6"));
        selectedDropShadow.setBlurType(BlurType.TWO_PASS_BOX);
        selectedDropShadow.setInput(selectedInnerShadow1);
        selected.setEffect(selectedDropShadow);

        icon = new Region();
        icon.getStyleClass().setAll("icon");
        pane.getChildren().setAll(frame,
                                  deselected,
                                  selected,
                                  icon);

        // Adjust visibility dependent on settings
        updateStatus();

        getChildren().setAll(pane);
        resize();
    }

    private void registerListeners() {
        getSkinnable().widthProperty().addListener(observable -> handleControlPropertyChanged("RESIZE") );
        getSkinnable().heightProperty().addListener(observable -> handleControlPropertyChanged("RESIZE") );
        getSkinnable().prefWidthProperty().addListener(observable -> handleControlPropertyChanged("PREF_SIZE") );
        getSkinnable().prefHeightProperty().addListener(observable -> handleControlPropertyChanged("PREF_SIZE") );
        getSkinnable().statusProperty().addListener(observable -> handleControlPropertyChanged("STATUS") );
        getSkinnable().colorProperty().addListener(observable -> handleControlPropertyChanged("COLOR") );
        getSkinnable().getStyleClass().addListener(new ListChangeListener<String>() {
            @Override public void onChanged(Change<? extends String> change) {
                resize();
            }
        });
    }


    // ******************** Methods *******************************************
    protected void handleControlPropertyChanged(final String PROPERTY) {
        if ("RESIZE".equals(PROPERTY)) {
            resize();
        } else if ("STATUS".equals(PROPERTY)) {
            updateStatus();
        } else if ("COLOR".equals(PROPERTY)) {
            icon.setBackground(new Background(new BackgroundFill(getSkinnable().getColor(), null, null)));
            resize();
        }
    }

    @Override protected double computeMinWidth(final double HEIGHT, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        return super.computeMinWidth(Math.max(MINIMUM_HEIGHT, HEIGHT - TOP_INSET - BOTTOM_INSET), TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }
    @Override protected double computeMinHeight(final double WIDTH, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        return super.computeMinHeight(Math.max(MINIMUM_WIDTH, WIDTH - LEFT_INSET - RIGHT_INSET), TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }

    @Override protected double computeMaxWidth(final double HEIGHT, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        return super.computeMaxWidth(Math.min(MAXIMUM_HEIGHT, HEIGHT - TOP_INSET - BOTTOM_INSET), TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }
    @Override protected double computeMaxHeight(final double WIDTH, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        return super.computeMaxHeight(Math.min(MAXIMUM_WIDTH, WIDTH - LEFT_INSET - RIGHT_INSET), TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }

    @Override protected double computePrefWidth(final double HEIGHT, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        double prefHeight = PREFERRED_HEIGHT;
        if (HEIGHT != -1) {
            prefHeight = Math.max(0, HEIGHT - TOP_INSET - BOTTOM_INSET);
        }
        return super.computePrefWidth(prefHeight, TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }
    @Override protected double computePrefHeight(final double WIDTH, double TOP_INSET, double RIGHT_INSET, double BOTTOM_INSET, double LEFT_INSET) {
        double prefWidth = PREFERRED_WIDTH;
        if (WIDTH != -1) {
            prefWidth = Math.max(0, WIDTH - LEFT_INSET - RIGHT_INSET);
        }
        return super.computePrefHeight(prefWidth, TOP_INSET, RIGHT_INSET, BOTTOM_INSET, LEFT_INSET);
    }

    private void updateStatus() {
        switch (getSkinnable().getStatus()) {
            case DESELECTED:
                selected.setOpacity(0);
                deselected.setOpacity(1);
                icon.getStyleClass().setAll("icon");
                icon.setOpacity(1);
                break;
            case SELECTED:
                selected.setOpacity(1);
                deselected.setOpacity(0);
                icon.getStyleClass().setAll("icon", "icon-selected");
                icon.setOpacity(1);
                break;
            case EMPTY:
            default:
                selected.setOpacity(0);
                deselected.setOpacity(0);
                icon.setOpacity(0);
                break;
        }
    }


    // ******************** Resizing ******************************************
    private void resize() {
        size   = getSkinnable().getWidth() < getSkinnable().getHeight() ? getSkinnable().getWidth() : getSkinnable().getHeight();
        width  = getSkinnable().getWidth();
        height = getSkinnable().getHeight();
        if (getSkinnable().isKeepAspect()) {
            if (aspectRatio * width > height) {
                width  = 1 / (aspectRatio / height);
            } else if (1 / (aspectRatio / height) > width) {
                height = aspectRatio * width;
            }
        }
        if (width > 0 && height > 0) {
            frame.setPrefSize(width, height);

            deselected.setPrefSize(0.6875 * width, 0.6875 * height);
            deselected.setTranslateX(0.15625 * width);
            deselected.setTranslateY(0.15625 * height);
            deselectedDropShadow.setRadius(3.0 / 128.0 * size);

            selected.setPrefSize(0.6875 * width, 0.6796875 * height);
            selected.setTranslateX(0.15625 * width);
            selected.setTranslateY(0.15625 * height);
            selectedDropShadow.setRadius(2.0 / 128.0 * size);

            icon.setPrefSize(0.375 * width, 0.4375 * height);
            icon.setTranslateX(0.3125 * width);
            icon.setTranslateY(0.28125 * height);
        }
    }
}
TOP

Related Classes of eu.hansolo.enzo.experimental.pushbutton.skin.PushButtonSkin

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.