Observable-based virtual scroll implementation in Angular.
npm i -S od-virtualscroll
Let's you scroll efficiently through a humongous list/grid of items (with single predefined height) by recycling components and minimizing component updates.
{{target}}/{{module}}
)All examples are written in Angular 4 and provided in separate repositories to keep this repository simple.
Name | Description |
---|---|
od-vsstatic / Demo | Static example with 100k cells. Ideal for performance analysis and GC testing |
od-vsdynamic / Demo | Scroll through GIFs, without the risk of a CPU meltdown (GIPHY API) |
od-vslist / Demo | Render only 1 cell per row with dynamic width (randomuser API) |
od-vsadvanced / Demo | Shows more advanced API features and utilizes the auxiliary debug module |
od-vscolors / Demo | Just for fun |
However, this repository also holds a minimalistic demo, to allow local development and AoT compilation.
Import the module and specify the cell and container styling (traditional layout or flexbox/... your choice).
// app.module.ts
import {NgModule} from '@angular/core';
import {BrowserModule} from '@angular/platform-browser';
import {VirtualScrollModule} from 'od-virtualscroll';
import {AppComponent} from './app.component';
@NgModule({
bootstrap: [AppComponent],
declarations: [AppComponent],
imports: [
BrowserModule,
VirtualScrollModule
]
})
export class AppModule {}
// app.component.ts
import {Component} from '@angular/core';
import {Observable} from 'rxjs';
import {IVirtualScrollOptions} from 'od-virtualscroll';
@Component({
selector: 'app-shell',
styles: [`...`], // <-- Style your cell and container
template: `
<od-virtualscroll [vsData]="data$" [vsOptions]="options$">
<ng-template let-item let-row="row" let-column="column">
<span>Row: {{row}}</span><br>
<span>Column: {{column}}</span>
{{item}}
</ng-template>
</od-virtualscroll>`
})
export class AppComponent {
data$: Observable<any[]> = ... ; // <-- Define data
options$: Observable<IVirtualScrollOptions> = ... ; // <-- Define options
}
If you want to apply a traditional layout and wonder about the space between inline block elements - read this.
Name | Type | Description |
---|---|---|
vsData | Observable<any[]> |
Stream of data |
vsOptions | Observable<IVirtualScrollOptions> |
Stream of options |
vsResize | Observable<any> |
Stream of resize commands (optional, default: -\-> ) |
vsUserCmd | Observable<IUserCmd> |
Stream of user specific commands (optional, default: -\-> ) |
vsDebounceTime | number |
Debounce scroll and resize events [ms] (optional, default: 0) |
vsEqualsFunc | (prevIndex: number, curIndex:number) => boolean |
Function to determine equality, given two indicies in the array (optional, default: (p,c) => p === c) ) |
export interface IVirtualScrollOptions {
itemWidth?: number;
itemHeight: number;
numAdditionalRows?: number;
numLimitColumns?: number;
}
The component requires either fixed-size cells (itemWidth, itemHeight) or a fixed number of cells per row (itemHeight, numLimitColumns).
Further, to improve scrolling, additional rows may be requested.
Currently, the supported user specific commands are:
SetScrollTopCmd
: Set scroll top to specific valueFocusRowCmd
: Focus specific row indexFocusItemCmd
: Focus specific item indexE.g. Focus row index 42.
data$ = // Data...;
userCmd$ = of(new FocusRowCmd(42)).pipe(delay(2000));
<od-virtualscroll [vsData]="data$" [vsUserCmd]="userCmd$">
<!-- Your template -->
</od-virtualscroll>
Inject the ScrollObservableService to subscribe to key component observables.
Name | Type | Description |
---|---|---|
scrollWin$ | [IVirtualScrollWindow] |
Stream of the most important inner data structure |
createRow$ | [CreateRowCmd, ComponentRef<VirtualRowComponent>] |
Create row command and ComponentRef |
removeRow$ | [RemoveRowCmd, ComponentRef<VirtualRowComponent>] |
Remove row command and ComponentRef |
shiftRow$ | [ShiftRowCmd, ComponentRef<VirtualRowComponent>] |
Shift row command and ComponentRef |
createItem$ | [CreateItemCmd, ScrollItem, EmbeddedViewRef<ScrollItem>] |
Create item command, scroll item and EmbeddedViewRef |
updateItem$ | [UpdateItemCmd, ScrollItem, EmbeddedViewRef<ScrollItem>] |
Update item command, scroll item and EmbeddedViewRef |
removeItem$ | [RemoveItemCmd] |
Remove item command |
The od-vsdynamic and od-vsadvanced examples show how the API may be used.
This interface provides pretty much all needed information.
export interface IVirtualScrollWindow {
dataTimestamp: number;
containerWidth: number;
containerHeight: number;
itemWidth?: number;
itemHeight: number;
numVirtualItems: number;
numVirtualRows: number;
virtualHeight: number;
numAdditionalRows: number;
scrollTop: number;
scrollPercentage: number;
numActualRows: number;
numActualColumns: number;
actualHeight: number;
numActualItems: number;
visibleStartRow: number;
visibleEndRow: number;
}
It is used internally and may also be useful in consuming application components.
E.g.: The od-vsdynamic example.
The ScrollObservableService
is registered on the VirtualScrollModule by default, so it is available on the root injector.However, if you have multiple instances of the scroll component, a singleton instance of the ScrollObservableService
is not enough.Register the service on the wrapping component, via the providers property in the @Component
decorator, so that the injector bubbling will stop on the Component level and will serve the right instance of the ScrollObservableService.
Check the feature/testMultiInstances branch for a simple example.
api.ts reveals the current API surface.
The lib is AoT compatible and ships with FESM5 and FESM15 exports.
See Angular Package Format v4.0 for more info.
ES5/UMD, ES5/ES2015 and ES2015/ES2015 exports are also provided.
1.1.x uses Angular6/RxJS6.
Rename component input vsScrollTop
to vsUserCmd
.
npm run {{scriptName}}
Name | Description |
---|---|
buildAll | Build lib and demo |
cleanAll | Remove generated directories |
buildDemo | Build demo bundle with AoT compilation |
tslint | Lint lib and demo |
serve | Starts browser-sync for local development |
explore | Source map explorer of AoT compiled demo |
Contribution and feedback is highly appreciated.
MIT
问题: 在Chrome下,实现一个图片预览弹出对话框,在调整弹出框位置时,发现document.body.scrollTop返回为0,但是,窗口有明显的滚动条出现。 解决: 根据网上的做法,将document.body.scrollTop换为document.documentElement.scrollTop,问题解决,document.documentElement.scrollTop可以正确返
OllyDbg 常用快捷热键 聆风听雨整理 =============================================================== 打开一个新的可执行程序 (F3) 重新运行当前调试的程序 (Ctrl+F2) 当前调试的程序 (Alt+F2) 运行选定的程序进行调试 (F9) 暂时停止被调试程序的执行 (F12) 单步进入被调试程序的 Call 中 (F7)
介绍 介绍一下你的项目,技术栈? 前端:ant-design基于react 后端:SpringCloud基于SpringBoot 中间件:Redis,Rabbitmq,Xxl-job 数据库:Oracle,MySQL,ElasticSearch 日志:elk 链路追踪:skywalking 接口文档:swagger 1. 微服务和单体服务有什么区别? 微服务 单体应用 服务间调用存在网络延迟 本地
OllyDbg命令行命令 以下命令适用于 OllyDbg 的命令行插件 Cmdline.dll(显示于程序的插件菜单中) =============================================================== 命令行插件支持的命令 CALC 判断表达式 WATCH 添加监视表达式 AT 在指定地址进行反汇编 FOLLOW 跟随命令 ORIG 反汇编于 EIP
一、功能 查看非文本文档的内容 二、用法 1、语法 od [-A RADIX] [-t TYPE] 文件名 2、选项与参数 -A: 指定偏移量的输出形式 d[size] :利用十进制(decimal)输出数据,每个整数占用 size bytes ; o[size] :利用八进制(octal)输出数据,每个整数占用 size bytes ; x[size] :利用十六进制(hexadecimal)输
Linux指令:od 示例用法:od -c hello Linux指令:od od命令 用户通常使用od命令查看特殊格式的文件内容。通过指定该命令的不同选项可以以十进制、八进制、十六进制和ASCII码来显示文件。 语法:od [选项] 文件… 命令中各选项的含义: - A 指定地址基数,包括: d 十进制 o 八进制(系统默认值) x 十六进制 n 不打印位移值 - t 指定数据的显示格式,主要的
名称:od 作用:格式化输出文件中的数据 提要: od [OPTION]... [FILE]... od [-abcdfilosx]... [FILE] [[+]OFFSET[.][b]] od --traditional [OPTION]... [FILE] [[+]OFFSET[.][b] [+][LABEL][.][b]] 说明: 常见的文件为文
od审批到底要多久哇想在年前上班呢还 #华为od#
本人末2,制造业公司干了半年,gap了半年,然后接触OD。 时间线:6.11号接触HR->6.15机考->6.18心理测试->6.20资面->6.29技术一面->7.3技术二面->7.4主管面(岗位不太合适,换部门)->7.6资面->7.8主管面->7.10申报审批->7.11offer下来了 base:松山湖 部门:公共开发部 语言:python 岗位:开发 机考:很久没刷过题了,差不多接触HR
现在22岁,成专学历正在升成本,前端培训完干了两年外包,17k. 简历包装了下学历,写的是本科.. 性格测试已经过了,想问下这个硬件水平能审批过吗,能的话我就稍微准备下一面了.. 顺便分享下机试题和思路. 1.整理下题干就是给定一个的字符串,如:2,3,4,6,9; 找出存在几个最小公约数. 我的思路是: 转换成数组,写一个双循环,举例:如果2被%等于0并且两个数不相等,那就把2塞进一个新
9.19机试 一道字符ASCII码,两个字符串求最小子集,动态规划 总过300分飘~ 9.21性格测试.....比较喜欢积极乐观,团队,有朝气,很好调整心态的性格 9.27业务一面 字符串解析。。 项目经历 spring的理解 mybatis分页实现 orcle视图 怎么做sql优化 hashmap实现原理 jvm垃圾处理机制 springboot原理 自动装配注解,实现原理(忘了) 9.30业
OD常用断点 1、限制程序功能函数 EnableMenuItem 允许、禁止或变灰指定的菜单条目 EnableWindow 允许或禁止鼠标和键盘控制指定窗口和条目(禁止时菜单变灰) 2、对话框函数 CreateDialog 从资源模板建立一非模态对话窗 CreateDialogParam 从资源模板建立一非模态对话窗 CreateDialogIndirect 从内存模板建立一非模态对话窗 Crea
7.14 机考 时长150分钟,一二题简单题25分钟一遍ac,第三题是dijkstra最短路径,一遍ac。加上写注释60分钟搞定。(自输入输出,按照最新提交计算分数) 7.18收到综测邮件。 看攻略,一些选项优先级排序,同一选项会稍微改动问很多次,。同时对之前选择的陌生选项做个笔记,后面还会遇到很多次,确保一致性选择,好多雷点千万记得避开。 7.18晚技术一面 自我介绍 介绍毕设的技术栈,功能与亮