feat(qrcode): 实现图片转二维码右键菜单功能
- 添加图片类型的右键菜单配置 - 修改 parseContextMenuClick 支持 srcUrl 参数 - 实现图片URL自动解析功能 - 检测图片URL自动切换到解析模式 - 更新测试用例覆盖新功能 - 新增国际化文案
This commit is contained in:
@@ -12,8 +12,8 @@ describe('contextMenu', () => {
|
||||
});
|
||||
|
||||
describe('CONTEXT_MENU_CONFIGS', () => {
|
||||
it('应该包含 7 个菜单项配置', () => {
|
||||
expect(CONTEXT_MENU_CONFIGS).toHaveLength(7);
|
||||
it('应该包含 8 个菜单项配置', () => {
|
||||
expect(CONTEXT_MENU_CONFIGS).toHaveLength(8);
|
||||
});
|
||||
|
||||
it('应该有一个父级菜单项 Testing Tools', () => {
|
||||
@@ -43,13 +43,22 @@ describe('contextMenu', () => {
|
||||
expect(pageMenus).toHaveLength(2);
|
||||
expect(pageMenus.map((m) => m.id)).toEqual(['storageCleaner', 'qrCode-page']);
|
||||
});
|
||||
|
||||
it('应该有 1 个 image 上下文的子菜单', () => {
|
||||
const imageMenus = CONTEXT_MENU_CONFIGS.filter(
|
||||
(c) => c.contexts[0] === 'image' && c.parentId === 'testing-tools-parent',
|
||||
);
|
||||
expect(imageMenus).toHaveLength(1);
|
||||
expect(imageMenus[0].id).toBe('qrCode-image');
|
||||
expect(imageMenus[0].title).toBe('🖼️ 图片转二维码');
|
||||
});
|
||||
});
|
||||
|
||||
describe('createAllContextMenus', () => {
|
||||
it('应该为每个配置调用 chrome.contextMenus.create', () => {
|
||||
createAllContextMenus();
|
||||
|
||||
expect(chrome.contextMenus.create).toHaveBeenCalledTimes(7);
|
||||
expect(chrome.contextMenus.create).toHaveBeenCalledTimes(8);
|
||||
});
|
||||
|
||||
it('应该使用正确的参数创建菜单项', () => {
|
||||
@@ -185,5 +194,33 @@ describe('contextMenu', () => {
|
||||
data: { featureKey: 'textStatistics', payload: 'short text' },
|
||||
});
|
||||
});
|
||||
|
||||
it('当点击 qrCode-image 菜单时应返回 qrCode 功能和图片URL', () => {
|
||||
const info = createMockOnClickData({
|
||||
srcUrl: 'https://example.com/image.png',
|
||||
});
|
||||
|
||||
const result = parseContextMenuClick('qrCode-image', info);
|
||||
|
||||
expect(result).toEqual({
|
||||
success: true,
|
||||
data: { featureKey: 'qrCode', payload: 'https://example.com/image.png' },
|
||||
});
|
||||
});
|
||||
|
||||
it('srcUrl 优先于 selectionText 和 pageUrl', () => {
|
||||
const info = createMockOnClickData({
|
||||
srcUrl: 'https://example.com/image.png',
|
||||
selectionText: 'selected text',
|
||||
pageUrl: 'https://example.com',
|
||||
});
|
||||
|
||||
const result = parseContextMenuClick('qrCode-image', info);
|
||||
|
||||
expect(result).toEqual({
|
||||
success: true,
|
||||
data: { featureKey: 'qrCode', payload: 'https://example.com/image.png' },
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -25,6 +25,7 @@ export const MAX_PAYLOAD_LENGTH = 10000;
|
||||
/** 菜单项 ID 到 PageType 的映射(仅处理非常规映射) */
|
||||
const MENU_ID_TO_PAGE_TYPE: Record<string, PageType> = {
|
||||
'qrCode-page': 'qrCode',
|
||||
'qrCode-image': 'qrCode',
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -77,6 +78,12 @@ export const CONTEXT_MENU_CONFIGS: ContextMenuItemConfig[] = [
|
||||
contexts: [chrome.contextMenus.ContextType.PAGE],
|
||||
parentId: PARENT_MENU_ID,
|
||||
},
|
||||
{
|
||||
id: 'qrCode-image',
|
||||
title: '🖼️ 图片转二维码',
|
||||
contexts: [chrome.contextMenus.ContextType.IMAGE],
|
||||
parentId: PARENT_MENU_ID,
|
||||
},
|
||||
];
|
||||
|
||||
export function createAllContextMenus(): void {
|
||||
@@ -96,6 +103,14 @@ export function parseContextMenuClick(
|
||||
): ParseResult {
|
||||
const featureKey = getMenuPageType(menuItemId);
|
||||
|
||||
// 处理图片 URL(右键点击图片时)
|
||||
if (info.srcUrl) {
|
||||
return {
|
||||
success: true,
|
||||
data: { featureKey, payload: info.srcUrl },
|
||||
};
|
||||
}
|
||||
|
||||
if (info.selectionText) {
|
||||
const text = info.selectionText;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user