feat(activities): remove an assignee from the share list
A team, role, or person can be taken off the activity from the progress chips, and ungrouped people use the same chip as grouped members. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -168,13 +168,24 @@ function commit(ids: string[]) {
|
||||
|
||||
function onUpdate(value: unknown) {
|
||||
const tokens = Array.isArray(value) ? value.map(String) : [];
|
||||
const tokenSet = new Set(tokens);
|
||||
const removedMemberIds = new Set<string>();
|
||||
for (const token of selectValue.value) {
|
||||
if (tokenSet.has(token)) continue;
|
||||
const dropped = catalogByToken.value.get(token);
|
||||
if (!dropped) continue;
|
||||
for (const id of dropped.userIds) removedMemberIds.add(id);
|
||||
}
|
||||
const ids = new Set<string>();
|
||||
const pins = new Set<string>();
|
||||
for (const token of tokens) {
|
||||
const group = catalogByToken.value.get(token);
|
||||
if (group) {
|
||||
pins.add(token);
|
||||
for (const id of group.userIds) ids.add(id);
|
||||
for (const id of group.userIds) {
|
||||
if (removedMemberIds.has(id)) continue;
|
||||
ids.add(id);
|
||||
}
|
||||
continue;
|
||||
}
|
||||
if (!token.startsWith('role:') && !token.startsWith('team:')) ids.add(token);
|
||||
|
||||
@@ -323,6 +323,18 @@ function shareExpanded(group: ShareGroup) {
|
||||
function toggleShare(group: ShareGroup) {
|
||||
shareOpen.value = { ...shareOpen.value, [group.key]: !shareExpanded(group) };
|
||||
}
|
||||
|
||||
function removeAssignees(ids: string[]) {
|
||||
if (!canReassign.value || saving.value) return;
|
||||
const drop = new Set(ids);
|
||||
const next = assignUserIds.value.filter((id) => !drop.has(id));
|
||||
if (!next.length) {
|
||||
error.value = 'حداقل یک مسئول لازم است.';
|
||||
return;
|
||||
}
|
||||
assignUserIds.value = next;
|
||||
void reassign();
|
||||
}
|
||||
const myShareDone = computed(() => {
|
||||
const mine = auth.user?.id;
|
||||
return Boolean(mine && completedIds.value.has(mine));
|
||||
@@ -808,21 +820,33 @@ onMounted(() => {
|
||||
{{ toFaDigits(shareDoneTotal) }} از {{ toFaDigits(assigneePeople.length) }} انجام شده
|
||||
</p>
|
||||
<div v-for="group in shareGroups" :key="group.key" class="share-group">
|
||||
<button type="button" class="share-group-head" @click="toggleShare(group)">
|
||||
<UiIcon
|
||||
name="chevron"
|
||||
:size="14"
|
||||
class="share-caret"
|
||||
:class="{ open: shareExpanded(group) }"
|
||||
/>
|
||||
<span class="share-group-name">
|
||||
<small v-if="shareKindLabel(group)">{{ shareKindLabel(group) }}</small>
|
||||
{{ group.name }}
|
||||
</span>
|
||||
<em :class="{ done: shareDoneCount(group.members) === group.members.length }">
|
||||
{{ toFaDigits(shareDoneCount(group.members)) }} از {{ toFaDigits(group.members.length) }}
|
||||
</em>
|
||||
</button>
|
||||
<div class="share-group-bar">
|
||||
<button type="button" class="share-group-head" @click="toggleShare(group)">
|
||||
<UiIcon
|
||||
name="chevron"
|
||||
:size="14"
|
||||
class="share-caret"
|
||||
:class="{ open: shareExpanded(group) }"
|
||||
/>
|
||||
<span class="share-group-name">
|
||||
<small v-if="shareKindLabel(group)">{{ shareKindLabel(group) }}</small>
|
||||
{{ group.name }}
|
||||
</span>
|
||||
<em :class="{ done: shareDoneCount(group.members) === group.members.length }">
|
||||
{{ toFaDigits(shareDoneCount(group.members)) }} از {{ toFaDigits(group.members.length) }}
|
||||
</em>
|
||||
</button>
|
||||
<button
|
||||
v-if="canReassign"
|
||||
type="button"
|
||||
class="share-remove"
|
||||
:disabled="saving"
|
||||
:aria-label="`برداشتن ${group.name}`"
|
||||
@click="removeAssignees(group.members.map((person) => person.id))"
|
||||
>
|
||||
×
|
||||
</button>
|
||||
</div>
|
||||
<ul v-if="shareExpanded(group)" class="share-members">
|
||||
<li
|
||||
v-for="person in group.members"
|
||||
@@ -831,11 +855,21 @@ onMounted(() => {
|
||||
>
|
||||
<span>{{ person.fullName }}</span>
|
||||
<em>{{ completedIds.has(person.id) ? 'انجام شد' : 'مانده' }}</em>
|
||||
<button
|
||||
v-if="canReassign"
|
||||
type="button"
|
||||
class="share-remove"
|
||||
:disabled="saving"
|
||||
:aria-label="`برداشتن ${person.fullName}`"
|
||||
@click="removeAssignees([person.id])"
|
||||
>
|
||||
×
|
||||
</button>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<ul v-else-if="needsEveryone && !isDone" class="share-list">
|
||||
<ul v-else-if="needsEveryone && !isDone" class="share-members loose">
|
||||
<li
|
||||
v-for="person in assigneePeople"
|
||||
:key="person.id"
|
||||
@@ -843,6 +877,16 @@ onMounted(() => {
|
||||
>
|
||||
<span>{{ person.fullName }}</span>
|
||||
<em>{{ completedIds.has(person.id) ? 'انجام شد' : 'مانده' }}</em>
|
||||
<button
|
||||
v-if="canReassign"
|
||||
type="button"
|
||||
class="share-remove"
|
||||
:disabled="saving"
|
||||
:aria-label="`برداشتن ${person.fullName}`"
|
||||
@click="removeAssignees([person.id])"
|
||||
>
|
||||
×
|
||||
</button>
|
||||
</li>
|
||||
</ul>
|
||||
<button
|
||||
@@ -1452,31 +1496,19 @@ dd {
|
||||
color: #0f766e;
|
||||
}
|
||||
|
||||
.share-list {
|
||||
list-style: none;
|
||||
margin: 0.55rem 0 0;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
.share-group-bar {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 0.25rem;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.share-list li {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
gap: 0.75rem;
|
||||
font-size: 0.86rem;
|
||||
color: #334155;
|
||||
.share-group-bar .share-group-head {
|
||||
width: auto;
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.share-list em {
|
||||
font-style: normal;
|
||||
color: #94a3b8;
|
||||
}
|
||||
|
||||
.share-list li.done em {
|
||||
color: #0f766e;
|
||||
.share-group-bar > .share-remove {
|
||||
margin-inline-end: 0.45rem;
|
||||
}
|
||||
|
||||
.share-board {
|
||||
@@ -1561,6 +1593,13 @@ dd {
|
||||
gap: 0.35rem;
|
||||
}
|
||||
|
||||
.share-members.loose {
|
||||
width: 100%;
|
||||
margin-top: 0.55rem;
|
||||
padding: 0;
|
||||
max-height: none;
|
||||
}
|
||||
|
||||
.share-members li {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
@@ -1600,6 +1639,23 @@ dd {
|
||||
color: #0f766e;
|
||||
}
|
||||
|
||||
.share-remove {
|
||||
flex: 0 0 auto;
|
||||
border: 0;
|
||||
background: transparent;
|
||||
color: #94a3b8;
|
||||
font: inherit;
|
||||
font-size: 0.95rem;
|
||||
line-height: 1;
|
||||
padding: 0 0.1rem;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.share-remove:disabled {
|
||||
cursor: default;
|
||||
opacity: 0.45;
|
||||
}
|
||||
|
||||
.share-force {
|
||||
margin-top: 0.45rem;
|
||||
border: 0;
|
||||
|
||||
Reference in New Issue
Block a user