<?php
declare(strict_types=1);
namespace CoreBundle\Entity;
use DateTime;
use DateTimeZone;
use Doctrine\ORM\Mapping as ORM;
use Exception;
use UserBundle\Entity\User;
use Doctrine\Common\Collections\ArrayCollection;
use JsonSerializable;
/**
* @ORM\Table("quiz_session")
* @ORM\Entity(repositoryClass="CoreBundle\Entity\QuizSessionRepository")
*/
class QuizSession implements JsonSerializable
{
/**
* @var int
*
* @ORM\Column(name="id", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
private int $id;
/**
* @var Quiz
*
* @ORM\ManyToOne(targetEntity="CoreBundle\Entity\Quiz", inversedBy="quizSessions")
* @ORM\JoinColumn(name="quiz", referencedColumnName="id", onDelete="CASCADE", nullable=true)
*/
private ?Quiz $quiz;
/**
* @var User
*
* @ORM\ManyToOne(targetEntity="UserBundle\Entity\User")
* @ORM\JoinColumn(name="created_by", referencedColumnName="id")
*/
private ?User $createdBy;
/**
* @var Classroom
*
* @ORM\ManyToOne(targetEntity="Classroom", inversedBy="quizSessions")
* @ORM\JoinColumn(name="classroom", referencedColumnName="id", onDelete="CASCADE")
*/
private ?Classroom $classroom;
/**
* @var bool
*
* @ORM\Column(name="dormant", type="boolean", nullable=true)
*/
private ?bool $dormant;
/**
* @var int
*
* @ORM\Column(type="smallint", nullable=true)
*/
private ?int $duration;
/**
* @var DateTime|null
*
* @ORM\Column(name="startTime", type="datetime", nullable=true)
*/
private ?DateTime $startTime;
/**
* @ORM\Column(type="datetime", nullable=true)
*/
private ?DateTime $deadline;
/**
* @ORM\Column(type="string", length=255, nullable=true)
*/
private ?string $name;
/**
* @var DateTime
*
* @ORM\Column(name="createdAt", type="datetime", nullable=false)
*/
private DateTime $createdAt;
/**
* @var integer
* [0 - created, in phase of editing; 1 - ready to start, if it's dormant ; 2 - startTime set]
*
* @ORM\Column(type="integer", nullable=false, options={"default"=0})
*/
private int $status = 0;
/**
* @var integer
*
* @ORM\Column(type="integer", nullable=false, options={"default"=1})
*/
private int $isEnabled = 1;
/**
* @var QuizUnit[]
*
* @ORM\OneToMany(targetEntity="CoreBundle\Entity\QuizUnit", mappedBy="quizSession", cascade={"persist"})
*/
private $quizUnits;
/**
* @var bool
*
* @ORM\Column(type="boolean", nullable=true)
*/
private ?bool $durationIgnored;
/**
* @var bool
*
* @ORM\Column(name="hints_available", type="boolean", nullable=true)
*/
private ?bool $hintsAvailable;
/**
* @ORM\Column(name="results_available_before_deadline", type="boolean", nullable=true)
*/
private ?bool $resultsAvailableBeforeDeadline;
/**
* @var string|null
* @ORM\Column(name="isbn", type="string", length=255, nullable=true)
*/
private ?string $isbn;
/**
* @var DateTime
* @ORM\Column(name="updated_at", type="datetime", nullable=true)
*/
private DateTime $updatedAt;
/**
* @var User
*
* @ORM\ManyToOne(targetEntity="UserBundle\Entity\User")
* @ORM\JoinColumn(name="updated_by", referencedColumnName="id")
*/
private User $updatedBy;
/**
* @var string|null
* @ORM\Column(name="description", type="text", nullable=true)
*/
private ?string $description;
/**
* @var DateTime
* @ORM\Column(name="result_view_open_at", type="datetime", nullable=true)
*/
private ?DateTime $resultViewOpenAt;
/**
* @var ?bool
* @ORM\Column(name="extra_teachers", type="boolean", nullable=true)
*/
private ?bool $extraTeachers = null;
/**
* possible values: 'self_study_exam', 'self_study_topic', 'self_study_typical_problem'
* If it is null then it is a regular quiz
*
* @ORM\Column(name="type", type="string", length=255, nullable=true, options={"default"=""})
*/
private ?string $type = '';
/**
* @var SelfStudyTopic
*
* @ORM\ManyToOne(targetEntity="SelfStudyTopic")
* @ORM\JoinColumn(name="self_study_topic", referencedColumnName="id")
*/
private $selfStudyTopic = null;
/**
* @var SelfStudyTypicalExamProblem
*
* @ORM\ManyToOne(targetEntity="SelfStudyTypicalExamProblem")
* @ORM\JoinColumn(name="self_study_typical_exam_problem", referencedColumnName="id")
*/
private $selfStudyTypicalExamProblem = null;
/**
* @var SelfStudyExamQuiz
*
* @ORM\ManyToOne(targetEntity="SelfStudyExamQuiz")
* @ORM\JoinColumn(name="self_study_exam", referencedColumnName="id")
*/
private $selfStudyExam = null;
/**
* @var bool
* @ORM\Column(name="deactivated_questions", type="boolean", nullable=true)
*/
private ?bool $deactivatedProblems = null;
/**
* @var bool
* @ORM\Column(name="is_archived", type="boolean", nullable=true)
*/
private ?bool $isArchived = null;
/**
* @var int|null
* @ORM\Column(name="copy_of", type="integer", nullable=true)
*/
private ?int $copyOfSession = null;
/**
* @var bool|null
* @ORM\Column(name="is_shared_quiz", type="boolean", nullable=true)
*/
private ?bool $isSharedQuiz = null;
/**
* @var bool|null
* @ORM\Column(name="is_pinned", type="boolean", nullable=true)
*/
private ?bool $isPinned = null;
/**
* @ORM\Column(name="can_pause", type="boolean", options={"default"=false})
*/
private bool $canPause = false;
/**
*/
public function __construct(?int $duration)
{
$this->createdAt = new DateTime('now', new DateTimeZone('Europe/Copenhagen'));
$this->updatedAt = new DateTime('now', new DateTimeZone('Europe/Copenhagen'));
$this->quizUnits = new ArrayCollection();
$this->duration = $duration;
}
/**
* @return int|null
*/
public function getCopyOfSession(): ?int
{
return $this->copyOfSession;
}
/**
* @param int|null $copyOfSession
* @return void
*/
public function setCopyOfSession(?int $copyOfSession): void
{
$this->copyOfSession = $copyOfSession;
}
/**
* @return int
*/
public function getId(): int
{
return $this->id;
}
/**
* @return Quiz
*/
public function getQuiz(): ?Quiz
{
return $this->quiz;
}
/**
* @param Quiz $quiz
* @return $this
*/
public function setQuiz(?Quiz $quiz): static
{
$this->quiz = $quiz;
return $this;
}
/**
* @return User
*/
public function getCreatedBy(): ?User
{
return $this->createdBy;
}
/**
* @param User $createdBy
* @return $this
*/
public function setCreatedBy(?User $createdBy): static
{
$this->createdBy = $createdBy;
return $this;
}
/**
* @return Classroom
*/
public function getClassroom(): ?Classroom
{
return $this->classroom;
}
/**
* @param Classroom $classroom
* @return $this
*/
public function setClassroom(?Classroom $classroom)
{
$this->classroom = $classroom;
return $this;
}
/**
* @return boolean
*/
public function isDormant(): ?bool
{
return $this->dormant;
}
/**
* @param boolean $dormant
* @return $this
*/
public function setDormant(?bool $dormant)
{
$this->dormant = $dormant;
return $this;
}
/**
* @return DateTime
*/
public function getStartTime(): ?DateTime
{
return $this->startTime;
}
/**
* @param DateTime $startTime
* @return $this
*/
public function setStartTime(?DateTime $startTime)
{
$this->startTime = $startTime;
return $this;
}
/**
* @return DateTime
*/
public function getCreatedAt(): DateTime
{
return $this->createdAt;
}
/**
* @param DateTime $createdAt
* @return void
*/
public function setCreatedAt(DateTime $createdAt): void
{
$this->createdAt = $createdAt;
}
/**
* @return int
*/
public function getStatus(): int
{
return $this->status;
}
/**
* @param int $status
* @return $this
*/
public function setStatus(int $status): static
{
$this->status = $status;
return $this;
}
/**
* @return QuizUnit[]
*/
public function getQuizUnits()
{
return $this->quizUnits;
}
/**
* @param QuizUnit[] $quizUnits
* @return $this
*/
public function setQuizUnits($quizUnits)
{
$this->quizUnits = $quizUnits;
return $this;
}
/**
* @param QuizUnit $quizUnit
*
* @return $this
*/
public function addQuizUnit(QuizUnit $quizUnit)
{
$quizUnit->setQuizSession($this);
$this->quizUnits->add($quizUnit);
return $this;
}
public function getEndTime()
{
if ($this->getDeadline() !== null) {
return $this->getDeadline();
}
$endTime = clone $this->startTime;
return $endTime->modify(sprintf('+%d minutes', $this->getDuration()));
}
/**
* @param int $isEnabled
*/
public function setIsEnabled(int $isEnabled): void
{
$this->isEnabled = $isEnabled;
}
/**
* @return int
*/
public function getIsEnabled(): int
{
return $this->isEnabled;
}
/**
* @return DateTime|null
*/
public function getDeadline(): ?DateTime
{
return $this->deadline;
}
/**
* @param DateTime|null $deadline
*/
public function setDeadline(?DateTime $deadline = null): void
{
$this->deadline = $deadline;
}
/**
* @return bool|null
*/
public function isDurationIgnored(): ?bool
{
return $this->durationIgnored;
}
/**
* @param bool $durationIgnored
* @return void
*/
public function setDurationIgnored(bool $durationIgnored): void
{
$this->durationIgnored = $durationIgnored;
}
/**
* @return int|null
*/
public function getDuration(): ?int
{
return $this->duration;
}
/**
* @param int|null $duration
* @return void
*/
public function setDuration(?int $duration): void
{
$this->duration = $duration;
}
/**
* @return bool|null
*/
public function isHintsAvailable(): ?bool
{
return $this->hintsAvailable;
}
/**
* @param bool $hintsAvailable
* @return void
*/
public function setHintsAvailable(bool $hintsAvailable): void
{
$this->hintsAvailable = $hintsAvailable;
}
/**
* @return bool
*/
public function areResultsAvailableBeforeDeadline(): bool
{
return (bool)$this->resultsAvailableBeforeDeadline;
}
/**
* @param bool|null $resultsAvailableBeforeDeadline
* @return void
*/
public function setResultsAvailableBeforeDeadline(?bool $resultsAvailableBeforeDeadline): void
{
$this->resultsAvailableBeforeDeadline = $resultsAvailableBeforeDeadline;
}
/**
* @return string|null
*/
public function getName(): ?string
{
return $this->name;
}
/**
* @param string|null $name
* @return void
*/
public function setName(?string $name): void
{
$this->name = $name;
}
public function isHomework(): bool
{
return (bool)$this->deadline;
}
public function getType(): string
{
return $this->type;
}
public function isSelfStudyExamQuiz(): bool
{
return $this->type === 'self_study_exam';
}
public function isSelfStudyTopicQuiz(): bool
{
return $this->type === 'self_study_topic';
}
public function isSelfStudyTypicalProblemQuiz(): bool
{
return $this->type === 'self_study_typical_exam_problem';
}
public function isSelfStudyQuiz(): bool
{
return $this->isSelfStudyExamQuiz() || $this->isSelfStudyTopicQuiz() || $this->isSelfStudyTypicalProblemQuiz();
}
public function setTypeToSelfStudyExamQuiz(): void
{
$this->type = 'self_study_exam';
}
public function setTypeToSelfStudyTopicQuiz(): void
{
$this->type = 'self_study_topic';
}
public function setTypeToSelfStudyTypicalProblemQuiz(): void
{
$this->type = 'self_study_typical_problem';
}
public function setType(?string $type): void
{
$this->type = $type;
}
public function getSelfStudyTopic(): ?SelfStudyTopic
{
return $this->selfStudyTopic;
}
public function setSelfStudyTopic(?SelfStudyTopic $selfStudyTopic): void
{
$this->selfStudyTopic = $selfStudyTopic;
}
public function getSelfStudyTypicalExamProblem(): ?SelfStudyTypicalExamProblem
{
return $this->selfStudyTypicalExamProblem;
}
public function setSelfStudyTypicalExamProblem(?SelfStudyTypicalExamProblem $selfStudyTypicalExamProblem): void
{
$this->selfStudyTypicalExamProblem = $selfStudyTypicalExamProblem;
}
public function getSelfStudyExam(): ?SelfStudyExamQuiz
{
return $this->selfStudyExam;
}
public function setSelfStudyExam(?SelfStudyExamQuiz $selfStudyExam): void
{
$this->selfStudyExam = $selfStudyExam;
}
/**
* @throws Exception
*/
public function jsonSerialize(): mixed
{
return [
"duration" => $this->getDuration(),
"id" => $this->getId(),
"name" => $this->getName(),
"startTime" => $this->getStartTime(),
'deadline' => $this->getDeadline(),
'isHomework' => $this->isHomework(),
'secondsUntilDeadline' => $this->getSecondsUntilDeadline(),
'durationIgnored' => $this->isDurationIgnored()
];
}
public function setISBN(?string $isbn = null): void
{
$this->isbn = $isbn;
}
public function getISBN(): ?string
{
return $this->isbn;
}
public function getUpdatedAt(): DateTime
{
return $this->updatedAt;
}
public function setUpdatedAt(DateTime $updatedAt): void
{
$this->updatedAt = $updatedAt;
}
public function getUpdatedBy(): User
{
return $this->updatedBy;
}
public function setUpdatedBy(User $updatedBy): void
{
$this->updatedBy = $updatedBy;
}
public function getDescription(): string
{
return $this->description;
}
public function setDescription(string $description): void
{
$this->description = $description;
}
public function getResultViewOpenAt(): ?DateTime
{
return $this->resultViewOpenAt;
}
public function setResultViewOpenAt(?DateTime $resultViewOpenAt): void
{
$this->resultViewOpenAt = $resultViewOpenAt;
}
public function hasExtraTeachers(): ?bool
{
return $this->extraTeachers;
}
public function setExtraTeachers(?bool $extraTeachers): void
{
$this->extraTeachers = $extraTeachers;
}
public function hasDeactivatedProblems(): ?bool
{
return $this->deactivatedProblems;
}
public function setDeactivatedProblems(?bool $deactivatedProblems): void
{
$this->deactivatedProblems = $deactivatedProblems;
}
public function isArchived(): ?bool
{
return $this->isArchived;
}
public function setIsArchived(?bool $isArchived): void
{
$this->isArchived = $isArchived;
}
public function isSharedQuiz(): ?bool
{
return $this->isSharedQuiz;
}
public function setIsSharedQuiz(bool $isSharedQuiz): void
{
$this->isSharedQuiz = $isSharedQuiz;
}
public function getIsPinned(): ?bool
{
return $this->isPinned;
}
public function setIsPinned(?bool $isPinned): void
{
$this->isPinned = $isPinned;
}
public function getNameOrDefaultToQuizName(): ?string
{
return trim($this->getName() ?? '') === '' ? $this->getQuiz()->getName() : $this->getName();
}
/**
* @return bool
*/
public function getCanPause(): bool
{
return $this->canPause;
}
/**
* @return bool
*/
public function canPause(): bool
{
return $this->canPause;
}
/**
* @param bool $canPause
*/
public function setCanPause(?bool $canPause): void
{
$this->canPause = $canPause;
}
/**
* @return int
* @throws Exception
*/
public function getSecondsUntilDeadline():int
{
if($this->getDeadline() === null){
return 0;
}
$now = new DateTime('now', new DateTimeZone('Europe/Copenhagen'));
$interval = $now->diff($this->getDeadline());
$seconds = ($interval->days * 24 * 60 * 60) + ($interval->h * 60 * 60) + ($interval->i * 60) + $interval->s;
if($interval->invert){
return 0;
}
return $seconds;
}
}