package com.airbnb.lottie;

import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PorterDuff;
import android.graphics.PorterDuffXfermode;
import android.graphics.RectF;
import android.support.annotation.FloatRange;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.util.LongSparseArray;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

class LayerView extends AnimatableLayer {
  private static final int SAVE_FLAGS = Canvas.CLIP_SAVE_FLAG | Canvas.CLIP_TO_LAYER_SAVE_FLAG;
  private MaskKeyframeAnimation mask;
  private LayerView matteLayer;

  private final PorterDuffXfermode DST_OUT = new PorterDuffXfermode(PorterDuff.Mode.DST_OUT);
  private final PorterDuffXfermode DST_IN = new PorterDuffXfermode(PorterDuff.Mode.DST_IN);
  private final RectF rect = new RectF();
  private final List<LayerView> transformLayers = new ArrayList<>();
  private final Paint mainCanvasPaint = new Paint();
  private final Paint mattePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
  private final Paint maskPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
  private final Paint imagePaint =
      new Paint(Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG);

  private final Layer layerModel;
  private final LottieComposition composition;
  private final CanvasPool canvasPool;

  @Nullable private LayerView parentLayer;
  /**
   * The width and height of the precomp that this was added to.
   * This differs from the LayerModel precompWidth and height which will be set if this is
   * the precomp layer itself.
   */
  private int precompWidth;
  private int precompHeight;

  LayerView(Layer layerModel, LottieComposition composition, Callback callback, CanvasPool canvasPool) {
    super(callback);
    this.layerModel = layerModel;
    this.composition = composition;
    this.canvasPool = canvasPool;
    setBounds(composition.getBounds());

    if (layerModel.getMatteType() == Layer.MatteType.Invert) {
      mattePaint.setXfermode(DST_OUT);
    } else {
      mattePaint.setXfermode(DST_IN);
    }

    setupForModel();
  }

  private void setupForModel() {
    setBackgroundColor(layerModel.getSolidColor());
    setBounds(0, 0, layerModel.getSolidWidth(), layerModel.getSolidHeight());

    setTransform(layerModel.getTransform().createAnimation());
    setupInOutAnimations();

    switch (layerModel.getLayerType()) {
      case Shape:
        setupShapeLayer();
        break;
      case PreComp:
        setupPreCompLayer();
        break;
    }

    if (layerModel.getMasks() != null && !layerModel.getMasks().isEmpty()) {
      setMask(new MaskKeyframeAnimation(layerModel.getMasks()));
    }

    LongSparseArray<LayerView> layerMap = new LongSparseArray<>();

    for (AnimatableLayer layer : layers) {
      if (layer instanceof LayerView) {
        layerMap.put(((LayerView) layer).getId(), ((LayerView) layer));
        LayerView matteLayer = ((LayerView) layer).matteLayer;
        if (matteLayer != null) {
          layerMap.put(matteLayer.getId(), matteLayer);
        }
      }
    }

    for (AnimatableLayer layer : layers) {
      if (!(layer instanceof LayerView)) {
        continue;
      }
      long parentId = ((LayerView) layer).getLayerModel().getParentId();
      LayerView parentLayer = layerMap.get(parentId);
      if (parentLayer != null) {
        ((LayerView) layer).setParentLayer(parentLayer);
      }

      LayerView matteLayer = ((LayerView) layer).matteLayer;
      if (matteLayer != null) {
        parentId = matteLayer.getLayerModel().getParentId();
        parentLayer = layerMap.get(parentId);
        if (parentLayer != null) {
          matteLayer.setParentLayer(parentLayer);
        }
      }

    }
  }

