cjm-transcript-source-select 0.0.3__tar.gz → 0.0.5__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {cjm_transcript_source_select-0.0.3/cjm_transcript_source_select.egg-info → cjm_transcript_source_select-0.0.5}/PKG-INFO +24 -23
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/README.md +23 -22
- cjm_transcript_source_select-0.0.5/cjm_transcript_source_select/__init__.py +1 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/selection_queue.py +2 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/source_browser.py +11 -7
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/step_renderer.py +3 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/html_ids.py +3 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/core.py +35 -15
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5/cjm_transcript_source_select.egg-info}/PKG-INFO +24 -23
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/settings.ini +1 -1
- cjm_transcript_source_select-0.0.3/cjm_transcript_source_select/__init__.py +0 -1
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/LICENSE +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/MANIFEST.in +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/_modidx.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/__init__.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/helpers.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/local_files.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/components/preview_panel.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/models.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/__init__.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/filtering.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/init.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/local_files.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/queue.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/routes/tabs.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/services/__init__.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/services/source.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/services/source_utils.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select/utils.py +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/SOURCES.txt +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/dependency_links.txt +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/entry_points.txt +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/not-zip-safe +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/requires.txt +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/cjm_transcript_source_select.egg-info/top_level.txt +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/pyproject.toml +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/setup.cfg +0 -0
- {cjm_transcript_source_select-0.0.3 → cjm_transcript_source_select-0.0.5}/setup.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.2
|
|
2
2
|
Name: cjm-transcript-source-select
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.5
|
|
4
4
|
Summary: FastHTML source selection component for transcript decomposition workflows, with federated database browsing, drag-drop ordering, and keyboard navigation.
|
|
5
5
|
Home-page: https://github.com/cj-mills/cjm-transcript-source-select
|
|
6
6
|
Author: Christian J. Mills
|
|
@@ -109,48 +109,48 @@ graph LR
|
|
|
109
109
|
components_source_browser --> services_source_utils
|
|
110
110
|
components_source_browser --> html_ids
|
|
111
111
|
components_step_renderer --> components_selection_queue
|
|
112
|
-
components_step_renderer --> components_preview_panel
|
|
113
112
|
components_step_renderer --> components_local_files
|
|
114
|
-
components_step_renderer --> components_source_browser
|
|
115
113
|
components_step_renderer --> components_helpers
|
|
116
|
-
components_step_renderer --> utils
|
|
117
|
-
components_step_renderer --> html_ids
|
|
118
114
|
components_step_renderer --> models
|
|
115
|
+
components_step_renderer --> components_source_browser
|
|
116
|
+
components_step_renderer --> html_ids
|
|
117
|
+
components_step_renderer --> components_preview_panel
|
|
118
|
+
components_step_renderer --> utils
|
|
119
119
|
routes_core --> components_step_renderer
|
|
120
|
-
routes_core --> services_source
|
|
121
120
|
routes_core --> models
|
|
122
|
-
routes_core --> html_ids
|
|
123
|
-
routes_core --> components_selection_queue
|
|
124
121
|
routes_core --> components_source_browser
|
|
125
|
-
|
|
126
|
-
|
|
122
|
+
routes_core --> services_source
|
|
123
|
+
routes_core --> components_selection_queue
|
|
124
|
+
routes_core --> html_ids
|
|
127
125
|
routes_filtering --> routes_core
|
|
128
126
|
routes_filtering --> components_source_browser
|
|
127
|
+
routes_filtering --> services_source_utils
|
|
129
128
|
routes_filtering --> models
|
|
130
|
-
|
|
131
|
-
routes_init --> routes_local_files
|
|
132
|
-
routes_init --> services_source
|
|
133
|
-
routes_init --> routes_tabs
|
|
134
|
-
routes_init --> models
|
|
129
|
+
routes_filtering --> services_source
|
|
135
130
|
routes_init --> routes_core
|
|
136
131
|
routes_init --> routes_queue
|
|
132
|
+
routes_init --> models
|
|
133
|
+
routes_init --> services_source
|
|
134
|
+
routes_init --> routes_tabs
|
|
135
|
+
routes_init --> routes_filtering
|
|
136
|
+
routes_init --> routes_local_files
|
|
137
137
|
routes_local_files --> services_source
|
|
138
138
|
routes_local_files --> routes_core
|
|
139
139
|
routes_local_files --> models
|
|
140
140
|
routes_local_files --> components_local_files
|
|
141
141
|
routes_queue --> routes_core
|
|
142
142
|
routes_queue --> components_preview_panel
|
|
143
|
+
routes_queue --> models
|
|
143
144
|
routes_queue --> services_source
|
|
144
145
|
routes_queue --> services_source_utils
|
|
145
|
-
routes_queue --> models
|
|
146
|
-
routes_tabs --> routes_local_files
|
|
147
|
-
routes_tabs --> components_source_browser
|
|
148
|
-
routes_tabs --> services_source_utils
|
|
149
|
-
routes_tabs --> services_source
|
|
150
146
|
routes_tabs --> routes_core
|
|
151
147
|
routes_tabs --> models
|
|
152
|
-
routes_tabs -->
|
|
148
|
+
routes_tabs --> services_source
|
|
153
149
|
routes_tabs --> components_step_renderer
|
|
150
|
+
routes_tabs --> components_source_browser
|
|
151
|
+
routes_tabs --> routes_local_files
|
|
152
|
+
routes_tabs --> components_local_files
|
|
153
|
+
routes_tabs --> services_source_utils
|
|
154
154
|
```
|
|
155
155
|
|
|
156
156
|
*51 cross-module dependencies detected*
|
|
@@ -203,8 +203,8 @@ def _render_duplicate_flash(
|
|
|
203
203
|
candidate_provider_id: str, # Provider ID of the row the user clicked
|
|
204
204
|
existing_record_id: str, # Record ID of the conflicting selected row
|
|
205
205
|
existing_provider_id: str, # Provider ID of the conflicting selected row
|
|
206
|
-
) ->
|
|
207
|
-
"Render a
|
|
206
|
+
) -> Div: # OOB Div with flash script (replaces previous via innerHTML swap)
|
|
207
|
+
"Render a fixed-ID container with flash script for two source rows."
|
|
208
208
|
```
|
|
209
209
|
|
|
210
210
|
``` python
|
|
@@ -1043,6 +1043,7 @@ def _render_source_row(
|
|
|
1043
1043
|
remove_url: str, # URL for removing from queue
|
|
1044
1044
|
preview_url: str, # URL for previewing content
|
|
1045
1045
|
is_first: bool = False, # Whether this is the first row (gets initial focus)
|
|
1046
|
+
row_index: int = 0, # Index among selectable rows (for keyboard focus sync)
|
|
1046
1047
|
) -> Any: # Table row element
|
|
1047
1048
|
"Render a single source row in the browser table."
|
|
1048
1049
|
```
|
|
@@ -66,48 +66,48 @@ graph LR
|
|
|
66
66
|
components_source_browser --> services_source_utils
|
|
67
67
|
components_source_browser --> html_ids
|
|
68
68
|
components_step_renderer --> components_selection_queue
|
|
69
|
-
components_step_renderer --> components_preview_panel
|
|
70
69
|
components_step_renderer --> components_local_files
|
|
71
|
-
components_step_renderer --> components_source_browser
|
|
72
70
|
components_step_renderer --> components_helpers
|
|
73
|
-
components_step_renderer --> utils
|
|
74
|
-
components_step_renderer --> html_ids
|
|
75
71
|
components_step_renderer --> models
|
|
72
|
+
components_step_renderer --> components_source_browser
|
|
73
|
+
components_step_renderer --> html_ids
|
|
74
|
+
components_step_renderer --> components_preview_panel
|
|
75
|
+
components_step_renderer --> utils
|
|
76
76
|
routes_core --> components_step_renderer
|
|
77
|
-
routes_core --> services_source
|
|
78
77
|
routes_core --> models
|
|
79
|
-
routes_core --> html_ids
|
|
80
|
-
routes_core --> components_selection_queue
|
|
81
78
|
routes_core --> components_source_browser
|
|
82
|
-
|
|
83
|
-
|
|
79
|
+
routes_core --> services_source
|
|
80
|
+
routes_core --> components_selection_queue
|
|
81
|
+
routes_core --> html_ids
|
|
84
82
|
routes_filtering --> routes_core
|
|
85
83
|
routes_filtering --> components_source_browser
|
|
84
|
+
routes_filtering --> services_source_utils
|
|
86
85
|
routes_filtering --> models
|
|
87
|
-
|
|
88
|
-
routes_init --> routes_local_files
|
|
89
|
-
routes_init --> services_source
|
|
90
|
-
routes_init --> routes_tabs
|
|
91
|
-
routes_init --> models
|
|
86
|
+
routes_filtering --> services_source
|
|
92
87
|
routes_init --> routes_core
|
|
93
88
|
routes_init --> routes_queue
|
|
89
|
+
routes_init --> models
|
|
90
|
+
routes_init --> services_source
|
|
91
|
+
routes_init --> routes_tabs
|
|
92
|
+
routes_init --> routes_filtering
|
|
93
|
+
routes_init --> routes_local_files
|
|
94
94
|
routes_local_files --> services_source
|
|
95
95
|
routes_local_files --> routes_core
|
|
96
96
|
routes_local_files --> models
|
|
97
97
|
routes_local_files --> components_local_files
|
|
98
98
|
routes_queue --> routes_core
|
|
99
99
|
routes_queue --> components_preview_panel
|
|
100
|
+
routes_queue --> models
|
|
100
101
|
routes_queue --> services_source
|
|
101
102
|
routes_queue --> services_source_utils
|
|
102
|
-
routes_queue --> models
|
|
103
|
-
routes_tabs --> routes_local_files
|
|
104
|
-
routes_tabs --> components_source_browser
|
|
105
|
-
routes_tabs --> services_source_utils
|
|
106
|
-
routes_tabs --> services_source
|
|
107
103
|
routes_tabs --> routes_core
|
|
108
104
|
routes_tabs --> models
|
|
109
|
-
routes_tabs -->
|
|
105
|
+
routes_tabs --> services_source
|
|
110
106
|
routes_tabs --> components_step_renderer
|
|
107
|
+
routes_tabs --> components_source_browser
|
|
108
|
+
routes_tabs --> routes_local_files
|
|
109
|
+
routes_tabs --> components_local_files
|
|
110
|
+
routes_tabs --> services_source_utils
|
|
111
111
|
```
|
|
112
112
|
|
|
113
113
|
*51 cross-module dependencies detected*
|
|
@@ -160,8 +160,8 @@ def _render_duplicate_flash(
|
|
|
160
160
|
candidate_provider_id: str, # Provider ID of the row the user clicked
|
|
161
161
|
existing_record_id: str, # Record ID of the conflicting selected row
|
|
162
162
|
existing_provider_id: str, # Provider ID of the conflicting selected row
|
|
163
|
-
) ->
|
|
164
|
-
"Render a
|
|
163
|
+
) -> Div: # OOB Div with flash script (replaces previous via innerHTML swap)
|
|
164
|
+
"Render a fixed-ID container with flash script for two source rows."
|
|
165
165
|
```
|
|
166
166
|
|
|
167
167
|
``` python
|
|
@@ -1000,6 +1000,7 @@ def _render_source_row(
|
|
|
1000
1000
|
remove_url: str, # URL for removing from queue
|
|
1001
1001
|
preview_url: str, # URL for previewing content
|
|
1002
1002
|
is_first: bool = False, # Whether this is the first row (gets initial focus)
|
|
1003
|
+
row_index: int = 0, # Index among selectable rows (for keyboard focus sync)
|
|
1003
1004
|
) -> Any: # Table row element
|
|
1004
1005
|
"Render a single source row in the browser table."
|
|
1005
1006
|
```
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "0.0.5"
|
|
@@ -150,11 +150,13 @@ def _render_selection_queue(
|
|
|
150
150
|
),
|
|
151
151
|
|
|
152
152
|
# Queue list with native Sortable.js (initialized via script)
|
|
153
|
+
# hx_include="this" required for HTMX 2.x to collect child hidden inputs
|
|
153
154
|
Ul(
|
|
154
155
|
*queue_items,
|
|
155
156
|
id=SelectionHtmlIds.QUEUE_LIST,
|
|
156
157
|
hx_post=reorder_url,
|
|
157
158
|
hx_trigger="end",
|
|
159
|
+
hx_include="this",
|
|
158
160
|
hx_target=SelectionHtmlIds.as_selector(SelectionHtmlIds.QUEUE_CONTAINER),
|
|
159
161
|
hx_swap="outerHTML",
|
|
160
162
|
cls=combine_classes("sortable", grow(), overflow.y.auto, list_style.none, m(0), p(0))
|
|
@@ -39,7 +39,6 @@ from cjm_fasthtml_tailwind.utilities.interactivity import cursor
|
|
|
39
39
|
from cjm_fasthtml_tailwind.utilities.flexbox_and_grid import (
|
|
40
40
|
flex_display, flex_direction, justify, items, gap, grow
|
|
41
41
|
)
|
|
42
|
-
from cjm_fasthtml_tailwind.utilities.transitions_and_animation import transition, duration
|
|
43
42
|
from cjm_fasthtml_tailwind.core.base import combine_classes
|
|
44
43
|
|
|
45
44
|
# Local imports
|
|
@@ -84,6 +83,7 @@ def _render_source_row(
|
|
|
84
83
|
remove_url: str, # URL for removing from queue
|
|
85
84
|
preview_url: str, # URL for previewing content
|
|
86
85
|
is_first: bool = False, # Whether this is the first row (gets initial focus)
|
|
86
|
+
row_index: int = 0, # Index among selectable rows (for keyboard focus sync)
|
|
87
87
|
) -> Any: # Table row element
|
|
88
88
|
"""Render a single source row in the browser table."""
|
|
89
89
|
record_id = record.get("record_id", "")
|
|
@@ -139,6 +139,10 @@ def _render_source_row(
|
|
|
139
139
|
cls=combine_classes(tooltip, tooltip_placement.top)
|
|
140
140
|
)
|
|
141
141
|
|
|
142
|
+
# Click handler to sync keyboard focus with clicked row
|
|
143
|
+
zone_id = SelectionHtmlIds.SOURCE_LIST
|
|
144
|
+
focus_onclick = f"if(window.kbNav)window.kbNav.setItemFocus('{zone_id}',{row_index},true)"
|
|
145
|
+
|
|
142
146
|
return Tr(
|
|
143
147
|
# Hidden cell for keyboard action data (must be in TD for valid HTML)
|
|
144
148
|
Td(
|
|
@@ -178,15 +182,14 @@ def _render_source_row(
|
|
|
178
182
|
cls=combine_classes(
|
|
179
183
|
bg_dui.primary.opacity(10) if is_selected else "",
|
|
180
184
|
bg_dui.base_200.hover,
|
|
181
|
-
cursor.pointer
|
|
182
|
-
transition.colors,
|
|
183
|
-
duration(200)
|
|
185
|
+
cursor.pointer
|
|
184
186
|
),
|
|
185
187
|
tabindex="0",
|
|
186
188
|
data_selectable="true",
|
|
187
189
|
data_focused="true" if is_first else "false",
|
|
188
190
|
data_record_id=record_id,
|
|
189
191
|
data_provider_id=provider_id,
|
|
192
|
+
onclick=focus_onclick,
|
|
190
193
|
hx_get=preview_url,
|
|
191
194
|
hx_vals=json.dumps({"record_id": record_id, "provider_id": provider_id}),
|
|
192
195
|
hx_target=SelectionHtmlIds.as_selector(SelectionHtmlIds.PREVIEW_PANEL),
|
|
@@ -254,7 +257,7 @@ def _render_source_list(
|
|
|
254
257
|
|
|
255
258
|
# Build table rows
|
|
256
259
|
table_rows = []
|
|
257
|
-
|
|
260
|
+
row_index = 0
|
|
258
261
|
for group_key, records in grouped.items():
|
|
259
262
|
# Add group header
|
|
260
263
|
table_rows.append(_render_group_header(
|
|
@@ -268,9 +271,10 @@ def _render_source_list(
|
|
|
268
271
|
)
|
|
269
272
|
table_rows.append(_render_source_row(
|
|
270
273
|
record, is_selected, add_url, remove_url, preview_url,
|
|
271
|
-
is_first=
|
|
274
|
+
is_first=(row_index == 0),
|
|
275
|
+
row_index=row_index,
|
|
272
276
|
))
|
|
273
|
-
|
|
277
|
+
row_index += 1
|
|
274
278
|
|
|
275
279
|
return Div(
|
|
276
280
|
Table(
|
|
@@ -570,6 +570,9 @@ def render_selection_step(
|
|
|
570
570
|
# Sortable initialization script (htmx integration)
|
|
571
571
|
sortable_script,
|
|
572
572
|
|
|
573
|
+
# Script runner for OOB-triggered JS (duplicate rejection flash)
|
|
574
|
+
Div(id=SelectionHtmlIds.SCRIPT_RUNNER),
|
|
575
|
+
|
|
573
576
|
id=SelectionHtmlIds.SOURCE_SELECTOR,
|
|
574
577
|
cls=combine_classes(
|
|
575
578
|
w.full,
|
|
@@ -62,6 +62,9 @@ class SelectionHtmlIds:
|
|
|
62
62
|
SELECTION_FOOTER = "sd-selection-footer"
|
|
63
63
|
SELECTION_STATS = "sd-selection-stats"
|
|
64
64
|
|
|
65
|
+
# Script runner (OOB container for flash feedback scripts)
|
|
66
|
+
SCRIPT_RUNNER = "sd-selection-script-runner"
|
|
67
|
+
|
|
65
68
|
@staticmethod
|
|
66
69
|
def _safe_id(
|
|
67
70
|
value:str # Raw value to sanitize for HTML ID use
|
|
@@ -8,7 +8,7 @@ __all__ = ['DEBUG_SELECTION_STATE', 'WorkflowStateStore']
|
|
|
8
8
|
# %% ../../nbs/routes/core.ipynb #sel-core-imports
|
|
9
9
|
from typing import List, Dict, Any, Optional, Tuple, Union
|
|
10
10
|
|
|
11
|
-
from fasthtml.common import Script
|
|
11
|
+
from fasthtml.common import Div, Script
|
|
12
12
|
|
|
13
13
|
from cjm_workflow_state.state_store import SQLiteWorkflowStateStore
|
|
14
14
|
|
|
@@ -63,26 +63,46 @@ def _render_duplicate_flash(
|
|
|
63
63
|
candidate_provider_id: str, # Provider ID of the row the user clicked
|
|
64
64
|
existing_record_id: str, # Record ID of the conflicting selected row
|
|
65
65
|
existing_provider_id: str, # Provider ID of the conflicting selected row
|
|
66
|
-
) ->
|
|
67
|
-
"""Render a
|
|
66
|
+
) -> Div: # OOB Div with flash script (replaces previous via innerHTML swap)
|
|
67
|
+
"""Render a fixed-ID container with flash script for two source rows."""
|
|
68
68
|
row1 = SelectionHtmlIds.source_row(candidate_record_id, candidate_provider_id)
|
|
69
69
|
row2 = SelectionHtmlIds.source_row(existing_record_id, existing_provider_id)
|
|
70
|
-
return
|
|
70
|
+
return Div(
|
|
71
|
+
Script(f"""
|
|
71
72
|
(function() {{
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
[r1, r2].forEach(function(r) {{
|
|
76
|
-
if (r) {{ r.classList.add('bg-error'); }}
|
|
77
|
-
}});
|
|
78
|
-
setTimeout(function() {{
|
|
73
|
+
function flash() {{
|
|
74
|
+
var r1 = document.getElementById('{row1}');
|
|
75
|
+
var r2 = document.getElementById('{row2}');
|
|
79
76
|
[r1, r2].forEach(function(r) {{
|
|
80
|
-
if (r) {{
|
|
77
|
+
if (r) {{
|
|
78
|
+
r.style.transition = 'background-color 0.05s ease-in';
|
|
79
|
+
r.classList.add('bg-error');
|
|
80
|
+
}}
|
|
81
81
|
}});
|
|
82
|
-
|
|
83
|
-
|
|
82
|
+
setTimeout(function() {{
|
|
83
|
+
[r1, r2].forEach(function(r) {{
|
|
84
|
+
if (r) {{
|
|
85
|
+
r.style.transition = 'background-color 0.3s ease-out';
|
|
86
|
+
r.classList.remove('bg-error');
|
|
87
|
+
}}
|
|
88
|
+
}});
|
|
89
|
+
setTimeout(function() {{
|
|
90
|
+
[r1, r2].forEach(function(r) {{
|
|
91
|
+
if (r) {{ r.style.transition = ''; }}
|
|
92
|
+
}});
|
|
93
|
+
}}, 300);
|
|
94
|
+
}}, 600);
|
|
95
|
+
}}
|
|
96
|
+
// Defer until after HTMX finishes all OOB swaps
|
|
97
|
+
document.body.addEventListener('htmx:afterSettle', function handler() {{
|
|
98
|
+
document.body.removeEventListener('htmx:afterSettle', handler);
|
|
99
|
+
flash();
|
|
100
|
+
}});
|
|
84
101
|
}})();
|
|
85
|
-
""")
|
|
102
|
+
"""),
|
|
103
|
+
id=SelectionHtmlIds.SCRIPT_RUNNER,
|
|
104
|
+
hx_swap_oob="innerHTML",
|
|
105
|
+
)
|
|
86
106
|
|
|
87
107
|
# %% ../../nbs/routes/core.ipynb #3zll5oy1hsc
|
|
88
108
|
def _get_active_source_tab(
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.2
|
|
2
2
|
Name: cjm-transcript-source-select
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.5
|
|
4
4
|
Summary: FastHTML source selection component for transcript decomposition workflows, with federated database browsing, drag-drop ordering, and keyboard navigation.
|
|
5
5
|
Home-page: https://github.com/cj-mills/cjm-transcript-source-select
|
|
6
6
|
Author: Christian J. Mills
|
|
@@ -109,48 +109,48 @@ graph LR
|
|
|
109
109
|
components_source_browser --> services_source_utils
|
|
110
110
|
components_source_browser --> html_ids
|
|
111
111
|
components_step_renderer --> components_selection_queue
|
|
112
|
-
components_step_renderer --> components_preview_panel
|
|
113
112
|
components_step_renderer --> components_local_files
|
|
114
|
-
components_step_renderer --> components_source_browser
|
|
115
113
|
components_step_renderer --> components_helpers
|
|
116
|
-
components_step_renderer --> utils
|
|
117
|
-
components_step_renderer --> html_ids
|
|
118
114
|
components_step_renderer --> models
|
|
115
|
+
components_step_renderer --> components_source_browser
|
|
116
|
+
components_step_renderer --> html_ids
|
|
117
|
+
components_step_renderer --> components_preview_panel
|
|
118
|
+
components_step_renderer --> utils
|
|
119
119
|
routes_core --> components_step_renderer
|
|
120
|
-
routes_core --> services_source
|
|
121
120
|
routes_core --> models
|
|
122
|
-
routes_core --> html_ids
|
|
123
|
-
routes_core --> components_selection_queue
|
|
124
121
|
routes_core --> components_source_browser
|
|
125
|
-
|
|
126
|
-
|
|
122
|
+
routes_core --> services_source
|
|
123
|
+
routes_core --> components_selection_queue
|
|
124
|
+
routes_core --> html_ids
|
|
127
125
|
routes_filtering --> routes_core
|
|
128
126
|
routes_filtering --> components_source_browser
|
|
127
|
+
routes_filtering --> services_source_utils
|
|
129
128
|
routes_filtering --> models
|
|
130
|
-
|
|
131
|
-
routes_init --> routes_local_files
|
|
132
|
-
routes_init --> services_source
|
|
133
|
-
routes_init --> routes_tabs
|
|
134
|
-
routes_init --> models
|
|
129
|
+
routes_filtering --> services_source
|
|
135
130
|
routes_init --> routes_core
|
|
136
131
|
routes_init --> routes_queue
|
|
132
|
+
routes_init --> models
|
|
133
|
+
routes_init --> services_source
|
|
134
|
+
routes_init --> routes_tabs
|
|
135
|
+
routes_init --> routes_filtering
|
|
136
|
+
routes_init --> routes_local_files
|
|
137
137
|
routes_local_files --> services_source
|
|
138
138
|
routes_local_files --> routes_core
|
|
139
139
|
routes_local_files --> models
|
|
140
140
|
routes_local_files --> components_local_files
|
|
141
141
|
routes_queue --> routes_core
|
|
142
142
|
routes_queue --> components_preview_panel
|
|
143
|
+
routes_queue --> models
|
|
143
144
|
routes_queue --> services_source
|
|
144
145
|
routes_queue --> services_source_utils
|
|
145
|
-
routes_queue --> models
|
|
146
|
-
routes_tabs --> routes_local_files
|
|
147
|
-
routes_tabs --> components_source_browser
|
|
148
|
-
routes_tabs --> services_source_utils
|
|
149
|
-
routes_tabs --> services_source
|
|
150
146
|
routes_tabs --> routes_core
|
|
151
147
|
routes_tabs --> models
|
|
152
|
-
routes_tabs -->
|
|
148
|
+
routes_tabs --> services_source
|
|
153
149
|
routes_tabs --> components_step_renderer
|
|
150
|
+
routes_tabs --> components_source_browser
|
|
151
|
+
routes_tabs --> routes_local_files
|
|
152
|
+
routes_tabs --> components_local_files
|
|
153
|
+
routes_tabs --> services_source_utils
|
|
154
154
|
```
|
|
155
155
|
|
|
156
156
|
*51 cross-module dependencies detected*
|
|
@@ -203,8 +203,8 @@ def _render_duplicate_flash(
|
|
|
203
203
|
candidate_provider_id: str, # Provider ID of the row the user clicked
|
|
204
204
|
existing_record_id: str, # Record ID of the conflicting selected row
|
|
205
205
|
existing_provider_id: str, # Provider ID of the conflicting selected row
|
|
206
|
-
) ->
|
|
207
|
-
"Render a
|
|
206
|
+
) -> Div: # OOB Div with flash script (replaces previous via innerHTML swap)
|
|
207
|
+
"Render a fixed-ID container with flash script for two source rows."
|
|
208
208
|
```
|
|
209
209
|
|
|
210
210
|
``` python
|
|
@@ -1043,6 +1043,7 @@ def _render_source_row(
|
|
|
1043
1043
|
remove_url: str, # URL for removing from queue
|
|
1044
1044
|
preview_url: str, # URL for previewing content
|
|
1045
1045
|
is_first: bool = False, # Whether this is the first row (gets initial focus)
|
|
1046
|
+
row_index: int = 0, # Index among selectable rows (for keyboard focus sync)
|
|
1046
1047
|
) -> Any: # Table row element
|
|
1047
1048
|
"Render a single source row in the browser table."
|
|
1048
1049
|
```
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "0.0.3"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|