faj-cli
Version:
FAJ - A powerful CLI resume builder with AI enhancement and multi-format export
199 lines • 5.82 kB
JavaScript
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.menu = exports.InteractiveMenu = exports.menuStack = void 0;
exports.navigableMenu = navigableMenu;
exports.getBreadcrumb = getBreadcrumb;
exports.menuItem = menuItem;
exports.menuSeparator = menuSeparator;
const inquirer_1 = __importDefault(require("inquirer"));
const chalk_1 = __importDefault(require("chalk"));
// Custom menu state manager
class MenuStack {
stack = [];
push(menu) {
this.stack.push(menu);
}
pop() {
return this.stack.pop();
}
current() {
return this.stack[this.stack.length - 1];
}
clear() {
this.stack = [];
}
depth() {
return this.stack.length;
}
}
exports.menuStack = new MenuStack();
/**
* Enhanced menu prompt with navigation support
*/
async function navigableMenu(title, choices, options = {}) {
const { showHints = true, allowEscape = true, parentValue = 'back' } = options;
// Add keyboard hints
if (showHints) {
console.log(chalk_1.default.gray('\n Navigation: ↑↓ Move | Enter Select | ESC Back\n'));
}
// Enhanced choices with back option
const enhancedChoices = [...choices];
// Add separator before back if there are other choices
if (choices.length > 0 && !choices.some(c => c.value === parentValue)) {
enhancedChoices.push(new inquirer_1.default.Separator('──────────────'));
enhancedChoices.push({
name: chalk_1.default.gray('← Back / ESC'),
value: parentValue,
action: 'back'
});
}
try {
const { selection } = await inquirer_1.default.prompt([
{
type: 'list',
name: 'selection',
message: title,
choices: enhancedChoices.map(c => {
if (typeof c === 'object' && 'name' in c) {
return {
name: c.name,
value: c.value,
short: c.name.replace(/[^\w\s]/g, '').trim()
};
}
return c;
}),
loop: false,
pageSize: 12
}
]);
return selection;
}
catch (error) {
// Handle ESC key (user cancelled)
if (allowEscape) {
return parentValue;
}
throw error;
}
}
/**
* Create a breadcrumb trail for current menu location
*/
function getBreadcrumb(path) {
if (path.length === 0)
return '';
return chalk_1.default.gray(` ${path.join(' > ')}\n`);
}
/**
* Standard menu builder with consistent styling
*/
class InteractiveMenu {
menuPath = [];
/**
* Show main menu
*/
async showMainMenu(items, title) {
const header = title || '📋 Main Menu';
const breadcrumb = getBreadcrumb(this.menuPath);
const choices = items.map(item => ({
name: `${item.icon} ${item.label}`,
value: item.value
}));
if (breadcrumb) {
console.log(breadcrumb);
}
return navigableMenu(header, choices, {
showHints: this.menuPath.length === 0,
parentValue: 'exit'
});
}
/**
* Show submenu with automatic back option
*/
async showSubmenu(title, items, parentMenu) {
// Update menu path
if (parentMenu) {
this.menuPath.push(parentMenu);
}
const breadcrumb = getBreadcrumb(this.menuPath);
const choices = items.map(item => ({
name: item.icon ? `${item.icon} ${item.label}` : item.label,
value: item.value
}));
if (breadcrumb) {
console.log(breadcrumb);
}
const result = await navigableMenu(title, choices, {
showHints: false,
parentValue: 'back'
});
// Pop from path if going back
if (result === 'back' && this.menuPath.length > 0) {
this.menuPath.pop();
}
return result;
}
/**
* Clear navigation history
*/
clearHistory() {
this.menuPath = [];
}
/**
* Get current menu depth
*/
getDepth() {
return this.menuPath.length;
}
/**
* Quick confirmation prompt
*/
async confirm(message, defaultValue = false) {
const { confirmed } = await inquirer_1.default.prompt([
{
type: 'confirm',
name: 'confirmed',
message,
default: defaultValue
}
]);
return confirmed;
}
/**
* Quick input prompt
*/
async input(message, defaultValue) {
const { value } = await inquirer_1.default.prompt([
{
type: 'input',
name: 'value',
message,
default: defaultValue
}
]);
return value;
}
}
exports.InteractiveMenu = InteractiveMenu;
// Export singleton instance
exports.menu = new InteractiveMenu();
/**
* Helper function to create consistent menu items
*/
function menuItem(icon, label, value) {
return { icon, label, value };
}
/**
* Helper to create section separators
*/
function menuSeparator(label) {
if (label) {
return new inquirer_1.default.Separator(chalk_1.default.gray(`─── ${label} ───`));
}
return new inquirer_1.default.Separator(chalk_1.default.gray('──────────────'));
}
//# sourceMappingURL=InteractiveMenu.js.map
;