mirror of
https://github.com/iib0011/omni-tools.git
synced 2025-11-13 19:42:38 +05:30
Merge pull request #59 from iib0011/chesterkxng
feat: convert-seconds-to-time, convert-time-to-seconds
This commit is contained in:
commit
26ae9e06ee
10 changed files with 442 additions and 3 deletions
|
|
@ -0,0 +1,50 @@
|
|||
import { describe, it, expect } from 'vitest';
|
||||
import { convertSecondsToTime } from './service';
|
||||
|
||||
describe('convertSecondsToTime', () => {
|
||||
it('should convert seconds to a formatted time string', () => {
|
||||
const result = convertSecondsToTime('3661', true);
|
||||
expect(result).toBe('01:01:01');
|
||||
});
|
||||
|
||||
it('should handle zero seconds', () => {
|
||||
const result = convertSecondsToTime('0', true);
|
||||
expect(result).toBe('00:00:00');
|
||||
});
|
||||
|
||||
it('should handle seconds less than a minute', () => {
|
||||
const result = convertSecondsToTime('45', true);
|
||||
expect(result).toBe('00:00:45');
|
||||
});
|
||||
|
||||
it('should handle seconds equal to a full minute', () => {
|
||||
const result = convertSecondsToTime('60', true);
|
||||
expect(result).toBe('00:01:00');
|
||||
});
|
||||
|
||||
it('should handle seconds equal to a full hour', () => {
|
||||
const result = convertSecondsToTime('3600', true);
|
||||
expect(result).toBe('01:00:00');
|
||||
});
|
||||
it('should handle seconds equal to a full hour without padding', () => {
|
||||
const result = convertSecondsToTime('3600', false);
|
||||
expect(result).toBe('1:0:0');
|
||||
});
|
||||
|
||||
it('should handle large numbers of seconds with padding', () => {
|
||||
const result = convertSecondsToTime('7325', true);
|
||||
expect(result).toBe('02:02:05');
|
||||
});
|
||||
it('should handle large numbers of seconds without padding', () => {
|
||||
const result = convertSecondsToTime('7325', false);
|
||||
expect(result).toBe('2:2:5');
|
||||
});
|
||||
it('should handle numbers of seconds on multilines without padding', () => {
|
||||
const result = convertSecondsToTime('7325\n3600\n5c\n60', false);
|
||||
expect(result).toBe('2:2:5\n1:0:0\n\n0:1:0');
|
||||
});
|
||||
it('should handle numbers of seconds on multilines with padding', () => {
|
||||
const result = convertSecondsToTime('7325\n3600\n5c\n60', true);
|
||||
expect(result).toBe('02:02:05\n01:00:00\n\n00:01:00');
|
||||
});
|
||||
});
|
||||
111
src/pages/tools/time/convert-seconds-to-time/index.tsx
Normal file
111
src/pages/tools/time/convert-seconds-to-time/index.tsx
Normal file
|
|
@ -0,0 +1,111 @@
|
|||
import { Box } from '@mui/material';
|
||||
import React, { useState } from 'react';
|
||||
import ToolContent from '@components/ToolContent';
|
||||
import { ToolComponentProps } from '@tools/defineTool';
|
||||
import ToolTextInput from '@components/input/ToolTextInput';
|
||||
import ToolTextResult from '@components/result/ToolTextResult';
|
||||
import { GetGroupsType } from '@components/options/ToolOptions';
|
||||
import { CardExampleType } from '@components/examples/ToolExamples';
|
||||
import CheckboxWithDesc from '@components/options/CheckboxWithDesc';
|
||||
import { convertSecondsToTime } from './service';
|
||||
|
||||
const initialValues = {
|
||||
paddingFlag: false
|
||||
};
|
||||
type InitialValuesType = typeof initialValues;
|
||||
const exampleCards: CardExampleType<InitialValuesType>[] = [
|
||||
{
|
||||
title: '1 Second, 1 Minute, 1 Hour',
|
||||
description:
|
||||
"In this example, we convert 1 second, 60 seconds, and 3600 seconds to clock format. We don't use the zero-padding option and get three simple output values – 0:0:1 for 1 second, 0:1:0 for 60 seconds (1 minute), and 1:0:0 for 3600 seconds (1 hour).",
|
||||
sampleText: `1
|
||||
60
|
||||
3600`,
|
||||
sampleResult: `0:0:1
|
||||
0:1:0
|
||||
1:0:0`,
|
||||
sampleOptions: { paddingFlag: false }
|
||||
},
|
||||
{
|
||||
title: 'HH:MM:SS Digital Clock',
|
||||
description:
|
||||
"In this example, we enable the padding option and output digital clock time in the format HH:MM:SS. The first two integer timestamps don't contain a full minute and the third timestamp doesn't contain a full hour, there we get zeros in the minutes or hours positions in output.",
|
||||
sampleText: `0
|
||||
46
|
||||
890
|
||||
18305
|
||||
40271
|
||||
86399`,
|
||||
sampleResult: `00:00:00
|
||||
00:00:46
|
||||
00:14:50
|
||||
05:05:05
|
||||
11:11:11
|
||||
23:59:59`,
|
||||
sampleOptions: { paddingFlag: true }
|
||||
},
|
||||
{
|
||||
title: 'More Than a Day',
|
||||
description:
|
||||
"The values of all input seconds in this example are greater than the number of seconds in a day (86400 seconds). As our algorithm doesn't limit the time to just 23:59:59 hours, it can find the exact number of hours in large inputs.",
|
||||
sampleText: `86401
|
||||
123456
|
||||
2159999
|
||||
|
||||
3600000
|
||||
101010101`,
|
||||
sampleResult: `24:00:01
|
||||
34:17:36
|
||||
599:59:59
|
||||
|
||||
1000:00:00
|
||||
28058:21:41`,
|
||||
sampleOptions: { paddingFlag: true }
|
||||
}
|
||||
];
|
||||
|
||||
export default function SecondsToTime({
|
||||
title,
|
||||
longDescription
|
||||
}: ToolComponentProps) {
|
||||
const [input, setInput] = useState<string>('');
|
||||
const [result, setResult] = useState<string>('');
|
||||
|
||||
const compute = (optionsValues: typeof initialValues, input: string) => {
|
||||
setResult(convertSecondsToTime(input, optionsValues.paddingFlag));
|
||||
};
|
||||
|
||||
const getGroups: GetGroupsType<InitialValuesType> | null = ({
|
||||
values,
|
||||
updateField
|
||||
}) => [
|
||||
{
|
||||
title: 'Time Padding',
|
||||
component: (
|
||||
<Box>
|
||||
<CheckboxWithDesc
|
||||
onChange={(val) => updateField('paddingFlag', val)}
|
||||
checked={values.paddingFlag}
|
||||
title={'Add Padding'}
|
||||
description={'Add zero padding to hours, minutes, and seconds.'}
|
||||
/>
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
];
|
||||
|
||||
return (
|
||||
<ToolContent
|
||||
title={title}
|
||||
input={input}
|
||||
inputComponent={<ToolTextInput value={input} onChange={setInput} />}
|
||||
resultComponent={<ToolTextResult value={result} />}
|
||||
initialValues={initialValues}
|
||||
getGroups={getGroups}
|
||||
setInput={setInput}
|
||||
compute={compute}
|
||||
toolInfo={{ title: `What is a ${title}?`, description: longDescription }}
|
||||
exampleCards={exampleCards}
|
||||
/>
|
||||
);
|
||||
}
|
||||
15
src/pages/tools/time/convert-seconds-to-time/meta.ts
Normal file
15
src/pages/tools/time/convert-seconds-to-time/meta.ts
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
import { defineTool } from '@tools/defineTool';
|
||||
import { lazy } from 'react';
|
||||
|
||||
export const tool = defineTool('time', {
|
||||
path: 'convert-seconds-to-time',
|
||||
name: 'Convert Seconds to Time',
|
||||
icon: 'fluent-mdl2:time-picker',
|
||||
description:
|
||||
'With this browser-based application, you can convert seconds to clock time. Given the seconds input value, it converts them into full hours (H), minutes (M), and seconds (S) and prints them in human-readable clock format (H:M:S or HH:MM:SS) in the output field.',
|
||||
shortDescription: 'Quicky convert seconds to clock time in H:M:S format.',
|
||||
keywords: ['convert', 'seconds', 'time', 'clock'],
|
||||
longDescription:
|
||||
'This is a quick online utility for converting seconds to H:M:S or HH:MM:SS digital clock time format. It calculates the number of full hours, full minutes, and remaining seconds from the input seconds and outputs regular clock time. For example, 100 seconds is 1 minute and 40 seconds so we get the clock time 00:01:40. To convert seconds to human-readable time we use the Euclidean division algorithm, also known as a division with remainder. If "n" is the input seconds value, then the hours "h" are calculated from the formula n = 3600×h + r, where r is the remainder of dividing n by 3600. Minutes "m" are calculated from the formula r = 60×m + s, and seconds "s" is the remainder of dividing r by 60. For example, if the input n = 4000, then 4000 = 3600×1 + 400. From here we find that the full hours value is 1. Next, the remaining 400 seconds are equal to 60×6 + 40. From here, there are 6 full minutes and 40 more remaining seconds. Thus, we find that 4000 seconds in human time 1 hour, 6 minutes, and 40 seconds. By default, the program outputs the clock time in a padded HH:MM:SS format (i.e. 01:06:40) but you can also disable the padding option and get just H:M:S (i.e. 1:6:40). Timeabulous!',
|
||||
component: lazy(() => import('./index'))
|
||||
});
|
||||
32
src/pages/tools/time/convert-seconds-to-time/service.ts
Normal file
32
src/pages/tools/time/convert-seconds-to-time/service.ts
Normal file
|
|
@ -0,0 +1,32 @@
|
|||
import { containsOnlyDigits } from '@utils/string';
|
||||
|
||||
function compute(seconds: string, paddingFlag: boolean): string {
|
||||
if (!containsOnlyDigits(seconds)) {
|
||||
return '';
|
||||
}
|
||||
const hours = Math.floor(Number(seconds) / 3600);
|
||||
const minutes = Math.floor((Number(seconds) % 3600) / 60);
|
||||
const secs = Number(seconds) % 60;
|
||||
return paddingFlag
|
||||
? [hours, minutes, secs]
|
||||
.map((unit) => String(unit).padStart(2, '0')) // Ensures two-digit format
|
||||
.join(':')
|
||||
: [hours, minutes, secs].join(':');
|
||||
}
|
||||
|
||||
export function convertSecondsToTime(
|
||||
input: string,
|
||||
paddingFlag: boolean
|
||||
): string {
|
||||
const result: string[] = [];
|
||||
|
||||
const lines = input.split('\n');
|
||||
|
||||
lines.forEach((line) => {
|
||||
const seconds = line.trim();
|
||||
const time = compute(seconds, paddingFlag);
|
||||
result.push(time);
|
||||
});
|
||||
|
||||
return result.join('\n');
|
||||
}
|
||||
|
|
@ -0,0 +1,57 @@
|
|||
import { describe, it, expect } from 'vitest';
|
||||
import { convertTimetoSeconds } from './service';
|
||||
|
||||
describe('convertSecondsToTime', () => {
|
||||
it('should convert valid time strings to seconds', () => {
|
||||
const input = '01:02:03\n00:45:30\n12:00';
|
||||
const expectedOutput = '3723\n2730\n43200';
|
||||
expect(convertTimetoSeconds(input)).toBe(expectedOutput);
|
||||
});
|
||||
|
||||
it('should handle single-line input', () => {
|
||||
const input = '00:01:30';
|
||||
const expectedOutput = '90';
|
||||
expect(convertTimetoSeconds(input)).toBe(expectedOutput);
|
||||
});
|
||||
|
||||
it('should throw an error for invalid time format', () => {
|
||||
const input = '01:02:03\n01:02:03:04';
|
||||
expect(() => convertTimetoSeconds(input)).toThrow(
|
||||
'Time contains more than 3 parts on line 2'
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw an error for non-numeric values (minutes)', () => {
|
||||
const input = '01:XX:03';
|
||||
expect(() => convertTimetoSeconds(input)).toThrow(
|
||||
"Time doesn't contain valid minutes on line 1"
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw an error for non-numeric values (hours)', () => {
|
||||
const input = '0x:00:03';
|
||||
expect(() => convertTimetoSeconds(input)).toThrow(
|
||||
"Time doesn't contain valid hours on line 1"
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw an error for non-numeric values (seconds)', () => {
|
||||
const input = '01:00:0s';
|
||||
expect(() => convertTimetoSeconds(input)).toThrow(
|
||||
"Time doesn't contain valid seconds on line 1"
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw an error for non-numeric values multi lines (seconds)', () => {
|
||||
const input = '01:00:00\n01:00:0s';
|
||||
expect(() => convertTimetoSeconds(input)).toThrow(
|
||||
"Time doesn't contain valid seconds on line 2"
|
||||
);
|
||||
});
|
||||
|
||||
it('should handle empty input', () => {
|
||||
const input = '';
|
||||
const expectedOutput = '';
|
||||
expect(convertTimetoSeconds(input)).toBe(expectedOutput);
|
||||
});
|
||||
});
|
||||
99
src/pages/tools/time/convert-time-to-seconds/index.tsx
Normal file
99
src/pages/tools/time/convert-time-to-seconds/index.tsx
Normal file
|
|
@ -0,0 +1,99 @@
|
|||
import React, { useState } from 'react';
|
||||
import ToolContent from '@components/ToolContent';
|
||||
import { ToolComponentProps } from '@tools/defineTool';
|
||||
import ToolTextInput from '@components/input/ToolTextInput';
|
||||
import ToolTextResult from '@components/result/ToolTextResult';
|
||||
import { CardExampleType } from '@components/examples/ToolExamples';
|
||||
import { convertTimetoSeconds } from './service';
|
||||
|
||||
const initialValues = {};
|
||||
type InitialValuesType = typeof initialValues;
|
||||
const exampleCards: CardExampleType<InitialValuesType>[] = [
|
||||
{
|
||||
title: 'Multiple Clock Times',
|
||||
description:
|
||||
'In this example, we convert multiple clock times to seconds. Each clock time is listed on a new line and the spacing between input times is preserved in the output.',
|
||||
sampleText: `00:00:00
|
||||
|
||||
00:00:01
|
||||
00:01:00
|
||||
01:00:00
|
||||
01:59:59
|
||||
12:00:00
|
||||
18:30:30
|
||||
23:59:59
|
||||
|
||||
24:00:00`,
|
||||
sampleResult: `0
|
||||
|
||||
1
|
||||
60
|
||||
3600
|
||||
7199
|
||||
43200
|
||||
66630
|
||||
86399
|
||||
|
||||
86400`,
|
||||
sampleOptions: {}
|
||||
},
|
||||
{
|
||||
title: 'Partial Clock Times',
|
||||
description:
|
||||
'This example finds how many seconds there are in clock times that are partially written. Some of the clock times contain just the hours and some others contain just hours and minutes.',
|
||||
sampleText: `1
|
||||
1:10
|
||||
14:44
|
||||
23`,
|
||||
sampleResult: `3600
|
||||
4200
|
||||
53040
|
||||
82800`,
|
||||
sampleOptions: {}
|
||||
},
|
||||
{
|
||||
title: 'Time Beyond 24 Hours',
|
||||
description:
|
||||
'In this example, we go beyond the regular 24-hour clock. In fact, we even go beyond 60 minutes and 60 seconds.',
|
||||
sampleText: `24:00:01
|
||||
48:00:00
|
||||
72
|
||||
|
||||
00:100:00
|
||||
100:100:100`,
|
||||
sampleResult: `86401
|
||||
172800
|
||||
259200
|
||||
|
||||
6000
|
||||
366100`,
|
||||
sampleOptions: {}
|
||||
}
|
||||
];
|
||||
|
||||
export default function TimeToSeconds({
|
||||
title,
|
||||
longDescription
|
||||
}: ToolComponentProps) {
|
||||
const [input, setInput] = useState<string>('');
|
||||
const [result, setResult] = useState<string>('');
|
||||
|
||||
const compute = (optionsValues: typeof initialValues, input: string) => {
|
||||
setResult(convertTimetoSeconds(input));
|
||||
};
|
||||
|
||||
return (
|
||||
<ToolContent
|
||||
title={title}
|
||||
input={input}
|
||||
inputComponent={<ToolTextInput value={input} onChange={setInput} />}
|
||||
resultComponent={<ToolTextResult value={result} />}
|
||||
initialValues={initialValues}
|
||||
getGroups={null}
|
||||
setInput={setInput}
|
||||
compute={compute}
|
||||
toolInfo={{ title: `What is a ${title}?`, description: longDescription }}
|
||||
exampleCards={exampleCards}
|
||||
/>
|
||||
);
|
||||
}
|
||||
15
src/pages/tools/time/convert-time-to-seconds/meta.ts
Normal file
15
src/pages/tools/time/convert-time-to-seconds/meta.ts
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
import { defineTool } from '@tools/defineTool';
|
||||
import { lazy } from 'react';
|
||||
|
||||
export const tool = defineTool('time', {
|
||||
path: 'convert-time-to-seconds',
|
||||
name: 'Convert Time to Seconds',
|
||||
icon: 'ic:round-timer-10-select',
|
||||
description:
|
||||
'With this browser-based application, you can convert clock time provided in hours, minutes, and seconds into just seconds. Given a time in HH:MM:SS format, it calculates HH*3600 + MM*60 + SS and prints this value in the output box. It supports AM/PM time formats as well as clock times beyond 24 hours.',
|
||||
shortDescription: 'Quickly convert clock time in H:M:S format to seconds.',
|
||||
keywords: ['convert', 'seconds', 'time', 'clock'],
|
||||
longDescription:
|
||||
'This is a quick online utility for calculating how many seconds there are in the given time. When you input a full clock time in the input box (in format H:M:S), it gets split into hours, minutes, and seconds, and using the math formula hours×60×60 plus minutes×60 plus seconds, it finds the seconds. If seconds are missing (format is H:M), then the formula becomes hours×60×60 plus minutes×60. If minutes are also missing, then the formula becomes hours×60×60. As an extra feature, hours, minutes, and seconds are not limited to just 24 hours, 60 minutes, and 60 seconds. You can use any hours value, any minutes value, and any seconds value. For example, the input time "72:00:00" will find the number of seconds in three days (72 hours is 3×24 hours) and the input time "0:1000:0" will find seconds in 1000 minutes. Timeabulous!',
|
||||
component: lazy(() => import('./index'))
|
||||
});
|
||||
53
src/pages/tools/time/convert-time-to-seconds/service.ts
Normal file
53
src/pages/tools/time/convert-time-to-seconds/service.ts
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
import { containsOnlyDigits } from '@utils/string';
|
||||
|
||||
function recursiveTimeToSeconds(
|
||||
timeArray: string[],
|
||||
index: number = 0
|
||||
): number {
|
||||
if (index >= timeArray.length) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
const multipliers = [3600, 60, 1];
|
||||
return (
|
||||
Number(timeArray[index]) * multipliers[index] +
|
||||
recursiveTimeToSeconds(timeArray, index + 1)
|
||||
);
|
||||
}
|
||||
|
||||
function compute(timeArray: string[], lineNumber: number): string {
|
||||
if (timeArray[0] == '') {
|
||||
return '';
|
||||
}
|
||||
if (timeArray.length > 3) {
|
||||
throw new Error(`Time contains more than 3 parts on line ${lineNumber}`);
|
||||
}
|
||||
|
||||
const normalizedArray = [...timeArray, '0', '0'];
|
||||
|
||||
normalizedArray.forEach((time, index) => {
|
||||
if (!containsOnlyDigits(time)) {
|
||||
throw new Error(
|
||||
`Time doesn't contain valid ${
|
||||
['hours', 'minutes', 'seconds'][index]
|
||||
} on line ${lineNumber}`
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
return recursiveTimeToSeconds(timeArray).toString();
|
||||
}
|
||||
|
||||
export function convertTimetoSeconds(input: string): string {
|
||||
const result: string[] = [];
|
||||
|
||||
const lines = input.split('\n');
|
||||
|
||||
lines.forEach((line, index) => {
|
||||
const timeArray = line.split(':');
|
||||
const seconds = compute(timeArray, index + 1);
|
||||
result.push(seconds);
|
||||
});
|
||||
|
||||
return result.join('\n');
|
||||
}
|
||||
|
|
@ -1,4 +1,11 @@
|
|||
import { tool as daysDoHours } from './convert-days-to-hours/meta';
|
||||
import { tool as hoursToDays } from './convert-hours-to-days/meta';
|
||||
import { tool as convertSecondsToTime } from './convert-seconds-to-time/meta';
|
||||
import { tool as convertTimetoSeconds } from './convert-time-to-seconds/meta';
|
||||
|
||||
export const timeTools = [daysDoHours, hoursToDays];
|
||||
export const timeTools = [
|
||||
daysDoHours,
|
||||
hoursToDays,
|
||||
convertSecondsToTime,
|
||||
convertTimetoSeconds
|
||||
];
|
||||
|
|
|
|||
|
|
@ -41,8 +41,8 @@ export function reverseString(input: string): string {
|
|||
/**
|
||||
* Checks if the input string contains only digits.
|
||||
* @param input - The string to validate.
|
||||
* @returns True if the input contains only digits, false otherwise.
|
||||
* @returns True if the input contains only digits including float, false otherwise.
|
||||
*/
|
||||
export function containsOnlyDigits(input: string): boolean {
|
||||
return /^-?\d+(\.\d+)?$/.test(input.trim());
|
||||
return /^\d+(\.\d+)?$/.test(input.trim());
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue