Changes for Tab Notes

- change layout to classicFas to enable input note with one click less
- extend Tab component: add headerSuffix
- show count of messages in header
This commit is contained in:
ma0068
2025-08-07 15:30:04 +02:00
parent c96db9f573
commit b2d8b81ab5
7 changed files with 128 additions and 44 deletions
+4
View File
@@ -57,6 +57,10 @@ $config['tabs'] =
//if true, Anrechnungen can be added and edited in tab Anrechnungen
'editableAnrechnungen' => false,
],
'notes' => [
//if true, the count of Messages will be shown in the header of the Tab Messages
'showCountNotes' => true
]
];
// List of fields to show when ZGV_DOKTOR_ANZEIGEN is defined
@@ -62,10 +62,15 @@ class Config extends FHCAPI_Controller
'component' => './Stv/Studentenverwaltung/Details/Details.js',
'config' => $config['details']
];
$showSuffix = $config['notes']['showCountNotes'] ?? false;
$result['notes'] = [
'title' => $this->p->t('stv', 'tab_notes'),
'component' => './Stv/Studentenverwaltung/Details/Notizen.js'
'component' => './Stv/Studentenverwaltung/Details/Notizen.js',
'config' => $config['notes'],
'showSuffix' => $showSuffix && ($config['notes']['showCountNotes'] ?? false)
];
$result['contact'] = [
'title' => $this->p->t('stv', 'tab_contact'),
'component' => './Stv/Studentenverwaltung/Details/Kontakt.js',
+17
View File
@@ -21,6 +21,7 @@ abstract class Notiz_Controller extends FHCAPI_Controller
'loadDokumente' => self::DEFAULT_PERMISSION_R,
'getMitarbeiter' => self::DEFAULT_PERMISSION_R,
'isBerechtigt' => self::DEFAULT_PERMISSION_R,
'getCountNotes' => self::DEFAULT_PERMISSION_R,
];
if(!is_array($permissions))
@@ -459,4 +460,20 @@ abstract class Notiz_Controller extends FHCAPI_Controller
return $this->terminateWithSuccess($result);
}
public function getCountNotes($person_id)
{
$this->NotizzuordnungModel->addSelect('COUNT(*) AS anzahl', false);
$result = $this->NotizzuordnungModel->loadWhere(
array('person_id' => $person_id)
);
if (isError($result)) {
$this->terminateWithError(getError($result), self::ERROR_TYPE_GENERAL);
}
$anzahl = current(getData($result));
return $this->terminateWithSuccess($anzahl->anzahl ?: 0);
}
}
+6
View File
@@ -83,5 +83,11 @@ export default {
method: 'get',
url: 'api/frontend/v1/notiz/notizPerson/isBerechtigt/'
};
},
getCountNotes(person_id){
return {
method: 'get',
url: 'api/frontend/v1/notiz/notizPerson/getCountNotes/' + person_id
};
}
};
+26 -7
View File
@@ -296,6 +296,7 @@ export default {
showId: false,
showLastupdate: false
},
newCount: null
}
},
methods: {
@@ -367,6 +368,7 @@ export default {
.catch(this.$fhcAlert.handleSystemError)
.finally(() => {
window.scrollTo(0, 0);
this.getCountNotes();
});
},
deleteNotiz(notiz_id) {
@@ -381,6 +383,7 @@ export default {
.catch(this.$fhcAlert.handleSystemError)
.finally(() => {
window.scrollTo(0, 0);
this.getCountNotes();
});
},
loadNotiz(notiz_id) {
@@ -424,6 +427,7 @@ export default {
.catch(this.$fhcAlert.handleSystemError)
.finally(() => {
window.scrollTo(0, 0);
this.getCountNotes();
});
},
reload() {
@@ -464,7 +468,6 @@ export default {
});
},
initTinyMCE() {
const vm = this;
tinymce.init({
target: this.$refs.editor.$refs.input, //Important: not selector: to enable multiple import of component
@@ -503,15 +506,30 @@ export default {
this.showVariables[columnToShow] = true;
});
},
getCountNotes(){
return this.$api
.call(this.endpoint.getCountNotes(this.id))
.then(
result => {
this.newCount = result.data;
this.$nextTick(() => {
this.$emit('updateCount', this.newCount);
});
})
.catch(this.$fhcAlert.handleSystemError);
}
},
created() {
this.initializeShowVariables();
this.getUid();
},
async mounted() {
if(this.showTinyMce){
this.initTinyMCE();
if (this.showTinyMce) {
await this.initTinyMCE();
}
this.$nextTick(() => {
this.getCountNotes();
});
},
watch: {
//watcher für Tinymce-Textfeld
@@ -548,16 +566,17 @@ export default {
this.reload();
}
},
beforeDestroy() {
if(this.showTinyMce) {
this.editor.destroy();
beforeUnmount() {
if (this.editor && tinymce.get(this.editor.id)) {
tinymce.get(this.editor.id).remove();
this.editor = null;
}
},
template: `
<div class="core-notiz">
<div v-if="notizLayout=='classicFas'">
<core-filter-cmpt
ref="table"
:tabulator-options="tabulatorOptions"
@@ -12,26 +12,35 @@ export default {
},
data() {
return {
endpoint: ApiNotizPerson
endpoint: ApiNotizPerson,
countNotiz: ''
};
},
methods: {
updateCountNotes(countNew){
this.headerSuffix = "(" + countNew + ")";
this.$emit('update:suffix', this.headerSuffix);
}
},
template: `
<div class="stv-details-notizen h-100 pb-3">
<!-- mit factory als endpoint -->
<core-notiz
class="overflow-hidden"
:endpoint="endpoint"
ref="formc"
notiz-layout="popupModal"
type-id="person_id"
:id="modelValue.person_id"
show-document
show-tiny-mce
:visible-columns="['titel','text','verfasser','bearbeiter','dokumente']"
>
</core-notiz>
<!-- Test Version classicFas for enter with one click vs popupModal-->
<core-notiz
class="overflow-hidden"
:endpoint="endpoint"
ref="formc"
notiz-layout="classicFas"
type-id="person_id"
:id="modelValue.person_id"
show-document
show-tiny-mce
:visibleColumns="['titel','text','verfasser','bearbeiter','dokumente']"
@updateCount="updateCountNotes"
>
</core-notiz>
<!--
---------------------------------------------------------------------------------------------
-------------------- DESCRIPTION FOR PARAMETER PROPS ----------------------------------------
+45 -21
View File
@@ -14,7 +14,7 @@ export default {
emits: [
'update:modelValue',
'change',
'changed'
'changed',
],
props: {
config: {
@@ -40,7 +40,7 @@ export default {
currentTab() {
if (this.tabs[this.current])
return this.tabs[this.current];
return { component: 'div' };
},
value: {
@@ -97,13 +97,19 @@ export default {
if (!item.component)
return console.error('Component missing for ' + key);
//making it reactive for showing headerSuffix
const value = Vue.reactive({
suffix: '',
showSuffix: item.showSuffix || false
});
tabs[key] = {
component: Vue.markRaw(Vue.defineAsyncComponent(() => import(item.component))),
title: Vue.computed(() => item.title || key),
config: item.config,
key,
value: {}
}
value
};
}
if (Array.isArray(config))
@@ -118,6 +124,11 @@ export default {
this.current = Object.keys(tabs)[0];
}
this.tabs = tabs;
},
updateSuffix(event) {
if (this.currentTab?.value) {
this.currentTab.value.suffix = event;
}
}
},
created() {
@@ -126,28 +137,34 @@ export default {
template: `
<template v-if="useprimevue">
<tabview
:scrollable="true"
:lazy="true"
:activeIndex="calcActiveIndex"
@tab-click="handleTabClick"
>
<tabpanel
v-for="tab in tabs"
:key="tab.key"
:header="tab.title"
<tabview
:scrollable="true"
:lazy="true"
:activeIndex="calcActiveIndex"
@tab-click="handleTabClick"
>
<keep-alive>
<component :is="tab.component" v-model="value" :config="tab.config"></component>
</keep-alive>
</tabpanel>
</tabview>
<tabpanel
v-for="tab in tabs"
:key="tab.key"
:header="tab.title + (tab.value.showSuffix && tab.value.suffix ? tab.value.suffix : '')"
>
<keep-alive>
<component
:is="tab.component"
v-model="value"
:config="tab.config"
@update:suffix="updateSuffix($event)"
></component>
</keep-alive>
</tabpanel>
</tabview>
</template>
<template v-else="">
<div class="fhc-tabs d-flex" :class="vertical ? 'align-items-stretch gap-3' : (border ? 'flex-column' : 'flex-column gap-3')" v-if="Object.keys(tabs).length">
<div class="nav" :class="vertical ? 'nav-pills flex-column' : 'nav-tabs'">
<div
v-for="tab in tabs"
:key="tab.key"
@@ -157,15 +174,22 @@ export default {
:aria-current="tab.key == current ? 'page' : ''"
v-accessibility:tab.[vertical]
>
{{tab.title}}
{{tab.title}} <span v-if="tab.value.showSuffix && tab.value.suffix"> {{ tab.value.suffix }}</span>
</div>
</div>
<div :style="vertical ? '' : 'flex: 1 1 0%; height: 0%'" class="overflow-auto flex-grow-1" :class="vertical || !border ? '' : 'p-3 border-bottom border-start border-end'">
<keep-alive>
<component ref="current" :is="currentTab.component" v-model="value" :config="currentTab.config"></component>
<component
ref="current"
:is="currentTab.component"
v-model="value"
:config="currentTab.config"
@update:suffix="updateSuffix($event)"
></component>
</keep-alive>
</div>
</div>
</template>`
};