
--- client/views/pages/Manager/DeptList.vue
+++ client/views/pages/Manager/DeptList.vue
... | ... | @@ -1,14 +1,140 @@ |
1 | 1 |
<template> |
2 |
- <div class="services"> |
|
3 |
- <h1>Our Services</h1> |
|
4 |
- <p>We provide web development and design services.</p> |
|
5 |
- </div> |
|
6 |
- </template> |
|
7 |
- |
|
8 |
- <script> |
|
9 |
- </script> |
|
10 |
- |
|
11 |
- <style scoped> |
|
2 |
+ <div class="pagetitle"> |
|
3 |
+ <h1>부서관리</h1> |
|
4 |
+ </div> |
|
5 |
+ <!-- End Page Title --> |
|
6 |
+ <section class="section"> |
|
7 |
+ <div class="row"> |
|
12 | 8 |
|
13 |
- </style> |
|
14 |
-(파일 끝에 줄바꿈 문자 없음) |
|
9 |
+ |
|
10 |
+ <div class="col-lg-12"> |
|
11 |
+ <div class="card"> |
|
12 |
+ <div class="card-body"> |
|
13 |
+ <h5 class="card-title">부서관리</h5> |
|
14 |
+ <div class="d-flex pb-3 justify-content-end "> |
|
15 |
+ |
|
16 |
+ <div class="d-flex justify-content-end "> |
|
17 |
+ <button type="button" class="btn btn-outline-secondary" @click="registerLeave"> |
|
18 |
+ 등록 |
|
19 |
+ </button> |
|
20 |
+ <button type="button" class="btn btn-outline-success" @click="saveChanges"> |
|
21 |
+ 저장 |
|
22 |
+ </button> |
|
23 |
+ <button type="button" class="btn btn-outline-danger" @click="deletePending"> |
|
24 |
+ 삭제 |
|
25 |
+ </button> |
|
26 |
+ </div> |
|
27 |
+ |
|
28 |
+ </div> |
|
29 |
+ <!-- Table --> |
|
30 |
+ <table id="myTable" class="table datatable table-hover"> |
|
31 |
+ <!-- 동적으로 <th> 생성 --> |
|
32 |
+ <thead> |
|
33 |
+ <tr> |
|
34 |
+ <th>No </th> |
|
35 |
+ <th>부서명</th> |
|
36 |
+ <th>인원</th> |
|
37 |
+ </tr> |
|
38 |
+ </thead> |
|
39 |
+ <!-- 동적으로 <td> 생성 --> |
|
40 |
+ <tbody> |
|
41 |
+ <tr v-for="(item, index) in ChuljangData" :key="item.startDate + index"> |
|
42 |
+ <td> |
|
43 |
+ <div class="form-check"> |
|
44 |
+ <label class="form-check-label" for="acceptTerms">{{ index + 1 }}</label> |
|
45 |
+ <input v-model="item.acceptTerms" class="form-check-input" type="checkbox" /> |
|
46 |
+ </div> |
|
47 |
+ </td> |
|
48 |
+ <td><input type="text" v-model="item.deptNM" /></td> |
|
49 |
+ <td><input type="text" v-model="item.member" /></td> |
|
50 |
+ |
|
51 |
+</tr> |
|
52 |
+ </tbody> |
|
53 |
+ </table> |
|
54 |
+ |
|
55 |
+ <!-- End Table --> |
|
56 |
+ </div> |
|
57 |
+ </div> |
|
58 |
+ </div> |
|
59 |
+ </div> |
|
60 |
+ </section> |
|
61 |
+</template> |
|
62 |
+ |
|
63 |
+<script> |
|
64 |
+import { DataTable } from 'simple-datatables' |
|
65 |
+export default { |
|
66 |
+ data() { |
|
67 |
+ return { |
|
68 |
+ // 데이터 초기화 |
|
69 |
+ years: [2023, 2024, 2025], // 연도 목록 |
|
70 |
+ months: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12], // 월 목록 |
|
71 |
+ selectedYear: '', |
|
72 |
+ selectedMonth: '', |
|
73 |
+ ChuljangData: [ |
|
74 |
+ { startDate: '', endDate: '', where: '대구', purpose: '', acceptTerms: false }, |
|
75 |
+ { startDate: '', endDate: '', where: '경산', acceptTerms: false }, |
|
76 |
+ // 더 많은 데이터 추가... |
|
77 |
+ ], |
|
78 |
+ filteredData: [], |
|
79 |
+ }; |
|
80 |
+ }, |
|
81 |
+ computed: { |
|
82 |
+ |
|
83 |
+ }, |
|
84 |
+ methods: { |
|
85 |
+ |
|
86 |
+ registerLeave() { |
|
87 |
+ console.log("등록 버튼 클릭됨"); |
|
88 |
+ |
|
89 |
+ // Vue의 반응성 문제를 피하기 위해, 새로운 객체를 추가합니다. |
|
90 |
+ this.ChuljangData = [ |
|
91 |
+ ...this.ChuljangData, |
|
92 |
+ { startDate: '', endDate: '', where: '', acceptTerms: false } |
|
93 |
+ ]; |
|
94 |
+ |
|
95 |
+ console.log(this.ChuljangData); // 배열 상태 출력 |
|
96 |
+ }, |
|
97 |
+ saveChanges() { |
|
98 |
+ console.log("저장된 데이터:", this.ChuljangData); |
|
99 |
+ alert("저장되었습니다."); |
|
100 |
+ }, |
|
101 |
+ deletePending() { |
|
102 |
+ // 선택된 항목만 필터링하여 삭제 |
|
103 |
+ const selectedItems = this.ChuljangData.filter(item => item.acceptTerms); |
|
104 |
+ |
|
105 |
+ // 승인된 항목이 없으면 삭제 진행 |
|
106 |
+ if (selectedItems.length > 0) { |
|
107 |
+ this.ChuljangData = this.ChuljangData.filter(item => !item.acceptTerms); |
|
108 |
+ alert(`${selectedItems.length}개의 항목이 삭제되었습니다.`); |
|
109 |
+ } else { |
|
110 |
+ alert("선택된 항목이 없습니다."); |
|
111 |
+ } |
|
112 |
+ }, |
|
113 |
+ // 날짜 필터 적용 |
|
114 |
+ filterData() { |
|
115 |
+ this.filteredData = this.ChuljangData.filter(item => { |
|
116 |
+ const itemYear = new Date(item.startDate).getFullYear(); |
|
117 |
+ const itemMonth = new Date(item.startDate).getMonth() + 1; // 월은 0부터 시작하므로 1을 더해줍니다. |
|
118 |
+ |
|
119 |
+ return ( |
|
120 |
+ (!this.selectedYear || itemYear === parseInt(this.selectedYear)) && |
|
121 |
+ (!this.selectedMonth || itemMonth === parseInt(this.selectedMonth)) |
|
122 |
+ ); |
|
123 |
+ }); |
|
124 |
+ }, |
|
125 |
+ |
|
126 |
+ // 페이지 변경 |
|
127 |
+ changePage(page) { |
|
128 |
+ this.currentPage = page; |
|
129 |
+ }, |
|
130 |
+ }, |
|
131 |
+ mounted() { |
|
132 |
+ |
|
133 |
+ // 처음에는 모든 데이터를 표시 |
|
134 |
+ this.filteredData = this.ChuljangData; |
|
135 |
+ |
|
136 |
+ }, |
|
137 |
+}; |
|
138 |
+</script> |
|
139 |
+ |
|
140 |
+<style scoped></style> |
--- client/views/pages/Manager/EmployeeList.vue
+++ client/views/pages/Manager/EmployeeList.vue
... | ... | @@ -1,20 +1,134 @@ |
1 | 1 |
<template> |
2 |
- <div class="contact"> |
|
3 |
- <h1>Contact Us</h1> |
|
4 |
- <p>If you have any questions, feel free to reach out to us.</p> |
|
2 |
+ <div class="pagetitle"> |
|
3 |
+ <h1>직원관리</h1> |
|
4 |
+ </div> |
|
5 |
+ <!-- End Page Title --> |
|
6 |
+ <section class="section"> |
|
7 |
+ <div class="row"> |
|
8 |
+ |
|
9 |
+ |
|
10 |
+ <div class="col-lg-12"> |
|
11 |
+ <div class="card"> |
|
12 |
+ <div class="card-body"> |
|
13 |
+ <h5 class="card-title">직원관리</h5> |
|
14 |
+ <div class="d-flex pb-3 justify-content-between"> |
|
15 |
+ <div class="datatable-search d-flex gap-1 "> |
|
16 |
+ <div class=""> |
|
17 |
+ <select class="form-select " v-model="selectedDept"> |
|
18 |
+ <option value="" >이름</option> |
|
19 |
+ <option v-for="dept in depts" :key="dept" :value="dept">{{ dept }}</option> |
|
20 |
+ </select> |
|
21 |
+ </div> |
|
22 |
+ <div class="search-bar d-flex gap-2"> |
|
23 |
+ <form class="search-form d-flex align-items-center" method="POST" action="#" |
|
24 |
+ @submit.prevent="updateMember"> |
|
25 |
+ <input type="text" v-model="searchQuery" name="query" placeholder="Search" title="Enter search keyword"> |
|
26 |
+ <button type="submit" title="Search"><i class="bi bi-search"></i></button> |
|
27 |
+ </form> |
|
28 |
+ </div> |
|
29 |
+ <button type="button" class="btn btn-outline-secondary" |
|
30 |
+ @click="filterData">조회</button> |
|
31 |
+ |
|
32 |
+ </div> |
|
33 |
+ <div class="d-flex justify-content-end "> |
|
34 |
+ <!-- <button type="button" class="btn btn-outline-secondary" @click="registerLeave"> |
|
35 |
+ 등록 |
|
36 |
+ </button> |
|
37 |
+ <button type="button" class="btn btn-outline-success" @click="saveChanges"> |
|
38 |
+ 저장 |
|
39 |
+ </button> --> |
|
40 |
+ <button type="button" class="btn btn-outline-danger" @click="deletePending"> |
|
41 |
+ 삭제 |
|
42 |
+ </button> |
|
43 |
+ </div> |
|
44 |
+ |
|
45 |
+ </div> |
|
46 |
+ <!-- Table --> |
|
47 |
+ <table id="myTable" class="table datatable table-hover"> |
|
48 |
+ <!-- 동적으로 <th> 생성 --> |
|
49 |
+ <thead> |
|
50 |
+ <tr> |
|
51 |
+ <th>No </th> |
|
52 |
+ <th>이름</th> |
|
53 |
+ <th>부서</th> |
|
54 |
+ <th>직급</th> |
|
55 |
+ <th>이메일</th> |
|
56 |
+ </tr> |
|
57 |
+ </thead> |
|
58 |
+ <!-- 동적으로 <td> 생성 --> |
|
59 |
+ <tbody> |
|
60 |
+ <tr v-for="(item, index) in ChuljangData" :key="item.startDate + index"> |
|
61 |
+ <td> |
|
62 |
+ <div class="form-check"> |
|
63 |
+ <label class="form-check-label" for="acceptTerms">{{ index + 1 }}</label> |
|
64 |
+ <input v-model="item.acceptTerms" class="form-check-input" type="checkbox" /> |
|
5 | 65 |
</div> |
6 |
- </template> |
|
66 |
+ </td> |
|
67 |
+ <td><input type="text" v-model="item.name" /></td> |
|
68 |
+ <td><input type="text" v-model="item.dept" /></td> |
|
69 |
+ <td><input type="text" v-model="item.level" /></td> |
|
70 |
+ <td><input type="text" v-model="item.email" /></td> |
|
71 |
+</tr> |
|
72 |
+ </tbody> |
|
73 |
+ </table> |
|
74 |
+ |
|
75 |
+ <!-- End Table --> |
|
76 |
+ </div> |
|
77 |
+ </div> |
|
78 |
+ </div> |
|
79 |
+ </div> |
|
80 |
+ </section> |
|
81 |
+</template> |
|
82 |
+ |
|
83 |
+<script> |
|
84 |
+import { DataTable } from 'simple-datatables' |
|
85 |
+export default { |
|
86 |
+ data() { |
|
87 |
+ return { |
|
88 |
+ // 데이터 초기화 |
|
89 |
+ depts: [2023, 2024, 2025], // 연도 목록 |
|
90 |
+ levels: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12], // 월 목록 |
|
91 |
+ selectedDept: '', |
|
92 |
+ selectedlevel: '', |
|
93 |
+ ChuljangData: [ |
|
94 |
+ { startDate: '', endDate: '', where: '대구', purpose: '', acceptTerms: false }, |
|
95 |
+ { startDate: '', endDate: '', where: '경산', acceptTerms: false }, |
|
96 |
+ // 더 많은 데이터 추가... |
|
97 |
+ ], |
|
98 |
+ filteredData: [], |
|
99 |
+ }; |
|
100 |
+ }, |
|
101 |
+ computed: { |
|
102 |
+ |
|
103 |
+ }, |
|
104 |
+ methods: { |
|
105 |
+ |
|
106 |
+ |
|
107 |
+ deletePending() { |
|
108 |
+ // 선택된 항목만 필터링하여 삭제 |
|
109 |
+ const selectedItems = this.ChuljangData.filter(item => item.acceptTerms); |
|
110 |
+ |
|
111 |
+ // 승인된 항목이 없으면 삭제 진행 |
|
112 |
+ if (selectedItems.length > 0) { |
|
113 |
+ this.ChuljangData = this.ChuljangData.filter(item => !item.acceptTerms); |
|
114 |
+ alert(`${selectedItems.length}개의 항목이 삭제되었습니다.`); |
|
115 |
+ } else { |
|
116 |
+ alert("선택된 항목이 없습니다."); |
|
117 |
+ } |
|
118 |
+ }, |
|
119 |
+ |
|
120 |
+ // 페이지 변경 |
|
121 |
+ changePage(page) { |
|
122 |
+ this.currentPage = page; |
|
123 |
+ }, |
|
124 |
+ }, |
|
125 |
+ mounted() { |
|
126 |
+ |
|
127 |
+ // 처음에는 모든 데이터를 표시 |
|
128 |
+ this.filteredData = this.ChuljangData; |
|
7 | 129 |
|
8 |
- <script> |
|
9 |
- export default { |
|
10 |
- name: 'ContactPage', |
|
11 |
- } |
|
12 |
- </script> |
|
13 |
- |
|
14 |
- <style scoped> |
|
15 |
- .contact { |
|
16 |
- text-align: center; |
|
17 |
- margin-top: 50px; |
|
18 |
- } |
|
19 |
- </style> |
|
20 |
-(파일 끝에 줄바꿈 문자 없음) |
|
130 |
+ }, |
|
131 |
+}; |
|
132 |
+</script> |
|
133 |
+ |
|
134 |
+<style scoped></style> |
--- client/views/pages/User/Join.vue
+++ client/views/pages/User/Join.vue
... | ... | @@ -26,12 +26,23 @@ |
26 | 26 |
<input v-model="name" type="text" name="name" class="form-control" id="yourName" required> |
27 | 27 |
<div class="invalid-feedback">이름을 입력해주세요.</div> |
28 | 28 |
</div> |
29 |
- |
|
30 | 29 |
<div class="col-12"> |
31 |
- <label for="yourUsername" class="form-label">Email</label> |
|
30 |
+ <label for="yourdept" class="form-label">부서</label> |
|
31 |
+ <select v-model="dept" id="inputState" class="form-select"> |
|
32 |
+ <option selected></option> |
|
33 |
+ <option></option> |
|
34 |
+ </select> |
|
35 |
+ </div> |
|
36 |
+ <div class="col-12"> |
|
37 |
+ <label for="yourlevel" class="form-label">직급</label> |
|
38 |
+ <input v-model="level" type="text" name="name" class="form-control" id="yourlevel" required> |
|
39 |
+ <div class="invalid-feedback">직급을 입력해주세요.</div> |
|
40 |
+ </div> |
|
41 |
+ <div class="col-12"> |
|
42 |
+ <label for="youremail" class="form-label">Email</label> |
|
32 | 43 |
<div class="input-group has-validation"> |
33 | 44 |
<span class="input-group-text" id="inputGroupPrepend">@</span> |
34 |
- <input v-model="email" type="text" name="username" class="form-control" id="yourUsername" required> |
|
45 |
+ <input v-model="email" type="text" name="username" class="form-control" id="youremail" required> |
|
35 | 46 |
<div class="invalid-feedback">회사 이메일을 입력해주세요.</div> |
36 | 47 |
</div> |
37 | 48 |
</div> |
... | ... | @@ -76,6 +87,8 @@ |
76 | 87 |
name: '', |
77 | 88 |
email: '', |
78 | 89 |
password: '', |
90 |
+ dept: '', |
|
91 |
+ level: '', |
|
79 | 92 |
acceptTerms: false, |
80 | 93 |
formSubmitted: false, |
81 | 94 |
logo: "/client/resources/img/logo_t.png", // 경로를 Vue 프로젝트 구조에 맞게 설정 |
... | ... | @@ -85,7 +98,7 @@ |
85 | 98 |
handleRegister() { |
86 | 99 |
this.formSubmitted = true; |
87 | 100 |
// 이메일과 비밀번호가 빈 값이 아니어야 한다 |
88 |
- if (this.email && this.password && this.name && this.acceptTerms) { |
|
101 |
+ if (this.email && this.password && this.name && this.acceptTerms && this.dept && this.level) { |
|
89 | 102 |
// 로컬 스토리지에 회원가입 정보 저장 |
90 | 103 |
const userData = { |
91 | 104 |
name: this.name, |
Add a comment
Delete comment
Once you delete this comment, you won't be able to recover it. Are you sure you want to delete this comment?