<template>
  <div class="page-container" ref="container">
    <div class="layout-buttons">
      <button @click="switchLayout('strategy1')">默认布局</button>
      <button @click="switchLayout('strategy2')">策略2布局</button>
      <button @click="switchLayout('strategy3')">策略3布局</button>
    </div>

    <div>屏幕宽度：{{ screenWidth }}px</div>

    <div class="components-container">
      <component
        v-for="component in components"
        :is="component.comp"
        :key="component.id"
        class="component"
        :style="getComponentStyle(component)"
      ></component>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, onMounted } from 'vue';
import Comp1 from './comp1.vue';
import Comp2 from './comp2.vue';
import Comp3 from './comp3.vue';
import Comp4 from './comp4.vue';

interface ComponentState {
  id: string;
  comp: ReturnType<typeof defineComponent>;
  x: number | string;
  y: number | string;
  width?: number | string;
  minWidth?: number | string;
  maxWidth?: number | string;
  height: number;
  zIndex?: number | string;
  background?: string;
}

const components = ref<ComponentState[]>([]);
const container = ref<HTMLElement | null>(null);
const screenWidth = ref(0);
const screenHeight = ref(0);
const layoutComp1 = shallowRef(Comp1);
const layoutComp2 = shallowRef(Comp2);
const layoutComp3 = shallowRef(Comp3);
const layoutComp4 = shallowRef(Comp4);

const layoutCompMap = {
  comp1: layoutComp1,
  comp2: layoutComp2,
  comp3: layoutComp3,
  comp4: layoutComp4,
};

const containerWidth = ref(0);
const containerHeight = ref(0);
const currentLayoutStrategy = ref<LayoutStrategy>('strategy1');

onMounted(() => {
  const observedElement = document.querySelector('#app');
  if (observedElement) {
    const resizeObserver = new ResizeObserver((entries) => {
      const entry = entries[0];
      const { width, height } = entry.contentRect;
      screenWidth.value = width;
      screenHeight.value = height;

      console.log('screenWidth', width);

      const compStyles = loadComponentWidthRange(currentLayoutStrategy.value, width);
      if (compStyles) {
        setComponentStyleByStrategy(compStyles);
      }
      // const screenResolution = getComponentWidthRange(width);
      // if (screenResolution) {
      //   setComponentStyleByStrategy(screenResolution.compStyles);
      // }
    });
    resizeObserver.observe(observedElement);
  }
});

type Coordinate = number | [number, number];

type ComponentWidthRange = {
  width: [number, number];
  height: number;
  compName: string;
  background?: string;
  x: Coordinate;
  y: Coordinate;
};

type ScreenResolutionMap = {
  [resolutionRange: string]: {
    layoutStrategy: string;
    compStyles: ComponentWidthRange[];
  };
};

type LayoutStrategy = 'strategy1' | 'strategy2' | 'strategy3';

type Resolution = {
  [resolutionRange: string]: ComponentWidthRange[];
};

type ScreenResolutionMap1 = {
  layoutStrategy: LayoutStrategy;
  resolution: Resolution;
};