  private void setupShapeLayer() {
    List<Object> reversedItems = new ArrayList<>(layerModel.getShapes());
    Collections.reverse(reversedItems);
    AnimatableTransform currentTransform = null;
    ShapeTrimPath currentTrim = null;
    ShapeFill currentFill = null;
    ShapeStroke currentStroke = null;

    for (int i = 0; i < reversedItems.size(); i++) {
      Object item = reversedItems.get(i);
      if (item instanceof ShapeGroup) {
        GroupLayerView groupLayer = new GroupLayerView((ShapeGroup) item, currentFill,
            currentStroke, currentTrim, currentTransform, getCallback());
        addLayer(groupLayer);
      } else if (item instanceof AnimatableTransform) {
        currentTransform = (AnimatableTransform) item;
      } else if (item instanceof ShapeFill) {
        currentFill = (ShapeFill) item;
      } else if (item instanceof ShapeTrimPath) {
        currentTrim = (ShapeTrimPath) item;
      } else if (item instanceof ShapeStroke) {
        currentStroke = (ShapeStroke) item;
      } else if (item instanceof ShapePath) {
        ShapePath shapePath = (ShapePath) item;
        ShapeLayerView shapeLayer =
            new ShapeLayerView(shapePath, currentFill, currentStroke, currentTrim,
                AnimatableTransform.Factory.newInstance(composition), getCallback());
        addLayer(shapeLayer);
      } else if (item instanceof RectangleShape) {
        RectangleShape shapeRect = (RectangleShape) item;
        RectLayer shapeLayer =
            new RectLayer(shapeRect, currentFill, currentStroke, currentTrim,
                AnimatableTransform.Factory.newInstance(composition), getCallback());
        addLayer(shapeLayer);
      } else if (item instanceof CircleShape) {
        CircleShape shapeCircle = (CircleShape) item;
        EllipseLayer shapeLayer =
            new EllipseLayer(shapeCircle, currentFill, currentStroke, currentTrim,
                AnimatableTransform.Factory.newInstance(composition), getCallback());
        addLayer(shapeLayer);
      } else if (item instanceof PolystarShape) {
        PolystarShape polystarShape = (PolystarShape) item;
        PolystarLayer shapeLayer = new PolystarLayer(polystarShape, currentFill, currentStroke,
            currentTrim, AnimatableTransform.Factory.newInstance(composition), getCallback());
        addLayer(shapeLayer);
      }
    }
  }

  private void setupPreCompLayer() {
    List<Layer> precompLayers = composition.getPrecomps(layerModel.getRefId());
    if (precompLayers == null) {
      return;
    }
    LayerView mattedLayer = null;
    for (int i = precompLayers.size() - 1; i >= 0; i--) {
      Layer layer = precompLayers.get(i);
      LayerView layerView =
          new LayerView(layer, composition, getCallback(), canvasPool);
      layerView.setPrecompSize(layerModel.getPreCompWidth(), layerModel.getPreCompHeight());
      if (mattedLayer != null) {
        mattedLayer.setMatteLayer(layerView);
        mattedLayer = null;
      } else {
        addLayer(layerView);
        if (layer.getMatteType() == Layer.MatteType.Add) {
          mattedLayer = layerView;
        } else if (layer.getMatteType() == Layer.MatteType.Invert) {
          mattedLayer = layerView;
        }
      }
    }
  }

  private void setupInOutAnimations() {
    if (!layerModel.getInOutKeyframes().isEmpty()) {
      FloatKeyframeAnimation inOutAnimation =
          new FloatKeyframeAnimation(layerModel.getInOutKeyframes());
      inOutAnimation.setIsDiscrete();
      inOutAnimation.addUpdateListener(new KeyframeAnimation.AnimationListener<Float>() {
        @Override public void onValueChanged(Float value) {
          setVisible(value == 1f, false);
        }
      });
      setVisible(inOutAnimation.getValue() == 1f, false);
      addAnimation(inOutAnimation);
    } else {
      setVisible(true, false);
    }
  }

  Layer getLayerModel() {
    return layerModel;
  }

  void setParentLayer(@Nullable LayerView parentLayer) {
    this.parentLayer = parentLayer;
  }

  @Nullable
  private LayerView getParentLayer() {
    return parentLayer;
  }

  private void setPrecompSize(int width, int height) {
    precompWidth = width;
    precompHeight = height;
  }

  private void setMask(MaskKeyframeAnimation mask) {
    this.mask = mask;
    for (BaseKeyframeAnimation<?, Path> animation : mask.getMaskAnimations()) {
      addAnimation(animation);
      animation.addUpdateListener(pathChangedListener);
    }
  }

  void setMatteLayer(LayerView matteLayer) {
    this.matteLayer = matteLayer;
  }

