123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179 |
- <!-- 设计师分配组件 -->
- <div class="card designer-card">
- <div class="card-header">
- <h3 class="card-title">
- 设计师分配
- </h3>
- <p class="card-subtitle">先选择项目组,再选择组员</p>
- </div>
- <div class="card-content">
- <!-- 已分配组员展示 -->
- @if (projectTeams.length > 0) {
- <div class="assigned-teams-section">
- <h4 class="section-title">已分配组员</h4>
- <div class="team-list">
- @for (team of projectTeams; track team.id) {
- <div
- class="team-item"
- [class.clickable]="canEdit"
- (click)="canEdit ? editAssignedDesigner(team) : null">
- <div class="team-member">
- <div class="member-avatar">
- @if (team.get('profile')?.get('data')?.avatar) {
- <img [src]="team.get('profile').get('data').avatar" alt="组员头像" />
- } @else {
- <svg class="icon avatar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M256 48C141.31 48 48 141.31 48 256s93.31 208 208 208 208-93.31 208-208S370.69 48 256 48zm0 60a60 60 0 11-60 60 60 60 0 0160-60zm0 336c-63.6 0-119.92-36.47-146.39-89.68C109.74 329.09 176.24 296 256 296s146.26 33.09 146.39 58.32C376.92 407.53 319.6 444 256 444z"/>
- </svg>
- }
- </div>
- <div class="member-info">
- <h5>{{ team.get('profile')?.get('name') }}</h5>
- <p class="member-spaces">负责空间: {{ getMemberSpaces(team) }}</p>
- </div>
- </div>
- @if (canEdit) {
- <svg class="icon edit-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M384 224v184a40 40 0 01-40 40H104a40 40 0 01-40-40V168a40 40 0 0140-40h167.48M459.94 53.25a16.06 16.06 0 00-23.22-.56L424.35 65a8 8 0 000 11.31l11.34 11.32a8 8 0 0011.34 0l12.06-12c6.1-6.09 6.67-16.01.85-22.38zM399.34 90L218.82 270.2a9 9 0 00-2.31 3.93L208.16 299a3.91 3.91 0 004.86 4.86l24.85-8.35a9 9 0 003.93-2.31L422 112.66a9 9 0 000-12.66l-9.95-10a9 9 0 00-12.71 0z"/>
- </svg>
- }
- </div>
- }
- </div>
- </div>
- }
- <!-- 项目组选择 -->
- <div class="department-section">
- <h4 class="section-title">选择项目组</h4>
- @if (departments.length === 0) {
- <div class="empty-state">
- <p>暂无可用项目组</p>
- </div>
- } @else {
- <div class="department-grid">
- @for (dept of departments; track dept.id) {
- <div
- class="department-item"
- [class.selected]="selectedDepartment?.id === dept.id"
- (click)="selectDepartment(dept)">
- <h5>{{ dept.get('name') }}</h5>
- <p>组长: {{ dept.get('leader')?.get('name') || '未指定' }}</p>
- @if (selectedDepartment?.id === dept.id) {
- <svg class="icon selected-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M256 48C141.31 48 48 141.31 48 256s93.31 208 208 208 208-93.31 208-208S370.69 48 256 48zm-38 312.38L137.4 280.8a24 24 0 0133.94-33.94l50.2 50.2 95.74-95.74a24 24 0 0133.94 33.94z"/>
- </svg>
- }
- </div>
- }
- </div>
- }
- </div>
- <!-- 组员选择 -->
- @if (selectedDepartment) {
- <div class="designer-section">
- <h4 class="section-title">选择组员</h4>
- @if (loadingMembers) {
- <div class="loading-spinner">
- <div class="spinner-sm"></div>
- <p>加载组员中...</p>
- </div>
- } @else if (departmentMembers.length === 0) {
- <div class="empty-state">
- <p>该项目组暂无可用组员</p>
- </div>
- } @else {
- <div class="designer-grid">
- @for (designer of departmentMembers; track designer.id) {
- @if(designer?.get){
- <div
- class="designer-item"
- [class.selected]="selectedDesigner?.id === designer?.id"
- (click)="selectDesigner(designer)">
- <div class="designer-avatar">
- @if (designer?.get('data')?.avatar) {
- <img [src]="designer?.get('data').avatar" alt="设计师头像" />
- } @else {
- <svg class="icon avatar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M256 48C141.31 48 48 141.31 48 256s93.31 208 208 208 208-93.31 208-208S370.69 48 256 48zm0 60a60 60 0 11-60 60 60 60 0 0160-60zm0 336c-63.6 0-119.92-36.47-146.39-89.68C109.74 329.09 176.24 296 256 296s146.26 33.09 146.39 58.32C376.92 407.53 319.6 444 256 444z"/>
- </svg>
- }
- </div>
- <div class="designer-info">
- <h4>{{ designer?.get('name') }}</h4>
- <p>{{ getDesignerWorkload(designer) }}</p>
- </div>
- @if (selectedDesigner?.id === designer?.id) {
- <svg class="icon selected-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M256 48C141.31 48 48 141.31 48 256s93.31 208 208 208 208-93.31 208-208S370.69 48 256 48zm-38 312.38L137.4 280.8a24 24 0 0133.94-33.94l50.2 50.2 95.74-95.74a24 24 0 0133.94 33.94z"/>
- </svg>
- }
- </div>
- }
- }
- </div>
- }
- </div>
- }
- </div>
- </div>
- <!-- 设计师分配对话框 -->
- @if (showAssignDialog && assigningDesigner) {
- <div class="modal-overlay" (click)="cancelAssignDialog()">
- <div class="modal-dialog" (click)="$event.stopPropagation()">
- <div class="modal-header">
- <h3 class="modal-title">{{ editingTeam ? '编辑分配' : '分配设计师' }}</h3>
- <button class="modal-close" (click)="cancelAssignDialog()">
- <svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M289.94 256l95-95A24 24 0 00351 127l-95 95-95-95a24 24 0 00-34 34l95 95-95 95a24 24 0 1034 34l95-95 95 95a24 24 0 0034-34z"/>
- </svg>
- </button>
- </div>
- <div class="modal-content">
- <div class="designer-preview">
- <div class="designer-avatar">
- @if (assigningDesigner.get('data')?.avatar) {
- <img [src]="assigningDesigner.get('data').avatar" alt="设计师头像" />
- } @else {
- <svg class="icon avatar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
- <path fill="currentColor" d="M256 48C141.31 48 48 141.31 48 256s93.31 208 208 208 208-93.31 208-208S370.69 48 256 48zm0 60a60 60 0 11-60 60 60 60 0 0160-60zm0 336c-63.6 0-119.92-36.47-146.39-89.68C109.74 329.09 176.24 296 256 296s146.26 33.09 146.39 58.32C376.92 407.53 319.6 444 256 444z"/>
- </svg>
- }
- </div>
- <div class="designer-name">{{ assigningDesigner.get('name') }}</div>
- </div>
- <div class="space-selection-section">
- <h4 class="form-label">指派空间场景 <span class="required">*</span></h4>
- <p class="form-help">请选择该设计师负责的空间</p>
- <div class="space-checkbox-list">
- @for (space of projectSpaces; track space.id) {
- <label class="space-checkbox-item">
- <input
- type="checkbox"
- [checked]="selectedSpaces.includes(space.name)"
- (change)="toggleSpaceSelection(space.name)" />
- <span class="checkbox-custom"></span>
- <span class="space-name">{{ space.name }}</span>
- </label>
- }
- </div>
- </div>
- </div>
- <div class="modal-footer">
- <button class="btn btn-outline" (click)="cancelAssignDialog()">
- 取消
- </button>
- <button
- class="btn btn-primary"
- (click)="confirmAssignDesigner()"
- [disabled]="saving || selectedSpaces.length === 0">
- {{ editingTeam ? '确认更新' : '确认分配' }}
- </button>
- </div>
- </div>
- </div>
- }
|