STD
This commit is contained in:
@@ -36,8 +36,8 @@ try {
|
||||
horario_fecha_fin,
|
||||
horario_grupo,
|
||||
horario_hora,
|
||||
periodo_fecha_inicio,
|
||||
periodo_fecha_fin,
|
||||
PERIODO.periodo_fecha_inicio,
|
||||
PERIODO.periodo_fecha_fin,
|
||||
salon,
|
||||
materia_nombre as materia,
|
||||
carrera_nombre as carrera,
|
||||
@@ -49,10 +49,9 @@ try {
|
||||
JOIN carrera USING (carrera_id)
|
||||
JOIN nivel USING (nivel_id)
|
||||
JOIN facultad ON facultad.facultad_id = carrera.facultad_id
|
||||
JOIN PERIODO_CARRERA USING (carrera_id)
|
||||
JOIN PERIODO USING (periodo_id)
|
||||
JOIN SALON USING (salon_id)
|
||||
WHERE (periodo_id, facultad.facultad_id) = (:periodo_id, COALESCE(:facultad_id, facultad.facultad_id))
|
||||
WHERE (PERIODO.periodo_id, facultad.facultad_id) = (:periodo_id, COALESCE(:facultad_id, facultad.facultad_id))
|
||||
),
|
||||
fechas AS (
|
||||
SELECT fechas_clase(h.horario_id, true) as registro_fecha_ideal, h.horario_id
|
||||
|
||||
@@ -30,6 +30,7 @@ try {
|
||||
SELECT facultad_nombre, facultad_id, clave_dependencia
|
||||
FROM facultad
|
||||
WHERE facultad_id = :facultad_id OR :facultad_id IS NULL
|
||||
ORDER BY facultad_nombre ASC
|
||||
SQL
|
||||
,
|
||||
[':facultad_id' => $user->facultad['facultad_id']]
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
<?php
|
||||
|
||||
require_once "{$_SERVER['DOCUMENT_ROOT']}/class/c_login.php";
|
||||
header('Content-Type: application/json');
|
||||
|
||||
@@ -15,13 +14,44 @@ try {
|
||||
case 'GET':
|
||||
// Fetch all puestos
|
||||
$facultad_id = $user->facultad['facultad_id'];
|
||||
$periodo_nivel_id = $db->where('periodo_id', $user->periodo_id)->getOne('periodo', 'nivel_id')['nivel_id'];
|
||||
$carreras = $db->query(<<<SQL
|
||||
SELECT carrera_id, carrera_nombre, clave_carrera, facultad_id
|
||||
SELECT carrera_id, carrera_nombre, clave_carrera,
|
||||
facultad_id, facultad_nombre,
|
||||
nivel_id, nivel_nombre
|
||||
FROM carrera
|
||||
WHERE facultad_id = :facultad_id OR :facultad_id IS NULL
|
||||
SQL, ['facultad_id' => $facultad_id]);
|
||||
join nivel using (nivel_id)
|
||||
join facultad using (facultad_id)
|
||||
WHERE facultad_id = :facultad_id OR :facultad_id IS NULL AND
|
||||
nivel.nivel_id = :periodo_nivel_id
|
||||
ORDER BY facultad_nombre, carrera_nombre
|
||||
SQL, [
|
||||
'facultad_id' => $facultad_id,
|
||||
'periodo_nivel_id' => $periodo_nivel_id
|
||||
]);
|
||||
echo json_encode($carreras);
|
||||
break;
|
||||
|
||||
case 'PUT':
|
||||
// Update carrera {nivel_id}
|
||||
$raw = file_get_contents('php://input');
|
||||
$data = json_decode($raw, true);
|
||||
|
||||
if (!isset($data['carrera_id'], $data['nivel_id'])) {
|
||||
header('HTTP/1.1 400 Bad Request');
|
||||
echo json_encode(['error' => 'Falta el id de la carrera o el nivel']);
|
||||
exit();
|
||||
}
|
||||
|
||||
$carrera_id = $data['carrera_id'];
|
||||
$nivel_id = $data['nivel_id'];
|
||||
$db->where('carrera_id', $carrera_id)->update('carrera', ['nivel_id' => $nivel_id]);
|
||||
|
||||
$carrera_nombre = $db->where('carrera_id', $carrera_id)->getOne('carrera', 'carrera_nombre')['carrera_nombre'];
|
||||
$nivel_nombre = $db->where('nivel_id', $nivel_id)->getOne('nivel', 'nivel_nombre')['nivel_nombre'];
|
||||
|
||||
echo json_encode(['success' => "$carrera_nombre actualizada a $nivel_nombre"]);
|
||||
break;
|
||||
default:
|
||||
header('HTTP/1.1 405 Method Not Allowed');
|
||||
echo json_encode(['error' => 'Método no permitido']);
|
||||
|
||||
31
action/nivel.php
Normal file
31
action/nivel.php
Normal file
@@ -0,0 +1,31 @@
|
||||
<?php
|
||||
|
||||
require_once "{$_SERVER['DOCUMENT_ROOT']}/class/c_login.php";
|
||||
header('Content-Type: application/json');
|
||||
|
||||
if (!Login::is_logged()) {
|
||||
header('HTTP/1.1 401 Unauthorized');
|
||||
echo json_encode(['error' => 'No se ha iniciado sesión']);
|
||||
exit();
|
||||
}
|
||||
$user = Login::get_user();
|
||||
|
||||
try {
|
||||
switch ($_SERVER['REQUEST_METHOD']) {
|
||||
case 'GET':
|
||||
// Fetch all puestos
|
||||
$nivel = $db->get('nivel');
|
||||
echo json_encode($nivel);
|
||||
break;
|
||||
default:
|
||||
header('HTTP/1.1 405 Method Not Allowed');
|
||||
echo json_encode(['error' => 'Método no permitido']);
|
||||
break;
|
||||
}
|
||||
} catch (PDOException $e) {
|
||||
echo json_encode([
|
||||
'error' => $e->getMessage(),
|
||||
'query' => $db->getLastQuery(),
|
||||
'exception' => $e->getTraceAsString()
|
||||
]);
|
||||
}
|
||||
899
carreras.php
899
carreras.php
@@ -1,809 +1,124 @@
|
||||
<?php
|
||||
require_once 'class/c_login.php';
|
||||
require_once 'include/bd_pdo.php';
|
||||
|
||||
$user = Login::get_user();
|
||||
|
||||
$user->access('facultades');
|
||||
if($user->acceso == null){
|
||||
header('Location: main.php?error=1');
|
||||
}else{
|
||||
$user->print_to_log('Carreras');
|
||||
}
|
||||
if($user->facultad['facultad_id']!=$_GET['facultad']){
|
||||
header('Location: carreras.php?facultad='.$user->facultad['facultad_id']);
|
||||
$mal=true;
|
||||
}
|
||||
$mal=false;
|
||||
?>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Carreras</title>
|
||||
<link rel="stylesheet" href="css/jquery-ui.css">
|
||||
<link rel="stylesheet" href="css/calendar.css">
|
||||
<link rel="stylesheet" href="css/toggle.css" type="text/css">
|
||||
<title>Auditoría asistencial</title>
|
||||
<?php
|
||||
include 'import/html_css_files.php';
|
||||
?>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<?php
|
||||
if(isset($_GET['facultad'])){
|
||||
$facultad=query("SELECT facultad_nombre FROM facultad WHERE facultad_id = :facultad", array(":facultad" => $_GET['facultad']), true);
|
||||
$fs_carreras = query(
|
||||
"SELECT * FROM fs_carreras(:idfacultad, null, null)",
|
||||
array(':idfacultad' => $_GET['facultad']),
|
||||
single:false
|
||||
);
|
||||
<link rel="stylesheet" type="text/css" href="https://unpkg.com/trix@2.0.0/dist/trix.css">
|
||||
<style>
|
||||
[v-cloak] {
|
||||
display: none;
|
||||
}
|
||||
include "import/html_header.php";
|
||||
html_header(
|
||||
"CARRERAS | " . $facultad['facultad_nombre'],
|
||||
"Gestión de Checador "
|
||||
);
|
||||
$user->access('facultades');
|
||||
|
||||
|
||||
$fs_niveles = query(
|
||||
"SELECT * FROM nivel", null, false
|
||||
);
|
||||
|
||||
$fs_periodos = query(
|
||||
"SELECT * FROM fs_periodos(:idfacultad) WHERE estado = 'Activo' ",
|
||||
array(':idfacultad' => $_GET['facultad']),
|
||||
false
|
||||
);
|
||||
|
||||
$fs_tiempoLic = query(
|
||||
"SELECT * FROM fs_tiempo_checado(:idfacultad, 1)",
|
||||
array(':idfacultad' => $_GET['facultad']),
|
||||
true
|
||||
);
|
||||
$fs_tiempoPos = query(
|
||||
"SELECT * FROM fs_tiempo_checado(:idfacultad, 2)",
|
||||
array(':idfacultad' => $_GET['facultad']),
|
||||
true
|
||||
);
|
||||
?>
|
||||
<main class="content marco">
|
||||
<?php #if($mal==true){ ?>
|
||||
<div class="row">
|
||||
<div class="col-12 text-left">
|
||||
<a href="facultades.php" title="Volver">
|
||||
<button type="button" class="btn btn-outline-secondary"><span class="ing-regresar ing-fw"></span>Volver</button>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
<?php #} ?>
|
||||
<div id="message"></div>
|
||||
<ul class="nav nav-tabs mt-3" id="myTab" role="tablist">
|
||||
<li class="nav-item" role="presentation">
|
||||
<button class="nav-link active" id="periodo-tab" data-toggle="tab" data-target="#periodo" type="button" role="tab" aria-controls="periodo" aria-selected="true">Periodo</button>
|
||||
</li>
|
||||
<li class="nav-item" role="presentation">
|
||||
<button class="nav-link" id="carrera-tab" data-toggle="tab" data-target="#carrera" type="button" role="tab" aria-controls="carrera" aria-selected="false">Carrera</button>
|
||||
</li>
|
||||
<li class="nav-item" role="presentation">
|
||||
<button class="nav-link" id="carrera-tab" data-toggle="tab" data-target="#tiempos" type="button" role="tab" aria-controls="tiempos" aria-selected="false">Tiempos</button>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="tab-content" id="myTabContent">
|
||||
<!-- PERIODOS -->
|
||||
|
||||
<div class="tab-pane fade show active" id="periodo" role="tabpanel" aria-labelledby="periodo-tab">
|
||||
<div class="row mt-3">
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<div class="col-12 text-right">
|
||||
<button type="button" class="btn btn-outline-secondary" data-toggle="modal" data-target="#modal_periodo" data-tipo="1"><span class="ing-mas ing-fw"></span>Agregar periodo</button>
|
||||
</div>
|
||||
<?php }?>
|
||||
</div>
|
||||
<!-- Tabla -->
|
||||
<div class="row mt-3">
|
||||
<div class="col-12 table-responsive">
|
||||
<table class="table table-sm table-striped table-white">
|
||||
<thead class="thead-dark">
|
||||
<tr>
|
||||
<th>Estado</th>
|
||||
<th>Nivel</th>
|
||||
<th>Periodo</th>
|
||||
<th>Inicio</th>
|
||||
<th>Fin</th>
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<th>Acciones</th>
|
||||
<?php }?>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<?php foreach($fs_periodos as $periodo){
|
||||
$title=$periodo['estado'];
|
||||
if($title=='Activo')
|
||||
$color="success";
|
||||
else
|
||||
$color="danger";
|
||||
?>
|
||||
<tr data-id="<?= $periodo['id']?>" id="<?= $periodo['id']?>" >
|
||||
<td class="text-<?= $color ?> text-center" title="<?= $title?>">
|
||||
<span class="ing-bullet"></span>
|
||||
</td>
|
||||
<td class="text-primary">
|
||||
<?= $periodo['nivel']?>
|
||||
</td>
|
||||
<td class="text-primary">
|
||||
<?= $periodo['periodo']?>
|
||||
</td>
|
||||
<td class="text-primary">
|
||||
<?= $periodo['inicio']?>
|
||||
</td>
|
||||
<td class="text-primary">
|
||||
<?= $periodo['fin']?>
|
||||
</td>
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<td class="text-center icono-acciones">
|
||||
<a href="#" data-toggle="modal" data-target="#modal_periodo" data-tipo="2" title="Editar"><span class="ing-editar ing-fw"></span></a>
|
||||
</td>
|
||||
<?php }?>
|
||||
</tr>
|
||||
<?php } ?>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- CARRERAS -->
|
||||
<div class="tab-pane fade" id="carrera" role="tabpanel" aria-labelledby="carrera-tab">
|
||||
<div class="row mt-3">
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<div class="col-12 text-right">
|
||||
<button type="button" class="btn btn-outline-secondary" data-toggle="modal" data-target="#modal" data-tipo="1"><span class="ing-mas ing-fw"></span>Crear carrera</button>
|
||||
</div>
|
||||
<?php }?>
|
||||
</div>
|
||||
<!-- Tabla -->
|
||||
<div class="row mt-3">
|
||||
<div class="col-12 table-responsive">
|
||||
<table class="table table-sm table-striped table-white">
|
||||
<thead class="thead-dark">
|
||||
<tr>
|
||||
<th>Estado</th>
|
||||
<th>Nivel</th>
|
||||
<th>Carrera</th>
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<th>Acciones</th>
|
||||
<?php }?>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<?php
|
||||
foreach($fs_carreras as $carrera){
|
||||
$color = "danger";
|
||||
$title = "Inactiva";
|
||||
if($carrera["carrera_activa"]==1){
|
||||
$color ="success";
|
||||
$title="Activa";
|
||||
}
|
||||
$nivel='Licenciatura';
|
||||
if($carrera['nivel_id']==2)
|
||||
$nivel='Posgrado';
|
||||
?>
|
||||
<tr data-id="<?php echo $carrera['carrera_id'];?>" id="<?php echo $carrera['carrera_id'];?>">
|
||||
<td class="text-<?php echo $color;?> text-center" title="<?php echo $title;?>">
|
||||
<span class="ing-bullet"></span>
|
||||
</td>
|
||||
<td class="text-primary"><?php echo $nivel;?></td>
|
||||
<td class="text-primary"><?php echo $carrera["carrera_nombre"];?></td>
|
||||
<?php if($user->acceso == 'w') {?>
|
||||
<td class="text-center icono-acciones">
|
||||
<a href="#" data-toggle="modal" data-target="#modal" data-tipo="2" title="Editar"><span class="ing-editar ing-fw"></span></a>
|
||||
</td>
|
||||
<?php }?>
|
||||
</tr>
|
||||
<?php }?>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- Tiempos -->
|
||||
<div class="tab-pane fade" id="tiempos" role="tabpanel" aria-labelledby="tiempos-tab">
|
||||
<p class="mt-4">Asigna los minutos de tolerancia antes y después del horario de clase</p>
|
||||
|
||||
<form action="" method="post" id="formaModalTiempos" onsubmit="return valida_camposT()">
|
||||
<input type="hidden" name="facultadT" id="facultadT">
|
||||
<h3 class="text-center">Licenciatura</h3>
|
||||
<div class="row mt-3" style="border:solid 2px; border-radius: 8px;">
|
||||
<div class="offset-1 col-2 text-center">
|
||||
Antes
|
||||
<input id="antesL" name="antesL" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-2 text-center bg-light mt-4 mb-4">
|
||||
<h5 class="mt-2">Hora de clase</h5>
|
||||
</div>
|
||||
<div class="col-2 text-center">
|
||||
Despues
|
||||
<input id="despuesL" name="despuesL" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-2 text-center retardoLic">
|
||||
Retardos
|
||||
<input id="retardoL" name="retardoL" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-3 text-center">
|
||||
¿Tiene retardos?<br>
|
||||
<div class="custom-control custom-switch mt-2">
|
||||
<input type="checkbox" class="custom-control-input tipo-switch" name="retardoLic" id="retardoLic" value="1">
|
||||
<label class="custom-control-label" for="retardoLic">Si</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<br><br>
|
||||
<h3 class="text-center">Posgrado</h3>
|
||||
<div class="row mt-3" style="border:solid 2px; border-radius: 8px;">
|
||||
<div class="offset-1 col-2 text-center">
|
||||
Antes
|
||||
<input id="antesP" name="antesP" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-2 text-center bg-light mt-4 mb-4">
|
||||
<h5 class="mt-2">Hora de clase</h5>
|
||||
</div>
|
||||
<div class="col-2 text-center">
|
||||
Despues
|
||||
<input id="despuesP" name="despuesP" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-2 text-center retardoPos">
|
||||
Retardo
|
||||
<input id="retardoP" name="retardoP" type="number" class="form-control text-center" maxlenth="10">
|
||||
<div class="invalid-feedback">
|
||||
Debe ser un numero mayor que 0
|
||||
</div>
|
||||
min
|
||||
</div>
|
||||
<div class="col-3 text-center">
|
||||
¿Tiene retardos?<br>
|
||||
<div class="custom-control custom-switch mt-2">
|
||||
<input type="checkbox" class="custom-control-input tipo-switch" name="retardoPos" id="retardoPos" value="1">
|
||||
<label class="custom-control-label" for="retardoPos"></label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<br>
|
||||
</form>
|
||||
<div class="form-group row mt-3">
|
||||
<div class="offset-4 col-8">
|
||||
<button class="btn btn-outline-primary" id="submitBtnT">
|
||||
<span class="ing-aceptar ing-fw"></span> Guardar
|
||||
</button>
|
||||
<button type="reset" id="reset" class="btn btn-outline-danger" data-dismiss="modal">
|
||||
<span class="ing-cancelar ing-fw"></span> Limpiar
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
<!-- Footer -->
|
||||
<?php
|
||||
include "import/html_footer.php";
|
||||
?>
|
||||
<!-- Modal -->
|
||||
<div class="modal fade" id="modal_periodo" tabindex="-1" role="dialog" arialabelledby="modal" aria-hidden="true">
|
||||
<div class="modal-dialog modal-dialog-centered" role="document">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h4 class="col-12 modal-title text-center">
|
||||
<span id="modalLabelP">
|
||||
Editar periodo
|
||||
</span>
|
||||
<button type="button" class="close text-white" data-dismiss="modal" aria-label="close">
|
||||
<span aria-hidden="true">×</span>
|
||||
</button>
|
||||
</h4>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<form action="" method="post" id="formaModalP" onsubmit="return valida_camposP()">
|
||||
<input type="hidden" name="idP" id="idP">
|
||||
<input type="hidden" name="facultadP" id="facultadP" value="<?php echo $_GET['facultad']; ?>">
|
||||
<div class="form-box">
|
||||
<div class="form-group row">
|
||||
<label for="nombreP" class="col-4 col-form-label">Nombre *</label>
|
||||
<div class="col-8">
|
||||
<input id="nombreP" name="nombreP" type="text" class="form-control" maxlength="100">
|
||||
<div class="invalid-feedback" id="nombreP-error">Campo obligatorio</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="inicio" class="col-4 col-form-label">Fecha de inicio *</label>
|
||||
<div class="col-8">
|
||||
<input id="fecha_inicial" name="fecha_inicial" type="text" class="form-control date-picker" placeholder="dd/mm/aaaa" maxlength="10" required="required" readonly="">
|
||||
<div class="invalid-feedback">Debe seleccionar una fecha</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="fin" class="col-4 col-form-label">Fecha de fin *</label>
|
||||
<div class="col-8">
|
||||
<input id="fecha_final" name="fecha_final" type="text" class="form-control date-picker" placeholder="dd/mm/aaaa" maxlength="10" required="required" readonly="">
|
||||
<div class="invalid-feedback">Debe seleccionar una fecha</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="nivelP" class="col-4 col-form-label">Nivel *</label>
|
||||
<div class="col-8">
|
||||
<div class="datalist datalist-select mb-1 w-100">
|
||||
<div class="datalist-input">Mostrar todos</div>
|
||||
<span class="ing-buscar icono"></span>
|
||||
<ul style="display:none">
|
||||
<?php foreach($fs_niveles as $pnivel){?>
|
||||
<li data-id="<?php echo $pnivel['nivel_id']?>" class="pl-4"><?php echo $pnivel['nivel_nombre'] ?></li>
|
||||
<?php }?>
|
||||
</ul>
|
||||
<input type="hidden" id="nivelP" name="nivelP" value="">
|
||||
</div>
|
||||
<div class="invalid-feedback">Debe seleccionar un nivel</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="estadoP" class="col-4 col-form-label">Estado *</label>
|
||||
<div class="col-4">
|
||||
<div class="form-check form-check-inline">
|
||||
<input class="form-check-input radio-lg" type="radio" id="estado_activoP" name="estadoP" value="1" checked="checked">
|
||||
<label for="estado_activoP" class="col-form-label">Activo</label>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<div class="form-check form-check-inline">
|
||||
<input class="form-check-input radio-lg" type="radio" id="estado_inactivoP" name="estadoP" value="2">
|
||||
<label for="estado_inactivoP" class="col-form-label">Inactivo</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="from-group row">
|
||||
<div class="offset-4 col-8">
|
||||
<button type="submit" class="btn btn-outline-primary" id="submitBtnP" data-tipo="1">
|
||||
<span class="ing-aceptar ing-fw"></span> Guardar
|
||||
</button>
|
||||
<button type="reset" class="btn btn-outline-danger" data-dismiss="modal">
|
||||
<span class="ing-cancelar ing-fw"></span> Cancelar
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal fade" id="modal" tabindex="-1" role="dialog" arialabelledby="modal" aria-hidden="true">
|
||||
<div class="modal-dialog modal-dialog-centered" role="document">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h4 class="col-12 modal-title text-center">
|
||||
<span id="modalLabel">
|
||||
Editar nombre de Carrera
|
||||
</span>
|
||||
<button type="button" class="close text-white" data-dismiss="modal" aria-label="close">
|
||||
<span aria-hidden="true">×</span>
|
||||
</button>
|
||||
</h4>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<form action="" method="post" id="formaModal" onsubmit="return valida_campos()">
|
||||
<input type="hidden" name="id" id="id">
|
||||
<input type="hidden" name="facultad" id="facultad" value="<?php echo $_GET['facultad']; ?>">
|
||||
<div class="form-box">
|
||||
<div class="form-group row">
|
||||
<label for="nivel" class="col-4 col-form-label">Nivel *</label>
|
||||
<div class="col-8">
|
||||
<div class="datalist datalist-select mb-1 w-100">
|
||||
<div class="datalist-input">Mostrar todos</div>
|
||||
<span class="ing-buscar icono"></span>
|
||||
<ul style="display:none">
|
||||
|
||||
<?php foreach($fs_niveles as $pnivel){?>
|
||||
<li data-id="<?php echo $pnivel['nivel_id']?>" class="pl-4"><?php echo $pnivel['nivel_nombre'] ?></li>
|
||||
<?php }?>
|
||||
</ul>
|
||||
<input type="hidden" id="nivel" name="nivel" value="">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="nombre" class="col-4 col-form-label">Nombre *</label>
|
||||
<div class="col-8">
|
||||
<input id="nombre" name="nombre" type="text" class="form-control" maxlength="100">
|
||||
<div class="invalid-feedback" id="nombre-error">Campo obligatorio</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group row">
|
||||
<label for="estado" class="col-4 col-form-label">Estado *</label>
|
||||
<div class="col-4">
|
||||
<div class="form-check form-check-inline">
|
||||
<input class="form-check-input radio-lg" type="radio" id="estado_activo" name="estado" value="1" checked="checked">
|
||||
<label for="estado_activo" class="col-form-label">Activo</label>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<div class="form-check form-check-inline">
|
||||
<input class="form-check-input radio-lg" type="radio" id="estado_inactivo" name="estado" value="0">
|
||||
<label for="estado_inactivo" class="col-form-label">Inactivo</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="from-group row">
|
||||
<div class="offset-4 col-8">
|
||||
<button type="submit" class="btn btn-outline-primary" id="submitBtn" data-tipo="1">
|
||||
<span class="ing-aceptar ing-fw"></span> Guardar
|
||||
</button>
|
||||
<button type="reset" class="btn btn-outline-danger" id="reset" data-dismiss="modal">
|
||||
<span class="ing-cancelar ing-fw"></span> Cancelar
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</style>
|
||||
<script src="js/jquery.min.js"></script>
|
||||
<script src="js/jquery-ui.js"></script>
|
||||
<script src="js/bootstrap/bootstrap.min.js"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<?
|
||||
$redirect = $_SERVER['PHP_SELF'];
|
||||
include "import/html_header.php";
|
||||
global $user;
|
||||
|
||||
html_header(
|
||||
"Carreras",
|
||||
"Sistema de gestión de checador",
|
||||
);
|
||||
?>
|
||||
<main class="container-fluid px-4 my-4" id="app" v-cloak @vue:mounted="mounted" style="min-height: 70vh;">
|
||||
<section class="row mt-4">
|
||||
<div class="col-12 position-relative">
|
||||
<!-- Loop for messages -->
|
||||
<div class="toast show shadow-sm mb-3 bg-white"
|
||||
style="position: fixed; top: 15%; right: 1%; max-width: 300px;" role="alert" aria-live="assertive"
|
||||
aria-atomic="true"
|
||||
@vue:mounted="$('.toast').toast({delay: 5000}).toast('show').on('hidden.bs.toast', () => { message.text = '' })"
|
||||
v-if="message.text">
|
||||
<div class="toast-header">
|
||||
<strong class="mr-auto text-primary text-uppercase text-center w-100 px-4">
|
||||
{{ message.title }}
|
||||
</strong>
|
||||
<small class="text-muted">{{ message.timestamp }}</small>
|
||||
<button type="button" class="ml-2 mb-1 close" data-dismiss="toast" aria-label="Close"
|
||||
@click="message.text = ''">
|
||||
<span aria-hidden="true">
|
||||
<i class="fas fa-times"></i>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
<div class="toast-body">
|
||||
<div :class="message.type == 'success' ? 'text-success' : 'text-danger'"><i
|
||||
:class="message.type == 'success' ? 'fas fa-check-circle' : 'fas fa-times-circle'"></i>
|
||||
{{ message.text }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
<div class="container">
|
||||
<div class="row" v-for="facultad in carreras">
|
||||
<!-- Facultad Card -->
|
||||
<div class="card col-12 mb-4 shadow-lg">
|
||||
<div class="card-header bg-primary text-white">
|
||||
<h3 class="mb-1">{{ facultad.facultad_nombre }}</h3>
|
||||
</div>
|
||||
<div class="card-body bg-white">
|
||||
<div class="row justify-content-center">
|
||||
<!-- Loop for Carreras -->
|
||||
<div class="col-md-6 mb-3" v-for="carrera in facultad.carreras">
|
||||
<div class="card border-secondary mb-3 shadow-sm">
|
||||
<div class="card-body">
|
||||
<h5 class="card-title text-primary text-uppercase text-center w-100 px-4 mb-3 text-truncate text-break border-bottom border-secondary pb-2"
|
||||
:title="carrera.carrera_nombre">
|
||||
{{ carrera.carrera_nombre }}
|
||||
</h5>
|
||||
|
||||
<!-- Dropdown for Niveles -->
|
||||
<div class="dropdown">
|
||||
<button class="btn btn-outline-secondary dropdown-toggle" type="button"
|
||||
data-toggle="dropdown" aria-expanded="false"
|
||||
@vue:mounted="$('.dropdown-toggle').dropdown()">
|
||||
{{ carrera.nivel_nombre }}
|
||||
</button>
|
||||
<div class="dropdown-menu shadow">
|
||||
<a class="dropdown-item" v-for="nivel in niveles" key="nivel.nivel_id"
|
||||
style="cursor: pointer; user-select: none;"
|
||||
@click="setNivel(carrera, nivel)"
|
||||
:class="nivel.nivel_id == carrera.nivel_id ? 'active' : ''"
|
||||
:disabled="nivel.nivel_id == carrera.nivel_id">
|
||||
{{ nivel.nivel_nombre }}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div> <!-- End of Carreras loop -->
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- End of Facultad Card -->
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
<?
|
||||
include "import/html_footer.php"; ?>
|
||||
<script src="https://cdn.jsdelivr.net/npm/jquery@3.5.1/dist/jquery.slim.min.js"
|
||||
integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/popper.js@1.16.1/dist/umd/popper.min.js"
|
||||
integrity="sha384-9/reFTGAW83EW2RDu2S0VKaIzap3H66lZH81PoYlFhbGU+6BZp6G7niu735Sk7lN"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/bootstrap@4.6.2/dist/js/bootstrap.min.js"
|
||||
integrity="sha384-+sLIOodYLS7CIrQpBjl+C7nPvqq+FbNUBDunl/OZv93DB7Ln/533i8e/mZXLi/P+"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="js/datalist.js"></script>
|
||||
<script src="js/datepicker-es.js"></script>
|
||||
<script src="js/toggle.js"></script>
|
||||
<?php
|
||||
require_once 'js/messages.php';
|
||||
?>
|
||||
<script>
|
||||
$('#retardoLic').change(function(){
|
||||
if($(this).is(':checked')){
|
||||
$('.retardoLic').show();
|
||||
}
|
||||
else{
|
||||
$('.retardoLic').hide();
|
||||
$('#retardoL').val("0");
|
||||
}
|
||||
});
|
||||
$('#retardoPos').change(function(){
|
||||
if($(this).is(':checked')){
|
||||
$('.retardoPos').show();
|
||||
}
|
||||
else{
|
||||
$('.retardoPos').hide();
|
||||
$('#retardoP').val("0");
|
||||
}
|
||||
});
|
||||
$('#reset').on('click', function(){
|
||||
$('#antesL').val("<?= -1*($fs_tiempoLic['desde_asistencia'] ?? 0) ?>");
|
||||
$('#despuesL').val("<?= ($fs_tiempoLic['hasta_asistencia'] ?? 1)-1 ?>");
|
||||
$('#retardoL').val("<?= ($fs_tiempoLic['hasta_retardo'] ?? 0) - ($fs_tiempoLic['hasta_asistencia'] ?? 0) ?>");
|
||||
$('#antesP').val("<?= -1*($fs_tiempoPos['desde_asistencia'] ?? 0) ?>");
|
||||
$('#despuesP').val("<?= ($fs_tiempoPos['hasta_asistencia'] ?? 1)-1 ?>");
|
||||
$('#retardoP').val("<?= ($fs_tiempoPos['hasta_retardo'] ?? 0) - ($fs_tiempoPos['hasta_asistencia'] ?? 0) ?>");
|
||||
<?php
|
||||
if(($fs_tiempoLic['hasta_asistencia'] ?? 0) == ($fs_tiempoLic['hasta_retardo'] ?? 0)){ ?>
|
||||
$('.retardoLic').hide();
|
||||
$('#retardoL').val("0");
|
||||
$('#retardoLic').prop("checked", false).change();
|
||||
<?php }
|
||||
else{ ?>
|
||||
$('#retardoLic').prop("checked", true).change();
|
||||
<?php }
|
||||
if(($fs_tiempoPos['hasta_asistencia'] ?? 0) == ($fs_tiempoPos['hasta_retardo'] ?? 0)){ ?>
|
||||
$('.retardoPos').hide();
|
||||
$('#retardoP').val("0");
|
||||
$('#retardoPos').prop("checked", false).change();
|
||||
<?php }
|
||||
else{ ?>
|
||||
$('#retardoPos').prop("checked", true).change();
|
||||
<?php }
|
||||
?>
|
||||
$('#antesL').removeClass("is-invalid");
|
||||
$('#despuesL').removeClass("is-invalid");
|
||||
$('#retardoL').removeClass("is-invalid");
|
||||
$('#antesP').removeClass("is-invalid");
|
||||
$('#despuesP').removeClass("is-invalid");
|
||||
$('#retardoP').removeClass("is-invalid");
|
||||
});
|
||||
$(".date-picker").datepicker($.datepicker.regional["es"]);
|
||||
$(".date-picker").datepicker({
|
||||
dateFormat: "dd/mm/yyyy",
|
||||
changeMonth: true,
|
||||
});
|
||||
|
||||
$('#submitBtnT').on('click', function(){
|
||||
//$('#antesL').addClass("is-invalid");
|
||||
$('#formaModalTiempos').submit();
|
||||
});
|
||||
|
||||
var today = new Date();
|
||||
|
||||
function valida_camposT(){
|
||||
var error=false;
|
||||
if($('#antesL').val()==""){
|
||||
$('#antesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#antesL').val()<0){
|
||||
$('#antesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#antesL').val())){
|
||||
$('#antesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#despuesL').val()==""){
|
||||
$('#despuesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#despuesL').val()<0){
|
||||
$('#despuesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#despuesL').val())){
|
||||
$('#despuesL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#retardoL').val()==""){
|
||||
$('#retardoL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#retardoL').val()<0){
|
||||
$('#retardoL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#retardoL').val())){
|
||||
$('#retardoL').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#antesP').val()==""){
|
||||
$('#antesP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#antesP').val())){
|
||||
$('#antesP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#despuesP').val()==""){
|
||||
$('#despuesP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#despuesP').val())){
|
||||
$('#despuesP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($('#retardoP').val()==""){
|
||||
$('#retardoP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(isNaN($('#retardoP').val())){
|
||||
$('#retardoP').addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if(!error){
|
||||
$('#formaModalTiempos').prop("action", "./action/action_tiempos_update.php");
|
||||
}else{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
function valida_camposP(){
|
||||
var error=false;
|
||||
if($("#fecha_inicial").val()==""){
|
||||
$("#fecha_inicial").addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($("#fecha_final").val()==""){
|
||||
$("#fecha_final").addClass("is-invalid");
|
||||
error=true;
|
||||
}
|
||||
if($("#nombreP").val()==""){
|
||||
$("#nombreP").addClass("is-invalid");
|
||||
$("#nombreP-error").html("Campo obligatorio");
|
||||
error=true;
|
||||
}
|
||||
if($("#nombreP").val()[0]==" "){
|
||||
$("#nombreP").addClass("is-invalid");
|
||||
$("#nombreP-error").html("No puede haber espacios al inicio");
|
||||
error=true;
|
||||
}
|
||||
if($("#nivelP").val()==""){
|
||||
error=true;
|
||||
$("#nivelP").addClass("is-invalid");
|
||||
}
|
||||
if(error){
|
||||
return false;
|
||||
}else{
|
||||
var btn = $("#submitBtnP");
|
||||
if(btn.data("tipo")==2)//update
|
||||
$("#formaModalP").prop("action", "./action/action_periodos_update.php");
|
||||
else{//insert
|
||||
$("#formaModalP").prop("action", "./action/action_periodos_insert.php");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
<?php if(!$fs_carreras && !$fs_periodos){ ?>
|
||||
triggerMessage("No se encontraron carreras ni periodos en esta facultad", "Error");
|
||||
<?php } else if(!$fs_carreras){?>
|
||||
triggerMessage("No se encontraron carreras en esta facultad", "Error");
|
||||
<?php } else if(!$fs_periodos){?>
|
||||
triggerMessage("No se encontraron periodos en esta facultad", "Error");
|
||||
<?php }?>
|
||||
|
||||
function valida_campos(){
|
||||
var error=false;
|
||||
if($("#nombre").val()==""){
|
||||
$("#nombre").addClass("is-invalid");
|
||||
$("#nombre-error").html("Campo obligatorio");
|
||||
error=true;
|
||||
}
|
||||
if($("#nombre").val()[0]==" "){
|
||||
$("#nombre").addClass("is-invalid");
|
||||
$("#nombre-error").html("No puede haber espacios al inicio");
|
||||
error=true;
|
||||
}
|
||||
if($("#nivel").val()==""){
|
||||
error=true;
|
||||
}
|
||||
if($('#estado_activo').prop('checked') == false && $('#estado_inactivo').prop('checked') == false){
|
||||
error=true;
|
||||
}
|
||||
if(error){
|
||||
return false;
|
||||
}else{
|
||||
var btn = $('#submitBtn');
|
||||
if(btn.data("tipo")==2)//update
|
||||
$("#formaModal").prop("action", "./action/action_carreras_update.php");
|
||||
else//insert
|
||||
$("#formaModal").prop("action", "./action/action_carreras_insert.php");
|
||||
}
|
||||
}
|
||||
|
||||
$('#modal_periodo').on('show.bs.modal', function(event){//datos periodo
|
||||
var button = $(event.relatedTarget);
|
||||
var tipo = button.data('tipo');
|
||||
$("#nombreP").removeClass("is-invalid");
|
||||
if(tipo==1){//crear
|
||||
$('#modalLabelP').html("Agregar periodo");
|
||||
$("#submitBtnP").data("tipo", 1);
|
||||
$("#fecha_inicial").datepicker("setDate", today);
|
||||
$("#fecha_final").datepicker("setDate", today);
|
||||
$("#nombreP").val("");
|
||||
$("#estado_activoP").prop("checked", true);
|
||||
setDatalist("#nivelP",1);
|
||||
$("li").removeClass("selected");
|
||||
var fi = $("#fecha_inicial").datepicker("getDate");
|
||||
//$("#fecha_final").datepicker("option", "minDate", fi);
|
||||
}else{//editar
|
||||
$('#modalLabelP').html("Editar periodo");
|
||||
$("#submitBtnP").data("tipo", 2);
|
||||
var id = $(event.relatedTarget).parents("tr").data("id");
|
||||
var fac = $("#facultadP").val();
|
||||
$.ajax({
|
||||
url:"action/action_periodos_select.php",
|
||||
type:"post",
|
||||
dataType:"json",
|
||||
data:{idfacultad: fac, idperiodo: id},
|
||||
success:function(result){
|
||||
//console.log(result);
|
||||
$("#idP").val(result["id"]);
|
||||
$("#facultadP").val(result["facultad_id"]);
|
||||
$("#nombreP").val(result["periodo"]);
|
||||
var date = new Date(result["inicio"])
|
||||
date.setDate(date.getDate() + 1);
|
||||
$("#fecha_inicial").datepicker("setDate", date);
|
||||
date = new Date(result["fin"])
|
||||
date.setDate(date.getDate() + 1);
|
||||
$("#fecha_final").datepicker("setDate", date);
|
||||
//$(".datalist-input").html(result["nivel"]);
|
||||
setDatalist("#nivelP",result["nivel_id"]);
|
||||
var fi = $("#fecha_inicial").datepicker("getDate");
|
||||
//$("#fecha_final").datepicker("option", "minDate", fi);
|
||||
var ff = $("#fecha_final").datepicker("getDate");
|
||||
//$("#fecha_inicial").datepicker("option", "maxDate", ff);
|
||||
if(result['estado']=="Activo"){
|
||||
$('#estado_activoP').prop('checked', true);
|
||||
}else{
|
||||
$('#estado_inactivoP').prop('checked', true);
|
||||
}
|
||||
},
|
||||
error: function(){console.log("Error")}
|
||||
});
|
||||
}
|
||||
})
|
||||
|
||||
$('#modal').on('show.bs.modal', function(event){
|
||||
var button = $(event.relatedTarget);
|
||||
var tipo = button.data('tipo');
|
||||
var modal = $(this);
|
||||
$("#nombre").removeClass("is-invalid");
|
||||
if(tipo == 1){//crear
|
||||
$("#submitBtn").data('tipo', 1);
|
||||
$("#modalLabel").html("Crear Carrera");
|
||||
$("#nombre").val("");
|
||||
$('#estado_activo').prop('checked', true);
|
||||
$('li').removeClass('selected');
|
||||
$(".datalist-input").html("Mostrar todas");
|
||||
$("#nivel").val("");
|
||||
}else{//editar
|
||||
$("#submitBtn").data('tipo', 2);
|
||||
$("#modalLabel").html("Editar Carrera");
|
||||
$("#nombre").val("");
|
||||
$('#estado_activo').prop('checked', true);
|
||||
var id = $(event.relatedTarget).parents("tr").data("id");
|
||||
var fac = $("#facultad").val();
|
||||
$.ajax({
|
||||
url:"action/action_carreras_select.php",
|
||||
type:"post",
|
||||
dataType:"json",
|
||||
data:{idfacultad: fac, idcarrera: id},
|
||||
success:function(result){
|
||||
//console.log(result);
|
||||
$("#id").val(result["carrera_id"]);
|
||||
$("#nombre").val(result["carrera_nombre"])
|
||||
if(result['carrera_activa']==1){
|
||||
$('#estado_activo').prop('checked', true);
|
||||
}else{
|
||||
$('#estado_inactivo').prop('checked', true);
|
||||
}
|
||||
setDatalist("#nivel", result["nivel_id"]);
|
||||
},
|
||||
error: function(){console.log("Error")}
|
||||
});
|
||||
}
|
||||
});
|
||||
$(document).ready(function(){
|
||||
$('#antesL').val("<?= -1*($fs_tiempoLic['desde_asistencia'] ?? 0) ?>");
|
||||
$('#despuesL').val("<?= ($fs_tiempoLic['hasta_asistencia'] ?? 1)-1 ?>");
|
||||
$('#retardoL').val("<?= ($fs_tiempoLic['hasta_retardo'] ?? 1) - ($fs_tiempoLic['hasta_asistencia'] ?? 0) ?>");
|
||||
$('#antesP').val("<?= -1*($fs_tiempoPos['desde_asistencia'] ?? 0) ?>");
|
||||
$('#despuesP').val("<?= ($fs_tiempoPos['hasta_asistencia'] ?? 1) -1 ?>");
|
||||
$('#retardoP').val("<?= ($fs_tiempoPos['hasta_retardo'] ?? 1) - ($fs_tiempoPos['hasta_asistencia'] ?? 0) ?>");
|
||||
$('#facultadT').val("<?= $_GET['facultad'] ?>");
|
||||
<?php
|
||||
if(($fs_tiempoLic['hasta_asistencia'] ?? 0) == ($fs_tiempoLic['hasta_retardo'] ?? 0)){ ?>
|
||||
$('.retardoLic').hide();
|
||||
$('#retardoL').val("0");
|
||||
$('#retardoLic').prop("checked", false).change();
|
||||
<?php }
|
||||
else{ ?>
|
||||
$('#retardoLic').prop("checked", true).change();
|
||||
<?php }
|
||||
if(($fs_tiempoPos['hasta_asistencia'] ?? 0) == ($fs_tiempoPos['hasta_retardo'] ?? 0)){ ?>
|
||||
$('.retardoPos').hide();
|
||||
$('#retardoP').val("0");
|
||||
$('#retardoPos').prop("checked", false).change();
|
||||
<?php }
|
||||
else{ ?>
|
||||
$('#retardoPos').prop("checked", true).change();
|
||||
<?php }
|
||||
?>
|
||||
});
|
||||
</script>
|
||||
<script src="js/carreras.js?<?= rand(0, 2) ?>" type="module"></script>
|
||||
<script src="js/scrollables.js"></script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
11
css/sgi.css
11
css/sgi.css
@@ -863,7 +863,7 @@ footer ul {
|
||||
}
|
||||
|
||||
footer .footerTop .menuFooter ul>li {
|
||||
*zoom: 1;
|
||||
zoom: 1;
|
||||
float: left;
|
||||
clear: none;
|
||||
text-align: inherit;
|
||||
@@ -1058,11 +1058,18 @@ footer .tab-pane p {
|
||||
.movie {
|
||||
transition: all 0.1s;
|
||||
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.2);
|
||||
height: 8rem;
|
||||
/* align all inside content to the middle */
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
background-color: #f7f7f7;
|
||||
}
|
||||
|
||||
.movie:hover {
|
||||
transform: scale(1.05);
|
||||
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.2);
|
||||
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.5);
|
||||
font-size: 1.1em;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,133 +0,0 @@
|
||||
<?php
|
||||
require_once 'class/c_login.php';
|
||||
$user = Login::get_user();
|
||||
|
||||
$user->access();
|
||||
if (in_array($user->acceso, ['n']))
|
||||
die(header('Location: main.php?error=1'));
|
||||
|
||||
$user->print_to_log('Consultar horario');
|
||||
|
||||
$write = $user->admin || in_array($user->acceso, ['w']);
|
||||
// var_dump($user);
|
||||
?>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<title>Consultar horario | <?= $user->facultad['facultad'] ?? 'General' ?></title>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="content-type" content="text/plain; charset=UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||
<?php include_once "import/html_css_files.php"; ?>
|
||||
|
||||
<script src="js/scrollables.js" defer></script>
|
||||
<script src="js/jquery.min.js" defer></script>
|
||||
<script src="js/bootstrap/bootstrap.min.js" defer></script>
|
||||
|
||||
<script src="js/messages.js" defer></script>
|
||||
<script>
|
||||
const write = <?= $write ? 'true' : 'false' ?>;
|
||||
</script>
|
||||
<script src="js/moment.js" defer></script>
|
||||
<script src="js/horario_profesor.js" defer></script>
|
||||
</head>
|
||||
<!-- -->
|
||||
|
||||
<body style="display: block;">
|
||||
<?php
|
||||
include('include/constantes.php');
|
||||
include("import/html_header.php");
|
||||
html_header("Consultar horario", "Sistema de gestión de checador");
|
||||
?>
|
||||
<?= "<!-- $user -->" ?>
|
||||
<main class="container content marco content-margin" id="local-app">
|
||||
<section id="message"></section>
|
||||
<?php require('import/periodo.php') ?>
|
||||
|
||||
<form id="form" class="form-horizontal">
|
||||
<div class="form-group">
|
||||
<div class="form-box">
|
||||
<input type="hidden" name="periodo" value="<?= $user->periodo_id ?>" />
|
||||
<div class="form-group row">
|
||||
<label for="clave_profesor" class="col-4 col-form-label">Profesor</label>
|
||||
<div class="col-6">
|
||||
<input list="lista_profesores" name="clave_profesor" id="clave_profesor" class="form-control" placeholder="Profesor" required="required">
|
||||
<div class="valid-feedback">
|
||||
Profesor encontrado
|
||||
</div>
|
||||
<div class="invalid-feedback">
|
||||
Profesor no encontrado
|
||||
</div>
|
||||
<datalist id="lista_profesores">
|
||||
<?php
|
||||
$profesores = $db->where('facultad_id', $user->facultad['facultad_id'])->get("fs_profesor");
|
||||
foreach ($profesores as $profesor) {
|
||||
extract($profesor);
|
||||
?>
|
||||
<option data-grado="<?= $grado ?>" data-clave="<?= $clave ?>" data-profesor="<?= $profesor ?>" data-id="<?= $id; ?>" value="<?= "$clave | $grado $profesor" ?>"></option>
|
||||
<?php
|
||||
}
|
||||
?>
|
||||
</datalist>
|
||||
<ul class="list-group" id="profesores"></ul>
|
||||
<input type="hidden" id="periodo_id" name="periodo_id" value="<?= $user->periodo_id ?>">
|
||||
<input type="hidden" id="profesor_id" name="profesor_id" value="">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- ICO-BUSCAR FILTRAR & ICO-BORRAR LIMPIAR -->
|
||||
<div class="form-group row justify-content-center">
|
||||
<button class="btn btn-outline-primary mr-2">
|
||||
<span class="ing-buscar icono"></span>
|
||||
Buscar horario
|
||||
</button>
|
||||
<button type="button" class="btn btn-outline-danger" onclick="location.reload()">
|
||||
<span class="ing-borrar icono"></span>
|
||||
Limpiar
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
<div class="form-group mt-4 row justify-content-center">
|
||||
<?php if ($write) { ?>
|
||||
<button type="button" id="nuevo" class="btn btn-outline-primary ml-4 d-none" title="Nuevo horario" data-toggle="modal" data-target="#modal-editar">
|
||||
<span class="ing-mas ing-fw"></span> Nuevo
|
||||
</button>
|
||||
<?php } ?>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</form>
|
||||
<!-- Horario is a (table with one a cell) within a table
|
||||
7:15 - 8:45, 8:45 - 10:15, 10:30 - 12:00, 12:00 - 13:30
|
||||
de lunes a viernes, a excepción de que tenga sábado
|
||||
-->
|
||||
<div id="btn-excel-horario" class="mb-2 float-right hidden">
|
||||
<button class="btn btn-outline-secondary " title="Exportar a Excel">
|
||||
<span class="ing-descarga ing-fw"></span> Exportar a Excel
|
||||
</button>
|
||||
</div>
|
||||
<!-- Table responsive -->
|
||||
<div class="table-responsive">
|
||||
<table class="table table-bordered table-sm table-responsive-md" id="table-horario">
|
||||
<thead class="thead-dark">
|
||||
<tr id="headers">
|
||||
<th scope="col" class="text-center">Hora</th>
|
||||
<th scope="col" class="text-center">Lunes</th>
|
||||
<th scope="col" class="text-center">Martes</th>
|
||||
<th scope="col" class="text-center">Miércoles</th>
|
||||
<th scope="col" class="text-center">Jueves</th>
|
||||
<th scope="col" class="text-center">Viernes</th>
|
||||
<th scope="col" class="text-center">Sábado</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody id="horario"></tbody>
|
||||
</table>
|
||||
</div>
|
||||
</main>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
44
js/carreras.js
Normal file
44
js/carreras.js
Normal file
@@ -0,0 +1,44 @@
|
||||
import { createApp } from 'https://unpkg.com/petite-vue?module';
|
||||
const app = createApp({
|
||||
carreras: [],
|
||||
niveles: [],
|
||||
message: {},
|
||||
async setNivel(carrera, nivel) {
|
||||
if (carrera.nivel_id === nivel.nivel_id) {
|
||||
return;
|
||||
}
|
||||
carrera.nivel_id = nivel.nivel_id;
|
||||
carrera.nivel_nombre = nivel.nivel_nombre;
|
||||
await fetch('action/carrera.php', {
|
||||
method: 'PUT',
|
||||
body: JSON.stringify({
|
||||
carrera_id: carrera.carrera_id,
|
||||
nivel_id: nivel.nivel_id
|
||||
})
|
||||
})
|
||||
.then(res => res.json())
|
||||
.then(res => {
|
||||
this.message.title = "Actualización";
|
||||
this.message.text = res.error ?? res.success;
|
||||
this.message.type = res.error ? 'danger' : 'success';
|
||||
this.message.timestamp = new Date().toLocaleTimeString();
|
||||
});
|
||||
},
|
||||
async mounted() {
|
||||
this.carreras = await fetch('action/carrera.php').then(res => res.json());
|
||||
this.niveles = await fetch('action/nivel.php').then(res => res.json());
|
||||
// group by facultad_id
|
||||
const carreras = this.carreras.reduce((acc, cur) => {
|
||||
const { facultad_nombre } = cur;
|
||||
if (!acc[facultad_nombre]) {
|
||||
acc[facultad_nombre] = [];
|
||||
}
|
||||
acc[facultad_nombre].push(cur);
|
||||
return acc;
|
||||
}, {});
|
||||
this.carreras = Object.entries(carreras).map(([facultad_nombre, carreras]) => ({
|
||||
facultad_nombre: facultad_nombre,
|
||||
carreras
|
||||
}));
|
||||
}
|
||||
}).mount('#app');
|
||||
44
js/periodos.js
Normal file
44
js/periodos.js
Normal file
@@ -0,0 +1,44 @@
|
||||
import { createApp } from 'https://unpkg.com/petite-vue?module';
|
||||
const app = createApp({
|
||||
carreras: [],
|
||||
niveles: [],
|
||||
message: {},
|
||||
async setNivel(carrera, nivel) {
|
||||
if (carrera.nivel_id === nivel.nivel_id) {
|
||||
return;
|
||||
}
|
||||
carrera.nivel_id = nivel.nivel_id;
|
||||
carrera.nivel_nombre = nivel.nivel_nombre;
|
||||
await fetch('action/carrera.php', {
|
||||
method: 'PUT',
|
||||
body: JSON.stringify({
|
||||
carrera_id: carrera.carrera_id,
|
||||
nivel_id: nivel.nivel_id
|
||||
})
|
||||
})
|
||||
.then(res => res.json())
|
||||
.then(res => {
|
||||
this.message.title = "Actualización";
|
||||
this.message.text = res.error ?? res.success;
|
||||
this.message.type = res.error ? 'danger' : 'success';
|
||||
this.message.timestamp = new Date().toLocaleTimeString();
|
||||
});
|
||||
},
|
||||
async mounted() {
|
||||
this.carreras = await fetch('action/carrera.php').then(res => res.json());
|
||||
this.niveles = await fetch('action/nivel.php').then(res => res.json());
|
||||
// group by facultad_id
|
||||
const carreras = this.carreras.reduce((acc, cur) => {
|
||||
const { facultad_nombre } = cur;
|
||||
if (!acc[facultad_nombre]) {
|
||||
acc[facultad_nombre] = [];
|
||||
}
|
||||
acc[facultad_nombre].push(cur);
|
||||
return acc;
|
||||
}, {});
|
||||
this.carreras = Object.entries(carreras).map(([facultad_nombre, carreras]) => ({
|
||||
facultad_nombre: facultad_nombre,
|
||||
carreras
|
||||
}));
|
||||
}
|
||||
}).mount('#app');
|
||||
220
periodos.php
Normal file
220
periodos.php
Normal file
@@ -0,0 +1,220 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Auditoría asistencial</title>
|
||||
<?php
|
||||
include 'import/html_css_files.php';
|
||||
?>
|
||||
<link rel="stylesheet" type="text/css" href="https://unpkg.com/trix@2.0.0/dist/trix.css">
|
||||
<style>
|
||||
[v-cloak] {
|
||||
display: none;
|
||||
}
|
||||
</style>
|
||||
<script src="js/jquery.min.js"></script>
|
||||
<script src="js/jquery-ui.js"></script>
|
||||
<script src="js/bootstrap/bootstrap.min.js"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<?
|
||||
$redirect = $_SERVER['PHP_SELF'];
|
||||
include "import/html_header.php";
|
||||
global $user;
|
||||
|
||||
html_header("Periodos", "Sistema de gestión de checador");
|
||||
?>
|
||||
<main class="container-fluid px-4 my-4" id="app" v-cloak @vue:mounted="mounted" style="min-height: 70vh;">
|
||||
<section class="row mt-4">
|
||||
<div class="col-12 position-relative">
|
||||
<!-- Loop for messages -->
|
||||
<div class="toast show shadow-sm mb-3 bg-white"
|
||||
style="position: fixed; top: 15%; right: 1%; max-width: 300px;" role="alert" aria-live="assertive"
|
||||
aria-atomic="true"
|
||||
@vue:mounted="$('.toast').toast({delay: 5000}).toast('show').on('hidden.bs.toast', () => { message.text = '' })"
|
||||
v-if="message.text">
|
||||
<div class="toast-header">
|
||||
<strong class="mr-auto text-primary text-uppercase text-center w-100 px-4">
|
||||
{{ message.title }}
|
||||
</strong>
|
||||
<small class="text-muted">{{ message.timestamp }}</small>
|
||||
<button type="button" class="ml-2 mb-1 close" data-dismiss="toast" aria-label="Close"
|
||||
@click="message.text = ''">
|
||||
<span aria-hidden="true">
|
||||
<i class="fas fa-times"></i>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
<div class="toast-body">
|
||||
<div :class="message.type == 'success' ? 'text-success' : 'text-danger'"><i
|
||||
:class="message.type == 'success' ? 'fas fa-check-circle' : 'fas fa-times-circle'"></i>
|
||||
{{ message.text }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
<div class="container">
|
||||
<div class="d-flex flex-wrap justify-content-around">
|
||||
<div class="accordion col-8 mb-4" id="puestos"
|
||||
v-scope="{selected_carrera_id: -1, current_materia: null, current_encargado: null}"
|
||||
v-if="puestos.length">
|
||||
<div class="card" v-for="(puesto, index) in puestos" :key="puesto.puesto_id">
|
||||
<div class="card-header bg-primary" :id="`puesto-${puesto.nombre}`">
|
||||
<h2 class="mb-0">
|
||||
<button class="btn btn-link btn-block text-left text-light" type="button"
|
||||
data-toggle="collapse" :data-target="`#puesto-${puesto.puesto_id}`" aria-expanded="true"
|
||||
:aria-controls="`puesto-${puesto.puesto_id}`">
|
||||
{{puesto.nombre}}
|
||||
|
||||
<button type="button" class="btn btn-outline-danger float-right"
|
||||
data-target="#eliminar-puesto" data-toggle="modal" @click="to_delete = puesto">
|
||||
<span class="icono ing-basura"></span>
|
||||
</button>
|
||||
</button>
|
||||
</h2>
|
||||
</div>
|
||||
|
||||
<div :id="`puesto-${puesto.puesto_id}`" class="collapse" :class="{'show': index == 0}"
|
||||
:aria-labelledby="`puesto-${puesto.nombre}`" data-parent="#puestos">
|
||||
<div class="card-body">
|
||||
<!-- Encargado -->
|
||||
<div class="form-row justify-content-around align-items-center mb-2">
|
||||
<label :for="`encargado-${puesto.puesto_id}`" class="col-3">
|
||||
Encargado del área
|
||||
</label>
|
||||
<div id="encargados" class="datalist datalist-select mb-1 col-9">
|
||||
<div class="datalist-input" v-if="puesto.encargado">
|
||||
({{puesto.encargado.usuario_clave}}) {{ puesto.encargado.usuario_nombre }}
|
||||
</div>
|
||||
<div class="datalist-input" v-else>
|
||||
Selecciona un encargado
|
||||
</div>
|
||||
<span class="icono ing-buscar"></span>
|
||||
<ul style="display:none">
|
||||
<li class="datalist-option" v-for="usuario in usuarios"
|
||||
:key="usuario.usuario_id" :data-id="usuario.usuario_id"
|
||||
style=" white-space: nowrap;" @click="puesto.encargado = usuario"
|
||||
:class="{'selected': puesto.encargado?.usuario_id == usuario.usuario_id}">
|
||||
(<small> {{usuario.usuario_clave}} </small>) {{ usuario.usuario_nombre }}
|
||||
</li>
|
||||
</ul>
|
||||
<input type="hidden" id="encargado_id" name="id">
|
||||
</div>
|
||||
</div>
|
||||
<hr>
|
||||
|
||||
<div class="form-row justify-content-around align-items-center mb-2"
|
||||
v-show="carreras.length">
|
||||
<label :for="`carrera-${puesto.puesto_id}`" class="col-3">
|
||||
Carrera
|
||||
</label>
|
||||
<div id="dlCarreras" class="datalist datalist-select mb-1 col-9">
|
||||
<div class="datalist-input">
|
||||
Selecciona una carrera
|
||||
</div>
|
||||
<span class="icono ing-buscar"></span>
|
||||
<ul style="display:none">
|
||||
<li class="datalist-option" data-id="0" @click="selected_carrera_id = 0">
|
||||
Todas las carreras
|
||||
</li>
|
||||
<li class="datalist-option" v-for="carrera in carreras"
|
||||
:key="carrera.carrera_id" :data-id="carrera.carrera_id"
|
||||
style=" white-space: nowrap;"
|
||||
@click="selected_carrera_id = carrera.carrera_id">
|
||||
(<small> {{carrera.clave_carrera}} </small>) {{ carrera.carrera_nombre }}
|
||||
</li>
|
||||
</ul>
|
||||
<input type="hidden" id="carrera_id" name="id">
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-row justify-content-around align-items-center"
|
||||
v-scope="{to_add_materia: null}">
|
||||
<label :for="`materias-${puesto.puesto_id}`" class="col-3">
|
||||
Materias
|
||||
</label>
|
||||
<input name="materia" placeholder="Seleccione una materia" list="datalist-materias"
|
||||
class="form-control col-9 " v-model="current_materia" @input="to_add_materia = materias.find(m => current_materia == `${m.clave_materia} - ${m.materia_nombre}`);
|
||||
if (to_add_materia) {
|
||||
if (puesto.materias.find(p => p.materia_id == to_add_materia.materia_id)) {
|
||||
console.log('La materia ya está asignada');
|
||||
current_materia = null;
|
||||
return;
|
||||
}
|
||||
puesto.materias.push(to_add_materia);
|
||||
materias.splice(materias.indexOf(to_add_materia), 1);
|
||||
current_materia = null;
|
||||
}" :disabled="selected_carrera_id == -1" v-model="current_materia"
|
||||
:id="`materias-${puesto.puesto_id}`" autocomplete="off">
|
||||
</div>
|
||||
<datalist id="datalist-materias">
|
||||
<option
|
||||
v-for="materia in materias.filter(m => selected_carrera_id == 0 || m.carrera_id == selected_carrera_id).filter(m => !puesto.materias.find(p => p.materia_id == m.materia_id))"
|
||||
:value="`${materia.clave_materia} - ${materia.materia_nombre}`">
|
||||
</datalist>
|
||||
|
||||
<hr>
|
||||
<fieldset class="container d-flex flex-column justify-content-center align-items-center">
|
||||
<legend>Materias Asignadas <span
|
||||
class="badge badge-secondary">{{puesto.materias.length}}</span></legend>
|
||||
<ul class="list-group overflow-auto col-10" v-if="puesto.materias.length"
|
||||
style="max-height: 200px; overflow-y: auto;">
|
||||
<li class="list-group-item list-group-item-action"
|
||||
v-for="materia in puesto.materias" :key="materia.materia_id"
|
||||
@click="puesto.materias.splice(puesto.materias.indexOf(materia), 1); materias.push(materia)"
|
||||
style="cursor: pointer;">
|
||||
<div class="d-flex justify-content-center">
|
||||
<div class="col-2 text-center">
|
||||
<span class="icono ing-borrar text-danger"></span>
|
||||
</div>
|
||||
<div class="col-10 text-left">
|
||||
{{materia.clave_materia}} - {{materia.materia_nombre}}
|
||||
</div>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="alert alert-light" role="alert" v-else>
|
||||
No hay materias asignadas
|
||||
</div>
|
||||
</fieldset>
|
||||
|
||||
</div>
|
||||
<div class="card-footer text-muted">
|
||||
<!-- scroll to top -->
|
||||
<button type="button" class="btn btn-outline-primary btn-lg btn-block"
|
||||
@click="actualizarPuesto(puesto.puesto_id, puesto.materias, puesto.encargado?.usuario_id)"
|
||||
onclick="window.scrollTo(0, 0);">
|
||||
{{ puesto.encargado ? 'Guardar cambios' : 'Guardar sin encargado' }}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-else>
|
||||
<div class="alert alert-dark" role="alert">
|
||||
No hay puestos registrados
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
<?
|
||||
include "import/html_footer.php"; ?>
|
||||
<script src="https://cdn.jsdelivr.net/npm/jquery@3.5.1/dist/jquery.slim.min.js"
|
||||
integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/popper.js@1.16.1/dist/umd/popper.min.js"
|
||||
integrity="sha384-9/reFTGAW83EW2RDu2S0VKaIzap3H66lZH81PoYlFhbGU+6BZp6G7niu735Sk7lN"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/bootstrap@4.6.2/dist/js/bootstrap.min.js"
|
||||
integrity="sha384-+sLIOodYLS7CIrQpBjl+C7nPvqq+FbNUBDunl/OZv93DB7Ln/533i8e/mZXLi/P+"
|
||||
crossorigin="anonymous"></script>
|
||||
<script src="js/datalist.js"></script>
|
||||
<script src="js/periodos.js?<?= rand(0, 2) ?>" type="module"></script>
|
||||
<script src="js/scrollables.js"></script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
@@ -38,6 +38,10 @@
|
||||
<div class="alert alert-success" role="alert" v-if="message">
|
||||
{{message}}
|
||||
</div>
|
||||
|
||||
<?
|
||||
if ($user->acceso == 'w') {
|
||||
?>
|
||||
<div class="justify-content-between align-items-center d-flex mb-4">
|
||||
<button type="button" class="btn btn-primary" data-toggle="modal" data-target="#nuevo-puesto">
|
||||
<span class="ing-mas"></span>
|
||||
@@ -45,6 +49,10 @@
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<?
|
||||
}
|
||||
?>
|
||||
|
||||
<div class="d-flex flex-wrap justify-content-around">
|
||||
<div class="accordion col-8 mb-4" id="puestos"
|
||||
v-scope="{selected_carrera_id: -1, current_materia: null, current_encargado: null}"
|
||||
|
||||
63
ts/carreras.ts
Normal file
63
ts/carreras.ts
Normal file
@@ -0,0 +1,63 @@
|
||||
import { createApp, reactive } from 'https://unpkg.com/petite-vue?module'
|
||||
|
||||
type Carrera = {
|
||||
carrera_id: number;
|
||||
carrera_nombre: string;
|
||||
clave_carrera: string;
|
||||
facultad_id: number;
|
||||
facultad_nombre: string;
|
||||
nivel_id: number;
|
||||
nivel_nombre: string;
|
||||
}
|
||||
|
||||
type Nivel = {
|
||||
nivel_id: number;
|
||||
nivel_nombre: string;
|
||||
}
|
||||
|
||||
const app = createApp({
|
||||
carreras: [] as Carrera[],
|
||||
niveles: [] as Nivel[],
|
||||
message: {} as Record<string, string>,
|
||||
async setNivel(carrera: Carrera, nivel: Nivel) {
|
||||
if (carrera.nivel_id === nivel.nivel_id) {
|
||||
return
|
||||
}
|
||||
carrera.nivel_id = nivel.nivel_id
|
||||
carrera.nivel_nombre = nivel.nivel_nombre
|
||||
|
||||
await fetch('action/carrera.php', {
|
||||
method: 'PUT',
|
||||
body: JSON.stringify({
|
||||
carrera_id: carrera.carrera_id,
|
||||
nivel_id: nivel.nivel_id
|
||||
})
|
||||
})
|
||||
.then(res => res.json())
|
||||
.then(res => {
|
||||
this.message.title = "Actualización"
|
||||
this.message.text = res.error ?? res.success
|
||||
this.message.type = res.error ? 'danger' : 'success'
|
||||
this.message.timestamp = new Date().toLocaleTimeString()
|
||||
})
|
||||
|
||||
|
||||
},
|
||||
async mounted() {
|
||||
this.carreras = await fetch('action/carrera.php').then(res => res.json())
|
||||
this.niveles = await fetch('action/nivel.php').then(res => res.json())
|
||||
// group by facultad_id
|
||||
const carreras = this.carreras.reduce((acc, cur) => {
|
||||
const { facultad_nombre } = cur
|
||||
if (!acc[facultad_nombre]) {
|
||||
acc[facultad_nombre] = []
|
||||
}
|
||||
acc[facultad_nombre].push(cur)
|
||||
return acc
|
||||
}, {} as Record<number, Carrera[]>)
|
||||
this.carreras = Object.entries(carreras).map(([facultad_nombre, carreras]) => ({
|
||||
facultad_nombre: facultad_nombre,
|
||||
carreras
|
||||
}))
|
||||
}
|
||||
}).mount('#app')
|
||||
63
ts/periodos.ts
Normal file
63
ts/periodos.ts
Normal file
@@ -0,0 +1,63 @@
|
||||
import { createApp, reactive } from 'https://unpkg.com/petite-vue?module'
|
||||
|
||||
type Carrera = {
|
||||
carrera_id: number;
|
||||
carrera_nombre: string;
|
||||
clave_carrera: string;
|
||||
facultad_id: number;
|
||||
facultad_nombre: string;
|
||||
nivel_id: number;
|
||||
nivel_nombre: string;
|
||||
}
|
||||
|
||||
type Nivel = {
|
||||
nivel_id: number;
|
||||
nivel_nombre: string;
|
||||
}
|
||||
|
||||
const app = createApp({
|
||||
carreras: [] as Carrera[],
|
||||
niveles: [] as Nivel[],
|
||||
message: {} as Record<string, string>,
|
||||
async setNivel(carrera: Carrera, nivel: Nivel) {
|
||||
if (carrera.nivel_id === nivel.nivel_id) {
|
||||
return
|
||||
}
|
||||
carrera.nivel_id = nivel.nivel_id
|
||||
carrera.nivel_nombre = nivel.nivel_nombre
|
||||
|
||||
await fetch('action/carrera.php', {
|
||||
method: 'PUT',
|
||||
body: JSON.stringify({
|
||||
carrera_id: carrera.carrera_id,
|
||||
nivel_id: nivel.nivel_id
|
||||
})
|
||||
})
|
||||
.then(res => res.json())
|
||||
.then(res => {
|
||||
this.message.title = "Actualización"
|
||||
this.message.text = res.error ?? res.success
|
||||
this.message.type = res.error ? 'danger' : 'success'
|
||||
this.message.timestamp = new Date().toLocaleTimeString()
|
||||
})
|
||||
|
||||
|
||||
},
|
||||
async mounted() {
|
||||
this.carreras = await fetch('action/carrera.php').then(res => res.json())
|
||||
this.niveles = await fetch('action/nivel.php').then(res => res.json())
|
||||
// group by facultad_id
|
||||
const carreras = this.carreras.reduce((acc, cur) => {
|
||||
const { facultad_nombre } = cur
|
||||
if (!acc[facultad_nombre]) {
|
||||
acc[facultad_nombre] = []
|
||||
}
|
||||
acc[facultad_nombre].push(cur)
|
||||
return acc
|
||||
}, {} as Record<number, Carrera[]>)
|
||||
this.carreras = Object.entries(carreras).map(([facultad_nombre, carreras]) => ({
|
||||
facultad_nombre: facultad_nombre,
|
||||
carreras
|
||||
}))
|
||||
}
|
||||
}).mount('#app')
|
||||
Reference in New Issue
Block a user