EventosDetalle.js 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937
  1. import React, { useEffect, useState } from "react";
  2. import {
  3. Col,
  4. Row,
  5. Form,
  6. Input,
  7. Modal,
  8. Table,
  9. Select,
  10. Button,
  11. Upload,
  12. Divider,
  13. Checkbox,
  14. DatePicker,
  15. message,
  16. Tooltip,
  17. } from "antd";
  18. import {
  19. SaveOutlined,
  20. UploadOutlined,
  21. ArrowLeftOutlined,
  22. PlusCircleOutlined,
  23. MinusCircleOutlined,
  24. } from "@ant-design/icons";
  25. import "moment/locale/es-mx";
  26. import moment from "moment";
  27. import locale from "antd/es/date-picker/locale/es_ES";
  28. import { useHistory } from "react-router-dom";
  29. import { push, ref as refDatabase } from "firebase/database";
  30. import {
  31. addDoc,
  32. collection,
  33. doc,
  34. getDoc,
  35. updateDoc,
  36. onSnapshot,
  37. query as firebseQuery,
  38. getDocs,
  39. where,
  40. } from "firebase/firestore";
  41. import {
  42. ref as refStorage,
  43. uploadBytes,
  44. deleteObject,
  45. getStorage,
  46. getDownloadURL,
  47. } from "firebase/storage";
  48. import { useQuery } from "../../../hooks";
  49. import { ViewLoading } from "../../../components";
  50. import { DefaultLayout } from "../../../components/layouts";
  51. import { firestore, storage, database } from "../../../services/firebase";
  52. const EventosDetalle = () => {
  53. const urlweb = "/administracion/eventos";
  54. const query = useQuery();
  55. const history = useHistory();
  56. const { TextArea, Search } = Input;
  57. const { Option } = Select;
  58. const id = query.get("id");
  59. const editando = !!id;
  60. const [form] = Form.useForm();
  61. const [evento, setEvento] = useState([]);
  62. const [cargandoEvento, setCargandoEvento] = useState(true);
  63. const [guadandoCargando, setGuardandoCargando] = useState(false);
  64. const [sinFechaFin, setSinFechaFin] = useState(false);
  65. const [visible, setVisible] = useState(false);
  66. const [cargandoGrupos, setCargandoGrupos] = useState(true);
  67. const [grupos, setGrupos] = useState([]);
  68. const [filteredResults, setFilteredResults] = useState([]);
  69. const [searchInput, setSearchInput] = useState("");
  70. const [selectedGrupos, setSelectedGrupos] = useState([]);
  71. const [selectedFile, setSelectedFile] = useState(null);
  72. const [selectedFileList, setSelectedFileList] = useState([]);
  73. const [previaImg, setPreviaImg] = useState(null);
  74. const [redes, setRedes] = useState([]);
  75. const defaultText = (prop) =>
  76. prop || <span style={{ color: "#c7c3c3" }}>---</span>;
  77. const multipleButtonData = [
  78. {
  79. text: "Volver",
  80. to: () => history.goBack(),
  81. icon: <ArrowLeftOutlined />,
  82. props: { disabled: false, type: "primary" },
  83. },
  84. ];
  85. const columns = [
  86. {
  87. title: "Nombre",
  88. dataIndex: "nombre",
  89. key: "nombre",
  90. render: defaultText,
  91. },
  92. {
  93. title: "Ciudad",
  94. dataIndex: "ciudad",
  95. key: "ciudad",
  96. render: defaultText,
  97. },
  98. {
  99. title: "Creado",
  100. dataIndex: "timestamp",
  101. key: "timestamp",
  102. render: (_, item) =>
  103. moment(item?.timestamp?.toDate()).format("DD-MM-YYYY"),
  104. },
  105. ];
  106. const redesSociales = [
  107. "Facebook",
  108. "Twitter",
  109. "Instagram",
  110. "Whatsapp",
  111. "YouTube",
  112. "TikTok",
  113. "Otro",
  114. ];
  115. const acciones = [
  116. { id: 0, value: "Ver", label: "Ver", icon: "👁" },
  117. { id: 1, value: "Me gusta", label: "Me gusta", icon: "👍" },
  118. { id: 2, value: "Compartir", label: "Compartir", icon: "🔄" },
  119. ];
  120. const rowSelection = {
  121. onChange: (selectedRowKeys, _) => {
  122. setSelectedGrupos(selectedRowKeys);
  123. },
  124. };
  125. const obtenerUsuariosGrupo = async () => {
  126. try {
  127. const q = firebseQuery(
  128. collection(firestore, "usuarios"),
  129. where("grupos", "array-contains-any", selectedGrupos),
  130. );
  131. const querySnapshot = await getDocs(q);
  132. const docs = [];
  133. querySnapshot.forEach((doc) => {
  134. const data = doc.data();
  135. if (data?.estatus) {
  136. docs.push({
  137. grupos: data?.grupos,
  138. facebook: data?.facebook,
  139. twitter: data?.twitter,
  140. instagram: data?.instagram,
  141. telefono: data?.telefono,
  142. nombre: data?.nombre,
  143. uid: data?.uid,
  144. id: doc.id,
  145. facebookVerificado: data?.facebookVerificado,
  146. instagramVerificado: data?.instagramVerificado,
  147. twitterVerificado: data?.twitterVerificado,
  148. });
  149. }
  150. });
  151. return docs;
  152. } catch (error) {
  153. console.log("error al obtener grupos: ", error);
  154. }
  155. };
  156. const normFile = (e) => {
  157. if (Array.isArray(e)) {
  158. return e;
  159. }
  160. return e && e.fileList;
  161. };
  162. const dummyRequest = ({ onSuccess }) => {
  163. setTimeout(() => {
  164. onSuccess("ok");
  165. }, 0);
  166. };
  167. const onChangeFile = (info) => {
  168. let src = URL.createObjectURL(info.file.originFileObj);
  169. setPreviaImg(src);
  170. switch (info.file.status) {
  171. case "uploading":
  172. setSelectedFileList([info.file]);
  173. break;
  174. case "done":
  175. setSelectedFile(info.file);
  176. setSelectedFileList([info.file]);
  177. break;
  178. default:
  179. setSelectedFile(null);
  180. setSelectedFileList([]);
  181. }
  182. };
  183. const eliminarImagen = async (fileRoute) => {
  184. const storage = getStorage();
  185. const desertRef = refStorage(storage, fileRoute);
  186. deleteObject(desertRef)
  187. .then((e) => {})
  188. .catch((error) => {
  189. console.log(error);
  190. });
  191. };
  192. const onSearch = (searchValue) => {
  193. setSearchInput(searchValue);
  194. if (searchValue !== "") {
  195. const filteredData = grupos.filter((item) => {
  196. return Object.values(item)
  197. .join("")
  198. .toLowerCase()
  199. .includes(searchValue.toLowerCase());
  200. });
  201. setFilteredResults(filteredData);
  202. } else {
  203. setFilteredResults(grupos);
  204. }
  205. };
  206. const onFinish = async (values) => {
  207. try {
  208. const {
  209. accion,
  210. ciudad,
  211. descripcion,
  212. fechaFinal,
  213. fechaInicio,
  214. nombre,
  215. redSocial,
  216. url,
  217. } = values;
  218. setGuardandoCargando(true);
  219. let file = selectedFile ? selectedFile.originFileObj : null;
  220. if (!editando && !file) {
  221. Modal.warning({
  222. title: "Atención",
  223. content: "Debes subir una imagen del evento.",
  224. style: { marginTop: "20vh" },
  225. });
  226. }
  227. let rutaFoto = evento?.fotoEvento;
  228. let pathFirebase = evento?.pathFirebase;
  229. if (file) {
  230. if (editando) {
  231. await eliminarImagen(evento?.fotoEvento);
  232. }
  233. const postListRef = refDatabase(database, "fotosEventos");
  234. const newPostRef = push(postListRef);
  235. rutaFoto = `fotosEventos/${newPostRef?.key}`;
  236. const fotoRefStorage = refStorage(storage, rutaFoto);
  237. try {
  238. let res = await uploadBytes(fotoRefStorage, file);
  239. pathFirebase = await getDownloadURL(res?.ref);
  240. } catch (error) {
  241. console.log("Error en el uploadbytes: ", error);
  242. }
  243. }
  244. const docsUsuarios = await obtenerUsuariosGrupo();
  245. let resultado = { ...evento?.resultado };
  246. let usuarios = [];
  247. for (let u = 0; u < docsUsuarios?.length; u++) {
  248. if (resultado[docsUsuarios[u]?.uid] === undefined) {
  249. resultado[docsUsuarios[u]?.uid] = [];
  250. }
  251. if (resultado[docsUsuarios[u]?.uid]?.length < 1) {
  252. resultado = {
  253. ...resultado,
  254. [docsUsuarios[u].uid]: [],
  255. };
  256. }
  257. usuarios.push({
  258. id: docsUsuarios[u]?.id,
  259. uid: docsUsuarios[u]?.uid,
  260. grupos: docsUsuarios[u]?.grupos,
  261. nombre: docsUsuarios[u]?.nombre,
  262. twitter: docsUsuarios[u]?.twitter,
  263. telefono: docsUsuarios[u]?.telefono,
  264. facebook: docsUsuarios[u]?.facebook,
  265. instagram: docsUsuarios[u]?.instagram,
  266. facebookVerificado: Boolean(docsUsuarios[u]?.facebookVerificado),
  267. instagramVerificado: Boolean(docsUsuarios[u]?.instagramVerificado),
  268. twitterVerificado: Boolean(docsUsuarios[u]?.twitterVerificado),
  269. });
  270. }
  271. let body = {
  272. accion: accion || [],
  273. ciudad: ciudad || "",
  274. descripcion: descripcion || "",
  275. fechaFinal: fechaFinal?.toString() || "",
  276. fechaInicio: fechaInicio?.toString(),
  277. sinFechaFin: sinFechaFin,
  278. nombre: nombre || "",
  279. redSocial: redSocial || "",
  280. url: url || "",
  281. grupos: selectedGrupos,
  282. fotoEvento: rutaFoto,
  283. pathFirebase: pathFirebase,
  284. timestamp: editando ? evento?.timestamp : new Date(),
  285. estatus: editando ? evento?.estatus : true,
  286. usuarios: usuarios,
  287. redes: redes,
  288. resultado: resultado,
  289. sincronizado: null,
  290. };
  291. const tag = makeid(8);
  292. let grupoEventoRef = null;
  293. //Crear grupo de eventos
  294. if (redes.length > 0) {
  295. let grupoEvento = {
  296. accion: accion,
  297. ciudad: ciudad,
  298. descripcion: descripcion,
  299. fechaFinal: fechaFinal?.toString() || "",
  300. fechaInicio: fechaInicio?.toString(),
  301. sinFechaFin: sinFechaFin,
  302. nombre: nombre || "",
  303. grupos: selectedGrupos,
  304. fotoEvento: rutaFoto,
  305. pathFirebase: pathFirebase,
  306. timestamp: editando ? evento?.timestamp : new Date(),
  307. estatus: editando ? evento?.estatus : true,
  308. tag: tag,
  309. redes: redes,
  310. usuarios: usuarios,
  311. resultado: resultado,
  312. };
  313. grupoEventoRef = await addDoc(
  314. collection(firestore, "gruposEvento"),
  315. grupoEvento,
  316. );
  317. }
  318. if (editando) {
  319. await updateDoc(doc(firestore, "eventos", id), body);
  320. return;
  321. }
  322. for (let i = 0; i < redes?.length; i++) {
  323. body = {
  324. ...body,
  325. redSocial: redes[i]?.redSocial,
  326. url: redes[i]?.url,
  327. };
  328. if (!editando) {
  329. body["tag"] = tag;
  330. }
  331. await addDoc(collection(firestore, "eventos"), body);
  332. }
  333. Modal.success({
  334. title: "Éxito",
  335. content: "Evento guardado correctamente",
  336. });
  337. history.push(`${urlweb}/detalleGrupo?id=${grupoEventoRef.id}&tag=${tag}`);
  338. } catch (error) {
  339. Modal.warning({
  340. title: "Atención",
  341. content: "Hubo un problema al guardar, intentalo de nuevo.",
  342. });
  343. console.log("Error al guardar evento: ", error);
  344. } finally {
  345. setGuardandoCargando(false);
  346. }
  347. };
  348. const onFinishFailed = () => {
  349. Modal.warning({
  350. title: "Atención",
  351. content: "Por favor revise los datos.",
  352. style: { marginTop: "20vh" },
  353. });
  354. };
  355. function makeid(length) {
  356. let result = "";
  357. const characters =
  358. "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
  359. const charactersLength = characters.length;
  360. for (var i = 0; i < length; i++) {
  361. result += characters.charAt(Math.floor(Math.random() * charactersLength));
  362. }
  363. return result;
  364. }
  365. const agregarRedSocial = () => {
  366. const key = makeid(6);
  367. const datos = [...redes];
  368. const url = form.getFieldValue("url");
  369. const red = form.getFieldValue("redSocial");
  370. if (!url) {
  371. message.warning({
  372. content: "Ingresa una URL",
  373. });
  374. return;
  375. }
  376. if (!red) {
  377. message.warning({
  378. content: "Selecciona una red social",
  379. });
  380. return;
  381. }
  382. let existe = false;
  383. for (let i = 0; i < redes.length; i++) {
  384. if (redes[i]?.redSocial === red) existe = true;
  385. break;
  386. }
  387. if (existe) {
  388. message.warning({
  389. content: "Esta red social ya existe, elige otra diferente.",
  390. });
  391. return;
  392. }
  393. datos.push({
  394. key: key,
  395. url: url,
  396. redSocial: red,
  397. });
  398. setRedes(datos);
  399. form.setFieldsValue({
  400. url: null,
  401. redSocial: null,
  402. });
  403. };
  404. const quitarRedSocial = (key) => {
  405. let data = [...redes];
  406. for (let i = 0; i < data?.length; i++) {
  407. if (redes[i].key === key) {
  408. data.splice(i, 1);
  409. break;
  410. }
  411. }
  412. setRedes(data);
  413. };
  414. const leerLink = (evento) => {
  415. let link = evento?.target?.value;
  416. const facebook =
  417. /https?:\/\/(www\.)?facebook\.com\/[a-zA-Z0-9.-]+\/?/ ||
  418. /https?:\/\/(www\.)?fb\.com\/[a-zA-Z0-9.-]+\/?/;
  419. const x = /https?:\/\/(www\.)?x\.com\/[a-zA-Z0-9.-]+\/?/;
  420. const instagram = /https?:\/\/(www\.)?instagram\.com\/[a-zA-Z0-9.-]+\/?/;
  421. const whatsapp = /https?:\/\/(www\.)?wa\.me\/[a-zA-Z0-9.-]+\/?/;
  422. const youtube = /https?:\/\/(www\.)?youtube\.com\/[a-zA-Z0-9.-]+\/?/g;
  423. const ytShort = /https?:\/\/(www\.)?youtu\.be\/[a-zA-Z0-9.-]+\/?/g;
  424. const tiktok = /https?:\/\/(?:www\.)?tiktok\.com\/.*?/g;
  425. if (facebook.test(link)) {
  426. form.setFieldsValue({ redSocial: "Facebook" });
  427. } else if (x.test(link)) {
  428. form.setFieldsValue({ redSocial: "Twitter" });
  429. } else if (instagram.test(link)) {
  430. form.setFieldsValue({ redSocial: "Instagram" });
  431. } else if (whatsapp.test(link)) {
  432. form.setFieldsValue({ redSocial: "Whatsapp" });
  433. } else if (youtube.test(link) || ytShort.test(link)) {
  434. form.setFieldsValue({ redSocial: "YouTube" });
  435. } else if (tiktok.test(link)) {
  436. form.setFieldsValue({ redSocial: "TikTok" });
  437. } else {
  438. form.setFieldsValue({ redSocial: "Otro" });
  439. }
  440. };
  441. // Grupos
  442. useEffect(() => {
  443. try {
  444. onSnapshot(collection(firestore, "grupos"), (querySnapshot) => {
  445. const docs = [];
  446. querySnapshot.forEach((doc) => {
  447. if (doc.data()?.estatus) {
  448. docs.push({ ...doc.data(), id: doc.id });
  449. }
  450. });
  451. setGrupos(docs);
  452. });
  453. } catch (error) {
  454. console.log("error al cargar grupos de firebase: ", error);
  455. } finally {
  456. setCargandoGrupos(false);
  457. }
  458. }, []);
  459. // Limpiar imagen
  460. useEffect(() => {
  461. if (!selectedFile) {
  462. setPreviaImg(null);
  463. }
  464. }, [selectedFile]);
  465. // Obtener detalles del evento.
  466. useEffect(() => {
  467. let mounted = true;
  468. if (mounted && editando) {
  469. try {
  470. setTimeout(async () => {
  471. const docRef = doc(firestore, "eventos", id);
  472. const docSnap = await getDoc(docRef);
  473. setEvento(docSnap.data());
  474. }, 0);
  475. } catch (error) {
  476. console.log("error al obtener evento: ", error);
  477. } finally {
  478. setCargandoEvento(false);
  479. }
  480. }
  481. return () => (mounted = false);
  482. }, [editando, id]);
  483. useEffect(() => {
  484. let mounted = true;
  485. if (mounted && evento && editando) {
  486. setPreviaImg(evento?.pathFirebase);
  487. setSinFechaFin(evento?.sinFechaFin);
  488. setSelectedGrupos(evento?.grupos);
  489. form.setFieldsValue({
  490. ...evento,
  491. fechaFinal: moment(evento?.fechaFinal),
  492. fechaInicio: moment(evento?.fechaInicio),
  493. });
  494. }
  495. return () => (mounted = false);
  496. }, [editando, evento, form]);
  497. if (cargandoEvento && editando) return <ViewLoading />;
  498. return (
  499. <DefaultLayout multipleButtonData={multipleButtonData}>
  500. <Modal
  501. title="Agregar grupos"
  502. centered
  503. open={visible}
  504. onOk={() => setVisible(false)}
  505. onCancel={() => setVisible(false)}
  506. okText="Guardar"
  507. width={800}
  508. >
  509. <Search
  510. placeholder="Buscar..."
  511. enterButton="Buscar"
  512. size="large"
  513. style={{ width: "100%" }}
  514. onSearch={onSearch}
  515. />
  516. <Divider />
  517. <Table
  518. dataSource={searchInput?.length > 1 ? filteredResults : grupos}
  519. rowKey="id"
  520. pagination={{
  521. pageSize: 5,
  522. }}
  523. rowSelection={{
  524. type: "checkbox",
  525. selectedRowKeys: selectedGrupos,
  526. ...rowSelection,
  527. }}
  528. loading={cargandoGrupos}
  529. columns={columns}
  530. size="small"
  531. scroll={{ x: 700 }}
  532. />
  533. </Modal>
  534. <Form
  535. name="form"
  536. form={form}
  537. autoComplete="off"
  538. layout="vertical"
  539. onFinish={onFinish}
  540. onFinishFailed={onFinishFailed}
  541. >
  542. {/* Imagen - Nombre - Ciudad - Descripción - Url - Red social */}
  543. <Row gutter={10}>
  544. {/* Columna 1 */}
  545. <Col
  546. className="gutter-row"
  547. xs={{ span: 24 }}
  548. sm={{ span: 24 }}
  549. md={{ span: 8 }}
  550. lg={{ span: 8 }}
  551. >
  552. <Row
  553. gutter={10}
  554. style={{
  555. display: "flex",
  556. flexDirection: "row",
  557. height: "100%",
  558. }}
  559. >
  560. <Col span={24}>
  561. <Form.Item
  562. name="upload"
  563. label="Imagen del evento"
  564. valuePropName="fileList"
  565. rules={[
  566. { required: editando ? false : true, message: "Requerido" },
  567. ]}
  568. getValueFromEvent={normFile}
  569. extra={editando && evento ? evento?.fotoEvento : null}
  570. >
  571. <Upload
  572. accept="image/gif, image/jpeg, image/png"
  573. fileList={selectedFileList}
  574. customRequest={dummyRequest}
  575. onChange={onChangeFile}
  576. name="fotoEvento"
  577. multiple={false}
  578. maxCount={1}
  579. >
  580. <Button icon={<UploadOutlined />}>Elegir imagen</Button>
  581. </Upload>
  582. </Form.Item>
  583. </Col>
  584. <Col span={24}>
  585. {previaImg ? <img src={previaImg} width="100%" alt="" /> : null}
  586. </Col>
  587. <Col span={24} style={{ marginTop: 133 }}>
  588. <Button
  589. block
  590. type="dashed"
  591. icon={<PlusCircleOutlined />}
  592. onClick={() => setVisible(true)}
  593. >
  594. Agregar grupos ({selectedGrupos?.length})
  595. </Button>
  596. </Col>
  597. </Row>
  598. </Col>
  599. {/* Columna 2 */}
  600. <Col
  601. className="gutter-row"
  602. xs={{ span: 24 }}
  603. sm={{ span: 24 }}
  604. md={{ span: 16 }}
  605. lg={{ span: 16 }}
  606. >
  607. {/* Nombre evento - Ciuad */}
  608. <Row gutter={10}>
  609. <Col
  610. className="gutter-row"
  611. xs={{ span: 24 }}
  612. sm={{ span: 24 }}
  613. md={{ span: 12 }}
  614. lg={{ span: 12 }}
  615. >
  616. <Form.Item
  617. label="Nombre del evento"
  618. name="nombre"
  619. rules={[{ required: true, message: "Requerido" }]}
  620. >
  621. <Input />
  622. </Form.Item>
  623. </Col>
  624. <Col
  625. className="gutter-row"
  626. xs={{ span: 24 }}
  627. sm={{ span: 24 }}
  628. md={{ span: 12 }}
  629. lg={{ span: 12 }}
  630. >
  631. <Form.Item
  632. label="Ciudad"
  633. name="ciudad"
  634. rules={[{ required: true, message: "Requerido" }]}
  635. >
  636. <Input />
  637. </Form.Item>
  638. </Col>
  639. </Row>
  640. {/* Descripción */}
  641. <Row gutter={10}>
  642. <Col className="gutter-row" span={24}>
  643. <Form.Item
  644. label="Descripción"
  645. name="descripcion"
  646. rules={[{ required: true, message: "Requerido" }]}
  647. >
  648. <TextArea placeholder="Ingrese una descripción..." rows={4} />
  649. </Form.Item>
  650. </Col>
  651. </Row>
  652. </Col>
  653. </Row>
  654. {/* Fecha de inicio - Fecha fin - sin fecha - Accion */}
  655. <Row gutter={10} style={{ marginTop: 30 }}>
  656. <Col
  657. className="gutter-row"
  658. xs={{ span: 24 }}
  659. sm={{ span: 24 }}
  660. md={{ span: 6 }}
  661. lg={{ span: 6 }}
  662. >
  663. <Form.Item
  664. rules={[{ required: true, message: "Requerido" }]}
  665. label="Fecha de inicio"
  666. name="fechaInicio"
  667. >
  668. <DatePicker
  669. format="YYYY-MM-DD HH:mm"
  670. style={{ width: "100%" }}
  671. locale={locale}
  672. showTime={{
  673. defaultValue: moment("00:00", "HH:mm"),
  674. }}
  675. />
  676. </Form.Item>
  677. </Col>
  678. <Col
  679. className="gutter-row"
  680. xs={{ span: 24 }}
  681. sm={{ span: 24 }}
  682. md={{ span: 6 }}
  683. lg={{ span: 6 }}
  684. >
  685. <Form.Item
  686. rules={[{ required: !sinFechaFin, message: "Requerido" }]}
  687. label="Fecha de finalización"
  688. name="fechaFinal"
  689. >
  690. <DatePicker
  691. disabled={sinFechaFin}
  692. format="YYYY-MM-DD HH:mm"
  693. style={{ width: "100%" }}
  694. locale={locale}
  695. showTime={{
  696. defaultValue: moment("00:00", "HH:mm"),
  697. }}
  698. />
  699. </Form.Item>
  700. </Col>
  701. <Col
  702. className="gutter-row"
  703. xs={{ span: 24 }}
  704. sm={{ span: 24 }}
  705. md={{ span: 6 }}
  706. lg={{ span: 6 }}
  707. >
  708. <Form.Item label="&nbsp;">
  709. <Checkbox
  710. checked={sinFechaFin}
  711. onChange={(e) => setSinFechaFin(e.target.checked)}
  712. >
  713. Sin fecha de finalización
  714. </Checkbox>
  715. </Form.Item>
  716. </Col>
  717. <Col
  718. className="gutter-row"
  719. xs={{ span: 24 }}
  720. sm={{ span: 24 }}
  721. md={{ span: 6 }}
  722. lg={{ span: 6 }}
  723. >
  724. <Form.Item label="Acción" name="accion">
  725. <Select
  726. mode="multiple"
  727. style={{ width: "100%" }}
  728. placeholder="Selecciona una o más opciones"
  729. optionLabelProp="label"
  730. >
  731. {acciones?.map((item) => (
  732. <Option
  733. value={item?.value}
  734. label={item?.label}
  735. key={item?.id}
  736. >
  737. <div className="demo-option-label-item">
  738. <span role="img" aria-label={item?.label}>
  739. {item?.icon}
  740. </span>
  741. {item?.label}
  742. </div>
  743. </Option>
  744. ))}
  745. </Select>
  746. </Form.Item>
  747. </Col>
  748. </Row>
  749. {/* URL - Red Social - Agregar [+] */}
  750. <Row gutter={10}>
  751. <Col
  752. className="gutter-row"
  753. xs={{ span: 24 }}
  754. sm={{ span: 24 }}
  755. md={{ span: 12 }}
  756. lg={{ span: 12 }}
  757. >
  758. <Form.Item label="URL" name="url">
  759. <Input onChange={(v) => leerLink(v)} />
  760. </Form.Item>
  761. </Col>
  762. <Col
  763. className="gutter-row"
  764. xs={{ span: 24 }}
  765. sm={{ span: 24 }}
  766. md={{ span: editando ? 12 : 9 }}
  767. lg={{ span: editando ? 12 : 9 }}
  768. >
  769. <Form.Item label="Red social" name="redSocial">
  770. <Select style={{ width: "100%" }} placeholder="Selecciona">
  771. {redesSociales?.map((item) => (
  772. <Option key={item} value={item}>
  773. {item === "Twitter" ? "X" : item}
  774. </Option>
  775. ))}
  776. </Select>
  777. </Form.Item>
  778. </Col>
  779. {!editando && (
  780. <Col
  781. className="gutter-row"
  782. xs={{ span: 24 }}
  783. sm={{ span: 24 }}
  784. md={{ span: 3 }}
  785. lg={{ span: 3 }}
  786. >
  787. <Form.Item label="&nbsp;">
  788. <Button
  789. type="primary"
  790. icon={<PlusCircleOutlined />}
  791. block
  792. onClick={agregarRedSocial}
  793. />
  794. </Form.Item>
  795. </Col>
  796. )}
  797. </Row>
  798. {redes.map((item) => (
  799. <Row key={item.key} gutter={10}>
  800. <Col
  801. className="gutter-row"
  802. xs={{ span: 24 }}
  803. sm={{ span: 24 }}
  804. md={{ span: 12 }}
  805. lg={{ span: 12 }}
  806. >
  807. <Form.Item label="&nbsp;">
  808. <Input readOnly value={item?.url} />
  809. </Form.Item>
  810. </Col>
  811. <Col
  812. className="gutter-row"
  813. xs={{ span: 24 }}
  814. sm={{ span: 24 }}
  815. md={{ span: 9 }}
  816. lg={{ span: 9 }}
  817. >
  818. <Form.Item label="&nbsp;">
  819. <Input readOnly value={item?.redSocial} />
  820. </Form.Item>
  821. </Col>
  822. <Col
  823. className="gutter-row"
  824. xs={{ span: 24 }}
  825. sm={{ span: 24 }}
  826. md={{ span: 3 }}
  827. lg={{ span: 3 }}
  828. >
  829. <Form.Item label="&nbsp;">
  830. <Tooltip title="Remover">
  831. <Button
  832. type="danger"
  833. icon={<MinusCircleOutlined />}
  834. block
  835. onClick={() => quitarRedSocial(item?.key)}
  836. />
  837. </Tooltip>
  838. </Form.Item>
  839. </Col>
  840. </Row>
  841. ))}
  842. <Row gutter={10}>
  843. <Col
  844. xs={{ span: 24 }}
  845. sm={{ span: 24 }}
  846. md={{ span: 12 }}
  847. lg={{ span: 8 }}
  848. >
  849. <Button
  850. type="primary"
  851. htmlType="submit"
  852. icon={<SaveOutlined />}
  853. block
  854. size="large"
  855. loading={guadandoCargando}
  856. >
  857. Guardar
  858. </Button>
  859. </Col>
  860. </Row>
  861. </Form>
  862. </DefaultLayout>
  863. );
  864. };
  865. export default EventosDetalle;