Skip to content

Commit

Permalink
feat: add form step to batch search
Browse files Browse the repository at this point in the history
  • Loading branch information
caro3801 committed Dec 6, 2024
1 parent f7959d8 commit 8d49c94
Show file tree
Hide file tree
Showing 8 changed files with 220 additions and 70 deletions.
9 changes: 8 additions & 1 deletion src/components/Form/FormControl/FormControlTerm.vue
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,14 @@ defineProps({
@update:modelValue="$emit('update:modelValue', $event)"
>
<template #tag="{ tag, removeTag }">
<search-breadcrumb-form-entry class="p-0" :query="tag" :size="size" no-occurrences no-caret @click="removeTag(tag)" />
<search-breadcrumb-form-entry
class="p-0"
:query="tag"
:size="size"
no-occurrences
no-caret
@click="removeTag(tag)"
/>
</template>
</form-control-tag>
</template>
Expand Down
7 changes: 5 additions & 2 deletions src/components/Form/FormCreation.vue
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,9 @@ const props = defineProps({
type: Boolean,
default: true
},
contentClassList: {
type: String
},
submitLabel: {
type: String
},
Expand All @@ -32,10 +35,10 @@ function submit(values) {

<template>
<b-form class="form-creation" novalidate @reset.stop.prevent="reset" @submit.stop.prevent="submit">
<div aria-description="form-content">
<div aria-description="form-content" :class="contentClassList">
<slot></slot>
</div>
<div class="d-flex justify-content-end" aria-description="form-footer">
<div class="d-flex justify-content-end mb-4" aria-description="form-footer">
<span class="d-flex gap-2">
<button-icon
type="reset"
Expand Down
16 changes: 15 additions & 1 deletion src/components/Form/FormFieldset/FormFieldset.vue
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,9 @@ const props = defineProps({
},
withDescription: {
type: Boolean
},
labelVisuallyHidden: {
type: Boolean
}
})
Expand All @@ -55,6 +58,16 @@ const classList = computed(() => {
'form-fieldset--required': props.required
}
})
const labelColsSm = computed(() => {
return props.labelVisuallyHidden ? null : props.labelColsSm
})
const labelColsMd = computed(() => {
return props.labelVisuallyHidden ? null : props.labelColsMd
})
const labelColsLg = computed(() => {
return props.labelVisuallyHidden ? null : props.labelColsLg
})
</script>

<template>
Expand All @@ -68,6 +81,7 @@ const classList = computed(() => {
:label="label"
:label-for="labelFor"
:description="compact ? description : null"
:label-visually-hidden="labelVisuallyHidden"
>
<template #label>
<div class="form-fieldset__label text-body-emphasis">
Expand All @@ -88,7 +102,7 @@ const classList = computed(() => {
</div>
</template>
<template v-else>
<div class="row">
<div class="row gap-3">
<slot v-bind="{ compact }" />
</div>
</template>
Expand Down
6 changes: 5 additions & 1 deletion src/components/Form/FormFieldset/FormFieldsetI18n.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,10 @@ const props = defineProps({
translationKey: {
type: String
},
descriptionSide: { type: Boolean, default: false }
descriptionSide: { type: Boolean, default: false },
labelVisuallyHidden: {
type: Boolean
}
})
const { te, t } = useI18n()
Expand All @@ -32,6 +35,7 @@ const description = computed(() =>
:label-for="labelFor"
:description="description"
:description-side="descriptionSide"
:label-visually-hidden="labelVisuallyHidden"
>
<slot v-bind="{ name: labelFor, ...slotProps }"></slot>
</form-fieldset>
Expand Down
5 changes: 4 additions & 1 deletion src/components/Form/FormStep/FormStep.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@ defineProps({
index: {
type: Number,
required: true
},
contentClass: {
type: String
}
})
Expand All @@ -27,7 +30,7 @@ const classList = computed(() => ({
<slot name="title" />
</template>
</form-step-heading>
<form-step-content :collapse="collapse" class="ms-md-5">
<form-step-content :collapse="collapse" class="ms-md-5" :class="contentClass">
<slot />
</form-step-content>
</div>
Expand Down
193 changes: 131 additions & 62 deletions src/components/Task/TaskBatchSearch/TaskBatchSearchForm.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<script setup>
import { computed, ref, toRef } from 'vue'
import { computed, ref, toRef, reactive } from 'vue'
import { useI18n } from 'vue-i18n'
import FormStep from '@/components/Form/FormStep/FormStep'
import FormFieldsetI18n from '@/components/Form/FormFieldset/FormFieldsetI18n'
import SearchBarInputDropdownForProjects from '@/components/Search/SearchBar/SearchBarInputDropdownForProjects'
import FormCreation from '@/components/Form/FormCreation'
Expand Down Expand Up @@ -37,12 +38,14 @@ const description = ref('')
const csvFile = ref(null)
const phraseMatch = ref(true)
const phraseMatchOptions = computed(() => [
{ text: t('task.documents.form.extractOcr.options.yes'), value: true },
{ text: t('task.documents.form.extractOcr.options.no'), value: false }
{ text: t('task.batch-search.form.phraseMatch.options.yes'), value: true },
{ text: t('task.batch-search.form.phraseMatch.options.no'), value: false }
])
const phraseChanges = ref(2)
/* const paths = ref([]) */
const changesLevelKey = computed(() => {
return phraseMatch.value ? 'task.batch-search.form.phraseChanges' : 'task.batch-search.form.spellingChanges'
})
const projectNames = computed(() => {
return selectedProjects.value.map((p) => p.name)
})
Expand Down Expand Up @@ -103,73 +106,139 @@ const filterContentType = f({
})
const visibility = ref(true)
const visibilityOptions = computed(() => [
{ text: t('task.documents.form.visibility.options.shared'), value: true },
{ text: t('task.documents.form.visibility.options.private'), value: false }
{ text: t('task.batch-search.form.visibility.options.shared'), value: true },
{ text: t('task.batch-search.form.visibility.options.private'), value: false }
])
const sections = reactive({
general: { title: computed(() => t('task.batch-search.form.section.general')), collapse: false },
queries: { title: computed(() => t('task.batch-search.form.section.queries')), collapse: false },
search: { title: computed(() => t('task.batch-search.form.section.operators')), collapse: false },
filters: { title: computed(() => t('task.batch-search.form.section.filters')), collapse: false },
visibility: { title: computed(() => t('task.batch-search.form.section.visibility')), collapse: false }
})
</script>

<template>
<form-creation
class="task-batch-search-form"
class="task-batch-search-form d-flex flex-column gap-4"
content-class-list="d-flex flex-column gap-3"
:valid="valid"
:submit-label="submitLabel"
@reset="reset"
@submit="submit"
>
<form-fieldset-i18n name="name" translation-key="task.batch-search.form.name">
<b-form-input v-model="name" type="text" />
</form-fieldset-i18n>
<form-fieldset-i18n name="projects" translation-key="task.batch-search.form.projects">
<search-bar-input-dropdown-for-projects v-model="selectedProjects" />
</form-fieldset-i18n>
<form-fieldset-i18n name="description" translation-key="task.batch-search.form.description">
<b-form-textarea v-model="description" type="text" placeholder="task.batch-search.form.description.placeholder" />
</form-fieldset-i18n>
<form-fieldset-i18n name="csvFile" translation-key="task.batch-search.form.csvFile">
<b-form-file
v-model="csvFile"
:placeholder="$t('task.batch-search.form.csvFile.placeholder')"
:state="!!csvFile"
accept=".csv"
class="text-truncate"
no-drop
required
></b-form-file>
<div>
<ul>
<li>Only <abbr>CSV</abbr> format is accepted Export your spreadsheet as a CSV using encoding UTF-8</li>
<li>Your <abbr>CSV</abbr> file should not contain more than 60,000 queries</li>
<li>The first and only column should contain the terms to search No line break(s) in cells</li>
<li>
Selecting 'do phrase matches' prevent from using operators like <code>AND</code>, <code>OR</code>,
<code>NOT</code>, <code>*</code>, <code>?</code>, <code>!</code>, <code>+</code>, <code>-</code> or Regexes
(between 2 slashes).
</li>
</ul>
</div>
</form-fieldset-i18n>
<form-fieldset-i18n name="phraseMatch" translation-key="task.batch-search.form.phraseMatch">
<b-form-radio-group v-model="phraseMatch" name="extract-ocr" :options="phraseMatchOptions" stacked />
</form-fieldset-i18n>
<form-fieldset-i18n name="phraseChanges" translation-key="task.batch-search.form.phraseChanges">
<form-control-range v-model="phraseChanges" :min="0" :max="5" :step="1" />
</form-fieldset-i18n>

<form-fieldset-i18n name="path" translation-key="task.batch-search.form.path">
<filter-type-path :filter="filterPath" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n name="tags-included" translation-key="task.batch-search.form.tag-included">
<filter-type :filter="filterTag" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n name="tags-excluded" translation-key="task.batch-search.form.tags-excluded">
<filter-type :filter="filterTagExcluded" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n name="content-types" translation-key="task.batch-search.form.content-types">
<filter-type :filter="filterContentType" :projects="projectNames" />
</form-fieldset-i18n>

<form-fieldset-i18n name="visibility" translation-key="task.batch-search.form.visibility">
<b-form-radio-group v-model="visibility" name="visibility" :options="visibilityOptions" stacked />
</form-fieldset-i18n>
<form-step v-model:collapse="sections.general.collapse" :title="sections.general.title" index="1">
<form-fieldset-i18n name="name" translation-key="task.batch-search.form.name">
<b-form-input v-model="name" type="text" :placeholder="t('task.batch-search.form.name.placeholder')" />
</form-fieldset-i18n>
<form-fieldset-i18n name="projects" translation-key="task.batch-search.form.projects">
<search-bar-input-dropdown-for-projects v-model="selectedProjects" />
</form-fieldset-i18n>
<form-fieldset-i18n name="description" translation-key="task.batch-search.form.description">
<b-form-textarea
v-model="description"
type="text"
:placeholder="t('task.batch-search.form.description.placeholder')"
/>
</form-fieldset-i18n>
</form-step>
<form-step v-model:collapse="sections.queries.collapse" :title="sections.queries.title" index="2">
<form-fieldset-i18n name="csvFile" translation-key="task.batch-search.form.csvFile">
<b-form-file
v-model="csvFile"
:placeholder="$t('task.batch-search.form.csvFile.placeholder')"
:state="!!csvFile"
accept=".csv"
class="text-truncate"
no-drop
required
></b-form-file>
<div class="bg-tertiary-subtle rounded-2 p-3">
<ul class="m-0">
<li>Only <abbr>CSV</abbr> format is accepted Export your spreadsheet as a CSV using encoding UTF-8</li>
<li>Your <abbr>CSV</abbr> file should not contain more than 60,000 queries</li>
<li>The first and only column should contain the terms to search No line break(s) in cells</li>
<li>
Selecting 'do phrase matches' prevent from using operators like <code>AND</code>, <code>OR</code>,
<code>NOT</code>, <code>*</code>, <code>?</code>, <code>!</code>, <code>+</code>, <code>-</code> or
Regexes (between 2 slashes).
</li>
</ul>
</div>
</form-fieldset-i18n>
</form-step>
<form-step v-model:collapse="sections.search.collapse" :title="sections.search.title" index="3">
<form-fieldset-i18n name="phraseMatch" translation-key="task.batch-search.form.phraseMatch">
<b-form-radio-group v-model="phraseMatch" name="phraseMatch" :options="phraseMatchOptions" stacked />
</form-fieldset-i18n>
<form-fieldset-i18n name="phraseChanges" :translation-key="changesLevelKey">
<form-control-range v-model="phraseChanges" :min="0" :max="3" :step="1" />
</form-fieldset-i18n>
</form-step>
<form-step
v-model:collapse="sections.filters.collapse"
class="form-step__filters"
:title="sections.filters.title"
index="4"
>
<form-fieldset-i18n
class="form-step-sub-content"
label-visually-hidden
name="path"
translation-key="task.batch-search.form.path"
>
<filter-type-path :filter="filterPath" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n
class="form-step-sub-content"
label-visually-hidden
name="tags-included"
translation-key="task.batch-search.form.tag-included"
>
<filter-type :filter="filterTag" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n
label-visually-hidden
name="tags-excluded"
class="form-step-sub-content"
translation-key="task.batch-search.form.tags-excluded"
>
<filter-type :filter="filterTagExcluded" :projects="projectNames" />
</form-fieldset-i18n>
<form-fieldset-i18n
label-visually-hidden
class="form-step-sub-content"
name="content-types"
translation-key="task.batch-search.form.content-types"
>
<filter-type :filter="filterContentType" :projects="projectNames" />
</form-fieldset-i18n>
</form-step>
<form-step v-model:collapse="sections.visibility.collapse" :title="sections.visibility.title" index="5">
<form-fieldset-i18n label-visually-hidden name="visibility" translation-key="task.batch-search.form.visibility">
<b-form-radio-group
v-model="visibility"
name="visibility"
:options="visibilityOptions"
stacked
/> </form-fieldset-i18n
></form-step>
</form-creation>
</template>
<style lang="scss">
.task-batch-search-form {
& .project-dropdown-selector {
padding: 0;
}
& .form-step__filters {
& .form-step-content {
background: none;
padding: 0 !important;
}
& .form-step-sub-content .filters-panel-section-filter {
background: $white;
}
}
}
</style>
2 changes: 0 additions & 2 deletions src/components/Task/TaskList.vue
Original file line number Diff line number Diff line change
Expand Up @@ -70,8 +70,6 @@
</template>

<script setup>
import { useStore } from 'vuex'
import PageTable from '@/components/PageTable/PageTable'
import PageTableTr from '@/components/PageTable/PageTableTr'
import PageTableTh from '@/components/PageTable/PageTableTh'
Expand Down
Loading

0 comments on commit 8d49c94

Please sign in to comment.