// ==UserScript==
// @name XPath工具
// @namespace http://tampermonkey.net/
// @version 1.1
// @description 按Shift+X在鼠标位置显示输入框,并提供实时反馈和高级配置选项操作XPath元素
// @author Ace
// @match *://*/*
// @grant none
// @downloadURL none
// ==/UserScript==
(function () {
'use strict';
let toolbar = null;
const SHOW_KEY = 'KeyX';
function createToolbar() {
if (document.getElementById('custom-toolbar')) return;
toolbar = document.createElement('div');
toolbar.id = 'custom-toolbar';
toolbar.style.position = 'fixed';
toolbar.style.zIndex = '9999';
toolbar.style.backgroundColor = 'rgba(33, 33, 33, 0.95)';
toolbar.style.color = '#fff';
toolbar.style.padding = '15px';
toolbar.style.borderRadius = '8px';
toolbar.style.boxShadow = '0 4px 8px rgba(0, 0, 0, 0.2)';
toolbar.style.display = 'none';
const input = document.createElement('input');
input.id = 'custom-xpath-input';
input.type = 'text';
input.placeholder = '输入XPath';
input.style.width = '250px';
input.style.padding = '8px';
input.style.border = '1px solid #ccc';
input.style.borderRadius = '4px';
input.style.color = '#000'; // 固定文本颜色为黑色
input.style.backgroundColor = '#fff'; // 固定输入框背景颜色为白色
toolbar.appendChild(input);
const button = document.createElement('button');
button.innerText = '删除';
button.style.marginLeft = '10px';
button.style.padding = '8px 12px';
button.style.backgroundColor = '#e74c3c';
button.style.color = '#fff';
button.style.border = 'none';
button.style.borderRadius = '4px';
button.style.cursor = 'pointer';
button.style.transition = 'background-color 0.3s';
button.onmouseover = function () {
button.style.backgroundColor = '#c0392b';
};
button.onmouseout = function () {
button.style.backgroundColor = '#e74c3c';
};
button.onclick = function () {
const userXPath = input.value;
if (!userXPath) {
alert('请输入XPath');
return;
}
document.querySelectorAll('.highlighted-element').forEach((el) => {
el.style.outline = '';
el.classList.remove('highlighted-element');
});
const element = document.evaluate(
userXPath,
document,
null,
XPathResult.FIRST_ORDERED_NODE_TYPE,
null
).singleNodeValue;
if (element) {
if (document.getElementById('style-checkbox').checked) {
element.style.display = 'none';
alert(`已隐藏元素: ${userXPath}`);
} else {
element.remove();
alert(`已删除元素: ${userXPath}`);
}
} else {
alert('未找到匹配的元素');
}
};
toolbar.appendChild(button);
const styleCheckbox = document.createElement('div');
styleCheckbox.innerHTML = `
`;
styleCheckbox.querySelector('input').addEventListener('change', (event) => {
button.innerText = event.target.checked ? '隐藏' : '删除';
});
toolbar.appendChild(styleCheckbox);
const highlightCheckbox = document.createElement('div');
highlightCheckbox.innerHTML = `
`;
toolbar.appendChild(highlightCheckbox);
input.addEventListener('input', () => {
if (document.getElementById('highlight-checkbox').checked) {
highlightMatchingElements(input.value);
}
});
highlightCheckbox.addEventListener('change', () => {
const userXPath = input.value;
if (highlightCheckbox.querySelector('input').checked && userXPath) {
highlightMatchingElements(userXPath);
} else {
document.querySelectorAll('.highlighted-element').forEach((el) => {
el.style.outline = '';
el.classList.remove('highlighted-element');
});
}
});
document.body.appendChild(toolbar);
}
function highlightMatchingElements(userXPath) {
document.querySelectorAll('.highlighted-element').forEach((el) => {
el.style.outline = '';
el.classList.remove('highlighted-element');
});
if (userXPath) {
const element = document.evaluate(
userXPath,
document,
null,
XPathResult.FIRST_ORDERED_NODE_TYPE,
null
).singleNodeValue;
if (element) {
element.style.outline = '2px solid red';
element.classList.add('highlighted-element');
}
}
}
function toggleToolbarAtMouse(event) {
if (!toolbar) return;
const mouseX = event.clientX;
const mouseY = event.clientY;
toolbar.style.left = `${mouseX}px`;
toolbar.style.top = `${mouseY}px`;
toolbar.style.display = toolbar.style.display === 'none' ? 'block' : 'none';
}
createToolbar();
document.addEventListener('keydown', (event) => {
if (event.shiftKey && event.code === SHOW_KEY) {
document.addEventListener('mousemove', (mouseEvent) => {
toggleToolbarAtMouse(mouseEvent);
}, { once: true });
}
});
})();