package cn.forevermc.launcher.view.components;

import javafx.beans.binding.Bindings;
import javafx.beans.binding.BooleanBinding;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Node;
import javafx.scene.control.ScrollBar;
import javafx.scene.control.ScrollPane;
import javafx.scene.control.skin.ScrollPaneSkin;
import javafx.scene.layout.StackPane;
import lombok.extern.slf4j.Slf4j;
import com.imyeyu.fx.utils.BorderStroke;
import com.imyeyu.fx.utils.SmoothScroll;
import com.imyeyu.java.ref.Ref;

/**
 * 滚动面板，支持滚动的内容面板
 *
 * @author 夜雨
 * @since 2024-07-14 17:43
 */
@Slf4j
public abstract class AbstractScrollPane extends AbstractContentPane {

	private static final Insets PADDING_SCROLL = new Insets(0, 0, 0, 32);
	private static final Insets PADDING_SCROLL_R = new Insets(0, 0, 0, 0);

	private final StackPane content;

	protected final BooleanBinding showingVScrollBar;

	private ScrollBar vsb;

	public AbstractScrollPane() {
		content = new StackPane();
		content.setAlignment(Pos.CENTER);
		content.setPadding(new Insets(16, 0, 12, 0));

		ScrollPane scrollPane = new ScrollPane() {{
			setAlignment(content, Pos.TOP_CENTER);
			setFitToWidth(true);
			getStyleClass().add(CSS.BG_TP);

			setContent(content);
			SmoothScroll.scrollPane(this);
		}};
		setContentPane(scrollPane);

		showingVScrollBar = Bindings.createBooleanBinding(() -> {
			// TODO 最大化或最小化时无效
			try {
				if (vsb == null && scrollPane.getSkin() != null && scrollPane.getSkin() instanceof ScrollPaneSkin skin) {
					vsb = Ref.getFieldValue(skin, "vsb", ScrollBar.class);
				}
				if (vsb != null) {
					return vsb.isVisible();
				}
			} catch (Exception e) {
				log.error("ref MCList virtual scroll bar error", e);
			}
			return false;
		}, scrollPane.skinProperty(), scrollPane.layoutBoundsProperty());

		scrollPane.paddingProperty().bind(Bindings.when(showingVScrollBar).then(PADDING_SCROLL).otherwise(PADDING_SCROLL_R));
		scrollPane.maxWidthProperty().bind(Bindings.when(showingVScrollBar).then(690D).otherwise(640));
	}

	protected void setScrollContent(Node node) {
		content.getChildren().setAll(node);
	}
}
