feat: migrate view pages from FontAwesome to Phosphor Icons

This commit is contained in:
kolaente
2026-02-19 15:10:33 +01:00
parent b7d8f32659
commit 75100df674
14 changed files with 97 additions and 73 deletions

View File

@@ -2,7 +2,7 @@
<CreateEdit
v-model:loading="loadingModel"
:title="$t('filters.edit.title')"
primary-icon=""
:show-primary-icon="false"
:primary-label="$t('misc.save')"
:tertiary="$t('misc.delete')"
@primary="handleSave"

View File

@@ -6,8 +6,9 @@
<XButton
:to="{name:'labels.create'}"
class="is-pulled-right"
icon="plus"
>
<template #icon><PhPlus /></template>
{{ $t('label.create.header') }}
</XButton>
@@ -42,10 +43,7 @@
class="label-edit-button is-small"
@click.stop.prevent="editLabel(label)"
>
<Icon
icon="pen"
class="icon"
/>
<PhPencilSimple class="icon" />
</BaseButton>
</RouterLink>
</div>
@@ -87,10 +85,11 @@
</div>
<div class="control">
<XButton
icon="trash-alt"
danger
@click="showDeleteDialoge(labelEditLabel)"
/>
>
<template #icon><PhTrash /></template>
</XButton>
</div>
</div>
</form>
@@ -122,6 +121,7 @@ import {computed, nextTick, ref} from 'vue'
import {useI18n} from 'vue-i18n'
import BaseButton from '@/components/base/BaseButton.vue'
import {PhPencilSimple, PhPlus, PhTrash} from '@phosphor-icons/vue'
import Editor from '@/components/input/AsyncEditor'
import ColorPicker from '@/components/input/ColorPicker.vue'
import FormField from '@/components/input/FormField.vue'

View File

@@ -15,15 +15,17 @@
<div class="action-buttons">
<XButton
:to="{name: 'filters.create'}"
icon="filter"
>
<template #icon><PhFunnel /></template>
{{ $t('filters.create.title') }}
</XButton>
<XButton
v-cy="'new-project'"
:to="{name: 'project.create'}"
icon="plus"
>
<template #icon><PhPlus /></template>
{{ $t('project.create.header') }}
</XButton>
</div>
@@ -41,6 +43,8 @@ import {computed} from 'vue'
import {useI18n} from 'vue-i18n'
import FancyCheckbox from '@/components/input/FancyCheckbox.vue'
import {PhFunnel, PhPlus} from '@phosphor-icons/vue'
import ProjectCardGrid from '@/components/project/partials/ProjectCardGrid.vue'
import {useTitle} from '@/composables/useTitle'

View File

@@ -2,10 +2,10 @@
<CreateEdit
v-model:loading="loadingModel"
:title="$t('project.duplicate.title')"
primary-icon="paste"
:primary-label="$t('project.duplicate.label')"
@primary="duplicate"
>
<template #primary-icon><PhClipboard /></template>
<p>{{ $t('project.duplicate.text') }}</p>
<ProjectSearch v-model="parentProject" />
</CreateEdit>
@@ -17,6 +17,7 @@ import {useRoute} from 'vue-router'
import {useI18n} from 'vue-i18n'
import CreateEdit from '@/components/misc/CreateEdit.vue'
import {PhClipboard} from '@phosphor-icons/vue'
import ProjectSearch from '@/components/tasks/partials/ProjectSearch.vue'
import {success} from '@/message'

View File

@@ -2,7 +2,7 @@
<CreateEdit
v-model:loading="loadingModel"
:title="$t('project.edit.header')"
primary-icon=""
:show-primary-icon="false"
:primary-label="$t('misc.save')"
:tertiary="project.maxPermission === PERMISSIONS.ADMIN ? $t('misc.delete') : undefined"
@primary="save"

View File

