0.1.7-DEV-1: added on-the-fly relationship documents generation

This commit is contained in:
Elvanos 2021-05-03 21:49:11 +02:00
parent 8345634a93
commit 88bff4a5ba
20 changed files with 528 additions and 51 deletions

View file

@ -1,6 +1,6 @@
{
"name": "fantasiaarchive",
"version": "0.1.6",
"version": "0.1.7",
"description": "A database manager for world building",
"productName": "Fantasia Archive",
"author": "Elvanos <elvanos66@gmail.com>",

View file

@ -7,8 +7,8 @@
no-resize
dark
title="Advanced Search Cheatsheet"
:height="510"
:width="425"
:height="535"
:width="500"
:start-x="50"
:start-y="150"
:actions="['pin', 'close']"
@ -77,7 +77,7 @@ export default class App extends BaseClass {
// APP START & END SETUP
/****************************************************************/
created () {
async created () {
// Catch middle clicks
window.addEventListener("auxclick", this.reactToMiddleClick)
@ -89,19 +89,19 @@ export default class App extends BaseClass {
}
}
// Catch normal clicks inside wysiwyg
window.addEventListener("click", this.openWysiwygLink)
// Load settings
this.loadSettings().catch(e => console.log(e))
await this.loadSettings()
// React to keybind presses
window.addEventListener("keydown", this.triggerKeyPush)
await this.loadCorkboardCotent()
// Load the popup hint on start
this.loadHintPopup()
this.loadCorkboardCotent().catch(e => console.log(e))
// React to keybind presses
window.addEventListener("keydown", this.triggerKeyPush)
// Catch normal clicks inside wysiwyg
window.addEventListener("click", this.openWysiwygLink)
}
destroyed () {
@ -344,9 +344,31 @@ export default class App extends BaseClass {
}, 1000)
}
/**
* Corkboard checker
* Can go up to 3
*/
corkboardCheck = 0
async loadCorkboardCotent () {
const options = this.SGET_options
this.corkboardContent = await retrieveCorkboard()
if (this.corkboardContent.length > 0) {
// Considering there is a bit of a delay between the initial load of the store DB content, we give the program 3 attempts to load the data over 3 seconds. If no is loaded in that time, we assume that the settings are not set at all and display the hint as normal.
if ((!options._id || !options._rev) && this.corkboardCheck < 3) {
setTimeout(() => {
this.corkboardCheck++
this.loadCorkboardCotent().catch(e => console.log(e))
}, 1000)
return
}
if (options.preventFilledNoteBoardPopup) {
return
}
if (this.corkboardContent.length) {
this.corkboardWindowVisible = true
}
}

View file

@ -582,7 +582,7 @@ export default class DocumentControl extends BaseClass {
const savedDocument: {
documentCopy: I_OpenedDocument,
allOpenedDocuments: I_OpenedDocument[]
} = await saveDocument(currentDoc, this.documentsCopy, this.SGET_allDocuments.docs, editMode).catch(err => console.log(err))
} = await saveDocument(currentDoc, this.documentsCopy, this.SGET_allDocuments.docs, editMode, this).catch(err => console.log(err))
// Update the opened document
const dataPass = { doc: savedDocument.documentCopy, treeAction: true }

View file

@ -23,7 +23,7 @@
>
<q-tab name="uiSettings" label="Visuals & Accessibility" />
<q-tab name="docSettings" label="Document view/edit" />
<q-tab name="popupSettings" label="Popup dialogs" />
<q-tab name="popupSettings" label="Popups & Floating Windows" />
<q-tab name="treeSettings" label="Hierarchical tree" />
<q-separator dark />
@ -338,7 +338,7 @@
<div class="row justify-start">
<div class="col-12">
<div class="text-h6">
Popup dialogs
Popups & Floating Windows
</div>
</div>
@ -403,6 +403,31 @@
/>
</div>
<div class="col-12">
<div class="text-bold q-mt-xl">
Floating windows
</div>
</div>
<div class="col-12 col-md-6 col-lg-4 optionWrapper">
<div class="optionTitle">
Prevent filled note board showing
<q-icon name="mdi-help-circle" size="16px" class="q-ml-md">
<q-tooltip :delay="500">
Turning this on prevents the note board showing automatically
<br>
at the start of the app in case in contains any notes persisting
<br>
from previous sessions of FA that the user filed previously.
</q-tooltip>
</q-icon>
</div>
<q-toggle
v-model="options.preventFilledNoteBoardPopup"
/>
</div>
</div>
</q-scroll-area>
</q-tab-panel>
@ -917,6 +942,7 @@ export default class ProgramSettings extends DialogBase {
options: OptionsStateInteface = {
_id: "settings",
darkMode: false,
preventFilledNoteBoardPopup: false,
preventAutoScroll: false,
textShadow: false,
hideAdvSearchCheatsheetButton: false,

View file

@ -148,6 +148,8 @@
:option-disable="opt => Object(opt) === opt ? disabledIDList.includes(opt._id) : true"
:outlined="!isDarkMode"
:filled="isDarkMode"
new-value-mode="add-unique"
@new-value="addNewRelationshipObject"
use-chips
multiple
option-value="_id"
@ -170,10 +172,16 @@
dense
@remove="scope.removeAtIndex(scope.index)"
:tabindex="scope.tabindex"
color="accent"
:color="(scope.opt.isAutoGenerated) ? 'teal-3' : 'accent'"
text-color="dark"
class="text-bold"
>
<q-tooltip
v-if="scope.opt.isAutoGenerated"
:delay="500">
This document doesn't exist yet. It will be auto-generated on save.
</q-tooltip>
<template v-if="scope.opt.isDead">
</template>
@ -187,6 +195,7 @@
size="sm"
icon="mdi-open-in-new"
@click.stop.prevent="openNewTab(scope.opt)"
v-if="!scope.opt.isAutoGenerated"
>
<q-tooltip :delay="500">
Open in new tab without leaving this one
@ -433,7 +442,7 @@ import { Component, Emit, Prop, Watch } from "vue-property-decorator"
import FieldBase from "src/components/fields/_FieldBase"
import { advancedDocumentFilter } from "src/scripts/utilities/advancedDocumentFilter"
import { extend } from "quasar"
import { extend, uid } from "quasar"
import { I_ShortenedDocument, I_OpenedDocument } from "src/interfaces/I_OpenedDocument"
import { I_FieldRelationship, I_RelationshipPair } from "src/interfaces/I_FieldRelationship"
import { createNewWithParent } from "src/scripts/documentActions/createNewWithParent"
@ -625,22 +634,28 @@ export default class Field_MultiRelationship extends FieldBase {
this.localInput = (Array.isArray(this.localInput)) ? this.localInput : []
const toRemoveIndexList: string[] = []
let autoGenerateCleanup = false
for (const [index] of this.localInput.entries()) {
// Proceed only if the local input is properly set up
if (this.localInput[index]._id) {
// If the matched object doesn't exist in the object, assume it has been deleted or newer existed and silently emit a signal input which auto-updates the document
if (!allDbObjects.docs.find(e => e._id === this.localInput[index]._id)) {
if (!allDbObjects.docs.find(e => e._id === this.localInput[index]._id) && !this.localInput[index]?.isAutoGenerated) {
toRemoveIndexList.push(this.localInput[index]._id)
}
// If the object does exist, make sure we have the newest available name by reasigning the label if it is different. Then trigger a silent update
else {
if (allDbObjects.docs.find(e => e._id === this.localInput[index]._id)) {
const matchedFieldContent = allDbObjects.docs.find(e => e._id === this.localInput[index]._id)
if (matchedFieldContent) {
this.localInput[index].label = matchedFieldContent.label
this.localInput[index].isDead = matchedFieldContent.extraFields.find(e => e.id === "deadSwitch")?.value
}
if (this.localInput[index].isAutoGenerated) {
this.localInput[index].isAutoGenerated = false
autoGenerateCleanup = true
}
}
}
}
@ -648,7 +663,7 @@ export default class Field_MultiRelationship extends FieldBase {
this.allTypeDocuments = allDbObjects.docs
// Remove delete documents paired to this
if (toRemoveIndexList.length > 0) {
if (toRemoveIndexList.length > 0 || autoGenerateCleanup) {
toRemoveIndexList.forEach((id) => {
const indexToRemove = this.localInput.findIndex(doc => doc._id === id)
if (indexToRemove > -1) {
@ -721,6 +736,8 @@ export default class Field_MultiRelationship extends FieldBase {
id: e._id,
type: e.type,
url: e.url,
label: (e?.label) || "",
isAutoGenerated: (e.isAutoGenerated),
pairedField: (this.inputDataBluePrint?.relationshipSettings?.connectedField) || ""
}
}),
@ -819,6 +836,83 @@ export default class Field_MultiRelationship extends FieldBase {
console.log(e)
})
}
addNewRelationshipObject (input: string) {
const newObjectType = this.inputDataBluePrint?.relationshipSettings?.connectedObjectType as unknown as string
const pairedBlueprint = this.SGET_blueprint(newObjectType)
const newObjectID = uid()
const newDocument = {
bgColor: undefined,
color: undefined,
extraFields: [
{
id: "name",
value: input
},
{
id: "parentDoc",
value: ""
},
{
id: "documentColor",
value: ""
},
{
id: "documentBackgroundColor",
value: ""
},
{
id: "finishedSwitch",
value: ""
},
{
id: "minorSwitch",
value: ""
},
{
id: "deadSwitch",
value: ""
},
{
id: "categorySwitch",
value: ""
},
{
id: "order",
value: ""
},
{
id: "tags",
value: []
},
{
id: "categoryDescription",
value: ""
}
],
hierarchicalPath: pairedBlueprint.namePlural,
icon: pairedBlueprint.icon,
id: newObjectID,
isCategory: "",
isDead: undefined,
isMinor: undefined,
isAutoGenerated: true,
label: input,
tags: [],
type: newObjectType,
url: `/project/display-content/${newObjectType}/${newObjectID}`,
_id: newObjectID
}
// @ts-ignore
this.localInput.push(newDocument)
this.processInput()
}
}
</script>

View file

@ -143,6 +143,8 @@
:options="filterList"
:option-disable="opt => Object(opt) === opt ? disabledIDList.includes(opt._id) : true"
use-input
new-value-mode="add-unique"
@new-value="addNewRelationshipObject"
:outlined="!isDarkMode"
:filled="isDarkMode"
input-debounce="500"
@ -167,10 +169,16 @@
@click="openNewTab(scope.opt)"
@remove="scope.removeAtIndex(scope.index)"
:tabindex="scope.tabindex"
color="accent"
:color="(scope.opt.isAutoGenerated) ? 'teal-3' : 'accent'"
text-color="dark"
class="text-bold"
>
<q-tooltip
v-if="scope.opt.isAutoGenerated"
:delay="500">
This document doesn't exist yet. It will be auto-generated on save.
</q-tooltip>
<template v-if="scope.opt.isDead">
</template>
@ -183,6 +191,7 @@
style="color: #000 !important;"
size="sm"
icon="mdi-open-in-new"
v-if="!scope.opt.isAutoGenerated"
@click.stop.prevent="openNewTab(scope.opt)"
>
<q-tooltip :delay="500">
@ -386,7 +395,7 @@ import { Component, Emit, Prop, Watch } from "vue-property-decorator"
import FieldBase from "src/components/fields/_FieldBase"
import { advancedDocumentFilter } from "src/scripts/utilities/advancedDocumentFilter"
import { extend } from "quasar"
import { extend, uid } from "quasar"
import { I_OpenedDocument, I_ShortenedDocument } from "src/interfaces/I_OpenedDocument"
import { I_FieldRelationship, I_RelationshipPairSingle } from "src/interfaces/I_FieldRelationship"
@ -580,12 +589,14 @@ export default class Field_SingleRelationship extends FieldBase {
// Proceed only if the local input is properly set up
if (this.localInput._id) {
// If the matched object doesn't exist in the object, assume it has been deleted or never existed
if (!allDbObjects.docs.find(e => e._id === this.localInput._id)) {
if (!allDbObjects.docs.find(e => e._id === this.localInput._id) && !this.localInput?.isAutoGenerated) {
// @ts-ignore
this.localInput = ""
}
// If the object does exist, make sure we have the newest available name by reasigning the label if it is different
else {
if (allDbObjects.docs.find(e => e._id === this.localInput._id)) {
const matchedFieldContent = allDbObjects.docs.find(e => e._id === this.localInput._id)
if (matchedFieldContent && (
@ -595,6 +606,10 @@ export default class Field_SingleRelationship extends FieldBase {
this.localInput.label = matchedFieldContent.label
this.localInput.isDead = matchedFieldContent.extraFields.find(e => e.id === "deadSwitch")?.value
}
if (this.localInput.isAutoGenerated) {
this.localInput.isAutoGenerated = false
}
}
}
@ -664,6 +679,8 @@ export default class Field_SingleRelationship extends FieldBase {
id: this.localInput._id,
type: this.localInput.type,
url: this.localInput.url,
label: (this.localInput?.label) || "",
isAutoGenerated: (this.localInput.isAutoGenerated),
pairedField: (this.inputDataBluePrint?.relationshipSettings?.connectedField) || ""
}
: null
@ -753,6 +770,83 @@ export default class Field_SingleRelationship extends FieldBase {
console.log(e)
})
}
addNewRelationshipObject (input: string) {
const newObjectType = this.inputDataBluePrint?.relationshipSettings?.connectedObjectType as unknown as string
const pairedBlueprint = this.SGET_blueprint(newObjectType)
const newObjectID = uid()
const newDocument = {
bgColor: undefined,
color: undefined,
extraFields: [
{
id: "name",
value: input
},
{
id: "parentDoc",
value: ""
},
{
id: "documentColor",
value: ""
},
{
id: "documentBackgroundColor",
value: ""
},
{
id: "finishedSwitch",
value: ""
},
{
id: "minorSwitch",
value: ""
},
{
id: "deadSwitch",
value: ""
},
{
id: "categorySwitch",
value: ""
},
{
id: "order",
value: ""
},
{
id: "tags",
value: []
},
{
id: "categoryDescription",
value: ""
}
],
hierarchicalPath: pairedBlueprint.namePlural,
icon: pairedBlueprint.icon,
id: newObjectID,
isCategory: "",
isDead: undefined,
isMinor: undefined,
isAutoGenerated: true,
label: input,
tags: [],
type: newObjectType,
url: `/project/display-content/${newObjectType}/${newObjectID}`,
_id: newObjectID
}
// @ts-ignore
this.localInput = newDocument
this.processInput()
}
}
</script>

View file

@ -38,7 +38,7 @@
use-chips
@filter="filterFn"
input-debounce="0"
new-value-mode="add"
new-value-mode="add-unique"
multiple
v-model="localInput"
@new-value="addNewValue"

View file

@ -612,11 +612,11 @@ body .q-tooltip {
min-height: 186px !important;
min-width: 250px !important;
.q-window__body{
.q-window__body {
min-height: 146px !important;
min-width: 250px !important;
}
}
}
.corkboardInput {
height: 100%;
@ -627,7 +627,7 @@ body .q-tooltip {
height: 100%;
}
.q-validation-component{
.q-validation-component {
height: 100%;
}
@ -651,3 +651,8 @@ body .q-tooltip {
line-height: 20px;
}
}
#q-app {
position: relative;
overflow: hidden !important;
}

View file

@ -13,4 +13,5 @@
- Full search
- `%` - Beginning of the full-search
- `:` - Division between the field-name and field value
- `%:something` - Search through all fields for value
- `%some-field:some-value` - Search through all fields for value
- This can also be used to search for colors: `%color:blue`

View file

@ -3,6 +3,28 @@
---
## 0.1.7
### Known issues
- Creating a brand new project can sometimes get stuck. Restarting the app fixes this.
- Importing existing project can sometimes get stuck. Restarting the app fixes this.
### Bugfixes & Optimizations
- Fixed infinite vertical scroll of the app caused by buggy behavior of the floating windows being pulled on the bottom of the visible window
- Fixed a limiter for advanced search that was throwing errors in rare cases
- Fixed a bug that was causing single-to-single relationship notes not properly saving
### New features
- **Added on-the-fly relationship documents generation**
- Added option: Prevent filled note board showing
### QoL adjustments
- Added a note about possible color searching in the advanced search cheatsheet popup window
## 0.1.6a
### Known issues

2
src/env.d.ts vendored
View file

@ -1,5 +1,5 @@
declare namespace NodeJS {
interface ProcessEnv {
interface ProcessEnv {
NODE_ENV: string;
VUE_ROUTER_MODE: 'hash' | 'history' | 'abstract' | undefined;
VUE_ROUTER_BASE: string | undefined;

View file

@ -7,6 +7,7 @@ export interface I_FieldRelationship{
pairedField: string
isCategory: boolean
isDead: boolean
isAutoGenerated?: boolean
}
export interface I_RelationshipPair {

View file

@ -932,7 +932,7 @@ export default class PageDocumentDisplay extends BaseClass {
const savedDocument: {
documentCopy: I_OpenedDocument,
allOpenedDocuments: I_OpenedDocument[]
} = await saveDocument(currentDoc, openedDocumentsCopy, this.SGET_allDocuments.docs, keepEditMode)
} = await saveDocument(currentDoc, openedDocumentsCopy, this.SGET_allDocuments.docs, keepEditMode, this)
// Update the opened document
const dataPass = { doc: savedDocument.documentCopy, treeAction: true }

View file

@ -564,7 +564,7 @@ export const charactersBlueprint: I_Blueprint = {
"Focused",
"Folksy",
"Foolish",
"Forecful",
"Forceful",
"Forgetful",
"Forgiving",
"Formal",

View file

@ -346,7 +346,7 @@ export const guildsBlueprint: I_Blueprint = {
id: "pairedEnemyPolGroups",
name: "Enemy Ideologies/Political groups",
type: "manyToManyRelationship",
icon: "mdi-account-group",
icon: "mdi-bank-outline",
sizing: 4,
relationshipSettings: {
connectedObjectType: "politicalGroups",

View file

@ -1,8 +1,8 @@
import { single_changeRelationshipToAnotherObject, many_changeRelationshipToAnotherObject } from "src/scripts/databaseManager/relationshipManager"
import { I_OpenedDocument, I_ShortenedDocument } from "src/interfaces/I_OpenedDocument"
import { I_ExtraFields } from "src/interfaces/I_Blueprint"
import { extend } from "quasar"
import { I_Blueprint, I_ExtraFields } from "src/interfaces/I_Blueprint"
import PouchDB from "pouchdb"
import { Loading, QSpinnerGears, extend } from "quasar"
/**
* Saves the given project and handles all the needed procedures
@ -11,10 +11,27 @@ export const saveDocument = async (
document: I_OpenedDocument,
allOpenedDocuments: I_OpenedDocument[],
allDocuments: I_ShortenedDocument[],
editModeAfterSave: boolean
editModeAfterSave: boolean,
vueInstance: any
) => {
const BlueprintsDB = new PouchDB("blueprints")
const currentBlueprint: {extraFields: I_ExtraFields[]} = await BlueprintsDB.get(document.type)
const loadingSetup = {
message: "<h4>Saving document...</h4>",
spinnerColor: "primary",
messageColor: "cultured",
spinnerSize: 120,
backgroundColor: "dark",
// @ts-ignore
spinner: QSpinnerGears
}
// Time for cases when people want to auto-generate A LOT of documents
const saveTimeout = setTimeout(() => {
// @ts-ignore
Loading.show(loadingSetup)
}, 750)
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
const currentBlueprint: {extraFields: I_ExtraFields[]} = vueInstance.SGET_blueprint(document.type)
window.FA_dbs[document.type] = new PouchDB(document.type)
const CurrentObjectDB = window.FA_dbs[document.type]
@ -38,17 +55,100 @@ export const saveDocument = async (
allOpenedDocuments = allOpenedDocuments.filter(doc => doc._id !== document._id)
// Handle relationship fields
// Handle single document autogeneration
const single_relationshipTypesAutoGeneration = ["singleToNoneRelationship", "singleToSingleRelationship", "singleToManyRelationship"]
const single_allRelationshipFieldsAutoGeneration = documentCopy.extraFields.filter(field => {
const currentField = currentBlueprint.extraFields.find(e => e.id === field.id) as unknown as I_ExtraFields
return (currentField && single_relationshipTypesAutoGeneration.includes(currentField.type))
})
// Update single fields autogeneration
for (const field of single_allRelationshipFieldsAutoGeneration) {
const fieldValue = field.value?.value
if (fieldValue?.isAutoGenerated) {
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
const pairedBlueprint: I_Blueprint = vueInstance.SGET_blueprint(fieldValue.type)
const newDocument = {
bgColor: undefined,
color: undefined,
extraFields: [
{
id: "name",
value: fieldValue.label
},
{
id: "parentDoc",
value: ""
},
{
id: "documentColor",
value: ""
},
{
id: "documentBackgroundColor",
value: ""
},
{
id: "finishedSwitch",
value: ""
},
{
id: "minorSwitch",
value: ""
},
{
id: "deadSwitch",
value: ""
},
{
id: "categorySwitch",
value: ""
},
{
id: "order",
value: ""
},
{
id: "tags",
value: []
},
{
id: "categoryDescription",
value: ""
}
],
hierarchicalPath: pairedBlueprint.namePlural,
icon: pairedBlueprint.icon,
id: fieldValue.id,
type: fieldValue.type,
// eslint-disable-next-line @typescript-eslint/restrict-template-expressions
url: `/project/display-content/${fieldValue.type}/${fieldValue.id}`,
_id: fieldValue.id
}
// @ts-ignore
window.FA_dbs[newDocument.type] = new PouchDB(newDocument.type)
// @ts-ignore
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
await window.FA_dbs[newDocument.type].put(newDocument)
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
vueInstance.SSET_addDocument({ doc: vueInstance.mapShortDocument(newDocument, vueInstance.SGET_allDocumentsByType(newDocument.type).docs) })
delete (fieldValue.isAutoGenerated)
}
}
// Handle relationship single fields
const single_relationshipTypes = ["singleToSingleRelationship", "singleToManyRelationship"]
const single_allRelationshipFields = documentCopy.extraFields.filter(field => {
const currentField = currentBlueprint.extraFields.find(e => e.id === field.id) as unknown as I_ExtraFields
return (currentField && single_relationshipTypes.includes(currentField.type))
})
const many_relationshipTypes = ["manyToSingleRelationship", "manyToManyRelationship"]
const many_allRelationshipFields = documentCopy.extraFields.filter(field => {
const currentField = currentBlueprint.extraFields.find(e => e.id === field.id) as unknown as I_ExtraFields
return (currentField && many_relationshipTypes.includes(currentField.type))
})
// Update single fields
for (const field of single_allRelationshipFields) {
@ -93,6 +193,105 @@ export const saveDocument = async (
})
}
// Handle relationship many fields
const many_relationshipTypes = ["manyToSingleRelationship", "manyToManyRelationship"]
const many_allRelationshipFields = documentCopy.extraFields.filter(field => {
const currentField = currentBlueprint.extraFields.find(e => e.id === field.id) as unknown as I_ExtraFields
return (currentField && many_relationshipTypes.includes(currentField.type))
})
// Handle many document autogeneration
const many_relationshipTypesAutoGeneration = ["manyToNoneRelationship", "manyToSingleRelationship", "manyToManyRelationship"]
const many_allRelationshipFieldsAutoGeneration = documentCopy.extraFields.filter(field => {
const currentField = currentBlueprint.extraFields.find(e => e.id === field.id) as unknown as I_ExtraFields
return (currentField && many_relationshipTypesAutoGeneration.includes(currentField.type))
})
// Update many fields autogeneration
for (const field of many_allRelationshipFieldsAutoGeneration) {
const fieldArray = field.value?.value
if (Array.isArray(fieldArray)) {
for (const fieldValue of fieldArray) {
if (fieldValue?.isAutoGenerated) {
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
const pairedBlueprint: I_Blueprint = vueInstance.SGET_blueprint(fieldValue.type)
const newDocument = {
bgColor: undefined,
color: undefined,
extraFields: [
{
id: "name",
value: fieldValue.label
},
{
id: "parentDoc",
value: ""
},
{
id: "documentColor",
value: ""
},
{
id: "documentBackgroundColor",
value: ""
},
{
id: "finishedSwitch",
value: ""
},
{
id: "minorSwitch",
value: ""
},
{
id: "deadSwitch",
value: ""
},
{
id: "categorySwitch",
value: ""
},
{
id: "order",
value: ""
},
{
id: "tags",
value: []
},
{
id: "categoryDescription",
value: ""
}
],
hierarchicalPath: pairedBlueprint.namePlural,
icon: pairedBlueprint.icon,
id: fieldValue.id,
type: fieldValue.type,
// eslint-disable-next-line @typescript-eslint/restrict-template-expressions
url: `/project/display-content/${fieldValue.type}/${fieldValue.id}`,
_id: fieldValue.id
}
// @ts-ignore
window.FA_dbs[newDocument.type] = new PouchDB(newDocument.type)
// @ts-ignore
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
await window.FA_dbs[newDocument.type].put(newDocument)
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
vueInstance.SSET_addDocument({ doc: vueInstance.mapShortDocument(newDocument, vueInstance.SGET_allDocumentsByType(newDocument.type).docs) })
delete (fieldValue.isAutoGenerated)
}
}
}
}
// Update many fields
for (const field of many_allRelationshipFields) {
const many_updatedDocuments: I_OpenedDocument[] = await many_changeRelationshipToAnotherObject(field, documentCopy, currentDocument)
@ -151,6 +350,9 @@ export const saveDocument = async (
// Set edit mode for frontend
documentCopy.editMode = editModeAfterSave
clearTimeout(saveTimeout)
Loading.hide()
return { documentCopy, allOpenedDocuments }
}

View file

@ -29,7 +29,7 @@ export const single_changeRelationshipToAnotherObject = async (
if (previousValue && typeof currentValue !== "string" && currentValue) {
if (fieldType === "singleToSingleRelationship") {
updatedDocuments.push(await single_removeRelationshipFromAnotherObject(previousValue))
updatedDocuments.push(await single_removeRelationshipFromAnotherObject(currentValue, previousValue))
updatedDocuments.push(await single_addRelationshipToAnotherObject(field, currentValue, currentDocument))
}
if (fieldType === "singleToManyRelationship") {
@ -43,7 +43,7 @@ export const single_changeRelationshipToAnotherObject = async (
if ((previousValue && typeof currentValue === "string") || (previousValue && !currentValue)) {
if (fieldType === "singleToSingleRelationship") {
updatedDocuments.push(await single_removeRelationshipFromAnotherObject(previousValue))
updatedDocuments.push(await single_removeRelationshipFromAnotherObject(currentValue, previousValue))
}
if (fieldType === "singleToManyRelationship") {
const removedValued = await many_removeRelationshipFromAnotherObject(previousValue, currentDocument)
@ -102,6 +102,7 @@ export const single_addRelationshipToAnotherObject = async (
}
export const single_removeRelationshipFromAnotherObject = async (
currentValue: I_FieldRelationship,
previousValue: I_FieldRelationship
) => {
const typeToFind = previousValue.type
@ -113,7 +114,9 @@ export const single_removeRelationshipFromAnotherObject = async (
const pairedField = previousValue.pairedField
const pairedFieldIndex = pairedDocument.extraFields.findIndex(e => e.id === pairedField)
pairedDocument.extraFields[pairedFieldIndex].value = { value: "", addedValues: "" }
if (currentValue?._id !== previousValue?._id) {
pairedDocument.extraFields[pairedFieldIndex].value = { value: "", addedValues: "" }
}
// eslint-disable-next-line @typescript-eslint/no-unsafe-call
await window.FA_dbs[typeToFind].put(pairedDocument)
@ -157,7 +160,8 @@ export const many_changeRelationshipToAnotherObject = async (
}
if (fieldType === "manyToSingleRelationship") {
const removedValued = await single_removeRelationshipFromAnotherObject(removedValue)
// @ts-ignore
const removedValued = await single_removeRelationshipFromAnotherObject(removedValue, {})
if (removedValued) {
updatedDocuments.push(removedValued)
}

View file

@ -128,6 +128,7 @@ export const advancedDocumentFilter = (inputString: string, currentDocumentList:
// @ts-ignore
const matchingDocument = allDocuments.find(doc => doc.id === valueToMap._id)
if (matchingDocument) {
// @ts-ignore
returnValue = matchingDocument.extraFields.find(e => e.id === "name")?.value as string
@ -162,7 +163,7 @@ export const advancedDocumentFilter = (inputString: string, currentDocumentList:
}
// Fix all missing values that slipped through
if (!returnValue || returnValue.value === null) {
if (typeof returnValue !== "string") {
returnValue = ""
}

View file

@ -2,6 +2,7 @@ export interface OptionsStateInteface {
_id: string,
_rev?: string,
darkMode: boolean
preventFilledNoteBoardPopup: boolean
preventAutoScroll: boolean
hideAdvSearchCheatsheetButton: boolean
textShadow: boolean
@ -43,6 +44,7 @@ function state (): OptionsStateInteface {
return {
_id: "settings",
darkMode: false,
preventFilledNoteBoardPopup: false,
preventAutoScroll: false,
hideAdvSearchCheatsheetButton: false,
textShadow: false,

View file

@ -1,7 +1,10 @@
- **Add isAutoGenerated setter for document saving to prvent future conflicts**
- **Fix notes not saving in single-to-single relationships**
## THE GM BATCH
- Add on-the-fly generation of non-existent 2-way relationships
- Add hover/on-demand document preview to relationships
- Export for MD/PDF/ODT/DOCX
@ -15,8 +18,8 @@
- Add option for project graph to filter out categories or show them separately
- Add HTML webcolor cheatsheet in floating window (look for JSON of them somewhere?)
- Word count for editor fields
- Add "Open app folder" to help menu
- Try to get field titles to show in full-screen edit of text editor fields
- List of last saved documents on project overview
- Consider adding some kind of "Follower name" to different group types
- Consider reworking the save document mechanic (save doesnt close, open/exit edit mode instead)