package com.ads.cal.marquee;

import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.os.Handler;
import android.os.Message;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.util.DisplayMetrics;
import android.view.WindowManager;
import android.widget.TextView;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import java.util.ArrayList;

public class MarqueeView extends TextView {
    public MarqueeView(Context context) {
        super(context);
        initView();
    }

    public MarqueeView(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        initView();
    }

    public MarqueeView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        initView();
    }

    public MarqueeView(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
        initView();
    }

    private String text;
    private float x;
    private float y;
    private int d;
    private int width, height;
    private int model = SCROLL_H_MODEL;

    public static final int SCROLL_H_MODEL = 1;
    public static final int SCROLL_V_MODEL = 2;


    private Paint createPaint(String color, float textSize) {
        Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
        paint.setColor(Color.parseColor(color));
        paint.setTextSize(textSize);
        paint.setAntiAlias(true);
        return paint;
    }

    private final Rect rect = new Rect();
    private float[] temp = null;
    private int canvasNum;
    private ArrayList<PaintTextBean> paints;

    private void initView() {
        text = getResources().getString(R.string.text_welcome);
        d = dpToPx(getContext(), 50);
        initAllPainText();
    }

    private void initAllPainText() {
        if (paints == null) {
            paints = new ArrayList<>();
        } else {
            paints.clear();
        }
        int maxFontSize = (int) (getScreenHeight() * 0.8);
        int[] size = {maxFontSize / 8, maxFontSize / 4, maxFontSize / 2, (int) (maxFontSize / 1.5f), maxFontSize};
        for (int index : size) {
            paints.add(new PaintTextBean(createPaint("#ffffff", index), text, rect));
        }
        tempPaint = paints.get(selectIndex).t;
    }

    @Override
    protected void onDetachedFromWindow() {
        super.onDetachedFromWindow();
        handler.removeCallbacks(null);
    }


    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        if (width == 0 || height == 0) {
            width = getWidth();
            height = getHeight();
        }
        if (model == SCROLL_H_MODEL) {
            modelX(canvas);
        } else if (model == SCROLL_V_MODEL) {
            modelY(canvas);
        }
    }

    private int tempTextWidth;
    private Paint tempPaint;

    private void modelX(Canvas canvas) {
        if (y == 0) {
            tempTextWidth = paints.get(selectIndex).width;
            x = width;
            y = height / 2f + paints.get(selectIndex).height / 2.5f;
            canvasNum = width / (tempTextWidth + d) + 1;
            if (canvasNum < 3) {
                canvasNum = 3;
            }
            temp = new float[canvasNum];
            for (int i = 0; i < canvasNum; i++) {
                temp[i] = width + (tempTextWidth + d) * i;
            }
        }
//        if (y2 == 0) {
//            x2 = width;
//            y2 = height / 2f + textHeight / 2f;
//        }

        for (int i = 0; i < canvasNum; i++) {
            temp[i] -= scrollTo;
            if (temp[i] + tempTextWidth + d <= 0) {
                temp[i] = temp[(i - 1 + canvasNum) % canvasNum] + tempTextWidth + d;
            }
            canvas.drawText(text, temp[i], y, tempPaint);
        }

//        if (x + textWidth < width - d) {
//            if ((x + textWidth) <= 0 && x2 + textWidth <= width - d) {
//                x = width;
//            }
//            canvas.drawText(text, x2, y2, paint);
//            canvas.drawText(text, x, y, paint);
//        } else {
//            if (x2 + textWidth <= width - d) {
//                canvas.drawText(text, x2, y2, paint);
//            }
//            if (x2 < -(textWidth - (d / 2f))) {
//                x2 = width;
//            }
//            canvas.drawText(text, x, y, paint);
//        }
    }

    private int tempTextHeight;

    private void modelY(Canvas canvas) {
        if (x == 0) {
            tempTextHeight = paints.get(selectIndex).height;
            x = width / 2f - paints.get(selectIndex).width / 2f;
            y = height;
            canvasNum = height / (tempTextHeight + d);
            if (canvasNum < 5) {
                canvasNum = 5;
            }
            temp = new float[canvasNum];
            for (int i = 0; i < canvasNum; i++) {
                temp[i] = height + (tempTextHeight + d) * i;
            }
        }
//        if (x2 == 0) {
//            x2 = width / 2f - textWidth / 2f;
//            y2 = height;
//        }


        for (int i = 0; i < canvasNum; i++) {
            temp[i] -= scrollTo;
            if (temp[i] <= 0) {
                temp[i] = temp[(i - 1 + canvasNum) % canvasNum] + tempTextHeight + d;
            }
            if (temp[i] >= 0) {
                canvas.drawText(text, x, temp[i], tempPaint);
            }
        }


//        if (y + textHeight < height - d) {
//            if ((y + textHeight) <= 2 && y2 + textHeight <= height - d) {
//                y = height;
//            }
//            canvas.drawText(text, x2, y2, paint);
//            canvas.drawText(text, x, y, paint);
//        } else {
//            if (y2 + textHeight <= height - d) {
//                canvas.drawText(text, x2, y2, paint);
//            }
//            if (y2 < -(textHeight - (d / 2f))) {
//                y2 = height;
//            }
//            canvas.drawText(text, x, y, paint);
//        }
    }

    public void setTextValue(String t) {
        if (TextUtils.isEmpty(t)) {
            handler.removeCallbacksAndMessages(null);
            text = t;
            invalidate();
            return;
        }
        if (text.equals(t)) {
            return;
        }
        y = 0;
        x = 0;
        text = t;
        for (PaintTextBean bean : paints) {
            rect.setEmpty();
            bean.setValue(t, rect);
        }
        handler.sendEmptyMessageDelayed(0, 10);
    }


    private int oldColor;

    @SuppressLint("ResourceType")
    public void setTextColor(int color) {
        if (TextUtils.isEmpty(text)) {
            handler.removeCallbacksAndMessages(null);
            return;
        }
        if (oldColor == color) {
            return;
        }
        oldColor = color;
        for (PaintTextBean bean : paints) {
            bean.setTextColor(getResources().getColor(color));
        }
        handler.sendEmptyMessageDelayed(0, 10);
    }

    private int oldShadowLayerColor;

    public void setTextShadowLayer(int color) {
        if (TextUtils.isEmpty(text)) {
            handler.removeCallbacksAndMessages(null);
            return;
        }
        if (oldShadowLayerColor == color) {
            return;
        }
        oldShadowLayerColor = color;

        for (PaintTextBean bean : paints) {
            bean.setTextShadowLayer(getResources().getColor(color));
        }
        handler.sendEmptyMessageDelayed(0, 10);
    }

    private int selectIndex;

    public void setTextSizeD(int index, int d) {
        if (TextUtils.isEmpty(text)) {
            handler.removeCallbacksAndMessages(null);
            return;
        }
        if (selectIndex == index) {
            return;
        }
        selectIndex = index;
        tempPaint = paints.get(index).t;
        y = 0;
        x = 0;
        this.d = dpToPx(getContext(), d);
        handler.sendEmptyMessageDelayed(0, 10);
    }

    public void setModel(int model) {
        if (TextUtils.isEmpty(text)) {
            handler.removeCallbacksAndMessages(null);
            return;
        }
        y = 0;
        x = 0;
        for (PaintTextBean bean : paints) {
            rect.setEmpty();
            bean.setValue(text, rect);
        }
        this.model = model;
        handler.sendEmptyMessageDelayed(0, 10);
    }

    private float scrollTo;

    public void startRun(float scrollTo) {
        if (TextUtils.isEmpty(text)) {
            handler.removeCallbacksAndMessages(null);
            return;
        }
        if (this.scrollTo == scrollTo) {
            return;
        }
        this.scrollTo = scrollTo;
        handler.sendEmptyMessageDelayed(0, 10);
    }


    private final Handler handler = new Handler() {
        @Override
        public void handleMessage(@NonNull Message msg) {
            super.handleMessage(msg);

//            if (model == SCROLL_H_MODEL) {
//                if (x + textWidth < width - d || x2 + textWidth <= width - d) {
//                    x2 -= scrollTo;
//                }
////                x -= scrollTo;
//            } else if (model == SCROLL_V_MODEL) {
//                if (y + textHeight < height - d || y2 + textHeight <= height - d) {
//                    y2 -= scrollTo;
//                }
//                y -= scrollTo;
//            }

            handler.removeCallbacksAndMessages(null);
            handler.sendEmptyMessageDelayed(0, 10);
            invalidate();
        }
    };

    private int dpToPx(Context context, float dp) {
        // 获取屏幕密度
        float density = context.getResources().getDisplayMetrics().density;
        // 将dp转换为px（像素）
        return Math.round(dp * density);
    }

    private int getScreenHeight() {
        WindowManager wm = (WindowManager) getContext().getSystemService(Context.WINDOW_SERVICE);
        DisplayMetrics metrics = new DisplayMetrics();
        if (wm != null) {
            wm.getDefaultDisplay().getMetrics(metrics);
            return metrics.heightPixels;
        }
        return 0; // 默认返回0，表示未获取到屏幕宽度
    }


}
