# NFTDisplay

## 01 使用

### 01.01 默认样式

NFTDisplay 组件默认尺寸为 *150x150*, 可以通过 css 设置 width/height. 固定尺寸的使用场景感觉比较少, 多数情况应该都需要将 NFTDisplay 应用于响应式布局中. 

### 01.02 aspect ratio

可以使用 aspect prop 设置 NFTDisplay 的宽高比, NFTDisplay 包裹一两层 div/span 标签 (用来控制布局, 没有直接把 img 标签渲染出来), 所以这里说的长宽比指的不是 img 的长宽比, 图片的尺寸大小不一, 长宽比也是既定的, aspect prop 控制的是包裹 img 容器的长宽比.

NFTDisplay 宽高比的计算是根据父容器的 width 来确定的 (NFTDisplay 会填充整个宽度), 所以可以通过控制父容器的 width 来控制 NFTDisplay 的大小.

### 01.03 inset

inset 设置为 true 时 NFTDisplay 会镶嵌/填满父容器 (并垂直+水平居中显示图片), 所以父容器必须有明确的宽高 (尤其是高度). 响应式布局中应该会比较常用.

注: inset 比 aspect ratio 优先级高, 如果同时设置了 inset 和 aspect, 则后者不生效.

### 01.04 asset data (prop)

可以为 asset data prop 传入 raw data 或 parsed data, 避免多次解析 asset data.

### 01.05 broken image & error handling

* display 加载失败时会显示一个 broken-image, 可以从外部覆盖 `.nft-display--broken` 的样式来调整尺寸/颜色等样式
* error handling, 这部分感觉出错原因可能性会很多, 有 json 解析错误、某字段缺失、某 object 指定路径的值缺失、nft type 不支持等等, 暂时没想到如何更合理的捕获和处理这些错误. 

### 02 svg 加载

基于 `img` 标签加载 NFT Display. 几种 nft type 的加载:

- url  
  直接使用 `<img>`
- svg_gzipped  
  content => ungzip => svgToImgUrl => `<img>`
- svg (未测试, 需要测试数据)  
  content => svgToImgUrl => `<img>`
- html (TODO)  
  基于 `<img>` 的加载方式不适用, 目前没有发现这种 nft type 的测试数据

基于 `<img>` 标签的加载方式没有样式污染问题, 加载、尺寸控制也比较方便, 不过据说有些情况下 svg 可能无法正确显示 (比如 svg 加载了 font|image 资源), 目前没有发现问题, 还需要更多的观察

## 03 iframe 第三方嵌入 (TODO)

需要设计 iframe 的 API (iframe#src 查询参数), 目前想到的参数:

- address : asset address  
  调用 getAssetState 接口获取 display 数据进行展示
- 样式控制相关的参数 ?

## 04 参考

* [提供一个 NFT display 组件 · Issue #199 · ArcBlock/ux](https://github.com/ArcBlock/ux/issues/199)
* [2021徽章出现奇怪的渲染 · Issue #230 · blocklet/nft-marketplace](https://github.com/blocklet/nft-marketplace/issues/230)
* [Adding vector graphics to the Web - Learn web development | MDN](https://developer.mozilla.org/en-US/docs/Learn/HTML/Multimedia_and_embedding/Adding_vector_graphics_to_the_Web)
* [The Best Way to Embed SVG on HTML (2021)](https://vecta.io/blog/best-way-to-embed-svg)
* [javascript - Do I always need to call URL.revokeObjectURL() explicitly? - Stack Overflow](https://stackoverflow.com/questions/49209756/do-i-always-need-to-call-url-revokeobjecturl-explicitly)