const screenResolutionMap1: ScreenResolutionMap1[] = [
  {
    layoutStrategy: 'strategy1',
    resolution: {
      '[0, 768]': [
        { width: [498, 498], compName: 'comp1', height: 550, background: 'red', x: 266, y: 0 },
        { width: [498, 498], compName: 'comp2', height: 304, background: '#ccdc', x: [266, 266], y: 550 },
        { width: [266, 266], compName: 'comp3', height: 856, background: '#5E6673', x: 0, y: 0 },
        { width: [768, 768], compName: 'comp4', height: 304, background: 'blue', x: 0, y: 856 },
      ],
      '[769, 1280]': [
        { width: [498, 836], compName: 'comp1', height: 610, background: 'red', x: 0, y: 0 },
        { width: [135, 222], compName: 'comp2', height: 610, background: '#ccdc', x: [498, 836], y: 0 },
        { width: [135, 222], compName: 'comp3', height: 908, background: '#5E6673', x: [768, 1012], y: 0 },
        { width: [768, 1012], compName: 'comp4', height: 356, background: 'blue', x: 0, y: 610 },
      ],
      '[1281, 1440]': [
        { width: [836, 836], compName: 'comp1', height: 610, background: 'red', x: 0, y: 0 },
        { width: [222, 302], compName: 'comp2', height: 610, background: '#ccdc', x: 836, y: 0 },
        { width: [222, 302], compName: 'comp3', height: 908, background: '#5E6673', x: [1058, 1138], y: 0 },
        { width: [1012, 1138], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 610 },
      ],
      '[1441, 1920]': [
        { width: [836, 1196], compName: 'comp1', height: 610, background: 'red', x: 0, y: 0 },
        { width: [302, 362], compName: 'comp2', height: 610, background: '#ccdc', x: [836, 1196], y: 0 },
        { width: [302, 362], compName: 'comp3', height: 908, background: '#5E6673', x: [1138, 1158], y: 0 },
        { width: [1138, 1558], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 610 },
      ],
      '[1921, 3860]': [
        { width: [1196, 1696], compName: 'comp1', height: 610, background: 'red', x: 0, y: 0 },
        { width: [362, 432], compName: 'comp2', height: 610, background: '#ccdc', x: [1196, 1696], y: 0 },
        { width: [362, 432], compName: 'comp3', height: 908, background: '#5E6673', x: [1558, 2128], y: 0 },
        { width: [1558, 2128], compName: 'comp4', height: 356, background: 'blue', x: 0, y: 610 },
      ],
    },
  },
  {
    layoutStrategy: 'strategy2',
    resolution: {
      '[0, 768]': [
        { width: [200, 300], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [300, 400], compName: 'comp2', height: 500, background: '#ccdc', x: [200, 300], y: 0 },
        { width: [300, 400], compName: 'comp3', height: 970, background: '#5E6673', x: [500, 700], y: 0 },
        { width: [300, 400], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[769, 1280]': [
        { width: [200, 300], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [300, 400], compName: 'comp2', height: 500, background: '#ccdc', x: [200, 300], y: 0 },
        { width: [300, 400], compName: 'comp3', height: 970, background: '#5E6673', x: [500, 700], y: 0 },
        { width: [300, 400], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[1281, 1440]': [
        { width: [280, 400], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
        { width: [350, 450], compName: 'comp2', height: 500, background: '#ccdc', x: [280, 400], y: 0 },
        { width: [350, 450], compName: 'comp3', height: 970, background: '#5E6673', x: [630, 850], y: 0 },
        { width: [350, 450], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 600 },
      ],
      '[1441, 1920]': [
        { width: [320, 420], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [400, 500], compName: 'comp2', height: 500, background: '#ccdc', x: [320, 420], y: 0 },
        { width: [400, 500], compName: 'comp3', height: 970, background: '#5E6673', x: [720, 920], y: 0 },
        { width: [400, 500], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[1921, 3860]': [
        { width: [800, 1000], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
        { width: [500, 600], compName: 'comp2', height: 600, background: '#ccdc', x: [800, 1000], y: 0 },
        { width: [500, 600], compName: 'comp3', height: 1070, background: '#5E6673', x: [1300, 1600], y: 0 },
        { width: [500, 600], compName: 'comp4', height: 510, background: 'blue', x: 0, y: 600 },
      ],
    },
  },
  {
    layoutStrategy: 'strategy3',
    resolution: {
      '[0, 768]': [
        { width: [200, 300], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [300, 400], compName: 'comp2', height: 500, background: '#ccdc', x: [200, 300], y: 0 },
        { width: [300, 400], compName: 'comp3', height: 970, background: '#5E6673', x: [500, 700], y: 0 },
        { width: [300, 400], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[769, 1280]': [
        { width: [200, 300], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [300, 400], compName: 'comp2', height: 500, background: '#ccdc', x: [200, 300], y: 0 },
        { width: [300, 400], compName: 'comp3', height: 970, background: '#5E6673', x: [500, 700], y: 0 },
        { width: [300, 400], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[1281, 1440]': [
        { width: [280, 400], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
        { width: [350, 450], compName: 'comp2', height: 500, background: '#ccdc', x: [280, 400], y: 0 },
        { width: [350, 450], compName: 'comp3', height: 970, background: '#5E6673', x: [630, 850], y: 0 },
        { width: [350, 450], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 600 },
      ],
      '[1441, 1920]': [
        { width: [320, 420], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
        { width: [400, 500], compName: 'comp2', height: 500, background: '#ccdc', x: [320, 420], y: 0 },
        { width: [400, 500], compName: 'comp3', height: 970, background: '#5E6673', x: [720, 920], y: 0 },
        { width: [400, 500], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
      ],
      '[1921, 3860]': [
        { width: [800, 1000], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
        { width: [500, 600], compName: 'comp2', height: 600, background: '#ccdc', x: [800, 1000], y: 0 },
        { width: [500, 600], compName: 'comp3', height: 1070, background: '#5E6673', x: [1300, 1600], y: 0 },
        { width: [500, 600], compName: 'comp4', height: 510, background: 'blue', x: 0, y: 600 },
      ],
    },
  },
];

// 创建屏幕分辨率宽度到组件宽度区间的映射表
const screenResolutionMap: ScreenResolutionMap = {
  '[1024, 1280]': {
    layoutStrategy: 'strategy1',
    compStyles: [
      { width: [200, 300], compName: 'comp1', height: 500, background: 'red', x: 0, y: 0 },
      { width: [300, 400], compName: 'comp2', height: 500, background: '#ccdc', x: [200, 300], y: 0 },
      { width: [300, 400], compName: 'comp3', height: 970, background: '#5E6673', x: [500, 700], y: 0 },
      { width: [300, 400], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
    ],
  },
  '[1281, 1440]': {
    layoutStrategy: 'strategy2',
    compStyles: [
      { width: [280, 400], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
      { width: [350, 450], compName: 'comp2', height: 500, background: '#ccdc', x: [280, 400], y: 0 },
      { width: [350, 450], compName: 'comp3', height: 970, background: '#5E6673', x: [630, 850], y: 0 },
      { width: [350, 450], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 600 },
    ],
  },
  '[1441, 1920]': {
    layoutStrategy: 'strategy3',
    compStyles: [
      { width: [320, 420], compName: 'comp1', height: 500, background: 'red', x: [400, 500], y: 0 },
      { width: [400, 500], compName: 'comp2', height: 500, background: '#ccdc', x: 0, y: 0 },
      { width: [400, 500], compName: 'comp3', height: 970, background: '#5E6673', x: [720, 920], y: 0 },
      { width: [400, 500], compName: 'comp4', height: 410, background: 'blue', x: 0, y: 500 },
    ],
  },
  '[1921, 3860]': {
    layoutStrategy: 'strategy4',
    compStyles: [
      { width: [800, 1000], compName: 'comp1', height: 600, background: 'red', x: 0, y: 0 },
      { width: [500, 600], compName: 'comp2', height: 600, background: '#ccdc', x: [800, 1000], y: 0 },
      { width: [500, 600], compName: 'comp3', height: 1070, background: '#5E6673', x: [1300, 1600], y: 0 },
      { width: [500, 600], compName: 'comp4', height: 510, background: 'blue', x: 0, y: 600 },
    ],
  },
};

function getComponentWidthRange(screenWidth: number): ScreenResolutionMap | null {
  for (const resolutionRange in screenResolutionMap) {
    const [minWidth, maxWidth] = JSON.parse(resolutionRange.replace('[', '[').replace(']', ']'));
    if (screenWidth >= minWidth && screenWidth <= maxWidth) {
      return screenResolutionMap[resolutionRange];
    }
  }
  return null; // 如果没有找到对应的分辨率范围，则返回null
}

const getComponentWidthRange1 = (screenWidth: number, resolution: Resolution): ComponentWidthRange[] | null => {
  for (const resolutionRange in resolution) {
    const [minWidth, maxWidth] = JSON.parse(resolutionRange.replace('[', '[').replace(']', ']'));
    if (screenWidth >= minWidth && screenWidth <= maxWidth) {
      return resolution[resolutionRange];
    }
  }
  return null; // 如果没有找到对应的分辨率范围，则返回null
};

const loadComponentWidthRange = (layoutStrategy: LayoutStrategy, screenWidth: number): ComponentWidthRange[] => {
  let layoutStyles: ComponentWidthRange[] | null = [];
  for (let item of screenResolutionMap1) {
    console.log('layoutStrategy', item.layoutStrategy);
    if (item.layoutStrategy === layoutStrategy) {
      layoutStyles = getComponentWidthRange1(screenWidth, item.resolution);
      break;
    }
  }
  if (!layoutStyles || layoutStyles.length === 0) {
    layoutStyles = getComponentWidthRange1(screenWidth, screenResolutionMap1[0].resolution) as ComponentWidthRange[];
  }
  return layoutStyles;
};

const setComponentStyleByStrategy = (compStyles: ComponentWidthRange[]) => {
  components.value = compStyles.map((item) => {
    const compPosition = getRelativePosition(item, screenWidth.value);
    return {
      id: item.compName,
      comp: layoutCompMap[item.compName],
      x: compPosition.x,
      y: item.y,
      width: compPosition.width,
      height: item.height,
      zIndex: 1,
      background: item.background,
    };
  });
};

/**
 * 计算组件相对位置和大小的函数
 * @param compStyles - 组件的样式信息
 * @param screenWidth - 屏幕宽度
 * @returns 组件的计算位置和大小
 */
function getRelativePosition(compStyles: ComponentWidthRange, screenWidth: number): { x: string; width: string } {
  const { x, width } = compStyles;

  // 解析区间值
  const parseRange = (value: Coordinate): { min: number; max: number } => {
    if (Array.isArray(value)) {
      const [min, max] = value;
      return { min, max };
    }
    return { min: value, max: value };
  };

  // 转换为基于屏幕宽度的百分比
  const toPercentage = (
    range: { min: number; max: number },
    screenWidth: number,
  ): { minPercentage: number; maxPercentage: number } => {
    const minPercentage = (range.min / screenWidth) * 100;
    const maxPercentage = (range.max / screenWidth) * 100;
    return { minPercentage, maxPercentage };
  };

  // 解析并计算宽度和x值
  const widthRange = parseRange(width);
  const xRange = parseRange(x);

  const widthPercentage = toPercentage(widthRange, screenWidth);
  const xPercentage = toPercentage(xRange, screenWidth);

  // 假设我们取区间的中间值作为最终值
  const finalWidth = ((widthPercentage.minPercentage + widthPercentage.maxPercentage) / 2).toFixed(2);
  const finalX = ((xPercentage.minPercentage + xPercentage.maxPercentage) / 2).toFixed(2);

  return {
    x: finalX,
    width: finalWidth,
  };
}

onMounted(async () => {
  if (container.value) {
    containerWidth.value = container.value.clientWidth;
    containerHeight.value = container.value.clientHeight;
  }
});

const switchLayout = (layoutStrategy: LayoutStrategy) => {};

function getComponentStyle(component: ComponentState) {
  return {
    position: 'absolute',
    left: `${component.x}%`,
    top: `${component.y}px`,
    width: `${component.width}%`,
    height: `${component.height}px`,
    zIndex: component.zIndex,
    background: component.background,
    transition: 'all 0.25s ease',
  };
}
</script>

<style lang="less" scoped>
.page-container {
  width: 100%;
  height: 100%;
  position: relative;
  .layout-buttons {
    width: 100%;
    height: 5%;
  }
  .components-container {
    position: relative;
    width: 100%;
    height: 95%;
    border: 1px solid #ccc;
    overflow: hidden;
    .component {
      background-color: lightgray;
      border: 1px solid #ccc;
      box-shadow: 2px 2px 5px rgba(0, 0, 0, 0.1);
      transition: all 0.25s ease;
      font-size: 24px;
      color: #fff;
    }
  }
}
</style>
