import { getSecondsBetween } from '@suno/studiokit/timeMapping';
import {
  getWarpBeatsFromSeconds,
  getWarpSecondsFromBeats,
} from '@suno/studiokit/warpUtils';

import { EditTiming } from '../edit2025/types';
import { StudioClip } from './types';

// this returns an array of two numbers because some positions are best thought of as two positions.
// specifically, the end of a loop is technically also the start of the loop
const getClipRelativePoint = (
  timing: EditTiming,
  clip: StudioClip,
  absoluteBeats: number,
  ignoreLoop: boolean = false
): [number, number] => {
  let scaledAbsoluteBeats = absoluteBeats;

  if (!clip.warp?.enabled) {
    const secondsFromStart = getSecondsBetween(
      clip.startBeats,
      absoluteBeats,
      timing
    );

    const readStartSeconds = getWarpSecondsFromBeats(
      clip.warp,
      clip.readStartBeats
    );

    const clipBeatsFromStart = getWarpBeatsFromSeconds(
      clip.warp,
      secondsFromStart + readStartSeconds
    );

    scaledAbsoluteBeats =
      clip.startBeats + (clipBeatsFromStart - clip.readStartBeats);
  }

  const adjustedForTimelineOffset = scaledAbsoluteBeats - clip.startBeats;
  const adjustedForOriginalReadStart =
    clip.readStartBeats + adjustedForTimelineOffset;
  if (ignoreLoop || adjustedForOriginalReadStart < clip.loop.endBeats) {
    return [adjustedForOriginalReadStart, adjustedForOriginalReadStart];
  }

  const loopLength = clip.loop.endBeats - clip.loop.startBeats;
  const distanceIntoLoop =
    (adjustedForOriginalReadStart - clip.loop.startBeats) % loopLength;
  if (
    (clip.startBeats - clip.readStartBeats - scaledAbsoluteBeats) %
      loopLength ===
    0
  ) {
    return [clip.loop.startBeats, clip.loop.endBeats];
  }

  return [
    clip.loop.startBeats + distanceIntoLoop,
    clip.loop.startBeats + distanceIntoLoop,
  ];
};

export default getClipRelativePoint;
