diff --git a/README.md b/README.md index 3ae26f5..0baea10 100644 --- a/README.md +++ b/README.md @@ -115,6 +115,9 @@ ### 第七个功能 添加量表操作 +把量表的固定操作添加进来。 +目前做的是comment记录的方式。 +应该要改成双链的方式。 ![量表操作](doc/7量表操作.png) ### 建议的固定标签配置 diff --git a/src/component/PopupRoot.tsx b/src/component/PopupRoot.tsx index 26338f1..e23d1bb 100644 --- a/src/component/PopupRoot.tsx +++ b/src/component/PopupRoot.tsx @@ -71,6 +71,7 @@ export function PopupRoot({ // item.isCollection const _annotationManager = reader._annotationManager; const _keyboardManager = reader._keyboardManager; + const annotations = item.getAnnotations(); //定义状态 // ztoolkit.log("params", params); @@ -133,6 +134,7 @@ export function PopupRoot({ const [selectionPopupSize, setSelectionPopupSize] = useState({ width: 0, height: 0 }); const [configName, setConfigName] = useState(getPref("configName")); const [bScale, setBScale] = useState(getPref("bScale") as boolean) + const [exAction, setExAction] = useState(getPref("exAction") as string) const [sScale, setSScale] = useState(getPref("sScale")) const [sScaleType, setSScaleType] = useState(getPref("sScaleType") as string) const [sScaleItem, setSScaleItem] = useState("") @@ -405,6 +407,7 @@ export function PopupRoot({ const clickMeButtonRef = React.useRef(null); const vars = [ + exAction, bScale, sScale, sScaleType, @@ -1085,63 +1088,66 @@ export function PopupRoot({ }} > {!params.ids && (<> - {/* {item.getAnnotations().map(a => a.getTags().map(b => b.tag).join(","))} */} - {item.getAnnotations().some(s => s.hasTag("量表")) && (
-
-
- {bScale && (<> -
- {sScaleType ? ( - - ) : (["item", "CR", "CA", "AVE", "factorLoading", "reference", "description"].map(a => ())} + +
+ + {exAction == "量表" && (<> +
+ {sScaleType ? ( + + ) : (["item", "CR", "CA", "AVE", "factorLoading", "reference", "description"].map(a => ()))} +
+
+ {sScaleType && (sScale ? () : (item.getAnnotations().filter(f => f.hasTag("量表")).map(a => + () + ) + ))} +
+
+ {sScaleType == "factorLoading" && sScale && (sScaleItem ? () : (item.getAnnotations().filter(f => f.hasTag("量表item") && f.annotationComment.includes(`*${sScale}*`)).map(a => + () + ) + ))} +
+
{sScaleType != "" && sScale != "" && (sScaleType != "factor loading" || sScaleItem != "") && (
+ {["item", "CR", "CA", "AVE", "factorLoading", "reference", "description"]//.filter(f => f != sScaleType) + .map(a => ()))} -
-
- {sScaleType && (sScale ? () : (item.getAnnotations().filter(f => f.hasTag("量表")).map(a => - () - ) - ))} -
-
- {sScaleType == "factorLoading" && sScale && (sScaleItem ? () : (item.getAnnotations().filter(f => f.hasTag("量表item") && f.annotationComment.includes(`*${sScale}*`)).map(a => - () - ) - ))} -
-
{sScaleType != "" && sScale != "" && (sScaleType != "factor loading" || sScaleItem != "") && (
- {["item", "CR", "CA", "AVE", "factorLoading", "reference", "description"]//.filter(f => f != sScaleType) - .map(a => ())} -
)}
+ }}>{sScaleType == a ? `【${a}】` : a}))} +
)}
+ + + )} - )} - )} )}
- + ), vars, ); diff --git a/src/modules/AnnotationsToNote.tsx b/src/modules/AnnotationsToNote.tsx index b3459be..d21bfe3 100644 --- a/src/modules/AnnotationsToNote.tsx +++ b/src/modules/AnnotationsToNote.tsx @@ -940,6 +940,87 @@ export async function exportNoteByType(type: _ZoteroTypes.Annotations.Annotation }, }); } +export async function exportScaleCsv(collectionOrItem: "collection" | "item") { + + const pw = new ztoolkit.ProgressWindow("") + // const ans2 = await convertHtml(ans, note, pw) + + const sData = await getScaleData(collectionOrItem); + const data = sData.map(a => [a.authorYear ? `${a.authorYear?.author || " "}(${a.authorYear?.year || " "})` : " ", `${a.authorYear?.title || " "}`, `${a.variable?.text || " "}`, `${a.scaleItem?.text || " "}`, `${a.scaleItem?.comment || " "}`, `${a.factorLoading?.text || " "}`, `${a.reference?.text || " "}`, `${a.CR?.text || " "}`, `${a.CA?.text || " "}`, `${a.AVE?.text || " "}`, `${a.description?.text || " "}`, `${a.description?.comment || " "}`]); + + const csv = []; + const separator = ","; + for (let i = 0; i < data.length; i++) { + const row = [], cols = data[i]; + for (let j = 0; j < cols.length; j++) { + let data = cols[j]?.replace(/(\r\n|\n|\r)/gm, '').replace(/(\s\s)/gm, ' ') || "" + data = data.replace(/"/g, '""'); + row.push('"' + data + '"'); + } + csv.push(row.join(separator)); + } + const csv_string = csv.join('\n'); + const classes = Components.classes as any + const nsIFilePicker = Components.interfaces.nsIFilePicker; + const fp = classes["@mozilla.org/filepicker;1"].createInstance(nsIFilePicker); + + fp.defaultString = "EX - " + ZoteroPane.getSelectedCollection()?.name + ".csv"; + fp.init(window, "Save to file", nsIFilePicker.modeSave); + fp.appendFilter("CSV (*.csv; *.txt)", "*.csv; *.txt"); + fp.defaultExtension = "csv"; + + fp.open(function () { + const outputStream = classes["@mozilla.org/network/file-output-stream;1"].createInstance(Components.interfaces.nsIFileOutputStream); + outputStream.init(fp.file, 0x04 | 0x08 | 0x20, 420, 0); + const converter = classes["@mozilla.org/intl/converter-output-stream;1"].createInstance(Components.interfaces.nsIConverterOutputStream); + converter.init(outputStream, "gb2312", 0, 0); + converter.writeString(csv_string); + converter.close(); + outputStream.close(); + }); + +} +async function getScaleData(collectionOrItem: "collection" | "item") { + const items = await getSelectedItems(collectionOrItem); + const ans = getAllAnnotations(items).filter(f => f.annotationTags.includes("量表")); + const pw = new ztoolkit.ProgressWindow("") + const ans2group = groupBy(ans, a => a.item.key) + const title = `量表来自${ans2group.length}个条目`; + + const authorYear = "authorYear"; + const variable = "variable"; + const AVE = "AVE"; + const CA = "CA"; + const CR = "CR"; + const reference = "reference"; + const scaleItem = "item"; + const factorLoading = "factorLoading"; + const description = "description"; + const data = [] + // data.push({ authorYear, variable, factorLoading, scaleItem, reference, CR, CA, AVE, description }); + for (const item of ans2group) { + const vars = item.values.filter(f => f.tags.some(s => s.tag == "量表")) + const authorYear = item.values[0] + const getAns = (type: "AVE" | "CR" | "CA" | "reference" | "item" | "factorLoading" | "description" | "itemDescription", text: string = "**") => item.values.filter(f => f.tags.some(s => s.tag == "量表" + type) && f.comment.includes(`*${text}*`)) + for (const scale of vars) { + const variable = scale; + const description = getAns("description", scale.text)?.[0] + const AVE = getAns("AVE", scale.text)?.[0]; + const CA = getAns("CA", scale.text)?.[0] + const CR = getAns("CR", scale.text)?.[0] + const reference = getAns("reference", scale.text)?.[0] + data.push({ authorYear, variable, reference, CR, CA, AVE, description }); + const scaleItems = item.values.filter(f => f.tags.some(s => s.tag == "量表item") && f.comment.includes(`*${scale.text}*`)) + for (const scaleItem1 of scaleItems) { + const scaleItem = scaleItem1; + const description = getAns("itemDescription", scaleItem1.text)?.[0]; + const factorLoading = getAns("factorLoading", scaleItem1.text)?.[0]; + data.push({ factorLoading, scaleItem, description }); + } + } + } + return data +} export async function exportScaleNote(collectionOrItem: "collection" | "item") { const items = await getSelectedItems(collectionOrItem); const ans = getAllAnnotations(items).filter(f => f.annotationTags.includes("量表")); diff --git a/src/modules/menu.tsx b/src/modules/menu.tsx index abb861a..6bc2ffa 100644 --- a/src/modules/menu.tsx +++ b/src/modules/menu.tsx @@ -10,7 +10,7 @@ import { sortBy, sortValuesLengthKeyAsc } from "../utils/sort"; import { Tab } from "../utils/tab"; import { uniqueBy } from "../utils/uniqueBy"; import { ReTest, clearChild, createDialog, getChildCollections, isDebug, memFixedColor, stopPropagation } from "../utils/zzlb"; -import { createAnnotationMatrix, createChooseTagsDiv, createSearchAnnContent, exportNote, exportScaleNote, getAllAnnotations } from "./AnnotationsToNote"; +import { createAnnotationMatrix, createChooseTagsDiv, createSearchAnnContent, exportNote, exportScaleCsv, exportScaleNote, getAllAnnotations } from "./AnnotationsToNote"; import { copyAnnotations, mergePdfs, pasteAnnotations } from "./BackupAnnotation"; import { DDDTagClear, DDDTagRemove, DDDTagSet } from "./DDD"; import { getCiteItemHtml } from "./getCitationItem"; @@ -317,11 +317,18 @@ function buildMenu(collectionOrItem: "collection" | "item") { tag: "menuseparator", }, { tag: "menuitem", - label: "导出量表格式(测试中)", + label: "导出量表格式Note(测试中)", icon: iconBaseUrl + "favicon.png", commandListener: async (ev: Event) => { exportScaleNote(collectionOrItem); }, + }, { + tag: "menuitem", + label: "导出量表格式CSV(测试中)", + icon: iconBaseUrl + "favicon.png", + commandListener: async (ev: Event) => { + exportScaleCsv(collectionOrItem); + }, }, { tag: "menuseparator",