@taprootio/espalier 2.0.0 → 2.0.2

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.
@@ -4,7 +4,7 @@ import "../button/esp-button.js";
4
4
  import { EspalierElementBase } from "../shared/esp-element-base.js";
5
5
  import { type GridRow } from "./esp-grid-column.js";
6
6
  import "./esp-grid-column.js";
7
- import "@lit-labs/virtualizer";
7
+ import "../shared/virtualizer/lit-virtualizer.js";
8
8
  export type { GridRow };
9
9
  export type GridClickedEvent = {
10
10
  grid: EspalierGrid;
@@ -394,6 +394,13 @@ export declare class EspalierGrid extends EspalierElementBase {
394
394
  * If using a `data-url`, the items retrieved are available
395
395
  * in the items property. An items array can be assigned
396
396
  * instead of using a `data-url`.
397
+ *
398
+ * Assigning a new items array preserves the grid's current
399
+ * intrinsic state: an active search term is re-applied to the
400
+ * new items, the active sort column re-sorts them, and the
401
+ * current page is kept when it still exists (clamping to the
402
+ * nearest valid page otherwise). Infinite grids delegate search
403
+ * and sort to the server through `fetchPage` instead.
397
404
  */
398
405
  get items(): GridRow[];
399
406
  set items(newItems: GridRow[]);
@@ -1,4 +1,4 @@
1
- var h=function(I,e,t,i){var s=arguments.length,o=s<3?e:i===null?i=Object.getOwnPropertyDescriptor(e,t):i,r;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")o=Reflect.decorate(I,e,t,i);else for(var n=I.length-1;n>=0;n--)(r=I[n])&&(o=(s<3?r(o):s>3?r(e,t,o):r(e,t))||o);return s>3&&o&&Object.defineProperty(e,t,o),o};import{css as E,html as c}from"lit";import{customElement as A,property as m,state as u}from"lit/decorators.js";import"../input/esp-input.js";import"../button/esp-button.js";import{EspalierElementBase as S}from"../shared/esp-element-base.js";import{ref as y,createRef as w}from"lit/directives/ref.js";import"./esp-grid-column.js";import{classMap as x}from"lit/directives/class-map.js";import{styleMap as P}from"lit/directives/style-map.js";import{leftArrow as N}from"../shared/svgs/left-arrow.js";import{rightArrow as T}from"../shared/svgs/right-arrow.js";import{filter as G}from"../shared/svgs/filter.js";import"@lit-labs/virtualizer";const L="esp-grid-load-start",M="esp-grid-load-success",z="esp-grid-load-error",j="esp-grid-items-changed";let d=class extends S{constructor(){super(...arguments),this.columnDefinitionsSlot=w(),this.headerButtonsSlot=w(),this.filteredItems=[],this.sortColumn=void 0,this.itemsBacker=[],this.virtualizerRef=w(),this.gridHeaderRowRef=w(),this.infiniteContainerRef=w(),this.pageLoadVersion=0,this.nextCursor=null,this.searchTerm="",this.allowNext=!1,this.allowPrevious=!1,this.columnDefinitions=new Array,this.displayedItems=[],this.pageNumber=1,this.footerMessage="",this.allLoadedItems=[],this.hasMoreData=!1,this.isLoadingFirstPage=!1,this.isLoadingPage=!1,this.effectiveGridHeight="",this.pendingHeightRetry=!1,this.wheelHandlerAttached=!1,this.dataField="",this.dataUrl="",this.pageSize=10,this.gridHeight="60vh",this.searchFields=[],this.fetchPageBacker=null,this.isAdjustingHeight=!1,this.heightRetryObserver=null,this.pinnedOffsets=new Map,this.handleGridClick=e=>{const t=e.target,i=t.hasAttribute("grid-event")?t:t.closest("[grid-event]");if(!i)return;const s=i.closest("tr")??i.closest(".grid-row"),o=Number(s?.dataset.rowIndex),r=this.isInfiniteMode?this.allLoadedItems:this.displayedItems,n=Number.isInteger(o)&&o>=0?r[o]:void 0;this.dispatchEvent(new CustomEvent("grid-event",{detail:{grid:this,target:i,event:i.getAttribute("grid-event")??"",data:n??{}},bubbles:!1,composed:!0})),e.stopPropagation()},this.syncHeaderScroll=()=>{const e=this.virtualizerRef.value,t=this.gridHeaderRowRef.value;e&&t&&(t.scrollLeft=e.scrollLeft)},this.handleVirtualizerWheel=e=>{const t=this.infiniteContainerRef.value;if(!t)return;const i=t.getBoundingClientRect(),s=window.innerHeight,o=i.top>=0&&i.bottom<=s,r=i.top<=0&&i.bottom>=s;!o&&!r&&(e.preventDefault(),window.scrollBy(0,e.deltaY))},this.handleSearch=e=>{const t=e.detail.toLowerCase();if(this.isInfiniteMode)this.searchDebounceTimer&&clearTimeout(this.searchDebounceTimer),this.searchDebounceTimer=setTimeout(async()=>{this.searchTerm=t,await this.resetAndReload().catch(()=>{})},300);else{this.searchTerm=t;const i=this.items.filter(s=>{let o;return this.searchFields.length>0?o=this.searchFields.map(r=>s[r]):o=Object.values(s),o.some(r=>String(r).toLowerCase().includes(t))});this.filteredItems=i,this.setPage(1),this.dispatchItemsChanged()}}}get items(){return this.itemsBacker}set items(e){this.applyPagedItems(e)}applyPagedItems(e,t={}){const i=t.emitItemsChanged??!0,s=t.pageNumber??this.pageNumber??1;this.itemsBacker=e,this.filteredItems=this.itemsBacker,this.sortColumn?this.sort({emitItemsChanged:!1,pageNumber:s}):this.setPage(s),i&&this.dispatchItemsChanged()}get fetchPage(){return this.fetchPageBacker}set fetchPage(e){this.fetchPageBacker=e,e&&this.hasUpdated&&this.loadPage(null).then(async()=>{await this.updateComplete,this.measurePinnedOffsets()}).catch(()=>{})}get isInfiniteMode(){return this.fetchPage!==null}get currentDataStateItems(){return this.isInfiniteMode?this.allLoadedItems:this.filteredItems}getCurrentSortField(){return this.sortColumn?this.sortColumn.sortField.length>0?this.sortColumn.sortField:this.sortColumn.fieldName:""}createDataStateDetail(e={}){const t=[...this.currentDataStateItems],i=e.cursor??null,s=e.isFirstPage??(this.isInfiniteMode?i===null:this.pageNumber<=1);return{items:t,itemCount:t.length,isFirstPage:s,cursor:i,nextCursor:this.nextCursor,hasRows:t.length>0,isEmpty:t.length===0,search:this.searchTerm,sortField:this.getCurrentSortField(),sortOrder:this.sortColumn?.sortOrder??""}}dispatchGridDataEvent(e,t){this.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0}))}dispatchItemsChanged(e={}){this.dispatchGridDataEvent(j,this.createDataStateDetail(e))}setPage(e){const t=Math.ceil(this.filteredItems.length/this.pageSize);e>t&&(e=t),this.pageNumber=e;const i=(this.pageNumber-1)*this.pageSize;switch(this.displayedItems=this.filteredItems.slice(i,i+this.pageSize),this.allowPrevious=this.pageNumber>1,this.allowNext=t>this.pageNumber,t){case 0:this.footerMessage="No matching items";break;case 1:this.footerMessage=this.filteredItems.length<this.items.length?"Showing all filtered items":"Showing all items";break;default:this.footerMessage=`Showing page ${this.pageNumber} of ${t} pages`}}async loadPage(e){const t=this.fetchPage;if(!t||e!==null&&this.isLoadingPage)return;const i=++this.pageLoadVersion,s=e===null;let o=!1;this.isLoadingPage=!0,this.isLoadingFirstPage=s,s&&(this.nextCursor=null,this.hasMoreData=!1);const r={cursor:e,limit:this.pageSize,search:this.searchTerm,sortField:this.getCurrentSortField(),sortOrder:this.sortColumn?.sortOrder??""};this.dispatchGridDataEvent(L,this.createDataStateDetail({cursor:e,isFirstPage:s}));try{const n=await t(r);if(i!==this.pageLoadVersion)return;e===null?this.allLoadedItems=[...n.items]:this.allLoadedItems=[...this.allLoadedItems,...n.items],this.nextCursor=n.nextCursor,this.hasMoreData=n.nextCursor!==null,o=!0,this.dispatchGridDataEvent(M,this.createDataStateDetail({cursor:e,isFirstPage:s})),this.dispatchItemsChanged({cursor:e,isFirstPage:s})}catch(n){throw i===this.pageLoadVersion&&this.dispatchGridDataEvent(z,{...this.createDataStateDetail({cursor:e,isFirstPage:s}),error:n}),n}finally{if(i===this.pageLoadVersion){if(this.isLoadingPage=!1,this.isLoadingFirstPage=!1,s&&o){const n=this.virtualizerRef.value;if(n&&n.scrollTop>0)try{n.scrollTo({top:0})}catch{n.scrollTop=0}}await this.adjustInfiniteHeight()}}}async resetAndReload(){await this.loadPage(null)}onRangeChanged(e){this.isLoadingFirstPage||e.last>=this.allLoadedItems.length-5&&this.hasMoreData&&!this.isLoadingPage&&this.loadPage(this.nextCursor).catch(()=>{})}async adjustInfiniteHeight(){if(!this.isAdjustingHeight){this.isAdjustingHeight=!0;try{const e=this.virtualizerRef.value;e&&(e.style.minHeight=""),this.effectiveGridHeight=this.gridHeight,await this.updateComplete;const t=this.infiniteContainerRef.value,i=this.virtualizerRef.value;if(!t||this.hasMoreData)return;const o=this.gridHeaderRowRef.value?.offsetHeight??0;if(!i){const p=t.querySelector(".no-results");let f=0;p?f=o+p.offsetHeight:t.querySelectorAll(":scope > *").forEach(R=>f+=R.offsetHeight),f<t.offsetHeight&&(this.effectiveGridHeight=`${f}px`);return}const r=i.querySelectorAll(".grid-row");let n=0,a=!1;if(r.forEach(p=>{const f=p.offsetHeight;f===0&&(a=!0),n+=f}),r.length===0||a||n===0){this.pendingHeightRetry||(this.pendingHeightRetry=!0,this.observeForHeightRetry(i));return}const l=i.querySelectorAll(".grid-row :defined"),g=[];l.forEach(p=>{"updateComplete"in p&&g.push(p.updateComplete)}),g.length>0&&(await Promise.all(g),n=0,r.forEach(p=>{n+=p.offsetHeight}));const v=n+o,b=t.offsetHeight;v<b&&r.length>=this.allLoadedItems.length&&(i.style.minHeight=`${n}px`,this.effectiveGridHeight=`${v}px`),!this.hasMoreData&&!this.pendingHeightRetry&&(this.pendingHeightRetry=!0,setTimeout(()=>{this.pendingHeightRetry=!1;const p=this.infiniteContainerRef.value,f=this.virtualizerRef.value;if(!p||!f||this.hasMoreData)return;const O=this.gridHeaderRowRef.value?.offsetHeight??0,k=f.querySelectorAll(".grid-row");let C=0,D=!1;if(k.forEach(F=>{const H=F.offsetHeight;H===0&&(D=!0),C+=H}),k.length===0||D||C===0)return;const $=C+O;$<p.offsetHeight&&k.length>=this.allLoadedItems.length&&(f.style.minHeight=`${C}px`,this.effectiveGridHeight=`${$}px`)},100))}finally{this.isAdjustingHeight=!1}}}observeForHeightRetry(e){this.heightRetryObserver?.disconnect(),this.heightRetryObserver=new IntersectionObserver(t=>{if(!t.some(r=>r.isIntersecting))return;this.heightRetryObserver?.disconnect(),this.heightRetryObserver=null;let s=0;const o=()=>{this.pendingHeightRetry=!1,this.adjustInfiniteHeight(),this.pendingHeightRetry&&++s<5&&setTimeout(o,100)};requestAnimationFrame(()=>setTimeout(o,50))},{threshold:0}),this.heightRetryObserver.observe(e)}async sortOn(e){this.sortColumn===e?this.sortColumn.sortOrder=this.sortColumn.sortOrder=="asc"?"desc":"asc":(this.sortColumn=e,this.sortColumn.sortOrder="asc"),this.isInfiniteMode?await this.resetAndReload():this.sort()}sort(e={}){if(!this.sortColumn)return;const t=this.getCurrentSortField(),i=this.sortColumn.sortOrder==="asc"?1:-1,s=this.sortColumn.sortType,o=this.filteredItems.map((r,n)=>{const a=r[t]??"",l=s==="number"?Number(a):a.toString().toLowerCase();return{item:r,index:n,sortValue:l}});o.sort((r,n)=>r.sortValue<n.sortValue?-1*i:r.sortValue>n.sortValue?1*i:r.index-n.index),this.filteredItems=o.map(({item:r})=>r),this.setPage(e.pageNumber??1),(e.emitItemsChanged??!0)&&this.dispatchItemsChanged()}delete(e){if(this.isInfiniteMode){const t=this.allLoadedItems.filter(i=>!e(i));if(t.length===this.allLoadedItems.length)return;this.allLoadedItems=t,this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else{const t=this.items.filter(i=>!e(i));if(t.length===this.items.length)return;this.items=t}}addOrReplace(e,t){if(this.isInfiniteMode){const i=this.allLoadedItems.findIndex(e);if(i>=0){const s=[...this.allLoadedItems];s[i]={...s[i],...t},this.allLoadedItems=s}else this.allLoadedItems=[...this.allLoadedItems,t];this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else this.items.find(e)?this.items=this.items.map(s=>e(s)?{...s,...t}:s):this.items=[...this.items,t]}addInOrder(e,t,i){if(this.isInfiniteMode){const a=this.allLoadedItems.findIndex(e),l=[...this.allLoadedItems];if(a>=0)return l[a]={...l[a],...t},this.allLoadedItems=l,this.dispatchItemsChanged(),a;let g=0,v=l.length;for(;g<v;){const b=g+v>>>1;i(l[b],t)<0?g=b+1:v=b}return l.splice(g,0,t),this.allLoadedItems=l,this.dispatchItemsChanged(),this.adjustInfiniteHeight(),g}const s=this.items.findIndex(e),o=[...this.items];if(s>=0)return o[s]={...o[s],...t},this.items=o,s;let r=0,n=o.length;for(;r<n;){const a=r+n>>>1;i(o[a],t)<0?r=a+1:n=a}return o.splice(r,0,t),this.items=o,r}async scrollToIndex(e,t="center"){if(this.isInfiniteMode){await this.updateComplete;const i=this.virtualizerRef.value;if(!i)return;await i.updateComplete,await new Promise(s=>requestAnimationFrame(s)),await i.layoutComplete,i.scrollToIndex(e,t)}else{const i=Math.floor(e/this.pageSize)+1;this.setPage(i)}}clear(){if(this.isInfiniteMode){if(this.allLoadedItems.length===0&&this.nextCursor===null&&!this.hasMoreData)return;this.allLoadedItems=[],this.nextCursor=null,this.hasMoreData=!1,this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else{if(this.items.length===0)return;this.items=[]}}async reload(){this.isInfiniteMode&&await this.resetAndReload()}computePinnedStyles(){return this.pinnedOffsets}measurePinnedOffsets(){this.pinnedOffsets=new Map,this.isInfiniteMode?this.computePinnedOffsetsFromWidths():this.measurePinnedOffsetsFromCells(),this.requestUpdate()}computePinnedOffsetsFromWidths(){const e=this.columnDefinitions.filter(r=>r.pin==="left"),t=this.columnDefinitions.filter(r=>r.pin==="right"),i=[];for(let r=0;r<e.length;r++){const n=e[r],a=i.length===0?"0px":`calc(${i.join(" + ")})`;this.pinnedOffsets.set(n,{position:"sticky",left:a,zIndex:`${e.length-r+1}`}),i.push(n.width||"0px")}const s=[],o=[...t].reverse();for(let r=0;r<o.length;r++){const n=o[r],a=s.length===0?"0px":`calc(${s.join(" + ")})`;this.pinnedOffsets.set(n,{position:"sticky",right:a,zIndex:`${o.length-r+1}`}),s.push(n.width||"0px")}}measurePinnedOffsetsFromCells(){const e=this.shadowRoot?.querySelectorAll("thead th");if(!e)return;const t=this.columnDefinitions.filter(a=>a.pin==="left"),i=this.columnDefinitions.filter(a=>a.pin==="right"),s=new Map;this.columnDefinitions.forEach((a,l)=>{e[l]&&s.set(a,e[l])});let o=0;for(let a=0;a<t.length;a++){const l=t[a];this.pinnedOffsets.set(l,{position:"sticky",left:`${o}px`,zIndex:`${t.length-a+1}`});const g=s.get(l);g&&(o+=g.offsetWidth)}let r=0;const n=[...i].reverse();for(let a=0;a<n.length;a++){const l=n[a];this.pinnedOffsets.set(l,{position:"sticky",right:`${r}px`,zIndex:`${n.length-a+1}`});const g=s.get(l);g&&(r+=g.offsetWidth)}}computeGridTemplateColumns(){return this.columnDefinitions.map(e=>e.width?e.grow?`minmax(${e.width}, 1fr)`:e.width:e.grow?"minmax(0, 1fr)":"auto").join(" ")}get hasGrowableColumns(){return this.columnDefinitions.some(e=>e.grow)}computePinnedColumnFlags(){const e=new Map,t=this.columnDefinitions.filter(r=>r.pin==="left"),i=this.columnDefinitions.filter(r=>r.pin==="right"),s=t[t.length-1],o=i[0];return this.columnDefinitions.forEach((r,n)=>{e.set(r,{beforePinnedRight:this.columnDefinitions[n+1]?.pin==="right",firstPinnedRight:o===r,lastPinnedLeft:s===r})}),e}renderCell(e,t){if(!e.fieldName)return c`<span></span>`;const i=e.textAlign??"left";return c`<span style="text-align: ${i};"> ${t[e.fieldName]} </span>`}attachWheelHandler(){const e=this.virtualizerRef.value;e&&!this.wheelHandlerAttached?(e.addEventListener("wheel",this.handleVirtualizerWheel,{passive:!1}),this.wheelHandlerAttached=!0):!e&&this.wheelHandlerAttached&&(this.wheelHandlerAttached=!1)}async firstUpdated(e){super.firstUpdated(e),this.headerButtonsSlot.value.assignedElements().length===0&&this.headerButtonsSlot.value.remove();for(const i of this.columnDefinitionsSlot.value.assignedElements())i.localName==="esp-grid-column"&&this.columnDefinitions.push(i);const t=this.columnDefinitions.find(i=>i.sortOrder!=="");t&&(this.sortColumn=t),this.isInfiniteMode?await this.loadPage(null).catch(()=>{}):this.dataUrl.length&&await this.loadDataUrl().catch(()=>{}),await this.updateComplete,this.measurePinnedOffsets()}updated(e){super.updated(e),this.isInfiniteMode&&this.attachWheelHandler()}async loadDataUrl(){this.dispatchGridDataEvent(L,this.createDataStateDetail({cursor:null,isFirstPage:!0}));try{const t=await fetch(this.dataUrl).then(i=>i.json());this.applyPagedItems(this.dataField?t[this.dataField]:t,{emitItemsChanged:!1}),this.dispatchGridDataEvent(M,this.createDataStateDetail({cursor:null,isFirstPage:!0})),this.dispatchItemsChanged({cursor:null,isFirstPage:!0})}catch(t){throw this.dispatchGridDataEvent(z,{...this.createDataStateDetail({cursor:null,isFirstPage:!0}),error:t}),t}}disconnectedCallback(){super.disconnectedCallback();const e=this.virtualizerRef.value;e&&e.removeEventListener("wheel",this.handleVirtualizerWheel),this.wheelHandlerAttached=!1,this.heightRetryObserver?.disconnect(),this.heightRetryObserver=null}renderSortIcons(){return c`
1
+ var h=function(I,e,t,i){var s=arguments.length,o=s<3?e:i===null?i=Object.getOwnPropertyDescriptor(e,t):i,r;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")o=Reflect.decorate(I,e,t,i);else for(var n=I.length-1;n>=0;n--)(r=I[n])&&(o=(s<3?r(o):s>3?r(e,t,o):r(e,t))||o);return s>3&&o&&Object.defineProperty(e,t,o),o};import{css as E,html as c}from"lit";import{customElement as A,property as m,state as u}from"lit/decorators.js";import"../input/esp-input.js";import"../button/esp-button.js";import{EspalierElementBase as S}from"../shared/esp-element-base.js";import{ref as y,createRef as w}from"lit/directives/ref.js";import"./esp-grid-column.js";import{classMap as x}from"lit/directives/class-map.js";import{styleMap as P}from"lit/directives/style-map.js";import{leftArrow as T}from"../shared/svgs/left-arrow.js";import{rightArrow as G}from"../shared/svgs/right-arrow.js";import{filter as N}from"../shared/svgs/filter.js";import"../shared/virtualizer/lit-virtualizer.js";const L="esp-grid-load-start",M="esp-grid-load-success",z="esp-grid-load-error",j="esp-grid-items-changed";let d=class extends S{constructor(){super(...arguments),this.columnDefinitionsSlot=w(),this.headerButtonsSlot=w(),this.filteredItems=[],this.sortColumn=void 0,this.itemsBacker=[],this.virtualizerRef=w(),this.gridHeaderRowRef=w(),this.infiniteContainerRef=w(),this.pageLoadVersion=0,this.nextCursor=null,this.searchTerm="",this.allowNext=!1,this.allowPrevious=!1,this.columnDefinitions=new Array,this.displayedItems=[],this.pageNumber=1,this.footerMessage="",this.allLoadedItems=[],this.hasMoreData=!1,this.isLoadingFirstPage=!1,this.isLoadingPage=!1,this.effectiveGridHeight="",this.pendingHeightRetry=!1,this.wheelHandlerAttached=!1,this.dataField="",this.dataUrl="",this.pageSize=10,this.gridHeight="60vh",this.searchFields=[],this.fetchPageBacker=null,this.isAdjustingHeight=!1,this.heightRetryObserver=null,this.pinnedOffsets=new Map,this.handleGridClick=e=>{const t=e.target,i=t.hasAttribute("grid-event")?t:t.closest("[grid-event]");if(!i)return;const s=i.closest("tr")??i.closest(".grid-row"),o=Number(s?.dataset.rowIndex),r=this.isInfiniteMode?this.allLoadedItems:this.displayedItems,n=Number.isInteger(o)&&o>=0?r[o]:void 0;this.dispatchEvent(new CustomEvent("grid-event",{detail:{grid:this,target:i,event:i.getAttribute("grid-event")??"",data:n??{}},bubbles:!1,composed:!0})),e.stopPropagation()},this.syncHeaderScroll=()=>{const e=this.virtualizerRef.value,t=this.gridHeaderRowRef.value;e&&t&&(t.scrollLeft=e.scrollLeft)},this.handleVirtualizerWheel=e=>{const t=this.infiniteContainerRef.value;if(!t)return;const i=t.getBoundingClientRect(),s=window.innerHeight,o=i.top>=0&&i.bottom<=s,r=i.top<=0&&i.bottom>=s;!o&&!r&&(e.preventDefault(),window.scrollBy(0,e.deltaY))},this.handleSearch=e=>{const t=e.detail.toLowerCase();this.isInfiniteMode?(this.searchDebounceTimer&&clearTimeout(this.searchDebounceTimer),this.searchDebounceTimer=setTimeout(async()=>{this.searchTerm=t,await this.resetAndReload().catch(()=>{})},300)):(this.searchTerm=t,this.filteredItems=this.applySearchTerm(this.items),this.sortColumn?this.sort({emitItemsChanged:!1,pageNumber:1}):this.setPage(1),this.dispatchItemsChanged())}}get items(){return this.itemsBacker}set items(e){this.applyPagedItems(e)}applyPagedItems(e,t={}){const i=t.emitItemsChanged??!0,s=t.pageNumber??this.pageNumber??1;this.itemsBacker=e,this.filteredItems=this.applySearchTerm(this.itemsBacker),this.sortColumn?this.sort({emitItemsChanged:!1,pageNumber:s}):this.setPage(s),i&&this.dispatchItemsChanged()}get fetchPage(){return this.fetchPageBacker}set fetchPage(e){this.fetchPageBacker=e,e&&this.hasUpdated&&this.loadPage(null).then(async()=>{await this.updateComplete,this.measurePinnedOffsets()}).catch(()=>{})}get isInfiniteMode(){return this.fetchPage!==null}get currentDataStateItems(){return this.isInfiniteMode?this.allLoadedItems:this.filteredItems}getCurrentSortField(){return this.sortColumn?this.sortColumn.sortField.length>0?this.sortColumn.sortField:this.sortColumn.fieldName:""}createDataStateDetail(e={}){const t=[...this.currentDataStateItems],i=e.cursor??null,s=e.isFirstPage??(this.isInfiniteMode?i===null:this.pageNumber<=1);return{items:t,itemCount:t.length,isFirstPage:s,cursor:i,nextCursor:this.nextCursor,hasRows:t.length>0,isEmpty:t.length===0,search:this.searchTerm,sortField:this.getCurrentSortField(),sortOrder:this.sortColumn?.sortOrder??""}}dispatchGridDataEvent(e,t){this.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0}))}dispatchItemsChanged(e={}){this.dispatchGridDataEvent(j,this.createDataStateDetail(e))}setPage(e){const t=Math.ceil(this.filteredItems.length/this.pageSize);e>t&&(e=t),e<1&&(e=1),this.pageNumber=e;const i=(this.pageNumber-1)*this.pageSize;switch(this.displayedItems=this.filteredItems.slice(i,i+this.pageSize),this.allowPrevious=this.pageNumber>1,this.allowNext=t>this.pageNumber,t){case 0:this.footerMessage="No matching items";break;case 1:this.footerMessage=this.filteredItems.length<this.items.length?"Showing all filtered items":"Showing all items";break;default:this.footerMessage=`Showing page ${this.pageNumber} of ${t} pages`}}async loadPage(e){const t=this.fetchPage;if(!t||e!==null&&this.isLoadingPage)return;const i=++this.pageLoadVersion,s=e===null;let o=!1;this.isLoadingPage=!0,this.isLoadingFirstPage=s,s&&(this.nextCursor=null,this.hasMoreData=!1);const r={cursor:e,limit:this.pageSize,search:this.searchTerm,sortField:this.getCurrentSortField(),sortOrder:this.sortColumn?.sortOrder??""};this.dispatchGridDataEvent(L,this.createDataStateDetail({cursor:e,isFirstPage:s}));try{const n=await t(r);if(i!==this.pageLoadVersion)return;e===null?this.allLoadedItems=[...n.items]:this.allLoadedItems=[...this.allLoadedItems,...n.items],this.nextCursor=n.nextCursor,this.hasMoreData=n.nextCursor!==null,o=!0,this.dispatchGridDataEvent(M,this.createDataStateDetail({cursor:e,isFirstPage:s})),this.dispatchItemsChanged({cursor:e,isFirstPage:s})}catch(n){throw i===this.pageLoadVersion&&this.dispatchGridDataEvent(z,{...this.createDataStateDetail({cursor:e,isFirstPage:s}),error:n}),n}finally{if(i===this.pageLoadVersion){if(this.isLoadingPage=!1,this.isLoadingFirstPage=!1,s&&o){const n=this.virtualizerRef.value;if(n&&n.scrollTop>0)try{n.scrollTo({top:0})}catch{n.scrollTop=0}}await this.adjustInfiniteHeight()}}}async resetAndReload(){await this.loadPage(null)}onRangeChanged(e){this.isLoadingFirstPage||e.last>=this.allLoadedItems.length-5&&this.hasMoreData&&!this.isLoadingPage&&this.loadPage(this.nextCursor).catch(()=>{})}async adjustInfiniteHeight(){if(!this.isAdjustingHeight){this.isAdjustingHeight=!0;try{const e=this.virtualizerRef.value;e&&(e.style.minHeight=""),this.effectiveGridHeight=this.gridHeight,await this.updateComplete;const t=this.infiniteContainerRef.value,i=this.virtualizerRef.value;if(!t||this.hasMoreData)return;const o=this.gridHeaderRowRef.value?.offsetHeight??0;if(!i){const p=t.querySelector(".no-results");let f=0;p?f=o+p.offsetHeight:t.querySelectorAll(":scope > *").forEach(R=>f+=R.offsetHeight),f<t.offsetHeight&&(this.effectiveGridHeight=`${f}px`);return}const r=i.querySelectorAll(".grid-row");let n=0,a=!1;if(r.forEach(p=>{const f=p.offsetHeight;f===0&&(a=!0),n+=f}),r.length===0||a||n===0){this.pendingHeightRetry||(this.pendingHeightRetry=!0,this.observeForHeightRetry(i));return}const l=i.querySelectorAll(".grid-row :defined"),g=[];l.forEach(p=>{"updateComplete"in p&&g.push(p.updateComplete)}),g.length>0&&(await Promise.all(g),n=0,r.forEach(p=>{n+=p.offsetHeight}));const v=n+o,b=t.offsetHeight;v<b&&r.length>=this.allLoadedItems.length&&(i.style.minHeight=`${n}px`,this.effectiveGridHeight=`${v}px`),!this.hasMoreData&&!this.pendingHeightRetry&&(this.pendingHeightRetry=!0,setTimeout(()=>{this.pendingHeightRetry=!1;const p=this.infiniteContainerRef.value,f=this.virtualizerRef.value;if(!p||!f||this.hasMoreData)return;const O=this.gridHeaderRowRef.value?.offsetHeight??0,k=f.querySelectorAll(".grid-row");let C=0,D=!1;if(k.forEach(F=>{const H=F.offsetHeight;H===0&&(D=!0),C+=H}),k.length===0||D||C===0)return;const $=C+O;$<p.offsetHeight&&k.length>=this.allLoadedItems.length&&(f.style.minHeight=`${C}px`,this.effectiveGridHeight=`${$}px`)},100))}finally{this.isAdjustingHeight=!1}}}observeForHeightRetry(e){this.heightRetryObserver?.disconnect(),this.heightRetryObserver=new IntersectionObserver(t=>{if(!t.some(r=>r.isIntersecting))return;this.heightRetryObserver?.disconnect(),this.heightRetryObserver=null;let s=0;const o=()=>{this.pendingHeightRetry=!1,this.adjustInfiniteHeight(),this.pendingHeightRetry&&++s<5&&setTimeout(o,100)};requestAnimationFrame(()=>setTimeout(o,50))},{threshold:0}),this.heightRetryObserver.observe(e)}async sortOn(e){this.sortColumn===e?this.sortColumn.sortOrder=this.sortColumn.sortOrder=="asc"?"desc":"asc":(this.sortColumn=e,this.sortColumn.sortOrder="asc"),this.isInfiniteMode?await this.resetAndReload():this.sort()}sort(e={}){if(!this.sortColumn)return;const t=this.getCurrentSortField(),i=this.sortColumn.sortOrder==="asc"?1:-1,s=this.sortColumn.sortType,o=this.filteredItems.map((r,n)=>{const a=r[t]??"",l=s==="number"?Number(a):a.toString().toLowerCase();return{item:r,index:n,sortValue:l}});o.sort((r,n)=>r.sortValue<n.sortValue?-1*i:r.sortValue>n.sortValue?1*i:r.index-n.index),this.filteredItems=o.map(({item:r})=>r),this.setPage(e.pageNumber??1),(e.emitItemsChanged??!0)&&this.dispatchItemsChanged()}delete(e){if(this.isInfiniteMode){const t=this.allLoadedItems.filter(i=>!e(i));if(t.length===this.allLoadedItems.length)return;this.allLoadedItems=t,this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else{const t=this.items.filter(i=>!e(i));if(t.length===this.items.length)return;this.items=t}}addOrReplace(e,t){if(this.isInfiniteMode){const i=this.allLoadedItems.findIndex(e);if(i>=0){const s=[...this.allLoadedItems];s[i]={...s[i],...t},this.allLoadedItems=s}else this.allLoadedItems=[...this.allLoadedItems,t];this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else this.items.find(e)?this.items=this.items.map(s=>e(s)?{...s,...t}:s):this.items=[...this.items,t]}addInOrder(e,t,i){if(this.isInfiniteMode){const a=this.allLoadedItems.findIndex(e),l=[...this.allLoadedItems];if(a>=0)return l[a]={...l[a],...t},this.allLoadedItems=l,this.dispatchItemsChanged(),a;let g=0,v=l.length;for(;g<v;){const b=g+v>>>1;i(l[b],t)<0?g=b+1:v=b}return l.splice(g,0,t),this.allLoadedItems=l,this.dispatchItemsChanged(),this.adjustInfiniteHeight(),g}const s=this.items.findIndex(e),o=[...this.items];if(s>=0)return o[s]={...o[s],...t},this.items=o,s;let r=0,n=o.length;for(;r<n;){const a=r+n>>>1;i(o[a],t)<0?r=a+1:n=a}return o.splice(r,0,t),this.items=o,r}async scrollToIndex(e,t="center"){if(this.isInfiniteMode){await this.updateComplete;const i=this.virtualizerRef.value;if(!i)return;await i.updateComplete,await new Promise(s=>requestAnimationFrame(s)),await i.layoutComplete,i.scrollToIndex(e,t)}else{const i=Math.floor(e/this.pageSize)+1;this.setPage(i)}}clear(){if(this.isInfiniteMode){if(this.allLoadedItems.length===0&&this.nextCursor===null&&!this.hasMoreData)return;this.allLoadedItems=[],this.nextCursor=null,this.hasMoreData=!1,this.dispatchItemsChanged(),this.adjustInfiniteHeight()}else{if(this.items.length===0)return;this.items=[]}}async reload(){this.isInfiniteMode&&await this.resetAndReload()}computePinnedStyles(){return this.pinnedOffsets}measurePinnedOffsets(){this.pinnedOffsets=new Map,this.isInfiniteMode?this.computePinnedOffsetsFromWidths():this.measurePinnedOffsetsFromCells(),this.requestUpdate()}computePinnedOffsetsFromWidths(){const e=this.columnDefinitions.filter(r=>r.pin==="left"),t=this.columnDefinitions.filter(r=>r.pin==="right"),i=[];for(let r=0;r<e.length;r++){const n=e[r],a=i.length===0?"0px":`calc(${i.join(" + ")})`;this.pinnedOffsets.set(n,{position:"sticky",left:a,zIndex:`${e.length-r+1}`}),i.push(n.width||"0px")}const s=[],o=[...t].reverse();for(let r=0;r<o.length;r++){const n=o[r],a=s.length===0?"0px":`calc(${s.join(" + ")})`;this.pinnedOffsets.set(n,{position:"sticky",right:a,zIndex:`${o.length-r+1}`}),s.push(n.width||"0px")}}measurePinnedOffsetsFromCells(){const e=this.shadowRoot?.querySelectorAll("thead th");if(!e)return;const t=this.columnDefinitions.filter(a=>a.pin==="left"),i=this.columnDefinitions.filter(a=>a.pin==="right"),s=new Map;this.columnDefinitions.forEach((a,l)=>{e[l]&&s.set(a,e[l])});let o=0;for(let a=0;a<t.length;a++){const l=t[a];this.pinnedOffsets.set(l,{position:"sticky",left:`${o}px`,zIndex:`${t.length-a+1}`});const g=s.get(l);g&&(o+=g.offsetWidth)}let r=0;const n=[...i].reverse();for(let a=0;a<n.length;a++){const l=n[a];this.pinnedOffsets.set(l,{position:"sticky",right:`${r}px`,zIndex:`${n.length-a+1}`});const g=s.get(l);g&&(r+=g.offsetWidth)}}computeGridTemplateColumns(){return this.columnDefinitions.map(e=>e.width?e.grow?`minmax(${e.width}, 1fr)`:e.width:e.grow?"minmax(0, 1fr)":"auto").join(" ")}get hasGrowableColumns(){return this.columnDefinitions.some(e=>e.grow)}computePinnedColumnFlags(){const e=new Map,t=this.columnDefinitions.filter(r=>r.pin==="left"),i=this.columnDefinitions.filter(r=>r.pin==="right"),s=t[t.length-1],o=i[0];return this.columnDefinitions.forEach((r,n)=>{e.set(r,{beforePinnedRight:this.columnDefinitions[n+1]?.pin==="right",firstPinnedRight:o===r,lastPinnedLeft:s===r})}),e}renderCell(e,t){if(!e.fieldName)return c`<span></span>`;const i=e.textAlign??"left";return c`<span style="text-align: ${i};"> ${t[e.fieldName]} </span>`}attachWheelHandler(){const e=this.virtualizerRef.value;e&&!this.wheelHandlerAttached?(e.addEventListener("wheel",this.handleVirtualizerWheel,{passive:!1}),this.wheelHandlerAttached=!0):!e&&this.wheelHandlerAttached&&(this.wheelHandlerAttached=!1)}applySearchTerm(e){return this.searchTerm.length===0?e:e.filter(t=>{let i;return this.searchFields.length>0?i=this.searchFields.map(s=>t[s]):i=Object.values(t),i.some(s=>String(s).toLowerCase().includes(this.searchTerm))})}async firstUpdated(e){super.firstUpdated(e),this.headerButtonsSlot.value.assignedElements().length===0&&this.headerButtonsSlot.value.remove();for(const i of this.columnDefinitionsSlot.value.assignedElements())i.localName==="esp-grid-column"&&this.columnDefinitions.push(i);const t=this.columnDefinitions.find(i=>i.sortOrder!=="");t&&(this.sortColumn=t),this.isInfiniteMode?await this.loadPage(null).catch(()=>{}):this.dataUrl.length&&await this.loadDataUrl().catch(()=>{}),await this.updateComplete,this.measurePinnedOffsets()}updated(e){super.updated(e),this.isInfiniteMode&&this.attachWheelHandler()}async loadDataUrl(){this.dispatchGridDataEvent(L,this.createDataStateDetail({cursor:null,isFirstPage:!0}));try{const t=await fetch(this.dataUrl).then(i=>i.json());this.applyPagedItems(this.dataField?t[this.dataField]:t,{emitItemsChanged:!1}),this.dispatchGridDataEvent(M,this.createDataStateDetail({cursor:null,isFirstPage:!0})),this.dispatchItemsChanged({cursor:null,isFirstPage:!0})}catch(t){throw this.dispatchGridDataEvent(z,{...this.createDataStateDetail({cursor:null,isFirstPage:!0}),error:t}),t}}disconnectedCallback(){super.disconnectedCallback();const e=this.virtualizerRef.value;e&&e.removeEventListener("wheel",this.handleVirtualizerWheel),this.wheelHandlerAttached=!1,this.heightRetryObserver?.disconnect(),this.heightRetryObserver=null}renderSortIcons(){return c`
2
2
  <svg
3
3
  xmlns="http://www.w3.org/2000/svg"
4
4
  viewBox="0 0 24 24"
@@ -37,7 +37,7 @@ var h=function(I,e,t,i){var s=arguments.length,o=s<3?e:i===null?i=Object.getOwnP
37
37
  <slot ${y(this.columnDefinitionsSlot)}></slot>
38
38
 
39
39
  <div class="header-controls">
40
- <esp-input fieldName="filter" @value-changed=${this.handleSearch}> ${G} </esp-input>
40
+ <esp-input fieldName="filter" @value-changed=${this.handleSearch}> ${N} </esp-input>
41
41
  <slot name="header-buttons" ${y(this.headerButtonsSlot)}></slot>
42
42
  </div>
43
43
 
@@ -79,7 +79,7 @@ var h=function(I,e,t,i){var s=arguments.length,o=s<3?e:i===null?i=Object.getOwnP
79
79
  .disabled=${!this.allowPrevious}
80
80
  @clicked=${i=>{this.setPage(this.pageNumber-1),i.stopPropagation()}}
81
81
  >
82
- ${N}
82
+ ${T}
83
83
  </esp-button>
84
84
  <h4>${this.footerMessage}</h4>
85
85
  <esp-button
@@ -87,7 +87,7 @@ var h=function(I,e,t,i){var s=arguments.length,o=s<3?e:i===null?i=Object.getOwnP
87
87
  .disabled=${!this.allowNext}
88
88
  @clicked=${i=>{this.setPage(this.pageNumber+1),i.stopPropagation()}}
89
89
  >
90
- ${T}
90
+ ${G}
91
91
  </esp-button>
92
92
  </div>
93
93
  `}renderInfiniteMode(e,t){const i=this.computeGridTemplateColumns(),s=this.hasGrowableColumns?"":"width: max-content; min-width: 100%;",o=(r,n)=>this.renderVirtualRow(r,n,e,t,i);return c`
@@ -1,6 +1,6 @@
1
1
  import { LitElement, type PropertyValues } from "lit";
2
2
  import { type EspalierPickerItem, type PickerItem } from "./esp-picker-item.js";
3
- import "@lit-labs/virtualizer";
3
+ import "../shared/virtualizer/lit-virtualizer.js";
4
4
  /**
5
5
  * A menu used by Espalier pickers when choosing option(s).
6
6
  *
@@ -1,4 +1,4 @@
1
- var n=function(d,t,e,i){var l=arguments.length,s=l<3?t:i===null?i=Object.getOwnPropertyDescriptor(t,e):i,o;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")s=Reflect.decorate(d,t,e,i);else for(var h=d.length-1;h>=0;h--)(o=d[h])&&(s=(l<3?o(s):l>3?o(t,e,s):o(t,e))||s);return l>3&&s&&Object.defineProperty(t,e,s),s};import{LitElement as u,css as f,html as p}from"lit";import{customElement as v,property as g,state as m}from"lit/decorators.js";import{createRef as y,ref as I}from"lit/directives/ref.js";import"@lit-labs/virtualizer";import{styleMap as x}from"lit/directives/style-map.js";const c="highlighted";let r=class extends u{constructor(){super(),this.internals=this.attachInternals(),this.virtualizerRef=y(),this.maxAvailableHeight=0,this.lastViewportHeight=0,this.label="",this.virtualizedItemsPool=[],this.highlightIndex=-1,this.multiSelect=!1,this.loading=!1,this.emptyMessage="",this.handleItemPointerDown=t=>{this.selectItemFromPointerEvent(t)},this.renderPickerItem=(t,e)=>{const i={display:"block",cursor:"pointer",width:"100%",...t.styles};return p`<esp-picker-item
1
+ var n=function(d,t,e,i){var l=arguments.length,s=l<3?t:i===null?i=Object.getOwnPropertyDescriptor(t,e):i,o;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")s=Reflect.decorate(d,t,e,i);else for(var h=d.length-1;h>=0;h--)(o=d[h])&&(s=(l<3?o(s):l>3?o(t,e,s):o(t,e))||s);return l>3&&s&&Object.defineProperty(t,e,s),s};import{LitElement as u,css as f,html as p}from"lit";import{customElement as v,property as g,state as m}from"lit/decorators.js";import{createRef as y,ref as I}from"lit/directives/ref.js";import{styleMap as x}from"lit/directives/style-map.js";import"../shared/virtualizer/lit-virtualizer.js";const c="highlighted";let r=class extends u{constructor(){super(),this.internals=this.attachInternals(),this.virtualizerRef=y(),this.maxAvailableHeight=0,this.lastViewportHeight=0,this.label="",this.virtualizedItemsPool=[],this.highlightIndex=-1,this.multiSelect=!1,this.loading=!1,this.emptyMessage="",this.handleItemPointerDown=t=>{this.selectItemFromPointerEvent(t)},this.renderPickerItem=(t,e)=>{const i={display:"block",cursor:"pointer",width:"100%",...t.styles};return p`<esp-picker-item
2
2
  class="picker-item"
3
3
  data-picker-index=${e}
4
4
  .text=${t.text}
@@ -1,6 +1,6 @@
1
- import "@lit-labs/virtualizer";
2
1
  import { nothing, type PropertyValues, type TemplateResult } from "lit";
3
2
  import { EspalierElementBase } from "../shared/esp-element-base.js";
3
+ import "../shared/virtualizer/lit-virtualizer.js";
4
4
  export interface RepeaterFetchParams {
5
5
  cursor: string | null;
6
6
  limit: number;
@@ -1,4 +1,4 @@
1
- var l=function(y,e,t,i){var r=arguments.length,s=r<3?e:i===null?i=Object.getOwnPropertyDescriptor(e,t):i,o;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")s=Reflect.decorate(y,e,t,i);else for(var g=y.length-1;g>=0;g--)(o=y[g])&&(s=(r<3?o(s):r>3?o(e,t,s):o(e,t))||s);return r>3&&s&&Object.defineProperty(e,t,s),s};import"@lit-labs/virtualizer";import{css as T,html as d,nothing as I}from"lit";import{customElement as F,property as h,state as b}from"lit/decorators.js";import{keyed as j}from"lit/directives/keyed.js";import{ifDefined as M}from"lit/directives/if-defined.js";import{createRef as G,ref as O}from"lit/directives/ref.js";import{styleMap as A}from"lit/directives/style-map.js";import{EspalierElementBase as E}from"../shared/esp-element-base.js";let a=class extends E{constructor(){super(...arguments),this.virtualizerRef=G(),this.containerRef=G(),this.pageLoadVersion=0,this.nextCursor=null,this.lastObservedWidth=0,this.observersAttached=!1,this.gridObserversAttached=!1,this.resolvedGridColumns=1,this.memoizedGridRowsSource=null,this.memoizedGridRowsColumns=0,this.memoizedGridRows=[],this.hostAttributeObserver=null,this.resizeObserver=null,this.viewportResizeListener=null,this.pageScrollStabilizerActive=!1,this.activePageScrollStabilizer=null,this.isAdjustingHeight=!1,this.pendingHeightRetry=!1,this.heightRetryObserver=null,this.isLoadingPage=!1,this.loadedItems=[],this.hasMoreData=!1,this.effectiveListHeight="60vh",this.loadError="",this.items=[],this.renderItem=null,this.layout="list",this.scrollModel="contained",this.gridColumns=1,this.ariaLabel=null,this.listHeight="60vh",this.pageSize=25,this.prefetchThreshold=5,this.loading=!1,this.loadingMessage="Loading items\u2026",this.emptyMessage="No items found",this.errorMessage="",this.fetchPageBacker=null,this.renderVirtualItem=(e,t)=>{if(e===void 0)return d``;const i=this.renderItem??(r=>this.renderFallbackItem(r));return d`<div class="repeater-item" part="item" role="listitem">
1
+ var l=function(y,e,t,i){var r=arguments.length,s=r<3?e:i===null?i=Object.getOwnPropertyDescriptor(e,t):i,o;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")s=Reflect.decorate(y,e,t,i);else for(var g=y.length-1;g>=0;g--)(o=y[g])&&(s=(r<3?o(s):r>3?o(e,t,s):o(e,t))||s);return r>3&&s&&Object.defineProperty(e,t,s),s};import{css as T,html as d,nothing as I}from"lit";import{customElement as F,property as h,state as b}from"lit/decorators.js";import{keyed as j}from"lit/directives/keyed.js";import{ifDefined as M}from"lit/directives/if-defined.js";import{createRef as G,ref as O}from"lit/directives/ref.js";import{styleMap as A}from"lit/directives/style-map.js";import{EspalierElementBase as E}from"../shared/esp-element-base.js";import"../shared/virtualizer/lit-virtualizer.js";let a=class extends E{constructor(){super(...arguments),this.virtualizerRef=G(),this.containerRef=G(),this.pageLoadVersion=0,this.nextCursor=null,this.lastObservedWidth=0,this.observersAttached=!1,this.gridObserversAttached=!1,this.resolvedGridColumns=1,this.memoizedGridRowsSource=null,this.memoizedGridRowsColumns=0,this.memoizedGridRows=[],this.hostAttributeObserver=null,this.resizeObserver=null,this.viewportResizeListener=null,this.pageScrollStabilizerActive=!1,this.activePageScrollStabilizer=null,this.isAdjustingHeight=!1,this.pendingHeightRetry=!1,this.heightRetryObserver=null,this.isLoadingPage=!1,this.loadedItems=[],this.hasMoreData=!1,this.effectiveListHeight="60vh",this.loadError="",this.items=[],this.renderItem=null,this.layout="list",this.scrollModel="contained",this.gridColumns=1,this.ariaLabel=null,this.listHeight="60vh",this.pageSize=25,this.prefetchThreshold=5,this.loading=!1,this.loadingMessage="Loading items\u2026",this.emptyMessage="No items found",this.errorMessage="",this.fetchPageBacker=null,this.renderVirtualItem=(e,t)=>{if(e===void 0)return d``;const i=this.renderItem??(r=>this.renderFallbackItem(r));return d`<div class="repeater-item" part="item" role="listitem">
2
2
  ${i(e,t)}
3
3
  </div>`},this.renderVirtualRow=e=>{if(e===void 0)return d``;const t=this.renderItem??(r=>this.renderFallbackItem(r)),i={gridTemplateColumns:`repeat(${this.effectiveGridColumns}, minmax(0, 1fr))`};return d`<div
4
4
  class="repeater-row"
@@ -0,0 +1 @@
1
+ var l=function(u,e,r,o){var i=arguments.length,t=i<3?e:o===null?o=Object.getOwnPropertyDescriptor(e,r):o,c;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")t=Reflect.decorate(u,e,r,o);else for(var p=u.length-1;p>=0;p--)(c=u[p])&&(t=(i<3?c(t):i>3?c(e,r,t):c(e,r))||t);return i>3&&t&&Object.defineProperty(e,r,t),t};import{html as a,LitElement as f}from"lit";import{property as n}from"lit/decorators/property.js";import{virtualize as d,virtualizerRef as m,defaultRenderItem as y,defaultKeyFunction as h}from"./virtualize.js";class s extends f{constructor(){super(...arguments),this.items=[],this.renderItem=y,this.keyFunction=h,this.layout={},this.scroller=!1}createRenderRoot(){return this}render(){const{items:e,renderItem:r,keyFunction:o,layout:i,scroller:t}=this;return a`${d({items:e,renderItem:r,keyFunction:o,layout:i,scroller:t})}`}element(e){return this[m]?.element(e)}get layoutComplete(){return this[m]?.layoutComplete}scrollToIndex(e,r="start"){this.element(e)?.scrollIntoView({block:r})}}l([n({attribute:!1})],s.prototype,"items",void 0),l([n()],s.prototype,"renderItem",void 0),l([n()],s.prototype,"keyFunction",void 0),l([n({attribute:!1})],s.prototype,"layout",void 0),l([n({reflect:!0,type:Boolean})],s.prototype,"scroller",void 0);export{s as LitVirtualizer};
@@ -0,0 +1 @@
1
+ class n{constructor(t){this._element=null;const i=t??window;this._node=i,t&&(this._element=t)}get element(){return this._element||document.scrollingElement||document.documentElement}get scrollTop(){return this.element.scrollTop||window.scrollY}get scrollLeft(){return this.element.scrollLeft||window.scrollX}get scrollHeight(){return this.element.scrollHeight}get scrollWidth(){return this.element.scrollWidth}get viewportHeight(){return this._element?this._element.getBoundingClientRect().height:window.innerHeight}get viewportWidth(){return this._element?this._element.getBoundingClientRect().width:window.innerWidth}get maxScrollTop(){return this.scrollHeight-this.viewportHeight}get maxScrollLeft(){return this.scrollWidth-this.viewportWidth}}class h extends n{constructor(t,i){super(i),this._clients=new Set,this._retarget=null,this._end=null,this.__destination=null,this.correctingScrollError=!1,this._checkForArrival=this._checkForArrival.bind(this),this._updateManagedScrollTo=this._updateManagedScrollTo.bind(this),this.scrollTo=this.scrollTo.bind(this),this.scrollBy=this.scrollBy.bind(this);const e=this._node;this._originalScrollTo=e.scrollTo,this._originalScrollBy=e.scrollBy,this._originalScroll=e.scroll,this._attach(t)}get _destination(){return this.__destination}get scrolling(){return this._destination!==null}scrollTo(t,i){const e=typeof t=="number"&&typeof i=="number"?{left:t,top:i}:t;this._scrollTo(e)}scrollBy(t,i){const e=typeof t=="number"&&typeof i=="number"?{left:t,top:i}:t;e.top!==void 0&&(e.top+=this.scrollTop),e.left!==void 0&&(e.left+=this.scrollLeft),this._scrollTo(e)}_nativeScrollTo(t){this._originalScrollTo.bind(this._element||window)(t)}_scrollTo(t,i=null,e=null){this._end!==null&&this._end(),t.behavior==="smooth"?(this._setDestination(t),this._retarget=i,this._end=e):this._resetScrollState(),this._nativeScrollTo(t)}_setDestination(t){let{top:i,left:e}=t;return i=i===void 0?void 0:Math.max(0,Math.min(i,this.maxScrollTop)),e=e===void 0?void 0:Math.max(0,Math.min(e,this.maxScrollLeft)),this._destination!==null&&e===this._destination.left&&i===this._destination.top?!1:(this.__destination={top:i,left:e,behavior:"smooth"},!0)}_resetScrollState(){this.__destination=null,this._retarget=null,this._end=null}_updateManagedScrollTo(t){this._destination&&this._setDestination(t)&&this._nativeScrollTo(this._destination)}managedScrollTo(t,i,e){return this._scrollTo(t,i,e),this._updateManagedScrollTo}correctScrollError(t){this.correctingScrollError=!0,requestAnimationFrame(()=>requestAnimationFrame(()=>this.correctingScrollError=!1)),this._nativeScrollTo(t),this._retarget&&this._setDestination(this._retarget()),this._destination&&this._nativeScrollTo(this._destination)}_checkForArrival(){if(this._destination!==null){const{scrollTop:t,scrollLeft:i}=this;let{top:e,left:l}=this._destination;e=Math.min(e||0,this.maxScrollTop),l=Math.min(l||0,this.maxScrollLeft);const s=Math.abs(e-t),r=Math.abs(l-i);s<1&&r<1&&(this._end&&this._end(),this._resetScrollState())}}detach(t){return this._clients.delete(t),this._clients.size===0&&(this._node.scrollTo=this._originalScrollTo,this._node.scrollBy=this._originalScrollBy,this._node.scroll=this._originalScroll,this._node.removeEventListener("scroll",this._checkForArrival)),null}_attach(t){this._clients.add(t),this._clients.size===1&&(this._node.scrollTo=this.scrollTo,this._node.scrollBy=this.scrollBy,this._node.scroll=this.scrollTo,this._node.addEventListener("scroll",this._checkForArrival))}}export{h as ScrollerController,n as ScrollerShim};
@@ -0,0 +1 @@
1
+ import{RangeChangedEvent as v,VisibilityChangedEvent as S,UnpinnedEvent as L}from"./events.js";import{ScrollerController as V}from"./ScrollerController.js";let d=typeof window<"u"?window.ResizeObserver:void 0;function I(n){d=n}const R=Symbol("virtualizerRef"),_="virtualizer-sizer";let f;class T{constructor(t){if(this._benchmarkStart=null,this._layout=null,this._clippingAncestors=[],this._scrollSize=null,this._scrollError=null,this._childrenPos=null,this._childMeasurements=null,this._toBeMeasured=new Map,this._rangeChanged=!0,this._itemsChanged=!0,this._visibilityChanged=!0,this._scrollerController=null,this._isScroller=!1,this._sizer=null,this._hostElementRO=null,this._childrenRO=null,this._mutationObserver=null,this._scrollEventListeners=[],this._scrollEventListenerOptions={passive:!0},this._loadListener=this._childLoaded.bind(this),this._scrollIntoViewTarget=null,this._updateScrollIntoViewCoordinates=null,this._items=[],this._first=-1,this._last=-1,this._firstVisible=-1,this._lastVisible=-1,this._scheduled=new WeakSet,this._measureCallback=null,this._measureChildOverride=null,this._layoutCompletePromise=null,this._layoutCompleteResolver=null,this._layoutCompleteRejecter=null,this._pendingLayoutComplete=null,this._layoutInitialized=null,this._connected=!1,!t)throw new Error("Virtualizer constructor requires a configuration object");if(t.hostElement)this._init(t);else throw new Error('Virtualizer configuration requires the "hostElement" property')}set items(t){Array.isArray(t)&&t!==this._items&&(this._itemsChanged=!0,this._items=t,this._schedule(this._updateLayout))}_init(t){this._isScroller=!!t.scroller,this._initHostElement(t);const e=t.layout||{};this._layoutInitialized=this._initLayout(e)}_initObservers(){this._mutationObserver=new MutationObserver(this._finishDOMUpdate.bind(this)),this._hostElementRO=new d(()=>this._hostElementSizeChanged()),this._childrenRO=new d(this._childrenSizeChanged.bind(this))}_initHostElement(t){const e=this._hostElement=t.hostElement;this._applyVirtualizerStyles(),e[R]=this}connected(){this._initObservers();const t=this._isScroller;this._clippingAncestors=x(this._hostElement,t),this._scrollerController=new V(this,this._clippingAncestors[0]),this._schedule(this._updateLayout),this._observeAndListen(),this._connected=!0}_observeAndListen(){this._mutationObserver.observe(this._hostElement,{childList:!0}),this._hostElementRO.observe(this._hostElement),this._scrollEventListeners.push(window),window.addEventListener("scroll",this,this._scrollEventListenerOptions),this._clippingAncestors.forEach(t=>{t.addEventListener("scroll",this,this._scrollEventListenerOptions),this._scrollEventListeners.push(t),this._hostElementRO.observe(t)}),this._hostElementRO.observe(this._scrollerController.element),this._children.forEach(t=>this._childrenRO.observe(t)),this._scrollEventListeners.forEach(t=>t.addEventListener("scroll",this,this._scrollEventListenerOptions))}disconnected(){this._scrollEventListeners.forEach(t=>t.removeEventListener("scroll",this,this._scrollEventListenerOptions)),this._scrollEventListeners=[],this._clippingAncestors=[],this._scrollerController?.detach(this),this._scrollerController=null,this._mutationObserver?.disconnect(),this._mutationObserver=null,this._hostElementRO?.disconnect(),this._hostElementRO=null,this._childrenRO?.disconnect(),this._childrenRO=null,this._rejectLayoutCompletePromise("disconnected"),this._connected=!1}_applyVirtualizerStyles(){const e=this._hostElement.style;e.display=e.display||"block",e.position=e.position||"relative",e.contain=e.contain||"size layout",this._isScroller&&(e.overflow=e.overflow||"auto",e.minHeight=e.minHeight||"150px")}_getSizer(){const t=this._hostElement;if(!this._sizer){let e=t.querySelector(`[${_}]`);e||(e=document.createElement("div"),e.setAttribute(_,""),t.appendChild(e)),Object.assign(e.style,{position:"absolute",margin:"-2px 0 0 0",padding:0,visibility:"hidden",fontSize:"2px"}),e.textContent="&nbsp;",e.setAttribute(_,""),this._sizer=e}return this._sizer}async updateLayoutConfig(t){await this._layoutInitialized;const e=t.type||f;if(typeof e=="function"&&this._layout instanceof e){const i={...t};return delete i.type,this._layout.config=i,!0}return!1}async _initLayout(t){let e,i;if(typeof t.type=="function"){i=t.type;const s={...t};delete s.type,e=s}else e=t;i===void 0&&(f=i=(await import("./layouts/flow.js")).FlowLayout),this._layout=new i(s=>this._handleLayoutMessage(s),e),this._layout.measureChildren&&typeof this._layout.updateItemSizes=="function"&&(typeof this._layout.measureChildren=="function"&&(this._measureChildOverride=this._layout.measureChildren),this._measureCallback=this._layout.updateItemSizes.bind(this._layout)),this._layout.listenForChildLoadEvents&&this._hostElement.addEventListener("load",this._loadListener,!0),this._schedule(this._updateLayout)}startBenchmarking(){this._benchmarkStart===null&&(this._benchmarkStart=window.performance.now())}stopBenchmarking(){if(this._benchmarkStart!==null){const t=window.performance.now(),e=t-this._benchmarkStart,s=performance.getEntriesByName("uv-virtualizing","measure").filter(l=>l.startTime>=this._benchmarkStart&&l.startTime<t).reduce((l,r)=>l+r.duration,0);return this._benchmarkStart=null,{timeElapsed:e,virtualizationTime:s}}return null}_measureChildren(){const t={},e=this._children,i=this._measureChildOverride||this._measureChild;for(let s=0;s<e.length;s++){const l=e[s],r=this._first+s;(this._itemsChanged||this._toBeMeasured.has(l))&&(t[r]=i.call(this,l,this._items[r]))}this._childMeasurements=t,this._schedule(this._updateLayout),this._toBeMeasured.clear()}_measureChild(t){const{width:e,height:i}=t.getBoundingClientRect();return Object.assign({width:e,height:i},O(t))}async _schedule(t){this._scheduled.has(t)||(this._scheduled.add(t),await Promise.resolve(),this._scheduled.delete(t),t.call(this))}async _updateDOM(t){this._scrollSize=t.scrollSize,this._adjustRange(t.range),this._childrenPos=t.childPositions,this._scrollError=t.scrollError||null;const{_rangeChanged:e,_itemsChanged:i}=this;this._visibilityChanged&&(this._notifyVisibility(),this._visibilityChanged=!1),(e||i)&&(this._notifyRange(),this._rangeChanged=!1),this._finishDOMUpdate()}_finishDOMUpdate(){this._connected&&(this._children.forEach(t=>this._childrenRO.observe(t)),this._checkScrollIntoViewTarget(this._childrenPos),this._positionChildren(this._childrenPos),this._sizeHostElement(this._scrollSize),this._correctScrollError(),this._benchmarkStart&&"mark"in window.performance&&window.performance.mark("uv-end"))}_updateLayout(){this._layout&&this._connected&&(this._layout.items=this._items,this._updateView(),this._childMeasurements!==null&&(this._measureCallback&&this._measureCallback(this._childMeasurements),this._childMeasurements=null),this._layout.reflowIfNeeded(),this._benchmarkStart&&"mark"in window.performance&&window.performance.mark("uv-end"))}_handleScrollEvent(){if(this._benchmarkStart&&"mark"in window.performance){try{window.performance.measure("uv-virtualizing","uv-start","uv-end")}catch(t){console.warn("Error measuring performance data: ",t)}window.performance.mark("uv-start")}this._scrollerController.correctingScrollError===!1&&this._layout?.unpin(),this._schedule(this._updateLayout)}handleEvent(t){switch(t.type){case"scroll":(t.currentTarget===window||this._clippingAncestors.includes(t.currentTarget))&&this._handleScrollEvent();break;default:console.warn("event not handled",t)}}_handleLayoutMessage(t){t.type==="stateChanged"?this._updateDOM(t):t.type==="visibilityChanged"?(this._firstVisible=t.firstVisible,this._lastVisible=t.lastVisible,this._notifyVisibility()):t.type==="unpinned"&&this._hostElement.dispatchEvent(new L)}get _children(){const t=[];let e=this._hostElement.firstElementChild;for(;e;)e.hasAttribute(_)||t.push(e),e=e.nextElementSibling;return t}_updateView(){const t=this._hostElement,e=this._scrollerController?.element,i=this._layout;if(t&&e&&i){let s,l,r,h;const a=t.getBoundingClientRect();s=0,l=0,r=window.innerHeight,h=window.innerWidth;const o=this._clippingAncestors.map(c=>c.getBoundingClientRect());o.unshift(a);for(const c of o)s=Math.max(s,c.top),l=Math.max(l,c.left),r=Math.min(r,c.bottom),h=Math.min(h,c.right);const m=e.getBoundingClientRect(),y={left:a.left-m.left,top:a.top-m.top},g={width:e.scrollWidth,height:e.scrollHeight},C=s-a.top+t.scrollTop,E=l-a.left+t.scrollLeft,w=Math.max(0,r-s),b=Math.max(0,h-l);i.viewportSize={width:b,height:w},i.viewportScroll={top:C,left:E},i.totalScrollSize=g,i.offsetWithinScroller=y}}_sizeHostElement(t){const i=t&&t.width!==null?Math.min(82e5,t.width):0,s=t&&t.height!==null?Math.min(82e5,t.height):0;if(this._isScroller)this._getSizer().style.transform=`translate(${i}px, ${s}px)`;else{const l=this._hostElement.style;l.minWidth=i?`${i}px`:"100%",l.minHeight=s?`${s}px`:"100%"}}_positionChildren(t){t&&t.forEach(({top:e,left:i,width:s,height:l,xOffset:r,yOffset:h},a)=>{const o=this._children[a-this._first];o&&(o.style.position="absolute",o.style.boxSizing="border-box",o.style.transform=`translate(${i}px, ${e}px)`,s!==void 0&&(o.style.width=s+"px"),l!==void 0&&(o.style.height=l+"px"),o.style.left=r===void 0?null:r+"px",o.style.top=h===void 0?null:h+"px")})}async _adjustRange(t){const{_first:e,_last:i,_firstVisible:s,_lastVisible:l}=this;this._first=t.first,this._last=t.last,this._firstVisible=t.firstVisible,this._lastVisible=t.lastVisible,this._rangeChanged=this._rangeChanged||this._first!==e||this._last!==i,this._visibilityChanged=this._visibilityChanged||this._firstVisible!==s||this._lastVisible!==l}_correctScrollError(){if(this._scrollError){const{scrollTop:t,scrollLeft:e}=this._scrollerController,{top:i,left:s}=this._scrollError;this._scrollError=null,this._scrollerController.correctScrollError({top:t-i,left:e-s})}}element(t){return t===1/0&&(t=this._items.length-1),this._items?.[t]===void 0?void 0:{scrollIntoView:(e={})=>this._scrollElementIntoView({...e,index:t})}}_scrollElementIntoView(t){if(t.index>=this._first&&t.index<=this._last)this._children[t.index-this._first].scrollIntoView(t);else if(t.index=Math.min(t.index,this._items.length-1),t.behavior==="smooth"){const e=this._layout.getScrollIntoViewCoordinates(t),{behavior:i}=t;this._updateScrollIntoViewCoordinates=this._scrollerController.managedScrollTo(Object.assign(e,{behavior:i}),()=>this._layout.getScrollIntoViewCoordinates(t),()=>this._scrollIntoViewTarget=null),this._scrollIntoViewTarget=t}else this._layout.pin=t}_checkScrollIntoViewTarget(t){const{index:e}=this._scrollIntoViewTarget||{};e&&t?.has(e)&&this._updateScrollIntoViewCoordinates(this._layout.getScrollIntoViewCoordinates(this._scrollIntoViewTarget))}_notifyRange(){this._hostElement.dispatchEvent(new v({first:this._first,last:this._last}))}_notifyVisibility(){this._hostElement.dispatchEvent(new S({first:this._firstVisible,last:this._lastVisible}))}get layoutComplete(){return this._layoutCompletePromise||(this._layoutCompletePromise=new Promise((t,e)=>{this._layoutCompleteResolver=t,this._layoutCompleteRejecter=e})),this._layoutCompletePromise}_rejectLayoutCompletePromise(t){this._layoutCompleteRejecter!==null&&this._layoutCompleteRejecter(t),this._resetLayoutCompleteState()}_scheduleLayoutComplete(){this._layoutCompletePromise&&this._pendingLayoutComplete===null&&(this._pendingLayoutComplete=requestAnimationFrame(()=>requestAnimationFrame(()=>this._resolveLayoutCompletePromise())))}_resolveLayoutCompletePromise(){this._layoutCompleteResolver!==null&&this._layoutCompleteResolver(),this._resetLayoutCompleteState()}_resetLayoutCompleteState(){this._layoutCompletePromise=null,this._layoutCompleteResolver=null,this._layoutCompleteRejecter=null,this._pendingLayoutComplete=null}_hostElementSizeChanged(){this._schedule(this._updateLayout)}_childLoaded(){}_childrenSizeChanged(t){if(this._layout?.measureChildren){for(const e of t)this._toBeMeasured.set(e.target,e.contentRect);this._measureChildren()}this._scheduleLayoutComplete(),this._itemsChanged=!1,this._rangeChanged=!1}}function O(n){const t=window.getComputedStyle(n);return{marginTop:u(t.marginTop),marginRight:u(t.marginRight),marginBottom:u(t.marginBottom),marginLeft:u(t.marginLeft)}}function u(n){const t=n?parseFloat(n):NaN;return Number.isNaN(t)?0:t}function p(n){if(n.assignedSlot!==null)return n.assignedSlot;if(n.parentElement!==null)return n.parentElement;const t=n.parentNode;return t&&t.nodeType===Node.DOCUMENT_FRAGMENT_NODE&&t.host||null}function z(n,t=!1){const e=[];let i=t?n:p(n);for(;i!==null;)e.push(i),i=p(i);return e}function x(n,t=!1){let e=!1;return z(n,t).filter(i=>{if(e)return!1;const s=getComputedStyle(i);return e=s.position==="fixed",s.overflow!=="visible"})}export{T as Virtualizer,I as provideResizeObserver,R as virtualizerRef};
@@ -0,0 +1 @@
1
+ class s extends Event{constructor(e){super(s.eventName,{bubbles:!1}),this.first=e.first,this.last=e.last}}s.eventName="rangeChanged";class t extends Event{constructor(e){super(t.eventName,{bubbles:!1}),this.first=e.first,this.last=e.last}}t.eventName="visibilityChanged";class n extends Event{constructor(){super(n.eventName,{bubbles:!1})}}n.eventName="unpinned";export{s as RangeChangedEvent,n as UnpinnedEvent,t as VisibilityChangedEvent};
@@ -0,0 +1 @@
1
+ import{SizeCache as g}from"./shared/SizeCache.js";import{BaseLayout as f,dim1 as z}from"./shared/BaseLayout.js";const p=r=>Object.assign({type:C},r);function m(r){return r==="horizontal"?"marginLeft":"marginTop"}function S(r){return r==="horizontal"?"marginRight":"marginBottom"}function u(r){return r==="horizontal"?"xOffset":"yOffset"}function d(r,t){const i=[r,t].sort();return i[1]<=0?Math.min(...i):i[0]>=0?Math.max(...i):i[0]+i[1]}class M{constructor(){this._childSizeCache=new g,this._marginSizeCache=new g,this._metricsCache=new Map}update(t,i){const e=new Set;Object.keys(t).forEach(s=>{const a=Number(s);this._metricsCache.set(a,t[a]),this._childSizeCache.set(a,t[a][z(i)]),e.add(a),e.add(a+1)});for(const s of e){const a=this._metricsCache.get(s)?.[m(i)]||0,l=this._metricsCache.get(s-1)?.[S(i)]||0;this._marginSizeCache.set(s,d(a,l))}}get averageChildSize(){return this._childSizeCache.averageSize}get totalChildSize(){return this._childSizeCache.totalSize}get averageMarginSize(){return this._marginSizeCache.averageSize}get totalMarginSize(){return this._marginSizeCache.totalSize}getLeadingMarginValue(t,i){return this._metricsCache.get(t)?.[m(i)]||0}getChildSize(t){return this._childSizeCache.getSize(t)}getMarginSize(t){return this._marginSizeCache.getSize(t)}clear(){this._childSizeCache.clear(),this._marginSizeCache.clear(),this._metricsCache.clear()}}class C extends f{constructor(){super(...arguments),this._itemSize={width:100,height:100},this._physicalItems=new Map,this._newPhysicalItems=new Map,this._metricsCache=new M,this._anchorIdx=null,this._anchorPos=null,this._stable=!0,this._measureChildren=!0,this._estimate=!0}get measureChildren(){return this._measureChildren}updateItemSizes(t){this._metricsCache.update(t,this.direction),this._scheduleReflow()}_getPhysicalItem(t){return this._newPhysicalItems.get(t)??this._physicalItems.get(t)}_getSize(t){return this._getPhysicalItem(t)&&this._metricsCache.getChildSize(t)}_getAverageSize(){return this._metricsCache.averageChildSize||this._itemSize[this._sizeDim]}_estimatePosition(t){const i=this._metricsCache;if(this._first===-1||this._last===-1)return i.averageMarginSize+t*(i.averageMarginSize+this._getAverageSize());if(t<this._first){const e=this._first-t;return this._getPhysicalItem(this._first).pos-(i.getMarginSize(this._first-1)||i.averageMarginSize)-(e*i.averageChildSize+(e-1)*i.averageMarginSize)}else{const e=t-this._last;return this._getPhysicalItem(this._last).pos+(i.getChildSize(this._last)||i.averageChildSize)+(i.getMarginSize(this._last)||i.averageMarginSize)+e*(i.averageChildSize+i.averageMarginSize)}}_getPosition(t){const i=this._getPhysicalItem(t),{averageMarginSize:e}=this._metricsCache;return t===0?this._metricsCache.getMarginSize(0)??e:i?i.pos:this._estimatePosition(t)}_calculateAnchor(t,i){return t<=0?0:i>this._scrollSize-this._viewDim1?this.items.length-1:Math.max(0,Math.min(this.items.length-1,Math.floor((t+i)/2/this._delta)))}_getAnchor(t,i){if(this._physicalItems.size===0)return this._calculateAnchor(t,i);if(this._first<0)return this._calculateAnchor(t,i);if(this._last<0)return this._calculateAnchor(t,i);const e=this._getPhysicalItem(this._first),s=this._getPhysicalItem(this._last),a=e.pos;if(s.pos+this._metricsCache.getChildSize(this._last)<t)return this._calculateAnchor(t,i);if(a>i)return this._calculateAnchor(t,i);let n=this._firstVisible-1,h=-1/0;for(;h<t;)h=this._getPhysicalItem(++n).pos+this._metricsCache.getChildSize(n);return n}_getActiveItems(){this._viewDim1===0||this.items.length===0?this._clearItems():this._getItems()}_clearItems(){this._first=-1,this._last=-1,this._physicalMin=0,this._physicalMax=0;const t=this._newPhysicalItems;this._newPhysicalItems=this._physicalItems,this._newPhysicalItems.clear(),this._physicalItems=t,this._stable=!0}_getItems(){const t=this._newPhysicalItems;this._stable=!0;let i,e;if(this.pin!==null){const{index:h}=this.pin;this._anchorIdx=h,this._anchorPos=this._getPosition(h)}if(i=this._scrollPosition-this._overhang,e=this._scrollPosition+this._viewDim1+this._overhang,e<0||i>this._scrollSize){this._clearItems();return}(this._anchorIdx===null||this._anchorPos===null)&&(this._anchorIdx=this._getAnchor(i,e),this._anchorPos=this._getPosition(this._anchorIdx));let s=this._getSize(this._anchorIdx);s===void 0&&(this._stable=!1,s=this._getAverageSize());const a=this._metricsCache.getMarginSize(this._anchorIdx)??this._metricsCache.averageMarginSize,l=this._metricsCache.getMarginSize(this._anchorIdx+1)??this._metricsCache.averageMarginSize;this._anchorIdx===0&&(this._anchorPos=a),this._anchorIdx===this.items.length-1&&(this._anchorPos=this._scrollSize-l-s);let c=0;for(this._anchorPos+s+l<i&&(c=i-(this._anchorPos+s+l)),this._anchorPos-a>e&&(c=e-(this._anchorPos-a)),c&&(this._scrollPosition-=c,i-=c,e-=c,this._scrollError+=c),t.set(this._anchorIdx,{pos:this._anchorPos,size:s}),this._first=this._last=this._anchorIdx,this._physicalMin=this._anchorPos-a,this._physicalMax=this._anchorPos+s+l;this._physicalMin>i&&this._first>0;){let h=this._getSize(--this._first);h===void 0&&(this._stable=!1,h=this._getAverageSize());let _=this._metricsCache.getMarginSize(this._first);_===void 0&&(this._stable=!1,_=this._metricsCache.averageMarginSize),this._physicalMin-=h;const o=this._physicalMin;if(t.set(this._first,{pos:o,size:h}),this._physicalMin-=_,this._stable===!1&&this._estimate===!1)break}for(;this._physicalMax<e&&this._last<this.items.length-1;){let h=this._getSize(++this._last);h===void 0&&(this._stable=!1,h=this._getAverageSize());let _=this._metricsCache.getMarginSize(this._last);_===void 0&&(this._stable=!1,_=this._metricsCache.averageMarginSize);const o=this._physicalMax;if(t.set(this._last,{pos:o,size:h}),this._physicalMax+=h+_,!this._stable&&!this._estimate)break}const n=this._calculateError();n&&(this._physicalMin-=n,this._physicalMax-=n,this._anchorPos-=n,this._scrollPosition-=n,t.forEach(h=>h.pos-=n),this._scrollError+=n),this._stable&&(this._newPhysicalItems=this._physicalItems,this._newPhysicalItems.clear(),this._physicalItems=t)}_calculateError(){return this._first===0?this._physicalMin:this._physicalMin<=0?this._physicalMin-this._first*this._delta:this._last===this.items.length-1?this._physicalMax-this._scrollSize:this._physicalMax>=this._scrollSize?this._physicalMax-this._scrollSize+(this.items.length-1-this._last)*this._delta:0}_reflow(){const{_first:t,_last:i}=this;super._reflow(),(this._first===-1&&this._last==-1||this._first===t&&this._last===i)&&this._resetReflowState()}_resetReflowState(){this._anchorIdx=null,this._anchorPos=null,this._stable=!0}_updateScrollSize(){const{averageMarginSize:t}=this._metricsCache;this._scrollSize=Math.max(1,this.items.length*(t+this._getAverageSize())+t)}get _delta(){const{averageMarginSize:t}=this._metricsCache;return this._getAverageSize()+t}_getItemPosition(t){return{[this._positionDim]:this._getPosition(t),[this._secondaryPositionDim]:0,[u(this.direction)]:-(this._metricsCache.getLeadingMarginValue(t,this.direction)??this._metricsCache.averageMarginSize)}}_getItemSize(t){return{[this._sizeDim]:this._getSize(t)||this._getAverageSize(),[this._secondarySizeDim]:this._itemSize[this._secondarySizeDim]}}_viewDim2Changed(){this._metricsCache.clear(),this._scheduleReflow()}}export{C as FlowLayout,p as flow};
@@ -0,0 +1 @@
1
+ function _(e){return e==="horizontal"?"width":"height"}function a(e){return e==="horizontal"?"height":"width"}function c(e){return e==="horizontal"?"left":"top"}function d(e){return e==="horizontal"?"top":"left"}class f{_getDefaultConfig(){return{direction:"vertical"}}constructor(i,t){this._latestCoords={left:0,top:0},this._direction=null,this._viewportSize={width:0,height:0},this.totalScrollSize={width:0,height:0},this.offsetWithinScroller={left:0,top:0},this._pendingReflow=!1,this._pendingLayoutUpdate=!1,this._pin=null,this._firstVisible=0,this._lastVisible=0,this._physicalMin=0,this._physicalMax=0,this._first=-1,this._last=-1,this._sizeDim="height",this._secondarySizeDim="width",this._positionDim="top",this._secondaryPositionDim="left",this._scrollPosition=0,this._scrollError=0,this._items=[],this._scrollSize=1,this._overhang=1e3,this._hostSink=i,Promise.resolve().then(()=>this.config=t||this._getDefaultConfig())}set config(i){Object.assign(this,Object.assign({},this._getDefaultConfig(),i))}get config(){return{direction:this.direction}}get items(){return this._items}set items(i){this._setItems(i)}_setItems(i){i!==this._items&&(this._items=i,this._scheduleReflow())}get direction(){return this._direction}set direction(i){i=i==="horizontal"?i:"vertical",i!==this._direction&&(this._direction=i,this._sizeDim=i==="horizontal"?"width":"height",this._secondarySizeDim=i==="horizontal"?"height":"width",this._positionDim=i==="horizontal"?"left":"top",this._secondaryPositionDim=i==="horizontal"?"top":"left",this._triggerReflow())}get viewportSize(){return this._viewportSize}set viewportSize(i){const{_viewDim1:t,_viewDim2:s}=this;Object.assign(this._viewportSize,i),s!==this._viewDim2?this._scheduleLayoutUpdate():t!==this._viewDim1&&this._checkThresholds()}get viewportScroll(){return this._latestCoords}set viewportScroll(i){Object.assign(this._latestCoords,i);const t=this._scrollPosition;this._scrollPosition=this._latestCoords[this._positionDim],Math.abs(t-this._scrollPosition)>=1&&this._checkThresholds()}reflowIfNeeded(i=!1){(i||this._pendingReflow)&&(this._pendingReflow=!1,this._reflow())}set pin(i){this._pin=i,this._triggerReflow()}get pin(){if(this._pin!==null){const{index:i,block:t}=this._pin;return{index:Math.max(0,Math.min(i,this.items.length-1)),block:t}}return null}_clampScrollPosition(i){return Math.max(-this.offsetWithinScroller[this._positionDim],Math.min(i,this.totalScrollSize[_(this.direction)]-this._viewDim1))}unpin(){this._pin!==null&&(this._sendUnpinnedMessage(),this._pin=null)}_updateLayout(){}get _viewDim1(){return this._viewportSize[this._sizeDim]}get _viewDim2(){return this._viewportSize[this._secondarySizeDim]}_scheduleReflow(){this._pendingReflow=!0}_scheduleLayoutUpdate(){this._pendingLayoutUpdate=!0,this._scheduleReflow()}_triggerReflow(){this._scheduleLayoutUpdate(),Promise.resolve().then(()=>this.reflowIfNeeded())}_reflow(){this._pendingLayoutUpdate&&(this._updateLayout(),this._pendingLayoutUpdate=!1),this._updateScrollSize(),this._setPositionFromPin(),this._getActiveItems(),this._updateVisibleIndices(),this._sendStateChangedMessage()}_setPositionFromPin(){if(this.pin!==null){const i=this._scrollPosition,{index:t,block:s}=this.pin;this._scrollPosition=this._calculateScrollIntoViewPosition({index:t,block:s||"start"})-this.offsetWithinScroller[this._positionDim],this._scrollError=i-this._scrollPosition}}_calculateScrollIntoViewPosition(i){const{block:t}=i,s=Math.min(this.items.length,Math.max(0,i.index)),o=this._getItemPosition(s)[this._positionDim];let h=o;if(t!=="start"){const n=this._getItemSize(s)[this._sizeDim];if(t==="center")h=o-.5*this._viewDim1+.5*n;else{const l=o-this._viewDim1+n;if(t==="end")h=l;else{const r=this._scrollPosition;h=Math.abs(r-o)<Math.abs(r-l)?o:l}}}return h+=this.offsetWithinScroller[this._positionDim],this._clampScrollPosition(h)}getScrollIntoViewCoordinates(i){return{[this._positionDim]:this._calculateScrollIntoViewPosition(i)}}_sendUnpinnedMessage(){this._hostSink({type:"unpinned"})}_sendVisibilityChangedMessage(){this._hostSink({type:"visibilityChanged",firstVisible:this._firstVisible,lastVisible:this._lastVisible})}_sendStateChangedMessage(){const i=new Map;if(this._first!==-1&&this._last!==-1)for(let s=this._first;s<=this._last;s++)i.set(s,this._getItemPosition(s));const t={type:"stateChanged",scrollSize:{[this._sizeDim]:this._scrollSize,[this._secondarySizeDim]:null},range:{first:this._first,last:this._last,firstVisible:this._firstVisible,lastVisible:this._lastVisible},childPositions:i};this._scrollError&&(t.scrollError={[this._positionDim]:this._scrollError,[this._secondaryPositionDim]:0},this._scrollError=0),this._hostSink(t)}get _num(){return this._first===-1||this._last===-1?0:this._last-this._first+1}_checkThresholds(){if(this._viewDim1===0&&this._num>0||this._pin!==null)this._scheduleReflow();else{const i=Math.max(0,this._scrollPosition-this._overhang),t=Math.min(this._scrollSize,this._scrollPosition+this._viewDim1+this._overhang);this._physicalMin>i||this._physicalMax<t?this._scheduleReflow():this._updateVisibleIndices({emit:!0})}}_updateVisibleIndices(i){if(this._first===-1||this._last===-1)return;let t=this._first;for(;t<this._last&&Math.round(this._getItemPosition(t)[this._positionDim]+this._getItemSize(t)[this._sizeDim])<=Math.round(this._scrollPosition);)t++;let s=this._last;for(;s>this._first&&Math.round(this._getItemPosition(s)[this._positionDim])>=Math.round(this._scrollPosition+this._viewDim1);)s--;(t!==this._firstVisible||s!==this._lastVisible)&&(this._firstVisible=t,this._lastVisible=s,i&&i.emit&&this._sendVisibilityChangedMessage())}}export{f as BaseLayout,_ as dim1,a as dim2,c as pos1,d as pos2};
@@ -0,0 +1 @@
1
+ class r{constructor(e){this._map=new Map,this._roundAverageSize=!1,this.totalSize=0,e?.roundAverageSize===!0&&(this._roundAverageSize=!0)}set(e,t){const i=this._map.get(e)||0;this._map.set(e,t),this.totalSize+=t-i}get averageSize(){if(this._map.size>0){const e=this.totalSize/this._map.size;return this._roundAverageSize?Math.round(e):e}return 0}getSize(e){return this._map.get(e)}clear(){this._map.clear(),this.totalSize=0}}export{r as SizeCache};
@@ -0,0 +1 @@
1
+ import{html as o,noChange as a}from"lit";import{directive as h,PartType as l}from"lit/directive.js";import{AsyncDirective as u}from"lit/async-directive.js";import{repeat as _}from"lit/directives/repeat.js";import{Virtualizer as c}from"./Virtualizer.js";import{virtualizerRef as x}from"./Virtualizer.js";const d=n=>n,m=(n,e)=>o`${e}: ${JSON.stringify(n,null,2)}`;class f extends u{constructor(e){if(super(e),this._virtualizer=null,this._first=0,this._last=-1,this._renderItem=(t,i)=>m(t,i+this._first),this._keyFunction=(t,i)=>d(t,i+this._first),this._items=[],e.type!==l.CHILD)throw new Error("The virtualize directive can only be used in child expressions")}render(e){e&&this._setFunctions(e);const t=[];if(this._first>=0&&this._last>=this._first)for(let i=this._first;i<=this._last;i++)t.push(this._items[i]);return _(t,this._keyFunction,this._renderItem)}update(e,[t]){this._setFunctions(t);const i=this._items!==t.items;return this._items=t.items||[],this._virtualizer?this._updateVirtualizerConfig(e,t):this._initialize(e,t),i?a:this.render()}async _updateVirtualizerConfig(e,t){if(!await this._virtualizer.updateLayoutConfig(t.layout||{})){const s=e.parentNode;this._makeVirtualizer(s,t)}this._virtualizer.items=this._items}_setFunctions(e){const{renderItem:t,keyFunction:i}=e;t&&(this._renderItem=(s,r)=>t(s,r+this._first)),i&&(this._keyFunction=(s,r)=>i(s,r+this._first))}_makeVirtualizer(e,t){this._virtualizer&&this._virtualizer.disconnected();const{layout:i,scroller:s,items:r}=t;this._virtualizer=new c({hostElement:e,layout:i,scroller:s}),this._virtualizer.items=r,this._virtualizer.connected()}_initialize(e,t){const i=e.parentNode;i&&i.nodeType===1&&(i.addEventListener("rangeChanged",s=>{this._first=s.first,this._last=s.last,this.setValue(this.render())}),this._makeVirtualizer(i,t))}disconnected(){this._virtualizer?.disconnected()}reconnected(){this._virtualizer?.connected()}}const V=h(f);export{d as defaultKeyFunction,m as defaultRenderItem,V as virtualize,x as virtualizerRef};
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1 @@
1
+ import{LitVirtualizer as e}from"./internal/LitVirtualizer.js";typeof customElements<"u"&&!customElements.get("lit-virtualizer")&&customElements.define("lit-virtualizer",e);
File without changes
@@ -11,6 +11,7 @@ removing, or replacing non-code assets.
11
11
  | `css/fonts/**` | Generated Google Fonts preview CSS with per-family notices generated from upstream Google Fonts metadata links. | `licenses/GOOGLE_FONTS_NOTICES.md` |
12
12
  | `assets/icons.svg` | Tabler-derived SVG symbols plus Taproot-owned logo symbol. | `licenses/THIRD_PARTY_NOTICES.md` |
13
13
  | `*.ts` | Inline Tabler-style SVG templates and Taproot rendering helpers. | `licenses/THIRD_PARTY_NOTICES.md` |
14
+ | `dist/shared/virtualizer/**` | Vendored Lit Virtualizer runtime source compiled into Espalier's package. | `licenses/THIRD_PARTY_NOTICES.md` |
14
15
  | Brand favicons/logos | Taproot-owned Espalier brand assets. | None |
15
16
  | Demo textures | Taproot-owned generated PNG textures created for this repository. | None |
16
17
  | Demo JSON data | Taproot-authored fictitious samples or standards-derived factual color data. | None |
@@ -25,10 +25,11 @@ until reviewed and adapted by qualified IP and technology-transactions counsel.
25
25
  - `ESPALIER_DEAL_READINESS_CHECKLIST.md` - practical readiness checklist for
26
26
  lawyer review, diligence, packaging, and outreach.
27
27
  - `THIRD_PARTY_NOTICES.md` - third-party open-source notices for materials
28
- copied into Espalier distribution artifacts, including Tabler Icons.
28
+ copied into Espalier distribution artifacts, including Lit Virtualizer and
29
+ Tabler Icons.
29
30
  - `asset-provenance.json` and `ASSET_PROVENANCE.md` - machine-readable and
30
- human-readable provenance records for generated fonts, icons, textures, demo
31
- datasets, and docs assets.
31
+ human-readable provenance records for generated fonts, icons, vendored
32
+ runtime source, textures, demo datasets, and docs assets.
32
33
  - `open-source-audit/` - preserved dependency/license audit material for
33
34
  open-source diligence, SBOM planning, and third-party notice review.
34
35
 
@@ -3,6 +3,47 @@
3
3
  This file preserves notices for third-party open-source materials included in
4
4
  or substantially copied into Espalier distribution artifacts.
5
5
 
6
+ ## Lit Virtualizer
7
+
8
+ Espalier includes source code vendored from `@lit-labs/virtualizer` for
9
+ virtualized picker, repeater, and grid rendering.
10
+
11
+ - Project: Lit Virtualizer
12
+ - Upstream: https://github.com/lit/lit/tree/main/packages/labs/virtualizer
13
+ - Version: 2.1.1
14
+ - Published git head: 43c6168acc4a30d70091ee30c307f692a02387d5
15
+ - License: BSD-3-Clause
16
+ - Copyright: Copyright (c) 2017, Google LLC. All rights reserved.
17
+
18
+ BSD 3-Clause License
19
+
20
+ Copyright (c) 2017, Google LLC. All rights reserved.
21
+
22
+ Redistribution and use in source and binary forms, with or without
23
+ modification, are permitted provided that the following conditions are met:
24
+
25
+ * Redistributions of source code must retain the above copyright notice, this
26
+ list of conditions and the following disclaimer.
27
+
28
+ * Redistributions in binary form must reproduce the above copyright notice,
29
+ this list of conditions and the following disclaimer in the documentation
30
+ and/or other materials provided with the distribution.
31
+
32
+ * Neither the name of the copyright holder nor the names of its
33
+ contributors may be used to endorse or promote products derived from
34
+ this software without specific prior written permission.
35
+
36
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
37
+ AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
38
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
39
+ DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
40
+ FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
41
+ DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
42
+ SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
43
+ CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
44
+ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
45
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
46
+
6
47
  ## Tabler Icons
7
48
 
8
49
  Espalier includes SVG icon paths adapted from Tabler Icons in `assets/icons.svg`
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "schemaVersion": 1,
3
- "updatedAt": "2026-06-17",
3
+ "updatedAt": "2026-06-30",
4
4
  "entries": [
5
5
  {
6
6
  "id": "google-font-preview-assets",
@@ -110,6 +110,29 @@
110
110
  "noticePaths": [],
111
111
  "reviewStatus": "documented"
112
112
  },
113
+ {
114
+ "id": "vendored-lit-virtualizer",
115
+ "paths": [
116
+ "dist/shared/virtualizer/**"
117
+ ],
118
+ "assetType": "vendored runtime source",
119
+ "classification": "third-party vendored source",
120
+ "owner": "Google LLC and Lit contributors",
121
+ "source": "@lit-labs/virtualizer 2.1.1, published from git head 43c6168acc4a30d70091ee30c307f692a02387d5",
122
+ "license": "BSD-3-Clause",
123
+ "transformations": [
124
+ "Extracted upstream TypeScript sources from the published package source maps",
125
+ "Compiled into Espalier distribution JavaScript",
126
+ "Registered through an Espalier-owned guarded custom-element wrapper"
127
+ ],
128
+ "packageInclusion": "compiled into npm package JavaScript",
129
+ "docsInclusion": "used by picker, repeater, and grid examples when those components virtualize items",
130
+ "noticeRequirement": "required",
131
+ "noticePaths": [
132
+ "licenses/THIRD_PARTY_NOTICES.md"
133
+ ],
134
+ "reviewStatus": "documented"
135
+ },
113
136
  {
114
137
  "id": "generated-demo-textures",
115
138
  "paths": [
@@ -10,14 +10,16 @@ commercial licensing work. It is not legal advice.
10
10
 
11
11
  ## Executive Summary
12
12
 
13
- Espalier has an unusually small runtime dependency footprint for an enterprise
14
- front-end framework:
13
+ Espalier has a zero-runtime-dependency package footprint for an enterprise
14
+ front-end framework, with one required peer supplied by consumers:
15
15
 
16
- - 1 direct runtime dependency: `@lit-labs/virtualizer`
16
+ - 0 direct runtime dependencies
17
17
  - 1 required peer dependency: `lit`
18
- - Runtime/peer dependency graph licenses found: BSD-3-Clause, MIT, and 0BSD
18
+ - Runtime/peer dependency graph licenses found: BSD-3-Clause and MIT
19
19
  - No GPL, LGPL, AGPL, SSPL, source-available, noncommercial, or unknown
20
20
  licenses were found in the runtime/peer graph
21
+ - Espalier vendors BSD-3-Clause source from `@lit-labs/virtualizer@2.1.1`;
22
+ the required notice is preserved in `licenses/THIRD_PARTY_NOTICES.md`
21
23
  - Direct dev dependencies are also permissively licensed
22
24
  - Espalier also includes SVG icon paths adapted from Tabler Icons, which is MIT
23
25
  licensed; the required notice is preserved in `licenses/THIRD_PARTY_NOTICES.md`
@@ -67,37 +69,37 @@ external delivery.
67
69
 
68
70
  ## Copied Asset Notices
69
71
 
70
- Espalier includes SVG icon paths copied or adapted from Tabler Icons in
71
- `assets/icons.svg` and related inline SVG modules.
72
+ Espalier includes source and asset material copied or adapted from permissively
73
+ licensed third-party projects.
72
74
 
73
75
  | Material | Upstream | License | Notice file |
74
76
  |----------|----------|---------|-------------|
77
+ | Lit Virtualizer source | https://github.com/lit/lit/tree/main/packages/labs/virtualizer | BSD-3-Clause | `licenses/THIRD_PARTY_NOTICES.md` |
75
78
  | Tabler Icons SVG paths | https://github.com/tabler/tabler-icons | MIT | `licenses/THIRD_PARTY_NOTICES.md` |
76
79
 
77
- MIT does not require visible in-product attribution, but it does require
78
- preserving the upstream copyright notice and permission notice in copies or
79
- substantial portions of the licensed material. Because Espalier redistributes
80
- copied SVG path data, the notice file should ship with the package.
80
+ BSD-3-Clause and MIT do not require visible in-product attribution, but they do
81
+ require preserving the upstream copyright notice and permission/license notice
82
+ in source copies or binary redistribution materials. Because Espalier
83
+ redistributes vendored source-derived JavaScript and copied SVG path data, the
84
+ notice file should ship with the package.
81
85
 
82
86
  ## Published Package Dependency Surface
83
87
 
84
88
  | Role | Package | Version observed | License | Notes |
85
89
  |------|---------|------------------|---------|-------|
86
90
  | Peer dependency | `lit` | `3.3.2` | BSD-3-Clause | Required framework peer for consumers. |
87
- | Runtime dependency | `@lit-labs/virtualizer` | `2.1.1` | BSD-3-Clause | Used for virtualized list/grid behavior. |
91
+ | Vendored source | `@lit-labs/virtualizer` | `2.1.1` | BSD-3-Clause | Compiled into Espalier for virtualized picker/repeater/grid behavior; not an npm dependency. |
88
92
 
89
93
  ## Runtime / Peer Dependency Graph
90
94
 
91
95
  | Package | Version observed | License | Source in graph |
92
96
  |---------|------------------|---------|-----------------|
93
- | `@lit-labs/virtualizer` | `2.1.1` | BSD-3-Clause | Direct dependency |
94
- | `lit` | `3.3.2` | BSD-3-Clause | Peer dependency and transitive dependency of virtualizer |
97
+ | `lit` | `3.3.2` | BSD-3-Clause | Peer dependency |
95
98
  | `@lit/reactive-element` | `2.1.2` | BSD-3-Clause | Transitive via `lit` |
96
99
  | `lit-element` | `4.2.2` | BSD-3-Clause | Transitive via `lit` |
97
100
  | `lit-html` | `3.3.2` | BSD-3-Clause | Transitive via `lit` / `lit-element` |
98
101
  | `@lit-labs/ssr-dom-shim` | `1.5.1` | BSD-3-Clause | Transitive via Lit packages |
99
102
  | `@types/trusted-types` | `2.0.7` | MIT | Transitive type support via `lit-html` |
100
- | `tslib` | `2.8.1` | 0BSD | Transitive via `@lit-labs/virtualizer` |
101
103
 
102
104
  Runtime finding: no copyleft or unknown licenses found.
103
105
 
@@ -163,10 +165,9 @@ Installed snapshot finding: no unknown licenses found.
163
165
  `esbuild` platform packages. These are not declared in `package.json`; run
164
166
  the final audit/SBOM from a clean install before publishing diligence
165
167
  materials.
166
- - The public package currently declares `lit` as a peer dependency while
167
- `@lit-labs/virtualizer` also depends on `lit`. This is not a license issue,
168
- but release packaging should confirm the dependency tree consumers actually
169
- receive.
168
+ - The public package declares `lit` as a peer dependency and vendors the
169
+ virtualizer source. Release packaging should confirm the staged public
170
+ package has an empty `dependencies` object and retains the `lit` peer.
170
171
 
171
172
  ## Recommended Follow-Ups
172
173
 
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@taprootio/espalier",
3
- "version": "2.0.0",
4
- "description": "Espalier — an enterprise-grade web component design system built on Lit and browser standards. Provides accessible, themeable UI primitives with OKLCH perceptual color, APCA contrast, fluid typography, and native form participation via ElementInternals.",
3
+ "version": "2.0.2",
4
+ "description": "Espalier — a themeable, accessible, framework-agnostic, enterprise-grade design system built on web standards and love.",
5
5
  "customElements": "custom-elements.json",
6
6
  "type": "module",
7
7
  "main": "dist/index.js",
@@ -272,7 +272,8 @@
272
272
  "dist/index.js",
273
273
  "dist/*/esp-*.js",
274
274
  "dist/header/index.js",
275
- "dist/menu/index.js"
275
+ "dist/menu/index.js",
276
+ "dist/shared/virtualizer/lit-virtualizer.js"
276
277
  ],
277
278
  "files": [
278
279
  "dist/**/*.js",
@@ -332,9 +333,7 @@
332
333
  "optional": false
333
334
  }
334
335
  },
335
- "dependencies": {
336
- "@lit-labs/virtualizer": "^2.1.1"
337
- },
336
+ "dependencies": {},
338
337
  "publishConfig": {
339
338
  "registry": "https://registry.npmjs.org/",
340
339
  "access": "public"