mirror of
https://github.com/FH-Complete/FHC-Core.git
synced 2026-10-12 15:04:04 +00:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ec59af8d5f | ||
|
|
6d641bbd06 | ||
|
|
3455aed3f5 | ||
|
|
f84d12277d | ||
|
|
9bf5bc2ad9 | ||
|
|
27765606e3 | ||
|
|
75d2cabdbe | ||
|
|
bae9d6d9a0 | ||
|
|
43d6a882ce | ||
|
|
7f3b4100ab | ||
|
|
9f54ecce54 | ||
|
|
7af0f4a478 | ||
|
|
0f843db33d | ||
|
|
3e59648d5b | ||
|
|
5923991848 | ||
|
|
55a6ec9d0d | ||
|
|
78505589c8 | ||
|
|
5e15d4b219 | ||
|
|
afb8011347 | ||
|
|
15beaa9be8 | ||
|
|
574057da88 | ||
|
|
a5797a0bde | ||
|
|
37d5f2da5d | ||
|
|
27c39cfdca | ||
|
|
06895510e0 | ||
|
|
83b06b6c50 | ||
|
|
eeb1529b64 | ||
|
|
98c3707802 | ||
|
|
e5c8807f17 |
@@ -84,7 +84,7 @@ $config['tabs'] =
|
||||
'showCountNotes' => true,
|
||||
|
||||
//if true: section with following fields will be displayed: 'verfasser', 'bearbeiter', 'von', 'bis' and 'erledigt'
|
||||
'showErweitert' => true,
|
||||
'showErweitert' => false,
|
||||
|
||||
//notizlayout: choose of "classicFas", "twoColumnsFormLeft", twoColumnsFormRight, popupModal"
|
||||
'notizLayout' => 'popupModal'
|
||||
|
||||
@@ -114,6 +114,7 @@ class LvPlan extends FHCAPI_Controller
|
||||
|
||||
// fetching lvplan events
|
||||
$result = $this->stundenplanlib->getEventsUser($start_date, $end_date, $uid);
|
||||
|
||||
$lvplanEvents = $this->getDataOrTerminateWithError($result);
|
||||
|
||||
// fetching moodle events
|
||||
|
||||
@@ -18,7 +18,7 @@ class NotizPerson extends Notiz_Controller
|
||||
'loadDokumente' => ['admin:r', 'assistenz:r'],
|
||||
'getMitarbeiter' => ['admin:r', 'assistenz:r'],
|
||||
'isBerechtigt' => ['admin:r', 'assistenz:r'],
|
||||
'getCountNotes' => ['admin:r', 'assistenz:r']
|
||||
'getCountNotes' => ['admin:r', 'assistenz:r'],
|
||||
]);
|
||||
|
||||
//Load Models
|
||||
|
||||
@@ -12,7 +12,7 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
public function __construct($permissions)
|
||||
{
|
||||
$default_permissions = [
|
||||
'getDefaultVerfasser' => self::DEFAULT_PERMISSION_R,
|
||||
'getUid' => self::DEFAULT_PERMISSION_R,
|
||||
'getNotizen' => self::DEFAULT_PERMISSION_R,
|
||||
'loadNotiz' => self::DEFAULT_PERMISSION_R,
|
||||
'addNewNotiz' => self::DEFAULT_PERMISSION_RW,
|
||||
@@ -21,7 +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
|
||||
'getCountNotes' => self::DEFAULT_PERMISSION_R,
|
||||
];
|
||||
|
||||
if(!is_array($permissions))
|
||||
@@ -46,20 +46,9 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
]);
|
||||
}
|
||||
|
||||
public function getDefaultVerfasser()
|
||||
public function getUid()
|
||||
{
|
||||
$uid = getAuthUID();
|
||||
$this->load->model('ressource/Mitarbeiter_model', 'MitarbeiterModel');
|
||||
$this->MitarbeiterModel->addSelect('p.person_id, p.nachname, p.vorname, p.titelpost, p.titelpre, ben.uid');
|
||||
$this->MitarbeiterModel->addJoin('public.tbl_benutzer ben', 'ON (ben.uid = public.tbl_mitarbeiter.mitarbeiter_uid)', 'LEFT');
|
||||
$this->MitarbeiterModel->addJoin('public.tbl_person p', 'ON (p.person_id = ben.person_id)', 'LEFT');
|
||||
|
||||
$result = $this->MitarbeiterModel->loadWhere(
|
||||
array('mitarbeiter_uid' => $uid)
|
||||
);
|
||||
if(hasData($result))
|
||||
$data = getData($result);
|
||||
$this->terminateWithSuccess(current($data));
|
||||
$this->terminateWithSuccess(getAuthUID());
|
||||
}
|
||||
|
||||
|
||||
@@ -117,7 +106,7 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
$this->terminateWithError("in abstract function: define right in extension", self::ERROR_TYPE_GENERAL);
|
||||
}
|
||||
|
||||
/* public function loadNotiz()
|
||||
public function loadNotiz()
|
||||
{
|
||||
$_POST = json_decode(utf8_encode($this->input->raw_input_stream), true);
|
||||
|
||||
@@ -129,43 +118,6 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
THEN public.tbl_notiz.updateamum ELSE public.tbl_notiz.insertamum END::timestamp, 'DD.MM.YYYY HH24:MI:SS') AS lastUpdate");
|
||||
$this->NotizModel->addLimit(1);
|
||||
|
||||
$result = $this->NotizModel->loadWhere(
|
||||
array('notiz_id' => $notiz_id)
|
||||
);
|
||||
if (isError($result))
|
||||
{
|
||||
$this->terminateWithError($result, self::ERROR_TYPE_GENERAL);
|
||||
}
|
||||
elseif (!hasData($result))
|
||||
{
|
||||
$this->terminateWithError($this->p->t('ui', 'error_missingId', ['id'=>'Notiz_id']), self::ERROR_TYPE_GENERAL);
|
||||
}
|
||||
else
|
||||
{
|
||||
$this->terminateWithSuccess(current(getData($result)));
|
||||
}
|
||||
}*/
|
||||
|
||||
public function loadNotiz()
|
||||
{
|
||||
$_POST = json_decode(utf8_encode($this->input->raw_input_stream), true);
|
||||
|
||||
$notiz_id = $this->input->post('notiz_id');
|
||||
|
||||
$this->NotizModel->addSelect('public.tbl_notiz.*');
|
||||
$this->NotizModel->addSelect("TO_CHAR(CASE WHEN public.tbl_notiz.updateamum >= public.tbl_notiz.insertamum
|
||||
THEN public.tbl_notiz.updateamum ELSE public.tbl_notiz.insertamum END::timestamp, 'DD.MM.YYYY HH24:MI:SS') AS lastUpdate");
|
||||
$this->NotizModel->addSelect('perb.person_id AS perb_person_id, perb.vorname AS perb_vorname, perb.nachname AS perb_nachname,
|
||||
perb.titelpre AS perb_titelpre, perb.titelpost AS perb_titelpost, benb.uid AS perb_uid');
|
||||
$this->NotizModel->addSelect('perv.person_id AS perv_person_id, perv.vorname AS perv_vorname, perv.nachname AS perv_nachname,
|
||||
perv.titelpre AS perv_titelpre, perv.titelpost AS perv_titelpost, benv.uid AS perv_uid');
|
||||
$this->NotizModel->addJoin('public.tbl_notiz_dokument', 'notiz_id', 'LEFT');
|
||||
$this->NotizModel->addJoin('public.tbl_benutzer benb', 'ON (benb.uid = public.tbl_notiz.bearbeiter_uid)', 'LEFT');
|
||||
$this->NotizModel->addJoin('public.tbl_person perb', 'ON (perb.person_id = benb.person_id)', 'LEFT');
|
||||
$this->NotizModel->addJoin('public.tbl_benutzer benv', 'ON (benv.uid = public.tbl_notiz.verfasser_uid)', 'LEFT');
|
||||
$this->NotizModel->addJoin('public.tbl_person perv', 'ON (perv.person_id = benv.person_id)', 'LEFT');
|
||||
$this->NotizModel->addLimit(1);
|
||||
|
||||
$result = $this->NotizModel->loadWhere(
|
||||
array('notiz_id' => $notiz_id)
|
||||
);
|
||||
@@ -286,6 +238,7 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
|
||||
public function updateNotiz()
|
||||
{
|
||||
|
||||
$this->load->library('form_validation');
|
||||
$this->load->library('DmsLib');
|
||||
|
||||
@@ -316,7 +269,7 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
$uid = getAuthUID();
|
||||
$titel = $post_data['titel'];
|
||||
$text = $post_data['text'];
|
||||
$bearbeiter_uid = $post_data['bearbeiter'];
|
||||
$bearbeiter_uid = isset($post_data['bearbeiter']) ? $post_data['bearbeiter'] : $post_data['bearbeiter_uid'];
|
||||
$erledigt = $post_data['erledigt'];
|
||||
$start = $post_data['start'];
|
||||
$ende = $post_data['ende'];
|
||||
@@ -483,15 +436,14 @@ abstract class Notiz_Controller extends FHCAPI_Controller
|
||||
$this->terminateWithSuccess(getData($result));
|
||||
}
|
||||
|
||||
public function getMitarbeiter()
|
||||
public function getMitarbeiter($searchString)
|
||||
{
|
||||
$searchString = $this->input->get('searchString') ?? '';
|
||||
$this->load->model('ressource/Mitarbeiter_model', 'MitarbeiterModel');
|
||||
$result = $this->MitarbeiterModel->searchMitarbeiter($searchString, 'mitAkadGrad');
|
||||
$result = $this->MitarbeiterModel->searchMitarbeiter($searchString);
|
||||
if (isError($result)) {
|
||||
$this->terminateWithError($result, self::ERROR_TYPE_GENERAL);
|
||||
}
|
||||
$this->terminateWithSuccess($result ?: []);
|
||||
$this->terminateWithSuccess($result);
|
||||
}
|
||||
|
||||
public function getCountNotes($person_id)
|
||||
|
||||
@@ -94,13 +94,13 @@ class StundenplanLib
|
||||
if (isError($benutzer_gruppen))
|
||||
return $benutzer_gruppen;
|
||||
$benutzer_gruppen = getData($benutzer_gruppen);
|
||||
|
||||
$this->_ci->addMeta('spezialgruppen', $benutzer_gruppen);
|
||||
// getting the student_lehrverbaende of the student in the different studiensemester
|
||||
$student_lehrverband = $this->fetchStudentlehrverbandFromStudiensemester($student_uid, $semester_range);
|
||||
if (isError($student_lehrverband))
|
||||
return $student_lehrverband;
|
||||
$student_lehrverband = getData($student_lehrverband);
|
||||
|
||||
$this->_ci->addMeta('studentlehrvebaende', $student_lehrverband);
|
||||
$stundenplan_query = $this->_ci->StundenplanModel->getStundenplanQuery(
|
||||
$start,
|
||||
$end,
|
||||
@@ -632,6 +632,7 @@ class StundenplanLib
|
||||
$result->semester = $item->semester;
|
||||
$result->verband = $item->verband;
|
||||
$result->gruppe = $item->gruppe;
|
||||
$result->studiensemester_kurzbz = $item->studiensemester_kurzbz;
|
||||
return $result;
|
||||
},
|
||||
$lehrverband_query_result);
|
||||
|
||||
@@ -28,10 +28,21 @@ class CoreMissingZgvTagLib
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_prestudentstatus', 'prestudent_id');
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_benutzer bn', 'person_id');
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_studiengang', 'studiengang_kz');
|
||||
|
||||
$this->ci->PrestudentModel->db->group_start();
|
||||
|
||||
$this->ci->PrestudentModel->db->where('zgvdatum', null);
|
||||
$this->ci->PrestudentModel->db->where('typ', 'b');
|
||||
|
||||
$this->ci->PrestudentModel->db->or_group_start();
|
||||
$this->ci->PrestudentModel->db->where('zgvmadatum', null);
|
||||
$this->ci->PrestudentModel->db->where('typ', 'm');
|
||||
$this->ci->PrestudentModel->db->group_end();
|
||||
|
||||
$this->ci->PrestudentModel->db->group_end();
|
||||
|
||||
$result = $this->ci->PrestudentModel-> loadWhere(array(
|
||||
'bn.aktiv' => true, //check if necessary
|
||||
'zgvdatum' => null,
|
||||
'typ' => 'b',
|
||||
'bn.aktiv' => true,
|
||||
'studiensemester_kurzbz' => $semester
|
||||
));
|
||||
|
||||
@@ -60,16 +71,36 @@ class CoreMissingZgvTagLib
|
||||
$semester = $params['studiensemester_kurzbz'];
|
||||
$prestudent_id = $params['id'];
|
||||
|
||||
$this->ci->PrestudentModel->addSelect('prestudent_id');
|
||||
$this->ci->PrestudentModel->addSelect('start as von');
|
||||
$this->ci->PrestudentModel->addSelect('ende as bis');
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_prestudentstatus', 'prestudent_id');
|
||||
|
||||
//add studiensemester also here for manual rebuild
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_studiensemester', 'studiensemester_kurzbz');
|
||||
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_benutzer bn', 'person_id');
|
||||
$this->ci->PrestudentModel->addJoin('public.tbl_studiengang', 'studiengang_kz');
|
||||
$result = $this->ci->PrestudentModel->loadWhere(array(
|
||||
'bn.aktiv' => true, //check if necessary
|
||||
'zgvdatum' => null,
|
||||
'typ' => 'b',
|
||||
|
||||
$this->ci->PrestudentModel->db->group_start();
|
||||
|
||||
$this->ci->PrestudentModel->db->where('zgvdatum', null);
|
||||
$this->ci->PrestudentModel->db->where('typ', 'b');
|
||||
|
||||
$this->ci->PrestudentModel->db->or_group_start();
|
||||
$this->ci->PrestudentModel->db->where('zgvmadatum', null);
|
||||
$this->ci->PrestudentModel->db->where('typ', 'm');
|
||||
$this->ci->PrestudentModel->db->group_end();
|
||||
|
||||
$this->ci->PrestudentModel->db->group_end();
|
||||
$this->ci->PrestudentModel->db->limit(1);
|
||||
|
||||
$result = $this->ci->PrestudentModel-> loadWhere(array(
|
||||
'bn.aktiv' => true,
|
||||
'studiensemester_kurzbz' => $semester,
|
||||
'prestudent_id' => $prestudent_id
|
||||
));
|
||||
|
||||
if(hasData($result))
|
||||
{
|
||||
return $result;
|
||||
|
||||
@@ -225,6 +225,10 @@ class Gehaltsbestandteil extends AbstractBestandteil implements \JsonSerializabl
|
||||
$grundbetrag = number_format($grundbetrag, 2, '.', '');
|
||||
}
|
||||
$this->markDirty('grundbetrag', $this->grundbetrag, $grundbetrag);
|
||||
if(in_array('grundbetrag', $this->modifiedcolumns))
|
||||
{
|
||||
$this->setBetrag_valorisiert($grundbetrag);
|
||||
}
|
||||
$this->grundbetrag = $grundbetrag;
|
||||
return $this;
|
||||
}
|
||||
|
||||
@@ -204,7 +204,7 @@ class Student_model extends DB_Model
|
||||
|
||||
Events::trigger(
|
||||
'generate_student_uid',
|
||||
function ($value) use ($uid) {
|
||||
function ($value) use (&$uid) {
|
||||
$uid = $value;
|
||||
},
|
||||
$stgkzl,
|
||||
|
||||
@@ -457,6 +457,7 @@ class Studiengang_model extends DB_Model
|
||||
*/
|
||||
public function getLeitung($studiengang_kz = null)
|
||||
{
|
||||
$this->addDistinct();
|
||||
$this->addSelect('uid, studiengang_kz, oe_kurzbz, vorname, nachname, email, titelpre, titelpost, alias');
|
||||
$this->addJoin('public.tbl_benutzerfunktion', 'oe_kurzbz');
|
||||
$this->addJoin('public.tbl_benutzer', 'uid');
|
||||
|
||||
@@ -604,11 +604,17 @@ class Stundenplan_model extends DB_Model
|
||||
{
|
||||
foreach($semester_date_range as $sem_date => $sem_date_range)
|
||||
{
|
||||
if(!array_key_exists($sem_date,$studentlehrverbaende) || count($studentlehrverbaende[$sem_date]) == 0)
|
||||
if(!array_key_exists($sem,$studentlehrverbaende) || count($studentlehrverbaende[$sem]) == 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
foreach($studentlehrverbaende[$sem_date] as $key=>$lehrverband)
|
||||
$studlvbds = array_filter(
|
||||
$studentlehrverbaende[$sem],
|
||||
function($value) use ($sem_date) {
|
||||
return $value->studiensemester_kurzbz === $sem_date;
|
||||
}
|
||||
);
|
||||
foreach($studlvbds as $key=>$lehrverband)
|
||||
{
|
||||
$query .= "(((sp.studiengang_kz = ".$this->escape($lehrverband->studiengang_kz)." AND sp.semester = ".$this->escape($lehrverband->semester)." AND sp.verband = ".$this->escape($lehrverband->verband)." AND sp.gruppe = ".$this->escape($lehrverband->gruppe)." AND sp.datum BETWEEN ".$this->escape($sem_date_range->start)." AND ".$this->escape($sem_date_range->ende).")";
|
||||
// Eintraege fuer den ganzen Verband
|
||||
|
||||
@@ -62,3 +62,16 @@
|
||||
top:13%;"
|
||||
z-index: 104; font-size: 1rem; width: 2.5rem; height: 2.5rem; opacity:0; transition: opacity 0.2s; top:13%;"
|
||||
}*/
|
||||
|
||||
.tag-hover:hover {
|
||||
background-color: #e9ecef;
|
||||
}
|
||||
|
||||
.green {
|
||||
background-color: #e9ecef;
|
||||
}
|
||||
|
||||
.btn-hover {
|
||||
--bs-btn-hover-bg: #e9ecef; /* Neue Hintergrundfarbe beim Hover */
|
||||
--bs-btn-hover-border-color: #e9ecef; /* Neue Rahmenfarbe beim Hover */
|
||||
}
|
||||
|
||||
@@ -145,3 +145,8 @@
|
||||
float: right;
|
||||
margin-top: 3px;
|
||||
}
|
||||
|
||||
.btn-hover {
|
||||
--bs-btn-hover-bg: #e9ecef;
|
||||
--bs-btn-hover-border-color: #e9ecef;
|
||||
}
|
||||
|
||||
@@ -28,12 +28,6 @@ export default {
|
||||
url: 'api/frontend/v1/notiz/notizPerson/getUid/'
|
||||
};
|
||||
},
|
||||
getDefaultVerfasser() {
|
||||
return {
|
||||
method: 'get',
|
||||
url: 'api/frontend/v1/notiz/notizPerson/getDefaultVerfasser/'
|
||||
};
|
||||
},
|
||||
addNewNotiz(id, params) {
|
||||
return {
|
||||
method: 'post',
|
||||
@@ -77,11 +71,10 @@ export default {
|
||||
params
|
||||
};
|
||||
},
|
||||
getMitarbeiter(searchString) {
|
||||
getMitarbeiter(event) {
|
||||
return {
|
||||
method: 'get',
|
||||
url: 'api/frontend/v1/notiz/notizPerson/getMitarbeiter',
|
||||
params: { searchString }
|
||||
url: 'api/frontend/v1/notiz/notizPerson/getMitarbeiter/' + event
|
||||
};
|
||||
},
|
||||
isBerechtigt(id, type_id) {
|
||||
|
||||
@@ -22,6 +22,7 @@ import OtherLvPlan from "../../components/Cis/LvPlan/OtherLvPlan.js";
|
||||
|
||||
import ApiRouteInfo from '../../api/factory/routeinfo.js';
|
||||
import {capitalize} from "../../helpers/StringHelpers.js";
|
||||
import { getTodayISO, toDateTime } from "../../helpers/DateHelpers.js";
|
||||
|
||||
const ciPath = FHC_JS_DATA_STORAGE_OBJECT.app_root.replace(/(https:|)(^|\/\/)(.*?\/)/g, '') + FHC_JS_DATA_STORAGE_OBJECT.ci_router;
|
||||
const isMobile = window.matchMedia("(max-width: 767px)").matches;
|
||||
@@ -88,7 +89,7 @@ const router = VueRouter.createRouter({
|
||||
params: { // in this case always populate other params since they are not optional
|
||||
ort_kurzbz: to.params.ort_kurzbz,
|
||||
mode: isMobile ? DEFAULT_MODE_RAUMINFO_MOBILE : DEFAULT_MODE_RAUMINFO_DESKTOP,
|
||||
focus_date: new Date().toISOString().split("T")[0]
|
||||
focus_date: getTodayISO()
|
||||
},
|
||||
};
|
||||
},
|
||||
@@ -107,8 +108,7 @@ const router = VueRouter.createRouter({
|
||||
: (isMobile ? DEFAULT_MODE_RAUMINFO_MOBILE : DEFAULT_MODE_RAUMINFO_DESKTOP);
|
||||
|
||||
// default to today date if not provided
|
||||
const d = new Date(route.params.focus_date)
|
||||
const focus_date = !isNaN(d) ? route.params.focus_date : new Date().toISOString().split("T")[0];
|
||||
const focus_date = toDateTime(route.params.focus_date) ? route.params.focus_date : getTodayISO();
|
||||
|
||||
// for consistency reasons format the props into one object but actually use a new name to we dont collide with
|
||||
// existing viewData declaration written from codeigniter 3 into routerview tag
|
||||
@@ -127,7 +127,7 @@ const router = VueRouter.createRouter({
|
||||
name: "RoomInformation",
|
||||
params: {
|
||||
mode: to.params.mode || DEFAULT_MODE_RAUMINFO,
|
||||
focus_date: to.params.focus_date || new Date().toISOString().split("T")[0],
|
||||
focus_date: to.params.focus_date || getTodayISO(),
|
||||
ort_kurzbz: route.params.ort_kurzbz
|
||||
}
|
||||
});
|
||||
|
||||
@@ -174,6 +174,9 @@ export default {
|
||||
>
|
||||
{{ $p.t('lehre/noLvFound') }}
|
||||
</div>
|
||||
<div v-else-if="!renderers || !renderers[event.type]" class="placeholder-glow">
|
||||
<span class="placeholder col-12"></span>
|
||||
</div>
|
||||
<div
|
||||
v-else
|
||||
:class="'event-type-' + event.type + ' ' + mode + 'PageContainer'"
|
||||
|
||||
@@ -79,6 +79,9 @@ export default {
|
||||
>
|
||||
{{ $p.t('lehre/noLvFound') }}
|
||||
</div>
|
||||
<div v-else-if="!renderers || !renderers[event.type]" class="placeholder-glow">
|
||||
<span class="placeholder col-12"></span>
|
||||
</div>
|
||||
<component
|
||||
v-else-if="mode == 'eventheader'"
|
||||
:is="renderers[event.type]?.modalTitle"
|
||||
|
||||
@@ -2,7 +2,7 @@ import BsModal from '../../Bootstrap/Modal.js';
|
||||
import VueDatePicker from '../../vueDatepicker.js.php';
|
||||
import ApiAbgabe from '../../../api/factory/abgabe.js'
|
||||
import { getDateStyleClass } from "./getDateStyleClass.js";
|
||||
import {compareISODateValues, formatDateTime, formatISODate, getViennaTodayISO} from "./dateUtils.js";
|
||||
import { compareISODateValues, formatDate, formatDateTime, getTodayISO } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
|
||||
export const AbgabeMitarbeiterDetail = {
|
||||
@@ -174,7 +174,7 @@ export const AbgabeMitarbeiterDetail = {
|
||||
'fixtermin': false,
|
||||
'invertedFixtermin': true,
|
||||
'kurzbz': '', // todo kurzbz textfield value vorschlag für qualgates
|
||||
'datum': getViennaTodayISO(),
|
||||
'datum': getTodayISO(),
|
||||
'note': this.allowedNotenOptions.find(opt => opt.note == 9),
|
||||
'beurteilungsnotiz': '',
|
||||
'upload_allowed': false,
|
||||
@@ -351,9 +351,7 @@ export const AbgabeMitarbeiterDetail = {
|
||||
}
|
||||
}
|
||||
},
|
||||
formatDate(dateParam) {
|
||||
return formatISODate(dateParam)
|
||||
},
|
||||
formatDate,
|
||||
openCreateNewAbgabeModal() {
|
||||
if(this.projektarbeit?.betreuerart_kurzbz == 'Zweitbegutachter') {
|
||||
// maybe alert that this is not allowed or smth
|
||||
@@ -370,7 +368,7 @@ export const AbgabeMitarbeiterDetail = {
|
||||
'fixtermin': false,
|
||||
'invertedFixtermin': true,
|
||||
'kurzbz': '',
|
||||
'datum': getViennaTodayISO(),
|
||||
'datum': getTodayISO(),
|
||||
'note': this.allowedNotenOptions.find(opt => opt.note == 9),
|
||||
'beurteilungsnotiz': '',
|
||||
'upload_allowed': typ.upload_allowed_default,
|
||||
@@ -404,7 +402,7 @@ export const AbgabeMitarbeiterDetail = {
|
||||
'fixtermin': false,
|
||||
'invertedFixtermin': true,
|
||||
'kurzbz': '',
|
||||
'datum': getViennaTodayISO(),
|
||||
'datum': getTodayISO(),
|
||||
'note': this.allowedNotenOptions.find(opt => opt.note == 9),
|
||||
'beurteilungsnotiz': '',
|
||||
'upload_allowed': false,
|
||||
@@ -603,7 +601,7 @@ export const AbgabeMitarbeiterDetail = {
|
||||
'fixtermin': false,
|
||||
'invertedFixtermin': true,
|
||||
'kurzbz': '',
|
||||
'datum': getViennaTodayISO(),
|
||||
'datum': getTodayISO(),
|
||||
'note': this.allowedNotenOptions.find(opt => opt.note == 9),
|
||||
'beurteilungsnotiz': '',
|
||||
'upload_allowed': typ.upload_allowed_default,
|
||||
|
||||
@@ -3,7 +3,7 @@ import BsModal from '../../Bootstrap/Modal.js';
|
||||
import VueDatePicker from '../../vueDatepicker.js.php';
|
||||
import ApiAbgabe from '../../../api/factory/abgabe.js'
|
||||
import FhcOverlay from "../../Overlay/FhcOverlay.js";
|
||||
import { formatISODate, getViennaTodayISO } from "./dateUtils.js";
|
||||
import { formatDate, getTodayISO } from "../../../helpers/DateHelpers.js";
|
||||
import { validateThesisTitle } from './titleValidation.js'
|
||||
|
||||
|
||||
@@ -248,9 +248,7 @@ export const AbgabeStudentDetail = {
|
||||
|
||||
window.open(FHC_JS_DATA_STORAGE_OBJECT.app_root + FHC_JS_DATA_STORAGE_OBJECT.ci_router + url)
|
||||
},
|
||||
formatDate(dateParam) {
|
||||
return formatISODate(dateParam)
|
||||
},
|
||||
formatDate,
|
||||
async upload(termin) {
|
||||
|
||||
if (! await this.validate(termin))
|
||||
@@ -286,7 +284,7 @@ export const AbgabeStudentDetail = {
|
||||
if(res.meta.status == "success") {
|
||||
this.$fhcAlert.alertSuccess(this.$capitalize(this.$p.t('abgabetool/c4fileUploadSuccessv3')))
|
||||
|
||||
termin.abgabedatum = getViennaTodayISO();
|
||||
termin.abgabedatum = getTodayISO();
|
||||
if(res?.data?.signatur !== undefined) {
|
||||
termin.signatur = res.data.signatur
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import AbgabeterminStatusLegende from "./StatusLegende.js";
|
||||
import {formatDateTime} from "./dateUtils.js";
|
||||
import { formatDateTime } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
export const AbgabeStudentTimeline = {
|
||||
name: "AbgabeStudentTimeline",
|
||||
|
||||
@@ -11,7 +11,7 @@ import AbgabeStudentTimeline from "./AbgabeStudentTimeline.js";
|
||||
import { splitMailsHelper } from "../../../helpers/EmailHelpers.js"
|
||||
import { getDateStyleClass} from "./getDateStyleClass.js";
|
||||
import { dateFilter } from '../../../tabulator/filters/DatesManual.js';
|
||||
import { compareISODateValues, formatISODate, getViennaTodayISO, toViennaDate } from "./dateUtils.js";
|
||||
import { compareISODateValues, formatDate, getNow, getTodayISO, toDateTime } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
export const AbgabetoolAssistenz = {
|
||||
name: "AbgabetoolAssistenz",
|
||||
@@ -114,7 +114,7 @@ export const AbgabetoolAssistenz = {
|
||||
fixtermin: false,
|
||||
},
|
||||
serienTermin: Vue.reactive({
|
||||
datum: getViennaTodayISO(),
|
||||
datum: getTodayISO(),
|
||||
bezeichnung: {
|
||||
paabgabetyp_kurzbz: 'zwischen',
|
||||
bezeichnung: 'Zwischenabgabe'
|
||||
@@ -643,7 +643,7 @@ export const AbgabetoolAssistenz = {
|
||||
upload_allowed: false,
|
||||
fixtermin: false,
|
||||
}
|
||||
this.serienEdit.datum = getViennaTodayISO()
|
||||
this.serienEdit.datum = getTodayISO()
|
||||
this.serienEdit.bezeichnung = this.abgabeTypeOptions.find(opt => opt.paabgabetyp_kurzbz === 'zwischen')
|
||||
this.serienEdit.kurzbz = ''
|
||||
this.serienEdit.upload_allowed = false
|
||||
@@ -1091,23 +1091,9 @@ export const AbgabetoolAssistenz = {
|
||||
return false;
|
||||
}
|
||||
|
||||
const toLuxon = (val) => {
|
||||
if (!val) return null;
|
||||
let dt;
|
||||
if (val instanceof Date) {
|
||||
dt = luxon.DateTime.fromJSDate(val);
|
||||
} else if (typeof val === "string") {
|
||||
dt = toViennaDate(val);
|
||||
} else { // fallback
|
||||
dt = luxon.DateTime.fromMillis(Number(val));
|
||||
}
|
||||
|
||||
return dt.isValid ? dt : null;
|
||||
};
|
||||
|
||||
const rowDate = toLuxon(rowVal);
|
||||
const von = toLuxon(filterVal[0]);
|
||||
const bis = toLuxon(filterVal[1]);
|
||||
const rowDate = toDateTime(rowVal);
|
||||
const von = toDateTime(filterVal[0]);
|
||||
const bis = toDateTime(filterVal[1]);
|
||||
|
||||
// specific day
|
||||
if (von && !bis) {
|
||||
@@ -1128,22 +1114,8 @@ export const AbgabetoolAssistenz = {
|
||||
|
||||
const rowDate = rowVal.luxonDate;
|
||||
|
||||
const toLuxon = (val) => {
|
||||
if (!val) return null;
|
||||
let dt;
|
||||
if (val instanceof Date) {
|
||||
dt = luxon.DateTime.fromJSDate(val);
|
||||
} else if (typeof val === "string") {
|
||||
dt = toViennaDate(val);
|
||||
} else { // fallback
|
||||
dt = luxon.DateTime.fromMillis(Number(val));
|
||||
}
|
||||
|
||||
return dt.isValid ? dt : null;
|
||||
};
|
||||
|
||||
const von = toLuxon(filterVal[0]);
|
||||
const bis = toLuxon(filterVal[1]);
|
||||
const von = toDateTime(filterVal[0]);
|
||||
const bis = toDateTime(filterVal[1]);
|
||||
|
||||
// specific day
|
||||
if (von && !bis) {
|
||||
@@ -1372,7 +1344,7 @@ export const AbgabetoolAssistenz = {
|
||||
|
||||
},
|
||||
checkAbgabetermineProjektarbeit(projekt) {
|
||||
const now = luxon.DateTime.now()
|
||||
const now = getNow()
|
||||
|
||||
// calculate Abgabetermin time diff to now and assign last and next to projekt
|
||||
projekt.abgabetermine.forEach(termin => {
|
||||
@@ -1387,7 +1359,7 @@ export const AbgabetoolAssistenz = {
|
||||
// while already looping through each termin, calculate datestyle beforehand
|
||||
termin.dateStyle = getDateStyleClass(termin, this.notenOptions)
|
||||
|
||||
const date = toViennaDate(termin.datum).endOf('day')
|
||||
const date = toDateTime(termin.datum).endOf('day')
|
||||
termin.luxonDate = date
|
||||
termin.diffMs = date.toMillis() - now.toMillis(); // positive = future, negative = past
|
||||
|
||||
@@ -1654,9 +1626,7 @@ export const AbgabetoolAssistenz = {
|
||||
getNotenFilterOptionLabel(option) {
|
||||
return option.bezeichnung
|
||||
},
|
||||
formatDate(dateParam) {
|
||||
return formatISODate(dateParam);
|
||||
},
|
||||
formatDate,
|
||||
formAction(cell) {
|
||||
const actionButtons = document.createElement('div');
|
||||
actionButtons.className = "d-flex gap-3";
|
||||
@@ -1851,9 +1821,7 @@ export const AbgabetoolAssistenz = {
|
||||
return str
|
||||
},
|
||||
isPastDate(date) {
|
||||
const deadline = luxon.DateTime.fromISO(date, { zone: 'Europe/Vienna' }).endOf('day');
|
||||
const nowInVienna = luxon.DateTime.now().setZone('Europe/Vienna');
|
||||
return nowInVienna > deadline;
|
||||
return getNow() > toDateTime(date).endOf("day");
|
||||
},
|
||||
setDetailComponent(details){
|
||||
const pa = this.projektarbeiten.find(projektarbeit => projektarbeit.projektarbeit_id == details.projektarbeit_id)
|
||||
|
||||
@@ -7,7 +7,7 @@ import FhcOverlay from "../../Overlay/FhcOverlay.js";
|
||||
import { getDateStyleClass } from "./getDateStyleClass.js";
|
||||
import { dateFilter } from '../../../tabulator/filters/DatesManual.js';
|
||||
import {splitMailsHelper} from "../../../helpers/EmailHelpers.js";
|
||||
import { formatISODate, getViennaTodayISO, toViennaDate } from "./dateUtils.js";
|
||||
import { formatDate, getNow, getTodayISO, toDateTime } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
export const AbgabetoolMitarbeiter = {
|
||||
name: "AbgabetoolMitarbeiter",
|
||||
@@ -54,7 +54,7 @@ export const AbgabetoolMitarbeiter = {
|
||||
allowedNotenOptions: null,
|
||||
notenOptionsNonFinal: null,
|
||||
serienTermin: Vue.reactive({
|
||||
datum: getViennaTodayISO(),
|
||||
datum: getTodayISO(),
|
||||
bezeichnung: {
|
||||
paabgabetyp_kurzbz: 'zwischen',
|
||||
bezeichnung: 'Zwischenabgabe'
|
||||
@@ -668,22 +668,8 @@ export const AbgabetoolMitarbeiter = {
|
||||
|
||||
const rowDate = rowVal.luxonDate;
|
||||
|
||||
const toLuxon = (val) => {
|
||||
if (!val) return null;
|
||||
let dt;
|
||||
if (val instanceof Date) {
|
||||
dt = luxon.DateTime.fromJSDate(val);
|
||||
} else if (typeof val === "string") {
|
||||
dt = toViennaDate(val);
|
||||
} else { // fallback
|
||||
dt = luxon.DateTime.fromMillis(Number(val));
|
||||
}
|
||||
|
||||
return dt.isValid ? dt : null;
|
||||
};
|
||||
|
||||
const von = toLuxon(filterVal[0]);
|
||||
const bis = toLuxon(filterVal[1]);
|
||||
const von = toDateTime(filterVal[0]);
|
||||
const bis = toDateTime(filterVal[1]);
|
||||
|
||||
// specific day
|
||||
if (von && !bis) {
|
||||
@@ -899,14 +885,14 @@ export const AbgabetoolMitarbeiter = {
|
||||
}
|
||||
},
|
||||
checkAbgabetermineProjektarbeit(projekt) {
|
||||
const now = luxon.DateTime.now()
|
||||
const now = getNow()
|
||||
// calculate Abgabetermin time diff to now and assign last and next to projekt
|
||||
projekt.abgabetermine.forEach(termin => {
|
||||
|
||||
// while already looping through each termin, calculate datestyle beforehand
|
||||
termin.dateStyle = getDateStyleClass(termin, this.notenOptions)
|
||||
|
||||
const date = toViennaDate(termin.datum).endOf('day')
|
||||
const date = toDateTime(termin.datum).endOf('day')
|
||||
termin.luxonDate = date
|
||||
termin.diffMs = date.toMillis() - now.toMillis(); // positive = future, negative = past
|
||||
|
||||
@@ -1017,9 +1003,7 @@ export const AbgabetoolMitarbeiter = {
|
||||
getOptionLabelAbgabetyp(option){
|
||||
return this.$p.t('abgabetool/c4paatyp' + option.paabgabetyp_kurzbz)
|
||||
},
|
||||
formatDate(dateParam) {
|
||||
return formatISODate(dateParam);
|
||||
},
|
||||
formatDate,
|
||||
undoSelection(cell) {
|
||||
// checks if cells row is selected and unselects -> imitates columns which dont trigger row selection
|
||||
// but actually just revert it after the fact
|
||||
@@ -1104,9 +1088,7 @@ export const AbgabetoolMitarbeiter = {
|
||||
return str
|
||||
},
|
||||
isPastDate(date) {
|
||||
const deadline = luxon.DateTime.fromISO(date, { zone: 'Europe/Vienna' }).endOf('day');
|
||||
const nowInVienna = luxon.DateTime.now().setZone('Europe/Vienna');
|
||||
return nowInVienna > deadline;
|
||||
return getNow() > toDateTime(date).endOf("day");
|
||||
},
|
||||
setDetailComponent(details){
|
||||
this.loading=true
|
||||
|
||||
@@ -4,6 +4,7 @@ import ApiAuthinfo from '../../../api/factory/authinfo.js';
|
||||
import BsModal from "../../Bootstrap/Modal.js";
|
||||
import FhcOverlay from "../../Overlay/FhcOverlay.js";
|
||||
import { getDateStyleClass} from "./getDateStyleClass.js";
|
||||
import { getNow, toDateTime } from "../../../helpers/DateHelpers.js";
|
||||
import { validateThesisTitle } from './titleValidation.js'
|
||||
|
||||
export const AbgabetoolStudent = {
|
||||
@@ -171,9 +172,7 @@ export const AbgabetoolStudent = {
|
||||
return qgate1positiv && qgate2positiv
|
||||
},
|
||||
isPastDate(date) {
|
||||
const deadline = luxon.DateTime.fromISO(date, { zone: 'Europe/Vienna' }).endOf('day');
|
||||
const nowInVienna = luxon.DateTime.now().setZone('Europe/Vienna');
|
||||
return nowInVienna > deadline;
|
||||
return getNow() > toDateTime(date).endOf("day");
|
||||
},
|
||||
setDetailComponent(details){
|
||||
this.loading = true
|
||||
|
||||
@@ -1,33 +0,0 @@
|
||||
const zone = 'Europe/Vienna';
|
||||
|
||||
export function getViennaTodayISO() {
|
||||
return luxon.DateTime.now().setZone(zone).toISODate();
|
||||
}
|
||||
|
||||
export function formatISODate(dateParam) {
|
||||
if (!dateParam) return '';
|
||||
|
||||
const date = luxon.DateTime.fromISO(String(dateParam), { zone });
|
||||
return date.isValid ? date.toFormat('dd.MM.yyyy') : '';
|
||||
}
|
||||
|
||||
export function formatDateTime(dateParam) {
|
||||
if (!dateParam) return '';
|
||||
|
||||
const date = luxon.DateTime.fromSQL(dateParam);
|
||||
return date.isValid ? date.toFormat("dd.MM.yyyy HH:mm") : '';
|
||||
}
|
||||
|
||||
export function toViennaDate(dateParam) {
|
||||
if (!dateParam) return null;
|
||||
|
||||
return luxon.DateTime.fromISO(String(dateParam), { zone });
|
||||
}
|
||||
|
||||
export function compareISODateValues(a, b) {
|
||||
if (!a && !b) return 0;
|
||||
if (!a) return 1;
|
||||
if (!b) return -1;
|
||||
|
||||
return String(a).localeCompare(String(b));
|
||||
}
|
||||
@@ -1,12 +1,12 @@
|
||||
|
||||
const zone = 'Europe/Vienna';
|
||||
import { getNow, toDateTime } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
export function getDateStyleClass(termin, notenOptions) {
|
||||
const today = luxon.DateTime.now().setZone(zone);
|
||||
const datum = luxon.DateTime.fromISO(termin.datum, { zone }).endOf('day');
|
||||
const abgabedatum = termin.abgabedatum ? luxon.DateTime.fromISO(termin.abgabedatum, { zone }) : null;
|
||||
termin.diffindays = datum.diff(today, 'days').days;
|
||||
const isLate = abgabedatum && abgabedatum > datum;
|
||||
const today = getNow();
|
||||
const datum = toDateTime(termin.datum)?.endOf('day');
|
||||
const abgabedatum = toDateTime(termin.abgabedatum);
|
||||
termin.diffindays = datum ? datum.diff(today, 'days').days : NaN;
|
||||
const isLate = abgabedatum && datum && abgabedatum > datum;
|
||||
|
||||
// GRADE STATUS
|
||||
if (termin.note) {
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { numberPadding, formatDate } from "../../../helpers/DateHelpers.js"
|
||||
import { formatDate, formatTime } from "../../../helpers/DateHelpers.js"
|
||||
|
||||
export default {
|
||||
props: {
|
||||
@@ -25,27 +25,14 @@ export default {
|
||||
return FHC_JS_DATA_STORAGE_OBJECT.app_root + FHC_JS_DATA_STORAGE_OBJECT.ci_router + `/CisVue/Cms/content/${this.event.ort_content_id}`
|
||||
},
|
||||
start_time: function () {
|
||||
if (!this.event.start) return 'N/A';
|
||||
if (!this.event.start instanceof Date) {
|
||||
return this.event.start;
|
||||
}
|
||||
return numberPadding(this.event.start.getHours()) + ":" + numberPadding(this.event.start.getMinutes());
|
||||
return this.event.start ? formatTime(this.event.start) : 'N/A';
|
||||
},
|
||||
end_time: function () {
|
||||
if (!this.event.end) return 'N/A';
|
||||
if (!this.event.end instanceof Date) {
|
||||
return this.event.end;
|
||||
}
|
||||
return numberPadding(this.event.end.getHours()) + ":" + numberPadding(this.event.end.getMinutes());
|
||||
return this.event.end ? formatTime(this.event.end) : 'N/A';
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
mehtodNumberPadding: function (number) {
|
||||
return numberPadding(number);
|
||||
},
|
||||
methodFormatDate: function (d) {
|
||||
return formatDate(d);
|
||||
},
|
||||
methodFormatDate: formatDate,
|
||||
},
|
||||
template:/*html*/`
|
||||
<table class="table table-hover mb-4">
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import FhcCalendar from "../../Calendar/LvPlan.js";
|
||||
|
||||
import ApiLvPlan from '../../../api/factory/lvPlan.js';
|
||||
import { getTodayISO } from "../../../helpers/DateHelpers.js";
|
||||
|
||||
export const DEFAULT_MODE_RAUMINFO_MOBILE = 'List';
|
||||
export const DEFAULT_MODE_RAUMINFO_DESKTOP = 'Week';
|
||||
@@ -17,7 +18,7 @@ export default {
|
||||
inject: ["isMobile"],
|
||||
computed: {
|
||||
currentDay() {
|
||||
return this.propsViewData?.focus_date || luxon.DateTime.now().setZone(FHC_JS_DATA_STORAGE_OBJECT.timezone).toISODate();
|
||||
return this.propsViewData?.focus_date || getTodayISO();
|
||||
},
|
||||
currentMode() {
|
||||
const defaultMode = this.isMobile ? DEFAULT_MODE_RAUMINFO_MOBILE : DEFAULT_MODE_RAUMINFO_DESKTOP;
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import {CoreFilterCmpt} from "../../../components/filter/Filter.js";
|
||||
import VueDatePicker from '../../vueDatepicker.js.php';
|
||||
import ApiOrt from '../../../api/factory/ort.js'
|
||||
import { getNow, getTodayISO } from "../../../helpers/DateHelpers.js";
|
||||
export const Raumsuche = {
|
||||
name: "Raumsuche",
|
||||
components: {
|
||||
@@ -10,6 +11,8 @@ export const Raumsuche = {
|
||||
},
|
||||
inject: ["isMobile"],
|
||||
data() {
|
||||
const now = getNow();
|
||||
|
||||
return {
|
||||
phrasenPromise: null,
|
||||
phrasenResolved: false,
|
||||
@@ -23,14 +26,14 @@ export const Raumsuche = {
|
||||
},
|
||||
anzahl: 1,
|
||||
selectedType: null,
|
||||
datum: new Date(),
|
||||
datum: getTodayISO(),
|
||||
von: Vue.ref({
|
||||
hours: new Date().getHours(),
|
||||
minutes: new Date().getMinutes()
|
||||
hours: now.hour,
|
||||
minutes: now.minute
|
||||
}),
|
||||
bis: Vue.ref({
|
||||
hours: new Date().getHours() + 1,
|
||||
minutes: new Date().getMinutes()
|
||||
hours: now.plus({ hours: 1 }).hour,
|
||||
minutes: now.minute
|
||||
}),
|
||||
datepickerTextInputOptions: {
|
||||
enterSubmit: true,
|
||||
@@ -136,7 +139,7 @@ export const Raumsuche = {
|
||||
})
|
||||
},
|
||||
loadRooms() {
|
||||
this.$api.call(ApiOrt.getRooms(this.datum.toISOString(), this.getTimeString(this.von), this.getTimeString(this.bis), this.selectedType?.raumtyp_kurzbz ?? '', this.anzahl))
|
||||
this.$api.call(ApiOrt.getRooms(this.datum, this.getTimeString(this.von), this.getTimeString(this.bis), this.selectedType?.raumtyp_kurzbz ?? '', this.anzahl))
|
||||
.then(res => {
|
||||
if(res?.data?.retval) this.setupData(res.data.retval)
|
||||
})
|
||||
@@ -150,17 +153,6 @@ export const Raumsuche = {
|
||||
setRoute(val) {
|
||||
// TODO: router push
|
||||
},
|
||||
dateFormat(date) {
|
||||
const day = String(date.getDate()).padStart(2, '0');
|
||||
const month = String(date.getMonth() + 1).padStart(2, '0');
|
||||
const year = date.getFullYear();
|
||||
return `${day}.${month}.${year}`
|
||||
},
|
||||
timeFormat(date) {
|
||||
const hours = String(date.getHours()).padStart(2, '0');
|
||||
const minutes = String(date.getMinutes()).padStart(2, '0');
|
||||
return `${hours}:${minutes}`;
|
||||
},
|
||||
async setupMounted() {
|
||||
|
||||
this.tableBuiltPromise = new Promise(this.tableResolve)
|
||||
@@ -199,7 +191,8 @@ export const Raumsuche = {
|
||||
:dark="isDarkMode"
|
||||
:clearable="false"
|
||||
:enable-time-picker="false"
|
||||
:format="dateFormat"
|
||||
format="dd.MM.yyyy"
|
||||
model-type="yyyy-MM-dd"
|
||||
:text-input="datepickerTextInputOptions"
|
||||
:min-date="new Date()"
|
||||
date-picker
|
||||
@@ -213,7 +206,7 @@ export const Raumsuche = {
|
||||
v-model="von"
|
||||
:dark="isDarkMode"
|
||||
:clearable="false"
|
||||
:format="timeFormat"
|
||||
format="HH:mm"
|
||||
:text-input="timepickerTextInputOptions"
|
||||
:is-24="true"
|
||||
time-picker
|
||||
@@ -227,7 +220,7 @@ export const Raumsuche = {
|
||||
v-model="bis"
|
||||
:dark="isDarkMode"
|
||||
:clearable="false"
|
||||
:format="timeFormat"
|
||||
format="HH:mm"
|
||||
:text-input="timepickerTextInputOptions"
|
||||
:is-24="true"
|
||||
time-picker
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
import { formatDate, formatDateTime } from "../../helpers/DateHelpers.js";
|
||||
|
||||
export default {
|
||||
props: [
|
||||
"config",
|
||||
@@ -30,14 +32,7 @@ export default {
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
formatDateTime: function(dateTime) {
|
||||
const dt = new Date(dateTime);
|
||||
return dt.getDate() + '.' + (dt.getMonth()+1) + '.' + dt.getFullYear() + ' | '
|
||||
+ dt.getHours() + ':' + dt.getMinutes();
|
||||
},
|
||||
getDate: function(dateTime){
|
||||
const dt = new Date(dateTime);
|
||||
return dt.getDate() + '.' + (dt.getMonth()+1) + '.' + dt.getFullYear();
|
||||
}
|
||||
formatDateTime,
|
||||
getDate: formatDate
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import AbstractWidget from './Abstract.js';
|
||||
import BsModal from '../Bootstrap/Modal.js';
|
||||
import { numberPadding } from '../../helpers/DateHelpers.js';
|
||||
import { formatDate, formatTime } from '../../helpers/DateHelpers.js';
|
||||
import ApiCms from '../../api/factory/cms.js';
|
||||
|
||||
const MAX_LOADED_NEWS = 30;
|
||||
@@ -84,14 +84,8 @@ export default {
|
||||
});
|
||||
})
|
||||
},
|
||||
formatDate: function (dateTime) {
|
||||
const dt = new Date(dateTime);
|
||||
return numberPadding(dt.getDate()) + '.' + numberPadding((dt.getMonth() + 1)) + '.' + dt.getFullYear();
|
||||
},
|
||||
formatTime: function (dateTime) {
|
||||
const dt = new Date(dateTime);
|
||||
return numberPadding(dt.getHours()) + ':' + numberPadding(dt.getMinutes());
|
||||
},
|
||||
formatDate,
|
||||
formatTime,
|
||||
isString(value){
|
||||
return Object.prototype.toString.call(value) === '[object String]';
|
||||
},
|
||||
|
||||
@@ -400,32 +400,37 @@ export default {
|
||||
|
||||
<div v-if="headerData.length == 1">
|
||||
<div v-if="!isLoading" class="d-flex align-items-center gap-3">
|
||||
<h2 class="h4">
|
||||
<h2 class="h4 mt-2">
|
||||
{{headerData[0].titelpre}}
|
||||
{{headerData[0].vorname}}
|
||||
{{headerData[0].nachname}}
|
||||
<span v-if="headerData[0].titelpost">, </span>
|
||||
{{headerData[0].titelpost}}
|
||||
</h2>
|
||||
<core-tag ref="tagComponent"
|
||||
v-if="tagsEnabled"
|
||||
:endpoint="tagEndpoint"
|
||||
:values="prestudentIds"
|
||||
@added="addedTag"
|
||||
@deleted="deletedTag"
|
||||
@updated="updatedTag"
|
||||
zuordnung_typ="prestudent_id"
|
||||
></core-tag>
|
||||
<div
|
||||
role="button"
|
||||
v-if="tagsEnabled"
|
||||
@click="rebuildPrestudentTags"
|
||||
class="btn btn-outline btn-light mb-1"
|
||||
:title="'Automatische Tags fuer ' + currentSemester + ' neu laden'"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i>
|
||||
<span>{{currentSemester}}</span>
|
||||
|
||||
<div class="d-flex border rounded align-items-center ps-1">
|
||||
<core-tag ref="tagComponent"
|
||||
v-if="tagsEnabled"
|
||||
:endpoint="tagEndpoint"
|
||||
:values="prestudentIds"
|
||||
:show-hover="true"
|
||||
@added="addedTag"
|
||||
@deleted="deletedTag"
|
||||
@updated="updatedTag"
|
||||
zuordnung_typ="prestudent_id"
|
||||
></core-tag>
|
||||
<div
|
||||
role="button"
|
||||
v-if="tagsEnabled"
|
||||
@click="rebuildPrestudentTags"
|
||||
class="btn btn-outline btn-sm btn-hover m-1"
|
||||
:title="$p.t('tag','rebuild_tags') + ' ' + currentSemester"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i>
|
||||
<span>{{currentSemester}}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<h6 v-if="headerData[0].unruly" class="badge" :class="'bg-unruly rounded-0'"><strong>unruly</strong></h6>
|
||||
</div>
|
||||
<div v-else class="d-flex align-items-center gap-3">
|
||||
|
||||
+110
-167
@@ -4,7 +4,7 @@ import {CoreFilterCmpt} from "../filter/Filter.js";
|
||||
import BsModal from "../Bootstrap/Modal.js";
|
||||
import FormForm from '../Form/Form.js';
|
||||
import FormInput from '../Form/Input.js';
|
||||
import PvAutoComplete from "../../../../index.ci.php/public/js/components/primevue/autocomplete/autocomplete.esm.min.js";
|
||||
|
||||
|
||||
export default {
|
||||
components: {
|
||||
@@ -13,8 +13,7 @@ export default {
|
||||
FormUploadDms,
|
||||
FormForm,
|
||||
FormInput,
|
||||
BsModal,
|
||||
PvAutoComplete
|
||||
BsModal
|
||||
},
|
||||
props: {
|
||||
endpoint: {
|
||||
@@ -53,6 +52,7 @@ export default {
|
||||
multiupload: true,
|
||||
mitarbeiter: [],
|
||||
filteredMitarbeiter: [],
|
||||
zwischenvar: '',
|
||||
editorInitialized: false,
|
||||
editor: null,
|
||||
notizData: {
|
||||
@@ -85,11 +85,7 @@ export default {
|
||||
showId: false,
|
||||
showLastupdate: false
|
||||
},
|
||||
selectedBearbeiter: null,
|
||||
selectedVerfasser: null,
|
||||
abortController: {
|
||||
mitarbeiter: null
|
||||
}
|
||||
currentVerfasserUid: null
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
@@ -301,15 +297,6 @@ export default {
|
||||
},
|
||||
actionEditNotiz(notiz_id) {
|
||||
this.loadNotiz(notiz_id).then(() => {
|
||||
this.selectedBearbeiter = {
|
||||
label: this.getLabelUid(this.notizData.perb_titelpre, this.notizData.perb_nachname, this.notizData.perb_vorname, this.notizData.perb_titelpost, this.notizData.perb_uid),
|
||||
uid: this.notizData.perb_uid
|
||||
}
|
||||
this.selectedVerfasser = {
|
||||
label: this.getLabelUid(this.notizData.perv_titelpre, this.notizData.perv_nachname, this.notizData.perv_vorname, this.notizData.perv_titelpost, this.notizData.perv_uid),
|
||||
uid: this.notizData.perv_uid
|
||||
}
|
||||
|
||||
if (this.notizen.notiz_id) {
|
||||
this.notizData.typeId = this.typeId;
|
||||
this.notizData.titel = this.notizen.titel;
|
||||
@@ -321,13 +308,8 @@ export default {
|
||||
this.notizData.bis = this.notizen.ende;
|
||||
this.notizData.document = this.notizen.dms_id;
|
||||
this.notizData.erledigt = this.notizen.erledigt;
|
||||
//this.notizData.bearbeiter_uid = this.notizen.bearbeiter_uid;
|
||||
//for saving
|
||||
//this.notizData.intBearbeiter = this.notizen.bearbeiter_uid;
|
||||
//this.notizData.bearbeiter = this.notizen.bearbeiter_uid;
|
||||
//new way
|
||||
this.notizData.bearbeiter = this.selectedBearbeiter.uid;
|
||||
this.notizData.verfasser = this.selectedVerfasser.uid;
|
||||
this.notizData.intBearbeiter = this.notizen.bearbeiter_uid;
|
||||
this.notizData.bearbeiter = this.notizen.bearbeiter_uid;
|
||||
}
|
||||
})
|
||||
.then(() => {
|
||||
@@ -341,9 +323,7 @@ export default {
|
||||
});
|
||||
},
|
||||
actionNewNotiz() {
|
||||
console.log("auf plus");
|
||||
this.resetFormData();
|
||||
this.getDefaultVerfasser();
|
||||
if(this.notizLayout == 'popupModal') {
|
||||
this.$refs.NotizModal.show();
|
||||
}
|
||||
@@ -394,6 +374,7 @@ export default {
|
||||
this.notizData = result.data;
|
||||
this.notizData.typeId = this.typeId;
|
||||
this.notizData.anhang = [];
|
||||
this.currentVerfasserUid = result.data.verfasser_uid;
|
||||
return result;
|
||||
})
|
||||
.catch(this.$fhcAlert.handleSystemError);
|
||||
@@ -450,54 +431,24 @@ export default {
|
||||
bearbeiter: null,
|
||||
anhang: [],
|
||||
};
|
||||
this.selectedBearbeiter = null;
|
||||
this.selectedVerfasser = null;
|
||||
this.currentVerfasserUid = this.uid
|
||||
},
|
||||
getDefaultVerfasser() {
|
||||
getUid() {
|
||||
return this.$api
|
||||
.call(this.endpoint.getDefaultVerfasser())
|
||||
.call(this.endpoint.getUid())
|
||||
.then(result => {
|
||||
const verfasser = result.data;
|
||||
this.selectedVerfasser = {
|
||||
label: this.getLabelUid(verfasser.titelpre, verfasser.nachname, verfasser.vorname, verfasser.titelpost, verfasser.mitarbeiter_uid),
|
||||
uid: verfasser.uid
|
||||
}
|
||||
this.currentVerfasserUid = result.data;
|
||||
this.uid = result.data;
|
||||
})
|
||||
.catch(this.$fhcAlert.handleSystemError);
|
||||
},
|
||||
searchMitarbeiter(event) {
|
||||
if (this.abortController.mitarbeiter) {
|
||||
this.abortController.mitarbeiter.abort();
|
||||
}
|
||||
|
||||
this.abortController.mitarbeiter = new AbortController();
|
||||
|
||||
search(event) {
|
||||
return this.$api
|
||||
.call(this.endpoint.getMitarbeiter(event.query))
|
||||
.then(result => {
|
||||
//this.filteredMitarbeiter = result.data.retval;
|
||||
this.filteredMitarbeiter = [];
|
||||
for (let mitarbeiter of result.data.retval) {
|
||||
this.filteredMitarbeiter.push(
|
||||
{
|
||||
label: this.getLabelUid(
|
||||
mitarbeiter.titelpre,
|
||||
mitarbeiter.nachname,
|
||||
mitarbeiter.vorname,
|
||||
mitarbeiter.titelpost,
|
||||
mitarbeiter.mitarbeiter_uid
|
||||
),
|
||||
uid: mitarbeiter.mitarbeiter_uid
|
||||
}
|
||||
);
|
||||
}
|
||||
this.filteredMitarbeiter = result.data.retval;
|
||||
});
|
||||
},
|
||||
getLabelUid(titelpre, nachname, vorname, titelpost, uid) {
|
||||
if (!nachname && !vorname && !uid)
|
||||
return '';
|
||||
return nachname + ' ' + vorname + (titelpre ? ' ' + titelpre : '') + (titelpost ? ' ' + titelpost : '') + (uid ? ' (' + uid + ')' : '');
|
||||
},
|
||||
initTinyMCE() {
|
||||
const vm = this;
|
||||
tinymce.init({
|
||||
@@ -540,7 +491,7 @@ export default {
|
||||
},
|
||||
created() {
|
||||
this.initializeShowVariables();
|
||||
this.getDefaultVerfasser();
|
||||
this.getUid();
|
||||
},
|
||||
async mounted() {
|
||||
if (this.showTinyMce) {
|
||||
@@ -561,14 +512,18 @@ export default {
|
||||
}
|
||||
}
|
||||
},
|
||||
//Watcher für autocomplete Bearbeiter und Verfasser
|
||||
'notizData.intBearbeiter': {
|
||||
handler(newVal) {
|
||||
if (typeof newVal === 'object') {
|
||||
this.notizData.bearbeiter = newVal.mitarbeiter_uid;
|
||||
}
|
||||
},
|
||||
deep: true
|
||||
},
|
||||
|
||||
id() {
|
||||
this.reload();
|
||||
},
|
||||
selectedBearbeiter(newVal) {
|
||||
this.notizData.bearbeiter = newVal?.uid || null;
|
||||
},
|
||||
selectedVerfasser(newVal) {
|
||||
this.notizData.verfasser = newVal?.uid || null;
|
||||
}
|
||||
},
|
||||
beforeUnmount() {
|
||||
@@ -666,21 +621,9 @@ export default {
|
||||
<div class="row mb-3">
|
||||
<label for="bis" class="form-label col-sm-2">{{$p.t('notiz','verfasser')}}</label>
|
||||
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
container-class="col-3"
|
||||
v-model="selectedVerfasser"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
disabled
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
>
|
||||
</form-input>
|
||||
<div class="col-sm-3">
|
||||
<input type="text" readonly="readonly" class="form-control" id="name" v-model="currentVerfasserUid">
|
||||
</div>
|
||||
|
||||
<label for="von" class="form-label col-sm-1">{{$p.t('global','gueltigVon')}}</label>
|
||||
<div class="col-sm-3">
|
||||
@@ -701,20 +644,21 @@ export default {
|
||||
<div class="row mb-3">
|
||||
<label for="bis" class="form-label col-sm-2">{{$p.t('notiz','bearbeiter')}}</label>
|
||||
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
container-class="col-3"
|
||||
v-model="selectedBearbeiter"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
<div v-if="notizData.bearbeiter_uid" class="col-sm-3">
|
||||
<input type="text" class="form-control" id="name" v-model="notizData.bearbeiter_uid">
|
||||
</div>
|
||||
|
||||
<div v-else class="col-sm-3">
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
v-model="notizData.intBearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="search"
|
||||
optionLabel="mitarbeiter"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
</form-input>
|
||||
</div>
|
||||
|
||||
|
||||
<label for="bis" class="form-label col-sm-1">{{$p.t('global','gueltigBis')}}</label>
|
||||
@@ -872,36 +816,35 @@ export default {
|
||||
</div>
|
||||
|
||||
<div class="row mb-3">
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
<form-input
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'verfasser')"
|
||||
v-model="selectedVerfasser"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
disabled
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
type="text"
|
||||
readonly="readonly"
|
||||
v-model="currentVerfasserUid"
|
||||
name="verfasser"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
v-if="notizData.bearbeiter_uid"
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
v-model="selectedBearbeiter"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
v-model="notizData.bearbeiter_uid"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
<form-input
|
||||
v-else
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
type="autocomplete"
|
||||
v-model="notizData.intBearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="search"
|
||||
optionLabel="mitarbeiter"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
</div>
|
||||
@@ -1026,38 +969,37 @@ export default {
|
||||
|
||||
|
||||
<div class="row mb-3">
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
<form-input
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'verfasser')"
|
||||
v-model="selectedVerfasser"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
disabled
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
type="text"
|
||||
readonly="readonly"
|
||||
v-model="currentVerfasserUid"
|
||||
name="verfasser"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
v-if="notizData.bearbeiter_uid"
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
v-model="selectedBearbeiter"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
v-model="notizData.bearbeiter_uid"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
<form-input
|
||||
v-else
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
type="autocomplete"
|
||||
v-model="notizData.intBearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="search"
|
||||
optionLabel="mitarbeiter"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
</div>
|
||||
|
||||
<div class="row mb-3">
|
||||
@@ -1198,43 +1140,44 @@ export default {
|
||||
>
|
||||
</form-input>
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<div class="row mb-3">
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
<form-input
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'verfasser')"
|
||||
v-model="selectedVerfasser"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
disabled
|
||||
dropdown
|
||||
forceSelection
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
type="text"
|
||||
readonly="readonly"
|
||||
v-model="currentVerfasserUid"
|
||||
name="verfasser"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
|
||||
<form-input
|
||||
type="autocomplete"
|
||||
v-if="notizData.bearbeiter_uid"
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
v-model="selectedBearbeiter"
|
||||
optionLabel="label"
|
||||
optionValue="uid"
|
||||
dropdown
|
||||
forceSelection
|
||||
v-model="notizData.bearbeiter_uid"
|
||||
name="bearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="searchMitarbeiter"
|
||||
:min-length="3"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
|
||||
|
||||
<form-input
|
||||
v-else
|
||||
container-class="col-6"
|
||||
:label="$p.t('notiz', 'bearbeiter')"
|
||||
type="autocomplete"
|
||||
v-model="notizData.intBearbeiter"
|
||||
:suggestions="filteredMitarbeiter"
|
||||
@complete="search"
|
||||
optionLabel="mitarbeiter"
|
||||
name="bearbeiter"
|
||||
minlength="3"
|
||||
>
|
||||
</form-input>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="row mb-3">
|
||||
<div class="col-2 pt-4 d-flex align-items-center">
|
||||
<form-input
|
||||
|
||||
+6
-2
@@ -553,8 +553,12 @@ export default {
|
||||
}
|
||||
|
||||
if (!this.formData.akadgrad_id && this.arrAkadGrad.length > 0) {
|
||||
if(this.student.geschlecht == 'w')
|
||||
this.formData.akadgrad_id = this.arrAkadGrad[1].akadgrad_id;
|
||||
const akadGradByGeschlecht = this.arrAkadGrad.find((item) => {
|
||||
return item.geschlecht === this.student.geschlecht;
|
||||
});
|
||||
|
||||
if(akadGradByGeschlecht)
|
||||
this.formData.akadgrad_id = akadGradByGeschlecht.akadgrad_id;
|
||||
else
|
||||
this.formData.akadgrad_id = this.arrAkadGrad[0].akadgrad_id;
|
||||
}
|
||||
|
||||
@@ -317,6 +317,7 @@ export default {
|
||||
"$p.user_language.value"(n, o) {
|
||||
if (n !== o && o !== undefined && this.$refs.table.tableBuilt) {
|
||||
this.translateTabulator();
|
||||
this.$reloadList();
|
||||
}
|
||||
},
|
||||
"tagFilterState.selectedOptions": {
|
||||
@@ -842,35 +843,39 @@ export default {
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<template #actions>
|
||||
<core-tag ref="tagComponent"
|
||||
v-if="tagsEnabled"
|
||||
:endpoint="tagEndpoint"
|
||||
:values="selectedColumnValues"
|
||||
@added="addedTag"
|
||||
@deleted="deletedTag"
|
||||
@updated="updatedTag"
|
||||
zuordnung_typ="prestudent_id"
|
||||
></core-tag>
|
||||
<template #tags>
|
||||
<div class="d-flex border rounded align-items-center ps-1">
|
||||
<core-tag ref="tagComponent"
|
||||
v-if="tagsEnabled"
|
||||
:endpoint="tagEndpoint"
|
||||
:values="selectedColumnValues"
|
||||
@added="addedTag"
|
||||
@deleted="deletedTag"
|
||||
@updated="updatedTag"
|
||||
zuordnung_typ="prestudent_id"
|
||||
show-hover
|
||||
></core-tag>
|
||||
|
||||
<button
|
||||
v-if="!selected.length"
|
||||
class="btn btn-outline btn-light mb-1"
|
||||
@click="rebuild(selected)"
|
||||
:title="$p.t('tag','rebuild_tags') + ' Stg ' + currentSemester"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i> STG
|
||||
</button>
|
||||
<button
|
||||
v-else
|
||||
class="btn btn-outline btn-light mb-1"
|
||||
@click="rebuild(selected)"
|
||||
:title="$p.t('tag','rebuild_tags') + ' ' + $p.t('ui','selection') + ' ' + currentSemester"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i> {{selected.length}}
|
||||
</button>
|
||||
<button
|
||||
v-if="!selected.length"
|
||||
class="btn btn-outline btn-sm m-1 btn-hover"
|
||||
@click="rebuild(selected)"
|
||||
:title="$p.t('tag','rebuild_tags') + ' Stg ' + currentSemester"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i> STG
|
||||
</button>
|
||||
<button
|
||||
v-else
|
||||
class="btn btn-outline btn-sm m-1 btn-hover"
|
||||
@click="rebuild(selected)"
|
||||
:title="$p.t('tag','rebuild_tags') + ' ' + $p.t('ui','selection') + ' ' + currentSemester"
|
||||
>
|
||||
<i class="fa-solid fa-refresh pe-1"></i> {{selected.length}}
|
||||
</button>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<template v-if="filter.length || headerFilterActive">
|
||||
<template v-if="filter.length || headerFilterActive">
|
||||
<div class="d-flex justify-content-center align-items-center gap-2 ps-4 position-absolute start-50 translate-middle-x">
|
||||
<p class="text-danger mb-0">
|
||||
<strong>{{$p.t('filter','filterActive')}}</strong>
|
||||
@@ -884,8 +889,6 @@ export default {
|
||||
<span class="fa-solid fa-filter-circle-xmark"></span>
|
||||
</button>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
</template>
|
||||
|
||||
<template #filter>
|
||||
@@ -895,6 +898,7 @@ export default {
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
</core-filter-cmpt>
|
||||
</div>
|
||||
<list-new ref="new" :studiengang-kz="studiengangKz" :studiensemester-kurzbz="studiensemesterKurzbz"></list-new>
|
||||
|
||||
@@ -28,6 +28,10 @@ export default {
|
||||
confirmLimit: {
|
||||
type: Number,
|
||||
default: 20
|
||||
},
|
||||
showHover: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
},
|
||||
data() {
|
||||
@@ -228,7 +232,8 @@ export default {
|
||||
<span :title="values.length === 0 ? 'Bitte Zeilen markieren' : ''">
|
||||
<button @mouseover="showList = true"
|
||||
:disabled="!values || values.length === 0"
|
||||
class="btn btn-sm">
|
||||
class="btn btn-sm"
|
||||
:class="{'btn-hover': showHover}">
|
||||
<i class="fa-solid fa-tag fa-xl"></i>
|
||||
</button>
|
||||
</span>
|
||||
|
||||
@@ -1094,7 +1094,7 @@ export const CoreFilterCmpt = {
|
||||
<div :id="'filterCollapsables' + idExtra">
|
||||
|
||||
<div class="d-flex flex-row justify-content-between flex-wrap">
|
||||
<div v-if="newBtnShow || reload || $slots.search || $slots.actions" class="d-flex gap-2 align-items-baseline flex-wrap">
|
||||
<div v-if="newBtnShow || reload || $slots.search || $slots.actions || $slots.tags" class="d-flex gap-2 align-items-baseline flex-wrap">
|
||||
<button v-if="newBtnShow" class="btn btn-primary" :class="newBtnClass" :title="newBtnLabel ? undefined : 'New'" :aria-label="newBtnLabel ? undefined : 'New'" @click="$emit('click:new', $event)" :disabled="newBtnDisabled">
|
||||
<span class="fa-solid fa-plus" aria-hidden="true"></span>
|
||||
{{ newBtnLabel }}
|
||||
@@ -1107,6 +1107,7 @@ export const CoreFilterCmpt = {
|
||||
<span v-else id="selected-info-text"> Mit {{ selectedData.length }} ausgewählten:</span>
|
||||
</span>
|
||||
<slot name="actions" v-bind="{selected: tabulatorHasSelector ? selectedData : []}"></slot>
|
||||
<slot name="tags"></slot>
|
||||
<slot name="search"></slot>
|
||||
</div>
|
||||
<div class="d-flex gap-1 align-items-baseline flex-grow-1 justify-content-end">
|
||||
|
||||
@@ -1,61 +1,69 @@
|
||||
|
||||
// HELPER FILE -- that contains multiple functions which create, handle and manipulate js dates
|
||||
// Everything parses and formats with luxon in the server timezone. new Date("2026-09-02")
|
||||
// reads UTC midnight and shows the day before west of Greenwich.
|
||||
|
||||
// custom Error class for DateHelpers.js misuse
|
||||
class DateHelperError extends Error {
|
||||
constructor(message) {
|
||||
super(message);
|
||||
this.name = "DateHelperError";
|
||||
}
|
||||
|
||||
function getZone() {
|
||||
return globalThis.FHC_JS_DATA_STORAGE_OBJECT?.timezone || 'Europe/Vienna';
|
||||
}
|
||||
|
||||
/**
|
||||
* adds padding to a number
|
||||
* converts a date value into a luxon DateTime in the server timezone
|
||||
*
|
||||
* @param {number|string} number - the number on which padding should be added.
|
||||
* @returns {string} number with padding.
|
||||
* @param {string|number|Date|Object} value - ISO string, SQL string, milliseconds, Date or luxon DateTime.
|
||||
* @returns {Object|null} luxon DateTime, or null if the value is empty or unparsable.
|
||||
*/
|
||||
export function toDateTime(value) {
|
||||
if (!value) return null;
|
||||
|
||||
const zone = getZone();
|
||||
let date;
|
||||
|
||||
if (value instanceof luxon.DateTime) date = value.setZone(zone);
|
||||
else if (value instanceof Date) date = luxon.DateTime.fromJSDate(value, { zone });
|
||||
else if (typeof value === 'number') date = luxon.DateTime.fromMillis(value, { zone });
|
||||
// fromISO rejects the space that SQL puts between date and time
|
||||
else if (typeof value === 'string') date = value.includes(' ')
|
||||
? luxon.DateTime.fromSQL(value, { zone })
|
||||
: luxon.DateTime.fromISO(value, { zone });
|
||||
else return null;
|
||||
|
||||
return date.isValid ? date : null;
|
||||
}
|
||||
|
||||
// current time in the server timezone
|
||||
export function getNow() {
|
||||
return luxon.DateTime.now().setZone(getZone());
|
||||
}
|
||||
|
||||
// today in the server timezone, as yyyy-MM-dd
|
||||
export function getTodayISO() {
|
||||
return getNow().toISODate();
|
||||
}
|
||||
|
||||
// the three formatters return '' for an empty or unparsable value
|
||||
export function formatDate(value) {
|
||||
return toDateTime(value)?.toFormat('dd.MM.yyyy') ?? '';
|
||||
}
|
||||
|
||||
export function formatTime(value) {
|
||||
return toDateTime(value)?.toFormat('HH:mm') ?? '';
|
||||
}
|
||||
|
||||
export function formatDateTime(value) {
|
||||
return toDateTime(value)?.toFormat('dd.MM.yyyy HH:mm') ?? '';
|
||||
}
|
||||
|
||||
// tabulator sorter for ISO dates, sorts empty values last
|
||||
export function compareISODateValues(a, b) {
|
||||
if (!a && !b) return 0;
|
||||
if (!a) return 1;
|
||||
if (!b) return -1;
|
||||
|
||||
return String(a).localeCompare(String(b));
|
||||
}
|
||||
|
||||
// pads hours and minutes to two digits
|
||||
export function numberPadding(number) {
|
||||
if(typeof number !== "string" && typeof number !== "number")
|
||||
{
|
||||
throw new TypeError("function numberPadding in file DateHelpers.js is only usable with strings or numbers");
|
||||
}
|
||||
if(number.toString().length > 2)
|
||||
{
|
||||
throw new DateHelperError("The number on which the padding should be added should not be longer than to 2 characters, please refere to the function numberPadding in the helper file DateHelpers.js");
|
||||
}
|
||||
return number.toString().length == 1 ? '0' + number.toString() : number.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* formats date to dd.mm.yyyy
|
||||
*
|
||||
* @param {string|Date} d - the date that should be formatted.
|
||||
* @returns {string} formatted date string.
|
||||
*/
|
||||
export function formatDate(d) {
|
||||
// parameter is of type Date
|
||||
if(d instanceof Date)
|
||||
{
|
||||
if (isNaN(date.valueOf())) {
|
||||
return 'N/A';
|
||||
}
|
||||
// if the date is an invalid string then creating a date from the string will fail and N/A is returned
|
||||
return `${numberPadding(d.getDate())}.${numberPadding(d.getMonth() + 1)}.${d.getFullYear()}`;
|
||||
}
|
||||
// parameter is of type string
|
||||
else if (typeof d === "string")
|
||||
{
|
||||
let date = new Date(d);
|
||||
// if the date is an invalid string then creating a date from the string will fail and N/A is returned
|
||||
if (isNaN(date.valueOf())) {
|
||||
return 'N/A';
|
||||
}
|
||||
return `${numberPadding(date.getDate())}.${numberPadding(date.getMonth() + 1)}.${date.getFullYear()}`;
|
||||
}
|
||||
// parameter is not of type string or Date and an exception is thrown
|
||||
else
|
||||
{
|
||||
throw new TypeError("The parameter provided for this function is not a string or a Date object, please refere to the function formatDate in the DateHelpers.js file");
|
||||
}
|
||||
return String(number).padStart(2, '0');
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user