Skip to content

Commit

Permalink
feat: add timer option
Browse files Browse the repository at this point in the history
  • Loading branch information
Amber-Williams committed Aug 4, 2023
1 parent 8aafe4e commit bd5c6b2
Show file tree
Hide file tree
Showing 6 changed files with 169 additions and 42 deletions.
47 changes: 8 additions & 39 deletions index.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
#!/usr/bin/env node
import fs from "fs";
import { evaluate } from "mathjs";

import path from "path";

import { program } from "commander";

import logger from "./logger.js";
import * as math from "./modes/math.js";
import * as timer from "./modes/timer.js";
import * as utils from "./utils.js";

const { __dirname } = utils.fileDirName(import.meta);
Expand All @@ -18,23 +20,8 @@ program
.version(version)
.description(description)
.option("-e, --edit", "Edit your choices")
.option(
"-m, --math [expression]",
`Math mode
\n
• Handles numeric seprators
12,000 + 4,000 => 12,400
12_000 + 4_000 => 12_400
• Handles unit converstion expressions
12.7 cm to inch => 5 inch
• Complex expressions
"sin(45 deg) ^ 2" => 0.5
"9 / 3 + 2i" => 3 + 2i
"det([-1, 2; 3, 1])" => -7
`
)
.option(math.option, math.optionDef)
.option(timer.option, timer.optionDef)
.action(async (cmd) => {
if (cmd.edit) {
logger.warning("Opening choices file...");
Expand All @@ -44,27 +31,9 @@ program
logger.error(`An error occurred: ${error}`);
}
} else if (cmd.math) {
let mathResult;

try {
let mathString = cmd.math + program.args.join(" ");
const hasCommas =
mathString.replaceAll(",", "").length < mathString.length;
const hasUnderscores =
mathString.replaceAll("_", "").length < mathString.length;
mathString = mathString.replaceAll(",", "").replaceAll("_", "");
mathResult = evaluate(mathString);

if (hasUnderscores) {
mathResult = mathResult.toLocaleString().replace(/,/g, "_");
} else if (hasCommas) {
mathResult = mathResult.toLocaleString();
}

logger.branded(`${mathResult}`);
} catch {
logger.error("Unable evaluate the provided equation");
}
await math.logic([cmd.math, ...program.args]);
} else if (cmd.timer) {
await timer.logic(cmd.timer, program.args[0]);
} else {
utils.askChoices();
}
Expand Down
43 changes: 43 additions & 0 deletions lib/player.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
import { exec } from "child_process";
import util from "util";

const execPromise = util.promisify(exec);

/* MAC PLAY COMMAND */
const macPlayCommand = (path, volume) => `afplay \"${path}\" -v ${volume}`;

/* WINDOW PLAY COMMANDS */
const addPresentationCore = `Add-Type -AssemblyName presentationCore;`;
const createMediaPlayer = `$player = New-Object system.windows.media.mediaplayer;`;
const loadAudioFile = (path) => `$player.open('${path}');`;
const playAudio = `$player.Play();`;
const stopAudio = `Start-Sleep 1; Start-Sleep -s $player.NaturalDuration.TimeSpan.TotalSeconds;Exit;`;

const windowPlayCommand = (path, volume) =>
`powershell -c ${addPresentationCore} ${createMediaPlayer} ${loadAudioFile(
path
)} $player.Volume = ${volume}; ${playAudio} ${stopAudio}`;

const player = {
play: async (path, volume = 0.5) => {
/**
* Window: mediaplayer's volume is from 0 to 1, default is 0.5
* Mac: afplay's volume is from 0 to 255, default is 1. However, volume > 2 usually result in distortion.
* Therefore, it is better to limit the volume on Mac, and set a common scale of 0 to 1 for simplicity
*/
const volumeAdjustedByOS =
process.platform === "darwin" ? Math.min(2, volume * 2) : volume;

const playCommand =
process.platform === "darwin"
? macPlayCommand(path, volumeAdjustedByOS)
: windowPlayCommand(path, volumeAdjustedByOS);
try {
await execPromise(playCommand, { windowsHide: true });
} catch (err) {
throw err;
}
},
};

export default player;
Binary file added media/bells.mp3
Binary file not shown.
42 changes: 42 additions & 0 deletions modes/math.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import { evaluate } from "mathjs";

import logger from "./../logger.js";

export const option = "-m, --math [expression]";
export const optionDef = `Math mode
\n
• Handles numeric seprators
12,000 + 4,000 => 12,400
12_000 + 4_000 => 12_400
• Handles unit converstion expressions
12.7 cm to inch => 5 inch
• Complex expressions
"sin(45 deg) ^ 2" => 0.5
"9 / 3 + 2i" => 3 + 2i
"det([-1, 2; 3, 1])" => -7
`;

export const logic = async (args) => {
let mathResult;

try {
let mathString = args.join(" ");
const hasCommas = mathString.replaceAll(",", "").length < mathString.length;
const hasUnderscores =
mathString.replaceAll("_", "").length < mathString.length;
mathString = mathString.replaceAll(",", "").replaceAll("_", "");
mathResult = evaluate(mathString);

if (hasUnderscores) {
mathResult = mathResult.toLocaleString().replace(/,/g, "_");
} else if (hasCommas) {
mathResult = mathResult.toLocaleString();
}

logger.branded(`${mathResult}`);
} catch {
logger.error("Unable evaluate the provided equation");
}
};
73 changes: 73 additions & 0 deletions modes/timer.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import player from "./../lib/player.js";
import logger from "./../logger.js";

export const option = "-t, --timer [time unit] [number of units]";
export const optionDef = `Timer mode
\n
time units available:
s, sec, secs, second, seconds
m, min, mins, minute, minutes
h, hr, hrs, hour, hours
d, day, days
`;

const soundAlarm = () => {
player
.play("./media/bells.mp3", (err) => {
if (err) console.log(`Could not play sound: ${err}`);
})
.then(() => {
logger.branded("Time's up!");
});
};

export const logic = async (unit, num) => {
if (isNaN(Number(num))) {
logger.error("Please enter number of mins for timer");
return;
}

let time;
try {
switch (unit) {
case "s":
case "sec":
case "secs":
case "second":
case "seconds":
time = num * 1000;
unit = "seconds";
break;
case "m":
case "min":
case "mins":
case "minute":
case "minutes":
time = num * 1000 * 60;
unit = "minutes";
break;
case "h":
case "hr":
case "hrs":
case "hour":
case "hours":
time = num * 1000 * 60 * 60;
unit = "hours";
break;
case "d":
case "day":
case "days":
time = num * 1000 * 60 * 60 * 24;
unit = "days";
break;
default:
logger.error("Wrong time unit format was provided");
break;
}

setTimeout(soundAlarm, time);
logger.branded(`Setting timer for ${num} ${unit}...`);
} catch {
logger.error("Unable evaluate the provided equation");
}
};
6 changes: 3 additions & 3 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit bd5c6b2

Please sign in to comment.