more derails on survey-details;
publisher list
This commit is contained in:
@ -1,5 +1,5 @@
|
|||||||
import axiosInstance from '../../src/axiosSecure';
|
import axiosInstance from '../../src/axiosSecure';
|
||||||
import { useEffect, useState } from "react";
|
import { use, useEffect, useState } from "react";
|
||||||
import { toast } from "react-hot-toast";
|
import { toast } from "react-hot-toast";
|
||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import Link from "next/link";
|
import Link from "next/link";
|
||||||
@ -55,6 +55,8 @@ const SurveyForm: React.FC<SurveyFormProps> = ({ existingItem }) => {
|
|||||||
|
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
const [editMode, setEditMode] = useState(existingItem ? true : false);
|
const [editMode, setEditMode] = useState(existingItem ? true : false);
|
||||||
|
const [pubs, setPubs] = useState([]);
|
||||||
|
|
||||||
|
|
||||||
const [item, setItem] = useState(existingItem || {
|
const [item, setItem] = useState(existingItem || {
|
||||||
...existingItem,
|
...existingItem,
|
||||||
@ -72,6 +74,12 @@ const SurveyForm: React.FC<SurveyFormProps> = ({ existingItem }) => {
|
|||||||
setItem(transformedItem);
|
setItem(transformedItem);
|
||||||
}, [existingItem]);
|
}, [existingItem]);
|
||||||
|
|
||||||
|
useEffect(async () => {
|
||||||
|
const pubs = await axiosInstance.get("/api/data/publishers?select=id,firstName,lastName,email");
|
||||||
|
setPubs(pubs.data);
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
const handleChange = ({ target }) => {
|
const handleChange = ({ target }) => {
|
||||||
setItem({ ...item, [target.name]: target.value });
|
setItem({ ...item, [target.name]: target.value });
|
||||||
@ -96,7 +104,6 @@ const SurveyForm: React.FC<SurveyFormProps> = ({ existingItem }) => {
|
|||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
//get all publisherIds and create a message for each
|
//get all publisherIds and create a message for each
|
||||||
const pubs = await axiosInstance.get("/api/data/publishers");
|
|
||||||
const messages = pubs.data.map(pub => {
|
const messages = pubs.data.map(pub => {
|
||||||
return {
|
return {
|
||||||
publisherId: pub.id,
|
publisherId: pub.id,
|
||||||
@ -154,6 +161,34 @@ const SurveyForm: React.FC<SurveyFormProps> = ({ existingItem }) => {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
const getNamesByIds = (ids) => {
|
||||||
|
return ids
|
||||||
|
.map((id) => {
|
||||||
|
const pub = pubs.find((p) => p.id === id);
|
||||||
|
return pub ? `${pub.firstName} ${pub.lastName}` : null;
|
||||||
|
})
|
||||||
|
.filter((name) => name !== null)
|
||||||
|
.join(", ");
|
||||||
|
};
|
||||||
|
|
||||||
|
const getIdsForAnswer = (answer) => {
|
||||||
|
return item.messages
|
||||||
|
.filter((message) => message.answer === answer)
|
||||||
|
.map((message) => message.publisherId);
|
||||||
|
};
|
||||||
|
|
||||||
|
const getIdsForAnswered = () => {
|
||||||
|
return item.messages
|
||||||
|
.filter((message) => message.answer)
|
||||||
|
.map((message) => message.publisherId);
|
||||||
|
};
|
||||||
|
|
||||||
|
const getIdsForUnanswered = () => {
|
||||||
|
return item.messages
|
||||||
|
.filter((message) => !message.answer)
|
||||||
|
.map((message) => message.publisherId);
|
||||||
|
};
|
||||||
return (
|
return (
|
||||||
<div className="w-full max-w-md mx-auto" >
|
<div className="w-full max-w-md mx-auto" >
|
||||||
< form className="bg-white dark:bg-gray-800 shadow-md rounded px-8 pt-6 pb-8 mb-4" onSubmit={handleSubmit} >
|
< form className="bg-white dark:bg-gray-800 shadow-md rounded px-8 pt-6 pb-8 mb-4" onSubmit={handleSubmit} >
|
||||||
@ -186,29 +221,55 @@ const SurveyForm: React.FC<SurveyFormProps> = ({ existingItem }) => {
|
|||||||
</div>
|
</div>
|
||||||
{/* show count of each answer and the total answered/unanswered messages */}
|
{/* show count of each answer and the total answered/unanswered messages */}
|
||||||
{item?.answersCount?.length > 0 && (
|
{item?.answersCount?.length > 0 && (
|
||||||
<div className="mb-4">
|
<div>
|
||||||
<h3 className="text-lg font-semibold mb-2">Отговори:</h3>
|
{item?.answersCount?.length > 0 && (
|
||||||
{item.answersCount.map((answer, index) => (
|
<div className="mb-4">
|
||||||
<div key={index} className="mb-2">
|
<h3 className="text-lg font-semibold mb-2">Отговори:</h3>
|
||||||
<label className="block text-gray-700 text-sm font-bold mb-2" htmlFor={`answer-${index}`}>
|
{item.answersCount.map((answer, index) => {
|
||||||
{answer}
|
const currentCount = item.messages ? item.messages.filter((message) => message.answer === answer).length : 0;
|
||||||
</label>
|
const totalCount = item.messages ? item.messages.length : 0;
|
||||||
<p className="text-gray-700">
|
const percentage = totalCount > 0 ? (currentCount / totalCount) * 100 : 0;
|
||||||
{item.messages ? item.messages.filter((message) => message.answer === answer).length : 0}
|
const ids = getIdsForAnswer(answer);
|
||||||
</p>
|
const names = getNamesByIds(ids);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div key={index} className="mb-4">
|
||||||
|
<label className="block text-gray-700 text-sm font-bold mb-2" htmlFor={`answer-${index}`}>
|
||||||
|
{answer}
|
||||||
|
</label>
|
||||||
|
<div className="relative h-6 w-full bg-gray-200 rounded" title={names}>
|
||||||
|
<div className="absolute h-full bg-blue-600 rounded" style={{ width: `${percentage}%` }}></div>
|
||||||
|
<div className="absolute inset-0 flex items-center justify-center text-white font-bold">
|
||||||
|
{currentCount} ({percentage.toFixed(1)}%)
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
})}
|
||||||
|
<div className="mb-4">
|
||||||
|
<label className="block text-gray-700 text-sm font-bold mb-2">Общо отговорили</label>
|
||||||
|
<div className="relative h-6 w-full bg-gray-200 rounded" title={getNamesByIds(getIdsForAnswered())}>
|
||||||
|
<div className="absolute h-full bg-green-600 rounded" style={{ width: `${item.messages ? (item.messages.filter((message) => message.answer).length / item.messages.length) * 100 : 0}%` }}></div>
|
||||||
|
<div className="absolute inset-0 flex items-center justify-center text-white font-bold">
|
||||||
|
{item.messages ? item.messages.filter((message) => message.answer).length : 0}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className="mb-4">
|
||||||
|
<label className="block text-gray-700 text-sm font-bold mb-2">Общо неотговорили</label>
|
||||||
|
<div className="relative h-6 w-full bg-gray-200 rounded" title={getNamesByIds(getIdsForUnanswered())}>
|
||||||
|
<div className="absolute h-full bg-red-600 rounded" style={{ width: `${item.messages ? (item.messages.filter((message) => !message.answer).length / item.messages.length) * 100 : 0}%` }}></div>
|
||||||
|
<div className="absolute inset-0 flex items-center justify-center text-white font-bold">
|
||||||
|
{item.messages ? item.messages.filter((message) => !message.answer).length : 0}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
))}
|
)}
|
||||||
<div className="mb-2">
|
|
||||||
<label className="block text-gray-700 text-sm font-bold mb-2">Общо отговорили</label>
|
|
||||||
<p className="text-gray-700">{item.messages ? item.messages.filter((message) => message.answer).length : 0}</p>
|
|
||||||
</div>
|
|
||||||
<div className="mb-2">
|
|
||||||
<label className="block text-gray-700 text-sm font-bold mb-2">Общо неотговорили</label>
|
|
||||||
<p className="text-gray-700">{item.messages ? item.messages.filter((message) => !message.answer).length : 0}</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
|
|
||||||
<div className="flex items-center justify-between">
|
<div className="flex items-center justify-between">
|
||||||
{editMode && (<>
|
{editMode && (<>
|
||||||
<button className="button btn-outline bg-red-500 hover:bg-red-700 focus:outline-none focus:shadow-outline" type="button" onClick={handleDelete}>
|
<button className="button btn-outline bg-red-500 hover:bg-red-700 focus:outline-none focus:shadow-outline" type="button" onClick={handleDelete}>
|
||||||
|
Reference in New Issue
Block a user