javafx扫描渐变

本文档展示了如何在JavaFX中创建一个名为`ResetSwitchSkin`的自定义Gauge皮肤。该皮肤涉及到多个图形元素如Circle、Arc、Text等的配置,并使用ConicalGradient进行扫描渐变效果。代码详细地定义了各个图形的初始化、监听器注册、大小调整以及事件处理方法,以实时更新Gauge的显示。此外,还包含了标题、值、单位的文本处理和布局调整。
摘要由CSDN通过智能技术生成

javafx扫描渐变

ConicalGradient类

博客设置页面,选择一款你喜欢的代码片高亮样式,下面展示同样高亮的 代码片.

// An highlighted block
![在这里插入图片描述](https://img-blog.csdnimg.cn/a169f2741aba4770bb35991046e8dc52.png#pic_center)
package com.hirain.higale.plugin.monitoring.application.view.medusa;

import eu.hansolo.medusa.Fonts;
import eu.hansolo.medusa.Gauge;
import eu.hansolo.medusa.skins.GaugeSkinBase;
import eu.hansolo.medusa.tools.ConicalGradient;
import eu.hansolo.medusa.tools.Helper;
import javafx.beans.InvalidationListener;
import javafx.scene.layout.Pane;
import javafx.scene.paint.Color;
import javafx.scene.paint.CycleMethod;
import javafx.scene.paint.LinearGradient;
import javafx.scene.paint.Stop;
import javafx.scene.shape.*;
import javafx.scene.text.Text;

import java.util.List;
import java.util.Timer;
import java.util.TimerTask;

public class ResetSwitchSkin extends GaugeSkinBase {
    private double size;
    private Text titleText;
    private Text valueText;
    private Text unitText;
    private Circle fakeDot;
    private Arc arc;
    private Circle circle;
    private Circle circleBtn ;
    private Circle circleBtnBase;
    private Pane pane;

    private double center;
    private double range;
    private double angleStep;
    private final InvalidationListener currentValueListener;
    private final InvalidationListener barColorListener;
    private final InvalidationListener titleListener;
    private final InvalidationListener unitListener;
    private CubicCurveTo cc;
    private MoveTo mt;
    private LineTo lt1;
    private LineTo lt2;
    private Path path;
    private Polygon triangle;


    public ResetSwitchSkin(Gauge gauge) {
        super(gauge);
        if (gauge.isAutoScale()) {
            gauge.calcAutoScale();
        }

        this.range = gauge.getRange();
        this.angleStep = -360.0D / this.range;
        this.currentValueListener = (o) -> this.redraw();
        this.barColorListener = (o) -> {
            Color barColor = gauge.getBarColor();
            gauge.setGradientBarStops(new Stop(0.0D, barColor), new Stop(0.01D, barColor), new Stop(0.75D, barColor.deriveColor(-10.0D, 1.0D, 1.0D, 1.0D)), new Stop(1.0D, barColor.deriveColor(-20.0D, 1.0D, 1.0D, 1.0D)));
            this.resize();
        };
        this.titleListener = (o) -> {
            this.titleText.setText(gauge.getTitle());
            this.resizeTitleText();
        };
        this.unitListener = (o) -> {
            this.unitText.setText(gauge.getUnit());
            this.resizeUnitText();
        };
        this.initGraphics();
        this.registerListeners();
    }

    private void initGraphics() {
        if (Double.compare(this.gauge.getPrefWidth(), 0.0D) <= 0 || Double.compare(this.gauge.getPrefHeight(), 0.0D) <= 0 || Double.compare(this.gauge.getWidth(), 0.0D) <= 0 || Double.compare(this.gauge.getHeight(), 0.0D) <= 0) {
            if (this.gauge.getPrefWidth() > 0.0D && this.gauge.getPrefHeight() > 0.0D) {
                this.gauge.setPrefSize(this.gauge.getPrefWidth(), this.gauge.getPrefHeight());
            } else {
                this.gauge.setPrefSize(250.0D, 250.0D);
            }
        }
        LinearGradient gradientBtnBase = new LinearGradient(0.0, 0.0, 1.0, 1.0, true, CycleMethod.NO_CYCLE,
                new Stop(0.2, Color.rgb(250, 250, 250, 1)),
                new Stop(0.4, Color.rgb(230, 230, 230, 1)),
                new Stop(0.6, Color.rgb(181, 181, 181, 1)),
                new Stop(1.0, Color.rgb(140, 140, 140, 1)));
        LinearGradient gradientBtn = new LinearGradient(0.0, 0.0, 1, 1, true, CycleMethod.NO_CYCLE,
                new Stop(0.0, Color.rgb(0, 0, 0, 0.2)),
                new Stop(0.6, Color.rgb(233, 233, 233, 1)),
                new Stop(1.0, Color.rgb(255, 255, 255, 1)));

        Color barColor = this.gauge.getBarColor();
        this.gauge.setGradientBarStops(new Stop(0.0D, barColor), new Stop(0.01D, barColor), new Stop(0.75D, barColor.deriveColor(-10.0D, 1.0D, 1.0D, 1.0D)), new Stop(1.0D, barColor.deriveColor(-20.0D, 1.0D, 1.0D, 1.0D)));
        this.circle = new Circle();
        this.circle.setFill(null);
        this.circleBtnBase = new Circle();
        this.circleBtnBase.setFill(gradientBtnBase);
        this.circleBtn  = new Circle();
        this.circleBtn.setFill(gradientBtn);
        this.arc = new Arc(125.0D, 125.0D, 240.0D, 120.0D, 90.0D, 0.0D);
        this.arc.setStrokeWidth(2.0D);
        this.arc.setStrokeType(StrokeType.CENTERED);
        this.arc.setStrokeLineCap(StrokeLineCap.ROUND);
        this.arc.setFill(null);
        this.fakeDot = new Circle();
        this.fakeDot.setStroke(null);
        this.fakeDot.setVisible(false);
        this.titleText = new Text(this.gauge.getTitle());
        this.titleText.setFont(Fonts.robotoLight(125.0D));
        this.titleText.setFill(this.gauge.getTitleColor());
        Helper.enableNode(this.titleText, !this.gauge.getTitle().isEmpty());
        this.valueText = new Text(Helper.formatNumber(this.gauge.getLocale(), this.gauge.getFormatString(), this.gauge.getDecimals(), this.gauge.getCurrentValue()));
        this.valueText.setFont(Fonts.robotoRegular(68.33250000000001D));
        this.valueText.setFill(this.gauge.getValueColor());
        Helper.enableNode(this.valueText, this.gauge.isValueVisible());
        this.unitText = new Text(this.gauge.getUnit());
        this.unitText.setFont(Fonts.robotoLight(20.0D));
        this.unitText.setFill(this.gauge.getUnitColor());
        Helper.enableNode(this.unitText, !this.gauge.getUnit().isEmpty());

        Pane pattern = new Pane();
        this.path = new Path();
        this.triangle = new Polygon();
        this.triangle.setFill(Color.rgb(105,105,105, 1));
        this.mt = new MoveTo();
        this.lt1 = new LineTo();
        this.cc = new CubicCurveTo();
        this.lt2 = new LineTo();
        this.path.getElements().addAll(this.mt,this.lt1,this.cc,this.lt2);
        this.path.setStroke(Color.rgb(105,105,105, 1));
        this.path.setSmooth(true);
        pattern.getChildren().addAll(this.path,this.triangle);

        this.pane = new Pane(this.circle,this.circleBtnBase,this.circleBtn, this.arc, this.fakeDot, this.titleText, this.valueText, this.unitText, pattern);
        this.getChildren().setAll(this.pane);
    }

    protected void getPattern()    {
        var lineLen  = this.size / 200 * 18;
        var curveW   = this.size / 200 * 15;
        var curveH   = this.size / 200 * 13;
        var triSide  = this.size / 200 * 18;
        var triH     = triSide /2 * Math.sqrt(3);
        var patternW = triH + lineLen + curveW * 2;

        this.mt.setX(this.center - patternW/4 + triH / 2);
        this.mt.setY(this.center - curveH);
        this.lt1.setX(this.center - patternW/4 + lineLen);
        this.lt1.setY(this.center - curveH);
        this.cc.setX(this.center - patternW/4 + lineLen);
        this.cc.setY(this.center - curveH + curveH*2);
        this.cc.setControlX1(this.center - patternW/4 + lineLen + curveW);
        this.cc.setControlY1(this.center - curveH);
        this.cc.setControlX2(this.center - patternW/4 + lineLen + curveW);
        this.cc.setControlY2(this.center - curveH + curveH * 2);
        this.lt2.setX(this.center - patternW/4);
        this.lt2.setY(this.center - curveH + curveH*2);
        this.path.setStrokeWidth(this.size / 200 * 5);
        this.triangle.getPoints().setAll(
                this.center - patternW/4 - triH / 2, this.center - curveH,
                this.center - patternW/4 + triH / 2, this.center - curveH + triSide/2,
                this.center - patternW/4 + triH / 2, this.center - curveH - triSide/2
        );

    }

    protected void registerListeners() {
        super.registerListeners();
        this.gauge.currentValueProperty().addListener(this.currentValueListener);
        this.gauge.barColorProperty().addListener(this.barColorListener);
        this.gauge.titleProperty().addListener(this.titleListener);
        this.gauge.unitProperty().addListener(this.unitListener);

//        this.gauge.onMousePressedProperty().set((event) ->{
//            gauge.setAnimationDuration((long) (getModel().getDuration() * 1000));
//            gauge.setValue(onValue);
//
//            new Timer().schedule(new TimerTask() {
//                public void run() {
//                    gauge.setAnimationDuration(0);
//                    gauge.setValue(offValue);
//                }
//            }, (long) (getModel().getDuration() * 1000));
//        });
    }

    protected void handleEvents(String EVENT_TYPE) {
        super.handleEvents(EVENT_TYPE);
        if ("RECALC".equals(EVENT_TYPE)) {
            this.range = this.gauge.getRange();
            this.angleStep = -360.0D / this.range;
            this.redraw();
        } else if ("VISIBILITY".equals(EVENT_TYPE)) {
            Helper.enableNode(this.titleText, !this.gauge.getTitle().isEmpty());
        }

    }

    public void dispose() {
        this.gauge.currentValueProperty().removeListener(this.currentValueListener);
        this.gauge.barColorProperty().removeListener(this.barColorListener);
        this.gauge.titleProperty().removeListener(this.titleListener);
        this.gauge.unitProperty().removeListener(this.unitListener);
        super.dispose();
    }

    private void resizeTitleText() {
        double maxWidth = 0.48D * this.size;
        double fontSize = 0.08D * this.size;
        this.titleText.setFont(Fonts.robotoLight(fontSize));
        if (this.titleText.getLayoutBounds().getWidth() > maxWidth) {
            Helper.adjustTextSize(this.titleText, maxWidth, fontSize);
        }

        this.titleText.relocate((this.size - this.titleText.getLayoutBounds().getWidth()) * 0.5D, this.size * 0.25D);
    }

    private void resizeValueText() {
        double maxWidth = 0.5D * this.size;
        double fontSize = 0.3D * this.size;
        this.valueText.setFont(Fonts.robotoRegular(fontSize));
        if (this.valueText.getLayoutBounds().getWidth() > maxWidth) {
            Helper.adjustTextSize(this.valueText, maxWidth, fontSize);
        }

        this.valueText.relocate((this.size - this.valueText.getLayoutBounds().getWidth()) * 0.5D, (this.size - this.valueText.getLayoutBounds().getHeight()) * 0.5D);
    }

    private void resizeUnitText() {
        double maxWidth = 0.56667D * this.size;
        double fontSize = 0.08D * this.size;
        this.unitText.setFont(Fonts.robotoLight(fontSize));
        if (this.unitText.getLayoutBounds().getWidth() > maxWidth) {
            Helper.adjustTextSize(this.unitText, maxWidth, fontSize);
        }

        this.unitText.relocate((this.size - this.unitText.getLayoutBounds().getWidth()) * 0.5D, this.size * 0.68D);
    }

    protected void resize() {
        double width = this.gauge.getWidth() - this.gauge.getInsets().getLeft() - this.gauge.getInsets().getRight();
        double height = this.gauge.getHeight() - this.gauge.getInsets().getTop() - this.gauge.getInsets().getBottom();

        this.size = Math.min(width, height);
        if (width > 0.0D && height > 0.0D) {
            this.pane.setMaxSize(this.size, this.size);
            this.pane.setPrefSize(this.size, this.size);
            this.pane.relocate((width - this.size) * 0.5D, (height - this.size) * 0.5D);
            this.center = this.size * 0.5D;
            this.circle.setCenterX(this.center);
            this.circle.setCenterY(this.center);
            this.circle.setRadius(this.size * 0.44D);
            this.circle.setStrokeWidth(this.size * 0.11D);

            this.circleBtnBase.setCenterX(this.center);
            this.circleBtnBase.setCenterY(this.center);
            this.circleBtnBase.setRadius(this.size * 0.385D);

            this.circleBtn.setCenterX(this.center);
            this.circleBtn.setCenterY(this.center);
            this.circleBtn.setRadius(this.size * 0.32D);

            this.arc.setCenterX(this.center);
            this.arc.setCenterY(this.center);
            this.arc.setRadiusX(this.size * 0.44D);
            this.arc.setRadiusY(this.size * 0.44D);
            this.arc.setStrokeWidth(this.size * 0.11D);
            Color barColor = this.gauge.getBarColor();
            double currentValue = this.gauge.getCurrentValue();
            List<Stop> gradientBarStops = this.gauge.getGradientBarStops();
            this.circle.setStroke(Color.rgb(222, 222, 222, 0.8));
            Rectangle bounds = new Rectangle(0.0D, 0.0D, this.size, this.size);
            ConicalGradient gradient = new ConicalGradient(this.center, this.center, Gauge.ScaleDirection.CLOCKWISE, gradientBarStops);
            this.arc.setStroke(gradient.getImagePattern(bounds));
//            this.arc.setFill(gradient.getImagePattern(bounds));
            this.arc.setLength(currentValue * this.angleStep);
            this.fakeDot.setRadius(this.size * 0.055D);
            this.fakeDot.setFill(gradientBarStops.get(1).getColor());
            this.titleText.setFill(barColor);
            this.getPattern();
            this.resizeTitleText();
            this.resizeValueText();
            this.resizeUnitText();
            this.redraw();
        }

    }

    protected void redraw() {
        double currentValue = this.gauge.getCurrentValue();
        double angle = currentValue * this.angleStep;
        double rotate = angle < -360.0D ? angle + 360.0D : 0.0D;
        this.arc.setRotate(-rotate);
        this.arc.setLength(Helper.clamp(-360.0D, 0.0D, angle));
        if (angle < -360.0D) {
            this.fakeDot.setCenterX(this.center + this.arc.getRadiusX() * Math.sin(Math.toRadians(180.0D + angle)));
            this.fakeDot.setCenterY(this.center + this.arc.getRadiusY() * Math.cos(Math.toRadians(180.0D + angle)));
        } else {
            this.fakeDot.setCenterX(this.center + this.arc.getRadiusX() * Math.sin(Math.toRadians(180.0D)));
            this.fakeDot.setCenterY(this.center + this.arc.getRadiusY() * Math.cos(Math.toRadians(180.0D)));
        }
        this.valueText.setText("");
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值