Spaces:
Running
on
CPU Upgrade
Running
on
CPU Upgrade
File size: 1,851 Bytes
bde82a3 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
import React from "react"
interface CommentWithTimeSeeksProps {
onSeek: (timeInSec: number) => void;
children: string;
className?: string;
linkClassName?: string;
}
export const CommentWithTimeSeeks: React.FC<CommentWithTimeSeeksProps> = ({ onSeek, children, className, linkClassName }) => {
// This function converts a time string like "HH:MM:SS", "MM:SS" or "SS" to seconds.
const convertTimeToSeconds = (timeString: string): number => {
const units = timeString.split(":").map(unit => parseInt(unit, 10));
const seconds = units.reverse().reduce((acc, unit, index) => acc + unit * Math.pow(60, index), 0);
return seconds;
};
// This function parses the text and replaces time seeks with clickable spans.
const renderWithTimeSeek = (text: string) => {
const timeSeekPattern = /\b(\d{1,2}:)?\d{1,2}:\d{2}\b/g;
const nodes = [];
let lastIndex = 0;
text.replace(timeSeekPattern, (match, ...args) => {
const index = args[args.length - 2]; // The second to last argument is the index of the match
nodes.push(
<React.Fragment key={lastIndex}>
{text.slice(lastIndex, index)}{/* Text before the match */}
<span
className={linkClassName}
onClick={() => onSeek(convertTimeToSeconds(match))}
>
{match}
</span>
</React.Fragment>
);
lastIndex = index + match.length; // Update lastIndex to end of the current match
return match; // return value is unused but needed for `replace` to work
});
// Append the remaining text after the last match (if any)
if (lastIndex < text.length) {
nodes.push(<React.Fragment key={lastIndex}>{text.slice(lastIndex)}</React.Fragment>);
}
return nodes;
};
return <p className={className}>{renderWithTimeSeek(children)}</p>;
};
|