@@ -7,6 +7,7 @@ import type {IProjectView} from '@/modelTypes/IProjectView'
import ViewEditForm from '@/components/project/views/ViewEditForm.vue'
import ProjectViewService from '@/services/projectViews'
import XButton from '@/components/input/Button.vue'
import {PhDotsSixVertical, PhPencilSimple, PhTrash} from '@phosphor-icons/vue'
import {error, success} from '@/message'
import {useI18n} from 'vue-i18n'
import ProjectService from '@/services/project'
@@ -193,19 +194,21 @@ async function saveViewPosition(e) {
<XButton
v-if="isAdmin"
class="is-danger mie-2"
icon="trash-alt"
@click="() => {
viewIdToDelete = v.id
showDeleteModal = true
}"
/>
>
<template #icon><PhTrash /></template>
</XButton>
<XButton
v-if="isAdmin"
icon="pen"
@click="viewToEdit = {...v}"
/>
>
<template #icon><PhPencilSimple /></template>
</XButton>
<span class="icon handle">
<Icon icon="grip-lines" />
<PhDotsSixVertical />
</span>
</td>
</template>

View File

@@ -9,6 +9,7 @@ import ProjectModel from '@/models/project'
import type {IProject} from '@/modelTypes/IProject'
import CreateEdit from '@/components/misc/CreateEdit.vue'
import {PhPlus, PhTrash} from '@phosphor-icons/vue'
import {useBaseStore} from '@/stores/base'
import type {IWebhook} from '@/modelTypes/IWebhook'
@@ -128,10 +129,10 @@ function validateSelectedEvents() {
>
<XButton
v-if="!(webhooks?.length === 0 || showNewForm)"
icon="plus"
class="mbe-4"
@click="showNewForm = true"
>
<template #icon><PhPlus /></template>
{{ $t('project.webhooks.create') }}
</XButton>
@@ -239,9 +240,9 @@ function validateSelectedEvents() {
</p>
</div>
<XButton
icon="plus"
@click="create"
>
<template #icon><PhPlus /></template>
{{ $t('project.webhooks.create') }}
</XButton>
</div>
@@ -277,9 +278,10 @@ function validateSelectedEvents() {
<td class="actions">
<XButton
danger
icon="trash-alt"
@click="() => {showDeleteModal = true;webhookIdToDelete = w.id}"
/>
>
<template #icon><PhTrash /></template>
</XButton>
</td>
</tr>
</tbody>

View File

@@ -28,7 +28,7 @@
class="clear-filter-button"
@click="clearLabelFilter"
>
<Icon icon="times" />
<PhX />
</BaseButton>
</Message>
<p
@@ -102,7 +102,7 @@ import {formatDate} from '@/helpers/time/formatDate'
import {setTitle} from '@/helpers/setTitle'
import BaseButton from '@/components/base/BaseButton.vue'
import Icon from '@/components/misc/Icon'
import {PhX} from '@phosphor-icons/vue'
import Message from '@/components/misc/Message.vue'
import FancyCheckbox from '@/components/input/FancyCheckbox.vue'
import SingleTaskInProject from '@/components/tasks/partials/SingleTaskInProject.vue'

View File

@@ -17,7 +17,7 @@
class="back-button mbs-2"
@click="lastProject ? router.back() : router.push(projectRoute)"
>
<Icon icon="arrow-left" />
<PhArrowLeft />
{{ $t('task.detail.back') }}
</BaseButton>
<Heading
@@ -73,7 +73,7 @@
>
<!-- Assignees -->
<div class="detail-title">
<Icon icon="users" />
<PhUsers />
{{ $t('task.attributes.assignees') }}
</div>
<EditAssignees
@@ -99,7 +99,7 @@
>
<!-- Priority -->
<div class="detail-title">
<Icon icon="exclamation-circle" />
<PhWarningCircle />
{{ $t('task.attributes.priority') }}
</div>
<PrioritySelect
@@ -120,7 +120,7 @@
>
<!-- Due Date -->
<div class="detail-title">
<Icon icon="calendar" />
<PhCalendar />
{{ $t('task.attributes.dueDate') }}
</div>
<div class="date-input">
@@ -137,7 +137,7 @@
@click="() => {task.dueDate = null;saveTask()}"
>
<span class="icon is-small">
<Icon icon="times" />
<PhX />
</span>
</BaseButton>
</div>
@@ -153,7 +153,7 @@
>
<!-- Progress -->
<div class="detail-title">
<Icon icon="percent" />
<PhPercent />
{{ $t('task.attributes.percentDone') }}
</div>
<PercentDoneSelect
@@ -174,7 +174,7 @@
>
<!-- Start Date -->
<div class="detail-title">
<Icon icon="play" />
<PhPlay />
{{ $t('task.attributes.startDate') }}
</div>
<div class="date-input">
@@ -191,7 +191,7 @@
@click="() => {task.startDate = null;saveTask()}"
>
<span class="icon is-small">
<Icon icon="times" />
<PhX />
</span>
</BaseButton>
</div>
@@ -207,7 +207,7 @@
>
<!-- End Date -->
<div class="detail-title">
<Icon icon="stop" />
<PhStop />
{{ $t('task.attributes.endDate') }}
</div>
<div class="date-input">
@@ -224,7 +224,7 @@
@click="() => {task.endDate = null;saveTask()}"
>
<span class="icon is-small">
<Icon icon="times" />
<PhX />
</span>
</BaseButton>
</div>
@@ -240,7 +240,7 @@
>
<!-- Reminders -->
<div class="detail-title">
<Icon :icon="['far', 'clock']" />
<PhClock />
{{ $t('task.attributes.reminders') }}
</div>
<Reminders
@@ -262,7 +262,7 @@
<!-- Repeat after -->
<div class="is-flex is-justify-content-space-between">
<div class="detail-title">
<Icon icon="history" />
<PhClockCounterClockwise />
{{ $t('task.attributes.repeat') }}
</div>
<BaseButton
@@ -271,7 +271,7 @@
@click="removeRepeatAfter"
>
<span class="icon is-small">
<Icon icon="times" />
<PhX />
</span>
</BaseButton>
</div>
@@ -293,7 +293,7 @@
>
<!-- Color -->
<div class="detail-title">
<Icon icon="fill-drip" />
<PhPaintBucket />
{{ $t('task.attributes.color') }}
</div>
<ColorPicker
@@ -313,7 +313,7 @@
>
<div class="detail-title">
<span class="icon is-grey">
<Icon icon="tags" />
<PhTag />
</span>
{{ $t('task.attributes.labels') }}
</div>
@@ -365,7 +365,7 @@
>
<h3>
<span class="icon is-grey">
<Icon icon="sitemap" />
<PhTreeStructure />
</span>
{{ $t('task.attributes.relatedTasks') }}
</h3>
@@ -386,7 +386,7 @@
>
<h3>
<span class="icon is-grey">
<Icon icon="list" />
<PhList />
</span>
{{ $t('task.detail.move') }}
</h3>
@@ -426,10 +426,10 @@
v-shortcut="'t'"
:class="{'is-pending': !task.done}"
class="button--mark-done"
icon="check-double"
variant="secondary"
@click="toggleTaskDone()"
>
<template #icon><PhChecks /></template>
{{ task.done ? $t('task.detail.undone') : $t('task.detail.done') }}
</XButton>
<TaskSubscription
@@ -441,9 +441,9 @@
<XButton
v-shortcut="'s'"
variant="secondary"
:icon="task.isFavorite ? 'star' : ['far', 'star']"
@click="toggleFavorite"
>
<template #icon><PhStar :weight="task.isFavorite ? 'fill' : 'regular'" /></template>
{{
task.isFavorite ? $t('task.detail.actions.unfavorite') : $t('task.detail.actions.favorite')
}}
@@ -454,33 +454,32 @@
<XButton
v-shortcut="'l'"
variant="secondary"
icon="tags"
@click="setFieldActive('labels')"
>
<template #icon><PhTag /></template>
{{ $t('task.detail.actions.label') }}
</XButton>
<XButton
v-shortcut="'p'"
variant="secondary"
icon="exclamation-circle"
@click="setFieldActive('priority')"
>
<template #icon><PhWarningCircle /></template>
{{ $t('task.detail.actions.priority') }}
</XButton>
<XButton
variant="secondary"
icon="percent"
@click="setFieldActive('percentDone')"
>
<template #icon><PhPercent /></template>
{{ $t('task.detail.actions.percentDone') }}
</XButton>
<XButton
v-shortcut="'c'"
variant="secondary"
icon="fill-drip"
:icon-color="color"
@click="setFieldActive('color')"
>
<template #icon><PhPaintBucket :style="{color}" /></template>
{{ $t('task.detail.actions.color') }}
</XButton>
@@ -490,33 +489,33 @@
v-shortcut="'a'"
v-cy="'taskDetail.assign'"
variant="secondary"
icon="users"
@click="setFieldActive('assignees')"
>
<template #icon><PhUsers /></template>
{{ $t('task.detail.actions.assign') }}
</XButton>
<XButton
v-shortcut="'f'"
variant="secondary"
icon="paperclip"
@click="openAttachments()"
>
<template #icon><PhPaperclip /></template>
{{ $t('task.detail.actions.attachments') }}
</XButton>
<XButton
v-shortcut="'r'"
variant="secondary"
icon="sitemap"
@click="setRelatedTasksActive()"
>
<template #icon><PhTreeStructure /></template>
{{ $t('task.detail.actions.relatedTasks') }}
</XButton>
<XButton
v-shortcut="'m'"
variant="secondary"
icon="list"
@click="setFieldActive('moveProject')"
>
<template #icon><PhList /></template>
{{ $t('task.detail.actions.moveProject') }}
</XButton>
@@ -525,47 +524,47 @@
<XButton
v-shortcut="'d'"
variant="secondary"
icon="calendar"
@click="setFieldActive('dueDate')"
>
<template #icon><PhCalendar /></template>
{{ $t('task.detail.actions.dueDate') }}
</XButton>
<XButton
variant="secondary"
icon="play"
@click="setFieldActive('startDate')"
>
<template #icon><PhPlay /></template>
{{ $t('task.detail.actions.startDate') }}
</XButton>
<XButton
variant="secondary"
icon="stop"
@click="setFieldActive('endDate')"
>
<template #icon><PhStop /></template>
{{ $t('task.detail.actions.endDate') }}
</XButton>
<XButton
v-shortcut="reminderShortcut"
variant="secondary"
:icon="['far', 'clock']"
@click="setFieldActive('reminders')"
>
<template #icon><PhClock /></template>
{{ $t('task.detail.actions.reminders') }}
</XButton>
<XButton
variant="secondary"
icon="history"
@click="setFieldActive('repeatAfter')"
>
<template #icon><PhClockCounterClockwise /></template>
{{ $t('task.detail.actions.repeatAfter') }}
</XButton>
<XButton
v-shortcut="'Shift+Delete'"
icon="trash-alt"
:shadow="false"
class="is-danger is-outlined has-no-border"
@click="showDeleteModal = true"
>
<template #icon><PhTrash /></template>
{{ $t('task.detail.actions.delete') }}
</XButton>
</template>
@@ -588,7 +587,7 @@
:aria-label="$t('task.detail.scrollToBottom')"
@click="scrollToBottom"
>
<Icon icon="chevron-down" />
<PhCaretDown />
</BaseButton>
<Modal
@@ -631,6 +630,13 @@ import {PERMISSIONS} from '@/constants/permissions'
import BaseButton from '@/components/base/BaseButton.vue'
import {
PhArrowLeft, PhUsers, PhWarningCircle, PhCalendar, PhX, PhPercent,
PhPlay, PhStop, PhClock, PhClockCounterClockwise, PhPaintBucket,
PhTag, PhTreeStructure, PhList, PhChecks, PhStar, PhCaretDown,
PhTrash, PhPaperclip,
} from '@phosphor-icons/vue'
// partials
import Attachments from '@/components/tasks/partials/Attachments.vue'
import ChecklistSummary from '@/components/tasks/partials/ChecklistSummary.vue'

View File

@@ -57,9 +57,10 @@
<XButton
:loading="teamService.loading"
danger
icon="trash-alt"
@click="showDeleteModal = true"
/>
>
<template #icon><PhTrash /></template>
</XButton>
</div>
</div>
</Card>
@@ -95,9 +96,9 @@
</div>
<div class="control">
<XButton
icon="plus"
@click="addUser"
>
<template #icon><PhPlus /></template>
{{ $t('team.edit.addUser') }}
</XButton>
</div>
@@ -130,13 +131,13 @@
<td class="type">
<template v-if="m.admin">
<span class="icon is-small">
<Icon icon="lock" />
<PhLock />
</span>
{{ $t('team.attributes.admin') }}
</template>
<template v-else>
<span class="icon is-small">
<Icon icon="user" />
<PhUser />
</span>
{{ $t('team.attributes.member') }}
</template>
@@ -157,9 +158,10 @@
v-if="m.id !== userInfo.id"
:loading="teamMemberService.loading"
danger
icon="trash-alt"
@click="() => {memberToDelete = m; showUserDeleteModal = true}"
/>
>
<template #icon><PhTrash /></template>
</XButton>
</td>
</tr>
</tbody>
@@ -236,6 +238,8 @@ import {useI18n} from 'vue-i18n'
import {useRoute, useRouter} from 'vue-router'
import Editor from '@/components/input/AsyncEditor'
import {PhLock, PhPlus, PhTrash, PhUser} from '@phosphor-icons/vue'
import FancyCheckbox from '@/components/input/FancyCheckbox.vue'
import FormField from '@/components/input/FormField.vue'
import Multiselect from '@/components/input/Multiselect.vue'

View File

@@ -6,8 +6,9 @@
<XButton
:to="{name:'teams.create'}"
class="is-pulled-right"
icon="plus"
>
<template #icon><PhPlus /></template>
{{ $t('team.create.title') }}
</XButton>
@@ -44,6 +45,7 @@ import {ref, shallowReactive} from 'vue'
import { useI18n } from 'vue-i18n'
import TeamService from '@/services/team'
import {PhPlus} from '@phosphor-icons/vue'
import { useTitle } from '@/composables/useTitle'
const { t } = useI18n({useScope: 'global'})

View File

@@ -27,9 +27,7 @@
{{ text }}
</span>
<span class="ml-1 has-text-grey-light is-size-7">
<Icon
icon="arrow-up-right-from-square"
/>
<PhArrowSquareOut />
</span>
</BaseButton>
</li>
@@ -51,6 +49,7 @@ import { useAuthStore } from '@/stores/auth'
import {useRoute} from 'vue-router'
import BaseButton from '@/components/base/BaseButton.vue'
import {PhArrowSquareOut} from '@phosphor-icons/vue'
const { t } = useI18n({useScope: 'global'})
useTitle(() => t('user.settings.title'))

View File

@@ -6,6 +6,7 @@ import {parseScopesFromQuery} from '@/helpers/parseScopesFromQuery'
import {useFlatpickrLanguage} from '@/helpers/useFlatpickrLanguage'
import {formatDateSince, formatDisplayDate} from '@/helpers/time/formatDate'
import XButton from '@/components/input/Button.vue'
import {PhPlus} from '@phosphor-icons/vue'
import BaseButton from '@/components/base/BaseButton.vue'
import ApiTokenModel from '@/models/apiTokenModel'
import FancyCheckbox from '@/components/input/FancyCheckbox.vue'
@@ -381,11 +382,11 @@ function toggleGroupPermissionsFromChild(group: string, checked: boolean) {
<XButton
v-else
icon="plus"
class="mbe-4"
:loading="service.loading"
@click="() => showCreateForm = true"
>
<template #icon><PhPlus /></template>
{{ $t('user.settings.apiTokens.createAToken') }}
</XButton>

View File

@@ -15,9 +15,10 @@
<XButton
v-tooltip="$t('misc.copy')"
:shadow="false"
icon="paste"
@click="copy(caldavUrl)"
/>
>
<template #icon><PhClipboard /></template>
</XButton>
</template>
</FormField>
@@ -75,11 +76,11 @@
</Message>
<XButton
icon="plus"
class="mbe-4"
:loading="service.loading"
@click="createToken"
>
<template #icon><PhPlus /></template>
{{ $t('user.settings.caldav.createToken') }}
</XButton>
@@ -103,6 +104,7 @@ import {useTitle} from '@/composables/useTitle'
import {useCopyToClipboard} from '@/composables/useCopyToClipboard'
import {success} from '@/message'
import BaseButton from '@/components/base/BaseButton.vue'
import {PhClipboard, PhPlus} from '@phosphor-icons/vue'
import Message from '@/components/misc/Message.vue'
import FormField from '@/components/input/FormField.vue'
import CaldavTokenService from '@/services/caldavToken'