#8448 - devToTest #1254

Merged
alexm merged 365 commits from 8448-devToTest into test 2025-01-21 10:44:46 +00:00
7 changed files with 120 additions and 57 deletions
Showing only changes of commit c0d909b3e8 - Show all commits

View File

@ -141,13 +141,16 @@ const handleInsertMode = (e) => {
<QIcon <QIcon
name="close" name="close"
size="xs" size="xs"
v-if=" :style="{
hover && visibility:
value && hover &&
!$attrs.disabled && value &&
!$attrs.readonly && !$attrs.disabled &&
$props.clearable !$attrs.readonly &&
" $props.clearable
? 'visible'
: 'hidden',
}"
@click=" @click="
() => { () => {
value = null; value = null;

View File

@ -1,14 +1,16 @@
<script setup> <script setup>
import { onMounted, ref, watch } from 'vue'; import { onMounted, ref, computed, watch } from 'vue';
import { useQuasar } from 'quasar'; import { useQuasar } from 'quasar';
import { useArrayData } from 'composables/useArrayData'; import { useArrayData } from 'composables/useArrayData';
import VnInput from 'src/components/common/VnInput.vue'; import VnInput from 'src/components/common/VnInput.vue';
import { useI18n } from 'vue-i18n'; import { useI18n } from 'vue-i18n';
import { useStateStore } from 'src/stores/useStateStore'; import { useStateStore } from 'src/stores/useStateStore';
import { useRoute } from 'vue-router';
const quasar = useQuasar(); const quasar = useQuasar();
const { t } = useI18n(); const { t } = useI18n();
const state = useStateStore(); const state = useStateStore();
const route = useRoute();
const props = defineProps({ const props = defineProps({
dataKey: { dataKey: {
@ -83,6 +85,17 @@ if (props.redirect)
}; };
let arrayData = useArrayData(props.dataKey, arrayDataProps); let arrayData = useArrayData(props.dataKey, arrayDataProps);
let store = arrayData.store; let store = arrayData.store;
const to = computed(() => {
const url = { path: route.path, query: { ...(route.query ?? {}) } };
const searchUrl = arrayData.store.searchUrl;
const currentFilter = {
...arrayData.store.currentFilter,
search: searchText.value || undefined,
};
if (searchUrl) url.query[searchUrl] = JSON.stringify(currentFilter);
return url;
});
watch( watch(
() => props.dataKey, () => props.dataKey,
@ -132,23 +145,32 @@ async function search() {
<template> <template>
<Teleport to="#searchbar" v-if="state.isHeaderMounted()"> <Teleport to="#searchbar" v-if="state.isHeaderMounted()">
<QForm @submit="search" id="searchbarForm"> <QForm @submit="search" id="searchbarForm">
<RouterLink
:to="to"
@click="
!$event.shiftKey && !$event.ctrlKey && search();
$refs.input.focus();
"
>
<QIcon
v-if="!quasar.platform.is.mobile"
class="cursor-pointer"
name="search"
size="sm"
>
<QTooltip>{{ t('link') }}</QTooltip>
</QIcon>
</RouterLink>
<VnInput <VnInput
id="searchbar" id="searchbar"
ref="input"
v-model.trim="searchText" v-model.trim="searchText"
:placeholder="t(props.label)" :placeholder="t(props.label)"
dense dense
standout
autofocus autofocus
data-cy="vnSearchBar" data-cy="vn-searchbar"
borderless
> >
<template #prepend>
<QIcon
v-if="!quasar.platform.is.mobile"
class="cursor-pointer"
name="search"
@click="search"
/>
</template>
<template #append> <template #append>
<QIcon <QIcon
v-if="props.info && $q.screen.gt.xs" v-if="props.info && $q.screen.gt.xs"
@ -173,20 +195,52 @@ async function search() {
.q-field { .q-field {
transition: width 0.36s; transition: width 0.36s;
} }
</style>
<style lang="scss"> :deep(.q-field__native) {
padding-top: 10px;
padding-left: 5px;
}
:deep(.q-field--dark .q-field__native:focus) {
color: black;
}
:deep(.q-field--focused) {
.q-icon {
color: black;
}
}
.cursor-info { .cursor-info {
cursor: help; cursor: help;
} }
#searchbar {
.q-field--standout.q-field--highlighted .q-field__control { .q-form {
display: flex;
align-items: center;
border-radius: 4px;
padding: 0 5px;
background-color: var(--vn-search-color);
&:hover {
background-color: var(--vn-search-color-hover);
}
&:focus-within {
background-color: white; background-color: white;
color: black;
.q-field__native,
.q-icon { .q-icon {
color: black !important; color: black;
} }
} }
} }
.q-icon {
color: var(--vn-label-color);
}
</style> </style>
<i18n>
en:
link: click to search, ctrl + click to open in a new tab, shift + click to open in a new window
es:
link: clic para buscar, ctrl + clic para abrir en una nueva pestaña, shift + clic para abrir en una nueva ventana
</i18n>

View File

@ -76,26 +76,7 @@ export function useArrayData(key = useRoute().meta.moduleName, userOptions) {
cancelRequest(); cancelRequest();
canceller = new AbortController(); canceller = new AbortController();
const { params, limit } = getCurrentFilter();
const filter = {
limit: store.limit,
};
let userParams = { ...store.userParams };
Object.assign(filter, store.userFilter);
let where;
if (filter?.where || store.filter?.where)
where = Object.assign(filter?.where ?? {}, store.filter?.where ?? {});
Object.assign(filter, store.filter);
filter.where = where;
const params = { filter };
Object.assign(params, userParams);
if (params.filter) params.filter.skip = store.skip;
if (store?.order && typeof store?.order == 'string') store.order = [store.order];
if (store.order?.length) params.filter.order = [...store.order];
else delete params.filter.order;
store.currentFilter = JSON.parse(JSON.stringify(params)); store.currentFilter = JSON.parse(JSON.stringify(params));
delete store.currentFilter.filter.include; delete store.currentFilter.filter.include;
@ -121,7 +102,6 @@ export function useArrayData(key = useRoute().meta.moduleName, userOptions) {
params, params,
}); });
const { limit } = filter;
store.hasMoreData = limit && response.data.length >= limit; store.hasMoreData = limit && response.data.length >= limit;
processData(response.data, { map: !!store.mapKey, append }); processData(response.data, { map: !!store.mapKey, append });
@ -291,6 +271,31 @@ export function useArrayData(key = useRoute().meta.moduleName, userOptions) {
router.replace(newUrl); router.replace(newUrl);
} }
function getCurrentFilter() {
const filter = {
limit: store.limit,
};
let userParams = { ...store.userParams };
Object.assign(filter, store.userFilter);
let where;
if (filter?.where || store.filter?.where)
where = Object.assign(filter?.where ?? {}, store.filter?.where ?? {});
Object.assign(filter, store.filter);
filter.where = where;
const params = { filter };
Object.assign(params, userParams);
if (params.filter) params.filter.skip = store.skip;
if (store?.order && typeof store?.order == 'string') store.order = [store.order];
if (store.order?.length) params.filter.order = [...store.order];
else delete params.filter.order;
return { filter, params, limit: filter.limit };
}
function processData(data, { map = true, append = true }) { function processData(data, { map = true, append = true }) {
if (!append) { if (!append) {
store.data = []; store.data = [];
@ -323,6 +328,7 @@ export function useArrayData(key = useRoute().meta.moduleName, userOptions) {
fetch, fetch,
applyFilter, applyFilter,
addFilter, addFilter,
getCurrentFilter,
addFilterWhere, addFilterWhere,
addOrder, addOrder,
deleteOrder, deleteOrder,

View File

@ -10,6 +10,8 @@ body.body--light {
--vn-text-color: black; --vn-text-color: black;
--vn-label-color: #5f5f5f; --vn-label-color: #5f5f5f;
--vn-accent-color: #e7e3e3; --vn-accent-color: #e7e3e3;
--vn-search-color: #d4d4d4;
--vn-search-color-hover: #cfcfcf;
--vn-empty-tag: #acacac; --vn-empty-tag: #acacac;
--vn-black-text-color: black; --vn-black-text-color: black;
--vn-text-color-contrast: white; --vn-text-color-contrast: white;
@ -28,6 +30,8 @@ body.body--dark {
--vn-text-color: white; --vn-text-color: white;
--vn-label-color: #a8a8a8; --vn-label-color: #a8a8a8;
--vn-accent-color: #424242; --vn-accent-color: #424242;
--vn-search-color: #4b4b4b;
--vn-search-color-hover: #5b5b5b;
--vn-empty-tag: #2d2d2d; --vn-empty-tag: #2d2d2d;
--vn-black-text-color: black; --vn-black-text-color: black;
--vn-text-color-contrast: black; --vn-text-color-contrast: black;

View File

@ -41,7 +41,7 @@ describe('OrderCatalog', () => {
} }
}); });
cy.get( cy.get(
'[data-cy="vnSearchBar"] > .q-field > .q-field__inner > .q-field__control' '[data-cy="vn-searchbar"] > .q-field > .q-field__inner > .q-field__control'
).type('{enter}'); ).type('{enter}');
cy.get(':nth-child(1) > [data-cy="catalogFilterCategory"]').click(); cy.get(':nth-child(1) > [data-cy="catalogFilterCategory"]').click();
cy.dataCy('catalogFilterValueDialogBtn').last().click(); cy.dataCy('catalogFilterValueDialogBtn').last().click();

View File

@ -9,9 +9,9 @@ describe('TicketList', () => {
}); });
const searchResults = (search) => { const searchResults = (search) => {
cy.dataCy('vnSearchBar').find('input').focus(); cy.dataCy('vn-searchbar').find('input').focus();
if (search) cy.dataCy('vnSearchBar').find('input').type(search); if (search) cy.dataCy('vn-searchbar').find('input').type(search);
cy.dataCy('vnSearchBar').find('input').type('{enter}'); cy.dataCy('vn-searchbar').find('input').type('{enter}');
cy.dataCy('ticketListTable').should('exist'); cy.dataCy('ticketListTable').should('exist');
cy.get(firstRow).should('exist'); cy.get(firstRow).should('exist');
}; };

View File

@ -274,15 +274,11 @@ Cypress.Commands.add('openLeftMenu', (element) => {
Cypress.Commands.add('clearSearchbar', (element) => { Cypress.Commands.add('clearSearchbar', (element) => {
if (element) cy.waitForElement(element); if (element) cy.waitForElement(element);
cy.get( cy.get('[data-cy="vn-searchbar"]').clear();
'#searchbar > form > div:nth-child(1) > label > div:nth-child(1) input'
).clear();
}); });
Cypress.Commands.add('typeSearchbar', (value) => { Cypress.Commands.add('writeSearchbar', (value) => {
cy.get('#searchbar > form > div:nth-child(1) > label > div:nth-child(1) input').type( cy.get('[data-cy="vn-searchbar"]').type(value);
value
);
}); });
Cypress.Commands.add('validateContent', (selector, expectedValue) => { Cypress.Commands.add('validateContent', (selector, expectedValue) => {