建议在目录树后面新增统计子文档数量,并且在子文档数量有变化时,及时更新统计数量。
我是知道停留在文档上是可以看到子文档数量,但我希望能够更直观一点。
有一位大神写了代码,代码如下,但是实现不了文档树变化及时更新数量,有大神会改吗?还有一个需求,我希望能够知道已经写了多少篇文章了,能否在目录树的根,显示数量
(() => {
// 样式常量
const STYLE_CONFIG = {
color: '#888', // 数字颜色
fontSize: '12px', // 字体大小
backgroundColor: '', // 背景色
borderRadius: '4px', // 圆角
padding: '0 4px', // 内边距
marginRight: '10px', // 右侧间距
fontWeight: 'normal', // 字体粗细
};
// 创建样式表
const createStyleSheet = () => {
const style = document.createElement('style');
style.id = 'custom-folder-count-style';
style.textContent = `
.custom-folder-count {
position: absolute;
right: 0;
top: 50%;
transform: translateY(-50%);
color: ${STYLE_CONFIG.color};
font-size: ${STYLE_CONFIG.fontSize};
background-color: ${STYLE_CONFIG.backgroundColor};
border-radius: ${STYLE_CONFIG.borderRadius};
padding: ${STYLE_CONFIG.padding};
margin-right: ${STYLE_CONFIG.marginRight};
font-weight: ${STYLE_CONFIG.fontWeight};
pointer-events: none;
}
.b3-list-item {
position: relative;
}
`;
document.head.appendChild(style);
};
// 给笔记本添加文档数
const setBoxCount = () => {
const boxes = document.querySelectorAll('ul[data-url]');
boxes.forEach(async box => {
const response = await query(`SELECT count(*) as count FROM blocks where box = '${box.dataset.url}' and type = 'd';`);
if(!response[0] || !response[0]['count']) return;
const count = response[0]['count'];
const li = box.querySelector('li[data-type="navigation-root"]');
if(!li) return;
// 移除旧的计数元素
li.querySelector('.custom-folder-count')?.remove();
// 创建新的计数元素
const countEl = document.createElement('span');
countEl.className = 'custom-folder-count';
countEl.textContent = `${count}`;
// 查找标题容器并添加计数元素
const titleContainer = li.querySelector('.b3-list-item__text')?.parentNode;
if(titleContainer) {
titleContainer.appendChild(countEl);
}
});
};
// 给文件夹添加文档数
const setFolderCount = () => {
const folders = document.querySelectorAll('li[data-count]:not([data-count="0"])');
folders.forEach(folder => {
const count = folder.dataset.count;
// 移除旧的计数元素
folder.querySelector('.custom-folder-count')?.remove();
// 创建新的计数元素
const countEl = document.createElement('span');
countEl.className = 'custom-folder-count';
countEl.textContent = `${count}`;
// 查找标题容器并添加计数元素
const titleContainer = folder.querySelector('.b3-list-item__text')?.parentNode;
if(titleContainer) {
titleContainer.appendChild(countEl);
}
});
};
// 初始化
whenElementExist('ul[data-url]').then(() => {
createStyleSheet();
setBoxCount();
setFolderCount();
});
// 每小时更新一次笔记本文档数
setInterval(() => {
setBoxCount();
setFolderCount();
}, 3600000);
// 监听右键菜单,动态显示文件夹的文档数
const treeSelector = isMobile()? '#sidebar .b3-list--mobile' : '.sy__file';
whenElementExist(treeSelector).then((fileTree) => {
const onMenuShow = (event) => {
const currLi = event.target.closest('li.b3-list-item:not([data-type="navigation-root"],[data-count="0"])');
if(!currLi) return;
// 关闭上次的菜单,防止2个菜单冲突
document.body.click();
whenElementExist('button[data-id="rename"]').then(renameBtn => {
const html = `<button data-id="docNums" class="b3-menu__item"><svg class="b3-menu__icon " style=""><use xlink:href="#iconList"></use></svg><span class="b3-menu__label">显示文档数</span></button>`;
renameBtn.insertAdjacentHTML('afterend', html);
renameBtn.parentElement.querySelector('button[data-id="docNums"]').onclick = async () => {
const response = await query(`SELECT count(*) as count FROM blocks where path like '%/${currLi.dataset.nodeId}%' and type = 'd' and id != '${currLi.dataset.nodeId}';`);
if(!response[0] || !response[0]['count']) {document.body.click();return;}
const count = response[0]['count'];
// 移除旧的计数元素
currLi.querySelector('.custom-folder-count')?.remove();
// 创建新的计数元素
const countEl = document.createElement('span');
countEl.className = 'custom-folder-count';
countEl.textContent = `${count}`;
// 查找标题容器并添加计数元素
const titleContainer = currLi.querySelector('.b3-list-item__text')?.parentNode;
if(titleContainer) {
titleContainer.appendChild(countEl);
}
document.body.click();
};
});
};
if(isMobile()) {
// 监听手机版更多按钮被单击
fileTree.addEventListener('touchend', (event) => {
if (event.target.closest('span[data-type="more-file"]')) {
onMenuShow(event);
}
});
} else {
// 监听更多按钮被单击
fileTree.addEventListener('mouseup', (event) => {
if (event.target.closest('span[data-type="more-file"]')) {
onMenuShow(event);
}
});
// 监听文档树右键事件
fileTree.addEventListener('contextmenu', onMenuShow);
}
});
// 工具函数保持不变...
function whenElementExist(selector, node) {
return new Promise(resolve => {
const check = () => {
const el = typeof selector==='function'?selector():(node||document).querySelector(selector);
if (el) resolve(el); else requestAnimationFrame(check);
};
check();
});
}
async function query(sql) {
const result = await fetchSyncPost('/api/query/sql', { "stmt": sql });
if (result.code !== 0) {
console.error("查询数据库出错", result.msg);
return [];
}
return result.data;
}
async function fetchSyncPost(url, data, returnType = 'json') {
const init = {
method: "POST",
};
if (data) {
if (data instanceof FormData) {
init.body = data;
} else {
init.body = JSON.stringify(data);
}
}
try {
const res = await fetch(url, init);
const res2 = returnType === 'json' ? await res.json() : await res.text();
return res2;
} catch(e) {
console.log(e);
return returnType === 'json' ? {code:e.code||1, msg: e.message||"", data: null} : "";
}
}
function isMobile() {
return !!document.getElementById("sidebar");
}
})();
欢迎来到这里!
我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。
注册 关于