BeritaAcara_A.js 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463
  1. import React, { useRef, Component } from 'react';
  2. import { useReactToPrint } from "react-to-print";
  3. import { Row, Col, Button, Popover, PopoverHeader, PopoverBody, } from "reactstrap";
  4. import Head from 'next/head'
  5. import SignatureCanvas from 'react-signature-canvas'
  6. import ComponentToPrint from "./SuratBA";
  7. import ReactToPrint, { PrintContextConsumer } from 'react-to-print';
  8. import { getOneLaporan, updateLaporan } from "@/actions/pelaporan";
  9. import DatePicker from "react-datepicker";
  10. import "react-datepicker/dist/react-datepicker.css";
  11. import id from 'date-fns/locale/id';
  12. import CopyToClipboard from "react-copy-to-clipboard";
  13. import { getAutoSave } from "@/actions/autosave";
  14. import ContentEditable from 'react-contenteditable'
  15. class BeritaAcara extends Component {
  16. constructor(props) {
  17. super(props);
  18. this.state = {
  19. isEditTempat: false,
  20. tempat: "[Mohon Diisi]",
  21. isEditTanggal: false,
  22. tanggal: "",
  23. setTanggal: false,
  24. isEditNamaPeserta: false,
  25. isEditTemuanLain: false,
  26. temuanLain: [],
  27. memberatkan: [],
  28. isEditKeberatan: false,
  29. isEditMeringankan: false,
  30. meringankan: [],
  31. sanksi: "[Mohon Diisi]",
  32. isEditSanksi: false,
  33. copied: false,
  34. setmeState: true,
  35. descPelanggaran: [],
  36. };
  37. this.updateValueRekomendasi = this.updateValueRekomendasi.bind(this)
  38. }
  39. static getInitialProps = async ({ query }) => {
  40. return { query };
  41. };
  42. componentDidMount = async () => {
  43. const { query, token, dataPelanggaran } = this.props;
  44. const { id } = query;
  45. const getDataSave = await getAutoSave({ id, laporan: true });
  46. const autosaveDataSuratBA = getDataSave.data?.PenetapanSanksi?.dataSuratBA;
  47. this.setState(autosaveDataSuratBA)
  48. };
  49. componentDidUpdate = (prevProps) => {
  50. const { dataPelanggaran } = this.state;
  51. if (prevProps.dataPelanggaran != this.state.dataPelanggaran) {
  52. // this.state.descPelanggaran = dataPelanggaran?.map((e) => ({ id: e._id, simpulan: "simpulan", rekomendasi: "rekomendasi" }))
  53. const descPelanggaran = {}
  54. dataPelanggaran?.forEach(e => {
  55. descPelanggaran[e._id] = {
  56. simpulan: 'simpulan',
  57. rekomendasi: 'rekomendasi'
  58. }
  59. });
  60. // this.setState({ descPelanggaran })
  61. }
  62. }
  63. updateValueSimpulan = (evt, id) => {
  64. this.setState((prevState) => ({
  65. ...prevState, descPelanggaran: {
  66. ...prevState.descPelanggaran, [id]: {
  67. ...prevState.descPelanggaran[id], simpulan: evt.target.value
  68. }
  69. }
  70. }), this.handleAutoSave)
  71. }
  72. updateValueRekomendasi = (evt, id) => {
  73. this.setState((prevState) => ({
  74. ...prevState, descPelanggaran: {
  75. ...prevState.descPelanggaran, [id]: {
  76. ...prevState.descPelanggaran[id], rekomendasi: evt.target.value
  77. }
  78. }
  79. }), this.handleAutoSave)
  80. }
  81. setDataSuratBA = () => {
  82. this.props.setDataSuratBA(this.state);
  83. }
  84. handleAutoSave = () => {
  85. this.props.handleAutoSave()
  86. }
  87. isEditTempat = () => {
  88. this.setState({
  89. isEditTempat: !this.state.isEditTempat,
  90. }, this.setDataSuratBA, this.handleAutoSave())
  91. }
  92. isEditTanggal = () => {
  93. this.setState({
  94. isEditTanggal: !this.state.isEditTanggal,
  95. }, this.setDataSuratBA, this.handleAutoSave())
  96. }
  97. isEditTemuanLain = () => {
  98. this.setState({
  99. isEditTemuanLain: !this.state.isEditTemuanLain,
  100. }, this.setDataSuratBA, this.handleAutoSave())
  101. }
  102. isEditKeberatan = () => {
  103. this.setState({
  104. isEditKeberatan: !this.state.isEditKeberatan,
  105. }, this.setDataSuratBA, this.handleAutoSave())
  106. }
  107. isEditMeringankan = () => {
  108. this.setState({
  109. isEditMeringankan: !this.state.isEditMeringankan,
  110. }, this.setDataSuratBA, this.handleAutoSave())
  111. }
  112. isEditSanksi = () => {
  113. this.setState({
  114. isEditSanksi: !this.state.isEditSanksi,
  115. }, this.setDataSuratBA, this.handleAutoSave())
  116. }
  117. updateValueTemuanLain = () => {
  118. const addTemuanLain = this.refs.inputTemuan.value
  119. this.state.temuanLain.push(addTemuanLain)
  120. this.setDataSuratBA(this.state)
  121. this.handleAutoSave()
  122. }
  123. updateValueMemringankan = () => {
  124. const addMeringankan = this.refs.inputMeringankan.value
  125. this.state.meringankan.push(addMeringankan)
  126. this.setDataSuratBA(this.state)
  127. this.handleAutoSave()
  128. }
  129. updateValueMemberatkan = () => {
  130. const addKeberatan = this.refs.inputMemberatkan.value
  131. this.state.memberatkan.push(addKeberatan)
  132. this.setDataSuratBA(this.state)
  133. this.handleAutoSave()
  134. }
  135. Copied = () => this.setState({
  136. copied: !this.state.copied
  137. })
  138. CloseCopied = () => {
  139. setTimeout(() => {
  140. this.setState({
  141. copied: !this.state.copied
  142. });
  143. }, 1000);
  144. }
  145. render() {
  146. const { dataLaporan, dataSuratBA, dataPelanggaran } = this.props
  147. const { descPelanggaran, tanggal, setTanggal } = this.state
  148. return (
  149. <div>
  150. <div className=' content-heading border-radius-login'>
  151. <span className="btn-radius">
  152. <ReactToPrint
  153. trigger={() => {
  154. return <span>
  155. <Button color className="btn-labeled-4">
  156. <h4 className="p-0 mt-2">Print dan Download</h4>
  157. </Button>
  158. </span>
  159. }}
  160. content={() => this.componentRef}
  161. />
  162. </span>
  163. </div>
  164. <div style={{ display: "none" }}>
  165. <ComponentToPrint ref={el => (this.componentRef = el)} query={this.props.query} dataPelanggaran={this.props.dataPelanggaran} dataSuratBA={this.props.dataSuratBA} />
  166. </div>
  167. <div className='page'>
  168. <page>
  169. <div className='BA-logo'>
  170. <img className='BA-logo' src="/static/img/logo-single-1-login.png" alt="logo" />
  171. </div>
  172. <h3 className='BA-header'>LAPORAN HASIL EVALUASI DAN PEMBAHASAN</h3>
  173. {dataLaporan.data && (<h3 className='BA-header'>{dataLaporan.data.pt.nama}</h3>)}
  174. <div className='body'>
  175. <p className='body'>
  176. Pada hari ini
  177. {dataSuratBA?.isEditTanggal &&
  178. <span>
  179. <DatePicker
  180. selected={tanggal ? new Date(tanggal) : tanggal}
  181. onChange={(tanggal) => {
  182. this.setState({ tanggal, setTanggal: true }, this.setDataSuratBA)
  183. }}
  184. dateFormat="dd/MM/yyyy"
  185. placeholderText="Isi Tanggal"
  186. locale={id}
  187. className="form-control bg-white"
  188. />
  189. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditTanggal} />
  190. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={this.isEditTanggal}
  191. />
  192. </span>
  193. }
  194. {setTanggal === true || this.state?.setTanggal === true ?
  195. <span onClick={this.isEditTanggal}> {moment(tanggal || this.state?.tanggal).locale("id").format("dddd")}, tanggal&nbsp;{moment(tanggal || this.state?.tanggal).format("D")}&nbsp; bulan &nbsp;{moment(tanggal || this.state?.tanggal).format("MMMM")} tahun &nbsp;{moment(tanggal || this.state?.tanggal).format("YYYY")},</span> :
  196. <span onClick={this.isEditTanggal}> &nbsp;[Mohon Diisi] &nbsp;</span>
  197. }
  198. &nbsp;bertempat di
  199. {dataSuratBA?.isEditTempat &&
  200. <span>
  201. <input type='text'
  202. defaultValue={dataSuratBA?.tempat}
  203. ref="inputTempat"
  204. onChange={() => {
  205. this.setState({ tempat: this.refs.inputTempat.value }, this.setDataSuratBA)
  206. }}
  207. />
  208. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditTempat} />
  209. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={() => { this.isEditTempat() }} />
  210. </span>
  211. }
  212. {dataSuratBA?.tempat || this.state?.tempat ?
  213. <span onClick={this.isEditTempat}>
  214. &nbsp;{dataSuratBA?.tempat || this.state?.tempat}
  215. </span>
  216. :
  217. <span onClick={this.isEditTempat}>[Mohon Diisi]</span>
  218. }
  219. ,
  220. telah dilakukan rapat evaluasi dan pembahasan dugaan pelanggaran penyelenggaraan oleh perguruan tinggi dan/atau badan penyelenggara {dataLaporan.data && (<span>{dataLaporan.data.pt.nama}</span>)}, yang dihadiri oleh:
  221. </p>
  222. <div className='body'>
  223. <ol>
  224. {dataLaporan.data?.peserta_penetapan_sanksi?.map((value) => <li>{value.nama}</li>)}
  225. </ol>
  226. </div>
  227. </div>
  228. <p>
  229. Berdasarkan rapat evaluasi dan pembahasan dugaan pelanggaran penyelenggaraan oleh perguruan tinggi dan/atau badan penyelenggara {dataLaporan.data && (<span>{dataLaporan.data.pt.nama}</span>)}, disampaikan sebagai berikut:
  230. </p>
  231. <div className='body'>
  232. <ol>
  233. <li>Telah dibacakan Berita Acara Evaluasi Kinerja Perguruan Tinggi {dataLaporan.data && (<span>{dataLaporan.data.pt.nama}</span>)}, tanggal
  234. {setTanggal === true || this.state?.setTanggal === true ?
  235. <span> &nbsp;{moment(tanggal || this.state?.tanggal).format("DD-MM-YYYY")}</span>
  236. :
  237. <span> &nbsp;....... &nbsp;</span>
  238. }
  239. </li>
  240. <li>Telah dilakukan pembahasan rekomendasi mengenai fakta-fakta yang ditemukan Tim EKPT Ditjen Diktiristek, dengan temuan sebagai berikut:</li>
  241. <table className='table-a'>
  242. <thead>
  243. <tr>
  244. <th rowspan="2">NO</th>
  245. <th rowspan="2">NAMA DAN IZIN PRODI</th>
  246. <th colspan="3">PELANGGARAN TERHADAP PERMENDIKBUD NO.7 TAHUN 2020</th>
  247. <th rowspan="2">SIMPULAN</th>
  248. <th rowspan="2">REKOMENDASI</th>
  249. </tr>
  250. <tr>
  251. <th>PASAL</th>
  252. <th>BUTIR PELANGGARAN</th>
  253. <th>DESKRIPSI PELANGGARAN</th>
  254. </tr>
  255. </thead>
  256. <tbody>
  257. {dataPelanggaran?.data?.map((e, i) => (
  258. <tr key={e._id}>
  259. <td>{++i}</td>
  260. {dataLaporan.data && (<td className='BA-header'>{dataLaporan.data.pt.nama}</td>)}
  261. <td>{e.pasal}</td>
  262. <td>{e.butir_pelanggaran}</td>
  263. <td>{e.pelanggaran}</td>
  264. <td>
  265. <ContentEditable
  266. html={descPelanggaran[e._id]?.simpulan || ""}
  267. disabled={false}
  268. onChange={(evt) => {
  269. this.updateValueSimpulan(evt, e._id), this.setDataSuratBA()
  270. }}
  271. />
  272. </td>
  273. <td>
  274. <ContentEditable
  275. html={descPelanggaran[e._id]?.rekomendasi || ""}
  276. disabled={false}
  277. onChange={(evt) => {
  278. this.updateValueRekomendasi(evt, e._id), this.setDataSuratBA()
  279. }}
  280. />
  281. </td>
  282. </tr>
  283. ))}
  284. </tbody>
  285. </table>
  286. <li>Temuan Lain:
  287. {this.props.dataSuratBA?.isEditTemuanLain ?
  288. <span>
  289. <input style={{ height: "30px", width: "250px" }} type='textarea' defaultValue={""} ref="inputTemuan"
  290. />
  291. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={() => {
  292. this.updateValueTemuanLain(), this.isEditTemuanLain()
  293. }} />
  294. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditTemuanLain} />
  295. </span>
  296. : <Button onClick={this.isEditTemuanLain} className=" p-0 m-0" color="success">Input Data</Button>}
  297. <ol type="a">
  298. {dataSuratBA?.temuanLain?.map((value) => <li>{value}</li>) || this.state?.temuanLain?.map((value) => <li>{value}</li>)}
  299. </ol>
  300. </li>
  301. <li>Hal-hal yang memberatkan, sebagai berikut:
  302. {this.props.dataSuratBA?.isEditKeberatan ?
  303. <span>
  304. <input style={{ height: "30px", width: "250px" }} type='text' defaultValue={""} ref="inputMemberatkan" />
  305. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={() => { this.updateValueMemberatkan(), this.isEditKeberatan() }} />
  306. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditKeberatan} />
  307. </span>
  308. : <Button onClick={this.isEditKeberatan} className=" p-0 m-0" color="success">Input Data</Button>}
  309. <ol type="a">
  310. {dataSuratBA?.memberatkan?.map((value) => <li>{value}</li>) || this.state?.memberatkan?.map((value) => <li>{value}</li>)}
  311. </ol>
  312. </li>
  313. <li>hal-hal yang meringankan, sebagai berikut:
  314. {this.props.dataSuratBA?.isEditMeringankan ?
  315. <span>
  316. <input type='text' defaultValue={""} ref="inputMeringankan" />
  317. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={() => { this.updateValueMemringankan(), this.isEditMeringankan() }} />
  318. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditMeringankan} />
  319. </span>
  320. : <Button onClick={this.isEditMeringankan} className=" p-0 m-0" color="success">Input Data</Button>}
  321. <ol type="a">
  322. {dataSuratBA?.meringankan?.map((value) => <li>{value}</li>) || this.state?.meringankan?.map((value) => <li>{value}</li>)}
  323. </ol>
  324. </li>
  325. <li>
  326. Berdasarkan pembahasan yang dilakukan, disepakati untuk merekomendasikan <strong>“Sanksi Administratif berupa
  327. {dataSuratBA?.isEditSanksi &&
  328. <span>
  329. <input type='text'
  330. defaultValue=""
  331. ref="inputsanksi"
  332. onChange={() => {
  333. this.setState({ sanksi: this.refs.inputsanksi.value }, this.setDataSuratBA)
  334. }}
  335. />
  336. <button className='bg-transparent button-transparent border-0 fas fa-times-circle text-danger' onClick={this.isEditSanksi} />
  337. <button className='bg-transparent button-transparent border-0 fas fa-check-circle text-success' onClick={() => { this.isEditSanksi() }} />
  338. </span>
  339. }
  340. {dataSuratBA?.sanksi || this.state?.sanksi ?
  341. <span onClick={this.isEditSanksi}>
  342. &nbsp;{dataSuratBA?.sanksi || this.state?.sanksi}
  343. </span>
  344. :
  345. <span onClick={this.isEditSanksi}>[Mohon Diisi]</span>
  346. }
  347. </strong>
  348. </li>
  349. </ol>
  350. </div>
  351. <p className=''>
  352. Demikian Laporan Evaluasi dan Pembahasan ini dibuat dengan sesungguhnya dan telah dibaca dan dicermati oleh peserta rapat yang hadir.
  353. </p>
  354. <p>
  355. <CopyToClipboard
  356. text={`https://dev.sidali.kemdikbud.go.id/signature/pleno-sanksi/${dataLaporan.data?._id}`}
  357. options={{ asHtml: true }}
  358. >
  359. <div>
  360. <span className="btn-radius">
  361. <Button color id="Popover1" className="btn-labeled-3" onClick={() => {
  362. this.setState({
  363. setmeState: !this.state.setmeState
  364. }, this.setDataSuratBA()), this.handleAutoSave(), this.CloseCopied()
  365. }} >
  366. <h4 className="p-0 mt-2 float-right"> <em className="fas fa-project-diagram float-left mt-1" /> &nbsp;Link Dokumen</h4>
  367. </Button>
  368. </span>
  369. <Popover placement="bottom" isOpen={this.state.copied} target="Popover1" toggle={this.Copied}>
  370. <PopoverHeader>Link Berhasil Disalin</PopoverHeader>
  371. </Popover>
  372. </div>
  373. </CopyToClipboard>
  374. </p>
  375. <table className='demo'>
  376. <tbody>
  377. <tr>
  378. <th className='thdemo' colspan="4">PESERTA RAPAT PENYUSUNAN REKOMENDASI</th>
  379. </tr>
  380. <tr className='trdemo'>
  381. <th className='trdemo'>No</th>
  382. <th className='trdemo'>Nama</th>
  383. <th className='trdemo'>Tanda Tangan</th>
  384. </tr>
  385. {dataLaporan
  386. ? dataLaporan.data?.peserta_penetapan_sanksi?.map((value, index) => (
  387. <tr>
  388. <td className='trdemo'>{index + 1}</td>
  389. <td className=' tddemo'>{value.nama}</td>
  390. <td className='tddemo'>
  391. <img
  392. style={{ width: "200px" }}
  393. src={value.ttd.path} />
  394. </td>
  395. </tr>)) : ""}
  396. </tbody>
  397. </table>
  398. {/* <div>
  399. <div id="ttd-header" className='text-center signature-border'>
  400. <span className='text-center'> PESERTA RAPAT PENYUSUNAN REKOMENDASI</span>
  401. </div>
  402. <div id="ttd">
  403. {dataLaporan
  404. ? dataLaporan.data?.peserta_penetapan_sanksi?.map((value) => (
  405. <div className='ttd-div'>
  406. <img
  407. className='sign-ttd'
  408. src={value.ttd.path} />
  409. <div className='sign-nama font-color-black'>{value.nama}</div>
  410. </div>
  411. )) : ""}
  412. </div>
  413. </div> */}
  414. </page>
  415. </div>
  416. </div >
  417. );
  418. }
  419. }
  420. export default BeritaAcara