mirror of
https://github.com/willmiao/ComfyUI-Lora-Manager.git
synced 2026-03-25 07:05:43 -03:00
Add name pattern filtering to LoRA Pool node allowing users to filter LoRAs by filename or model name using either plain text or regex patterns. Features: - Include patterns: only show LoRAs matching at least one pattern - Exclude patterns: exclude LoRAs matching any pattern - Regex toggle: switch between substring and regex matching - Case-insensitive matching for both modes - Invalid regex automatically falls back to substring matching - Filters apply to both file_name and model_name fields Backend: - Update LoraPoolLM._default_config() with namePatterns structure - Add name pattern filtering to _apply_pool_filters() and _apply_specific_filters() - Add API parameter parsing for name_pattern_include/exclude/use_regex - Update LoraPoolConfig type with namePatterns field Frontend: - Add NamePatternsSection.vue component with pattern input UI - Update useLoraPoolState to manage pattern state and API integration - Update LoraPoolSummaryView to display NamePatternsSection - Increase LORA_POOL_WIDGET_MIN_HEIGHT to accommodate new UI Tests: - Add 7 test cases covering text/regex include, exclude, combined filtering, model name fallback, and invalid regex handling Closes #839
116 lines
3.3 KiB
Vue
116 lines
3.3 KiB
Vue
<template>
|
|
<div class="summary-view">
|
|
<!-- Filter sections -->
|
|
<div class="summary-view__filters">
|
|
<BaseModelSection
|
|
:selected="selectedBaseModels"
|
|
:models="availableBaseModels"
|
|
@edit="$emit('open-modal', 'baseModels')"
|
|
/>
|
|
|
|
<TagsSection
|
|
:include-tags="includeTags"
|
|
:exclude-tags="excludeTags"
|
|
@edit-include="$emit('open-modal', 'includeTags')"
|
|
@edit-exclude="$emit('open-modal', 'excludeTags')"
|
|
/>
|
|
|
|
<FoldersSection
|
|
:include-folders="includeFolders"
|
|
:exclude-folders="excludeFolders"
|
|
@update:include-folders="$emit('update:includeFolders', $event)"
|
|
@update:exclude-folders="$emit('update:excludeFolders', $event)"
|
|
@edit-include="$emit('open-modal', 'includeFolders')"
|
|
@edit-exclude="$emit('open-modal', 'excludeFolders')"
|
|
/>
|
|
|
|
<NamePatternsSection
|
|
:include-patterns="includePatterns"
|
|
:exclude-patterns="excludePatterns"
|
|
:use-regex="useRegex"
|
|
@update:include-patterns="$emit('update:includePatterns', $event)"
|
|
@update:exclude-patterns="$emit('update:excludePatterns', $event)"
|
|
@update:use-regex="$emit('update:useRegex', $event)"
|
|
/>
|
|
|
|
<LicenseSection
|
|
:no-credit-required="noCreditRequired"
|
|
:allow-selling="allowSelling"
|
|
@update:no-credit-required="$emit('update:noCreditRequired', $event)"
|
|
@update:allow-selling="$emit('update:allowSelling', $event)"
|
|
/>
|
|
</div>
|
|
|
|
<!-- Preview -->
|
|
<LoraPoolPreview
|
|
:items="previewItems"
|
|
:match-count="matchCount"
|
|
:is-loading="isLoading"
|
|
@refresh="$emit('refresh')"
|
|
/>
|
|
</div>
|
|
</template>
|
|
|
|
<script setup lang="ts">
|
|
import BaseModelSection from './sections/BaseModelSection.vue'
|
|
import TagsSection from './sections/TagsSection.vue'
|
|
import FoldersSection from './sections/FoldersSection.vue'
|
|
import NamePatternsSection from './sections/NamePatternsSection.vue'
|
|
import LicenseSection from './sections/LicenseSection.vue'
|
|
import LoraPoolPreview from './LoraPoolPreview.vue'
|
|
import type { BaseModelOption, LoraItem } from '../../composables/types'
|
|
import type { ModalType } from '../../composables/useModalState'
|
|
|
|
defineProps<{
|
|
// Base models
|
|
selectedBaseModels: string[]
|
|
availableBaseModels: BaseModelOption[]
|
|
// Tags
|
|
includeTags: string[]
|
|
excludeTags: string[]
|
|
// Folders
|
|
includeFolders: string[]
|
|
excludeFolders: string[]
|
|
// Name patterns
|
|
includePatterns: string[]
|
|
excludePatterns: string[]
|
|
useRegex: boolean
|
|
// License
|
|
noCreditRequired: boolean
|
|
allowSelling: boolean
|
|
// Preview
|
|
previewItems: LoraItem[]
|
|
matchCount: number
|
|
isLoading: boolean
|
|
}>()
|
|
|
|
defineEmits<{
|
|
'open-modal': [modal: ModalType]
|
|
'update:includeFolders': [value: string[]]
|
|
'update:excludeFolders': [value: string[]]
|
|
'update:includePatterns': [value: string[]]
|
|
'update:excludePatterns': [value: string[]]
|
|
'update:useRegex': [value: boolean]
|
|
'update:noCreditRequired': [value: boolean]
|
|
'update:allowSelling': [value: boolean]
|
|
refresh: []
|
|
}>()
|
|
</script>
|
|
|
|
<style scoped>
|
|
.summary-view {
|
|
display: flex;
|
|
flex-direction: column;
|
|
height: 100%;
|
|
}
|
|
|
|
.summary-view__filters {
|
|
flex: 1;
|
|
overflow-y: auto;
|
|
padding-right: 4px;
|
|
margin-right: -4px;
|
|
/* Allow flex item to shrink below content size */
|
|
min-height: 0;
|
|
}
|
|
</style>
|