  @Override public void draw(@NonNull Canvas canvas) {
    if (!isVisible() || mainCanvasPaint.getAlpha() == 0) {
      return;
    }

    // Make a list of all parent layers.
    transformLayers.clear();
    LayerView parent = parentLayer;
    while (parent != null) {
      transformLayers.add(parent);
      parent = parent.getParentLayer();
    }

    if (!hasMasks() && !hasMatte()) {
      int mainCanvasCount = saveCanvas(canvas);
      if (precompWidth != 0 || precompHeight != 0) {
        canvas.clipRect(0, 0, precompWidth, precompHeight);
      }
      // Now apply the parent transformations from the top down.
      for (int i = transformLayers.size() - 1; i >= 0; i--) {
        LayerView layer = transformLayers.get(i);
        applyTransformForLayer(canvas, layer);
      }
      drawImageIfNeeded(canvas);
      super.draw(canvas);
      canvas.restoreToCount(mainCanvasCount);
      return;
    }


    BitmapCanvas bitmapCanvas =
        canvasPool.acquire(canvas.getWidth(), canvas.getHeight(), Bitmap.Config.ARGB_8888);

    // Now apply the parent transformations from the top down.
    bitmapCanvas.save();
    drawImageIfNeeded(bitmapCanvas);
    for (int i = transformLayers.size() - 1; i >= 0; i--) {
      LayerView layer = transformLayers.get(i);
      applyTransformForLayer(bitmapCanvas, layer);
    }
    super.draw(bitmapCanvas);

    rect.set(0, 0, canvas.getWidth(), canvas.getHeight());
    if (hasMasks()) {
      List<Mask> masks = mask.getMasks();
      List<BaseKeyframeAnimation<?, Path>> maskAnimations = mask.getMaskAnimations();
      for (int i = 0; i < masks.size(); i++) {
        applyMask(bitmapCanvas, masks.get(i), maskAnimations.get(i));
      }
    }
    bitmapCanvas.restore();

    if (hasMatte()) {
      bitmapCanvas.saveLayer(rect, mattePaint, SAVE_FLAGS);
      matteLayer.draw(bitmapCanvas);
      bitmapCanvas.restore();
    }

    if (precompWidth != 0 || precompHeight != 0) {
      canvas.clipRect(0, 0, precompWidth, precompHeight);
    }
    canvas.drawBitmap(bitmapCanvas.getBitmap(), 0, 0, null);
    canvasPool.release(bitmapCanvas);
  }

  private void applyMask(BitmapCanvas canvas, Mask mask,
      BaseKeyframeAnimation<?, Path> maskAnimation) {
    switch (mask.getMaskMode()) {
      case MaskModeSubtract:
        maskPaint.setXfermode(DST_OUT);
        break;
      case MaskModeAdd:
      default:
        maskPaint.setXfermode(DST_IN);
    }

    canvas.saveLayer(rect, maskPaint, SAVE_FLAGS);
    for (int i = transformLayers.size() - 1; i >= 0; i--) {
      LayerView layer = transformLayers.get(i);
      applyTransformForLayer(canvas, layer);
    }
    applyTransformForLayer(canvas, this);
    canvas.drawPath(maskAnimation.getValue(), mainCanvasPaint);
    canvas.restore();
  }

  private void drawImageIfNeeded(Canvas canvas) {
    if (!composition.hasImages()) {
      return;
    }
    String refId = layerModel.getRefId();
    Bitmap bitmap = getLottieDrawable().getImageAsset(refId);
    if (bitmap == null) {
      return;
    }

    canvas.save();
    applyTransformForLayer(canvas, this);
    canvas.drawBitmap(bitmap, 0, 0 ,imagePaint);
    canvas.restore();
  }

  boolean hasMatte() {
    return matteLayer != null;
  }

  boolean hasMasks() {
    return mask != null && !mask.getMaskAnimations().isEmpty();
  }

  @Override public void setProgress(@FloatRange(from = 0f, to = 1f) float progress) {
    // TODO: use this.
    // progress -= layerModel.getStartProgress();
    progress *= layerModel.getTimeStretch();


    super.setProgress(progress);
    if (matteLayer != null) {
      matteLayer.setProgress(progress);
    }
  }

  long getId() {
    return layerModel.getId();
  }

  @Override public String toString() {
    return layerModel.toString();
  }
}
