RFC: Multi-Token Extensible NFT (Draft Spec)

Thoughts regarding this?

This exact definition does not match a large segment of standards in existence. If I used this definition (in context) I could easily argue that ERC20 and ERC1155 are not standards since they specify the interface but not the behavior of the operation.

This is less a definition of standards and more of an actual standard in itself for extending the functionality. It makes sense and it’s a powerful concept worth exploring, not just for this standard, but for any future standard.

There is an inherent incentive for developers to create code that isn’t incompatible with the systems they are trying to interface with. I can point to the existing NFT marketplaces on Ethereum as an example of this. Their NFT standards make no guarantee of compatibility, yet the marketplaces still exist and continue to grow.

Sandboxing is a more ideal solution, but it just isn’t an option. We can’t control what an extension does once it executes because it operates in the exact same context as the caller. Only when the extension is executed can be controlled.

The current implementation already utilizes a few different rules for when the extension is executed based on the detected operation. Your suggestion is to take this further by using more granular operations and adding restrictions with some of them. I was unable to come up with any scenario where an operative restriction could be put in place without impeding some kind of potentially desired behavior.

However, I believe the tradeoff is worth it since we can guarantee certain operations for this particular opt-in asset class. A transfer operation, in particular, would be the most obvious. This design feature is something that should be named for future reference.

Below is an incomplete list of the operations that exist in the current implementation. Transfer, update, and burn operations can all occur at the same time, which can make classification difficult.

Looking at what can be isolated, a Pure Transfer and Burn operation can probably be isolated without issue. A Transfer Split and Transfer Combine get trickier because of the support for a zero quantity token instance.

Generate

  • Single
  • Multiple
  • Bare (Condensed form; no quantity, token logic, or custom data.)
  • With Quantity
  • With Quantity Zero
  • With Token Logic
  • With Token Logic Null
  • With Custom Data

Transfer

  • Pure (Does not modify any field values.)
    • To Self
    • To Other
  • Split
    • Standard
    • Zero Quantity
  • Combine
    • Standard
    • Zero Quantity (Burn)
  • + Update
  • + Burn

Update

  • Change Quantity
    • Split
    • Combine
    • Burn
  • Change Token Logic (Owner mode required.)
    • Set Token Logic
    • Set Null
  • Change Custom Data (Regulated by token logic.)
  • Shapeshift (Switch between condensed and expanded quantity and token logic.)
    • Condense Quantity
    • Expand Quantity
    • Condense Token Logic
    • Expand Token Logic
    • Condense Quantity + Token Logic
    • Expand Quantity + Token Logic
  • + Transfer
  • + Burn

Burn

  • Burn
  • Burn Zero
  • + Transfer
  • + Update
1 Like

Agree to disagree.

I’m not sure which side of the trade-off you’re saying is worth it here, nor which design feature you’re referring to. Could you elaborate?

I believe it is worth the trade-off of losing some potential avenues of desirable behavior to guarantee the success of certain operations. eg: It is worth the trade-off of restricting the capability of a token logic extension to control the outcome of a transfer operation because this guarantees that transfers can occur in an expected manner.

Which operations should be guaranteed operations is still an open question. Whatever is decided on needs to be absolutely enforceable in the implementation, and I haven’t been able to dedicate enough time to thinking it through yet.

1 Like

About that,I think there would be some conversations with Kyle’s proposal.

2 Likes

I’ve updated the implementation to include guaranteed operations for transfers and burns.

Because of this change, the token logic no longer can restrict:

  • Transfers
  • Burns
  • Splits (one cell into two)
  • Combines (two cells into one)
  • Zero quantity cell creation

The ability to control the latter three could be reintroduced by adding a permission system for more specific operations. However, this is adding a lot more complexity with limited benefits. I’m unsure if it’s needed for this standard.

what does the token platform you mean here ?

Does that mean that the quantity field always exists no matter devs define it to not?

like this 00000000000000000000000000000000 ?

1 Like

It is referring to any dapp that uses NFTs. This could be something like a marketplace or auction house. It could also be something like different games that share the same underlying NFTs.

Not exactly. The Instance ID field must contain a value at all times. The quantity and Token Logic fields are optional under specific conditions. This allows for smaller capacity requirements in some cases.

  • If the quantity value is not present, then it should be assumed to be equal to a value of 1.
  • If the Token Logic value is not included, then it should be assumed to be equal to all zeros.

Yes, a Token Logic value of all zeros, (0x0000000000000000000000000000000000000000000000000000000000000000), means that there is no extra token logic to execute. Having all zeros is also the same as having no value at all, which reduces the amount of capacity needed.

1 Like

Dose that mean when the Token Logic code hash is not all zero filled, Token Logic script could be executed ?

1 Like

Yes, that’s right. When the Token Logic code has is not all zeros, it will attempt to load and execute a matching Cell Dep with that code hash.

1 Like

Got it,many thanks!

Could you give me some example about that?
Like today if a NFT instance gun could be used with a NFT bullet to kill one enemy, its script could be verified to generate some other NFT?

1 Like

I am anticipating that when Token Logic executes, most of the time the logic will only be concerned with the cells that are using the same code hash. I often refer to this as the minimal concern principle. An example of this is in the SUDT type script. When SUDT is examining the transaction, it only cares about cells that are the same SUDT. Everything else is ignored. It may end up being similar with token logic.

An example of token logic that does not use the minimal concern principle would be an NFT gun that will shoot stronger if it is paired with NFT power ups in the same transaction. In this case the token logic in the gun NFT cell needs to examine the entire transaction and check all of the cells to see which NFT power ups are present so it can calculate the total power of the gun.

The example you give where an NFT is generated by some kind of an event is possible, but there are special considerations. Since this standard has trait of guaranteed scarcity, a new NFT instance is more difficult to create from within Token Logic. An item drop describes it better. For example, an NFT sword could be used to slay the NFT dragon, which is protecting an NFT magic item that is secured by the treasure chest lock script.

1 Like

Thanks for your detailed explanation. Have learned a lot from you.
Actually, such complicated logic should be verified by a custom rule so that it could prevent the limitation of the general guideline. But there is one more question here: how do we identify the common condition and complex interaction of NFT instances?
btw your example is more suitable.

Cannot understand what do you want to convey here. Could you share more information about that ?

Why would you want to emphasize " the need for centralization" here?

[翻译]RFC:多资产延伸性的 NFT 协议(规范草案)

简介

这是 Nervos CKB 上基于 Tannr Allard 原始草案的 NFT 替代规范,并从ERC721、ERC998 和 ERC1155 等Ethereum标准中获得灵感。

非同質化代幣 (NFT) 是具有唯一性质的代幣,它既可以是不可互换,又可以与同一幣種中的其他幣具有相同的价值。常见的用途包括包括数字收藏品,电子游戏项目,和标记的实物资产,如艺术品和房地产。

最常见的 NFT 代币标准是创建在以太坊的 ERC 721,最初他是为了 CryptoKitty 而开发的协议。然而,人们很快意识到,虽然这个标准非常适合加密猫,但对于越来越多的 NFT 使用场景来说,ERC 721 却是效率低下或是略显不足。于是几个月后,有人创建了ERC1155来应对这些使用场景。

我们更提出的这个标准更接近 ERC1155,其功能包括原本的规范草案中(Tannr之前提出的)基于 ERC721 的标准,和 SUDT 标准所基于的 ERC20 。

主要的差异和动

这次的规范与最初的规范草案最大的区别如下:

Quantity Field / Quantity 字段

一个 Quantity 字段包含了类似于 ERC1155 的功能。他允许代币变成具有可替换本质的非同质化代币。这有效地在 NFT 中添加了类似 SUDT 的功能,这让他与外部链上的代币标准可以进行更灵活的互操作性。
(注解:举个例子。如果今天有款链上三国的游戏,我得到了一捆来自蜀国的弓箭,和我的同伴得到的蜀国弓箭,可以是同质化代币;但是我的这些弓箭和别人手上的魏国制作的弓箭就不一样了)。
这使得这个标准适用于更常见的是使用案例中,如电玩游戏的物件,用户这里可以拥有一个以上的特定物件。这将节省大量的状态空间,这也意味着对于大量类似的物件来说,资产的所有权只会占用更好的 CKBytes 。

Dynamic Loading of Token Logic 代币逻辑的动态加载

开发者定义的代币逻辑是使用 deps 来动态加载实现的,而不是在 lock script 中实现的。这允许 NFTs 在不依赖于特定的自定义 lock script 的情况下还能包含自定义的功能。
这提高了代币平台间 NFTs 的互操作性,因为它允许使用任何的 lock script 。这是非常令人向往的,因为任何需要定制的 lock script 的平台,例如 NFT 拍卖平台,都没办法兼容。

钱包也将从中受益,因为它减少了众所周知的 lock script 的数量,这些脚本将包括在已知行为的安全脚本“白名单”中。当代币引入新功能时,开发人员不需要将新的 lock script 的定义通知钱包。

Specification 规范

该规范详细说明了 NFT 的数据结构和用途。描述了必须出现在任何实现中的功能,也包括其背后的基本原理。

Cell Structure cell 结构

这是一个 NFT cell 的基本结构

data:
  instance_id: * (32 bytes)
  quantity: u128 (16 bytes)
  token_logic: code_hash (32 bytes)
  custom: *
lock: <user_lock>
type:
  code_hash: NFT Code Hash (32 bytes)
  hash_type: code
  args: <governance_lock_hash>, *

NFT cell 中包含的数据字段如下:

  • instance_id :前 32个字节表示该物件的ID。这个标识符定义了一个代表某物件的代币。这32个字节是在生成 Cell 时创建的唯一一个的哈希。这个 id 的长度必须始终为32字节
  • quantity :接下来的16个字节是 u128,表示单元中代币物件的数量。quantity 的长度必须始终为 16 字节。该字段是可选的,如果未使用,可以省略。如果开发者没有使用 quantity ,但是该字段仍然存在,则会将其设置为默认值 1。(注解:也就是说开发者没特别说发行几个,这个资产他就会只有一个。)
  • token_logic:接下来的 32 个字节表示要使用的代币逻辑的 code hash 。该哈希必须与包含将要执行的代码的 cell 依赖项的数据哈希匹配。此代码包含开发人员为了管理代币而放置的任何逻辑。token_logic 字段的长度必须始终为 32 字节,但如果不使用 token_logic,则可以省略。但如果开发人员没有使用 token_logic,又存在 token_logic 字段,则该将其设置为一个由零组成的特殊值(注解:0x0000000000000000000000000000000000000000000000000000000000000000)。quantity 字段必须出现,以便使用 token_logic 字段。
  • costom: 超过前 80 个字节的其他数据可以在这里存储。该数据由开发者自定义,要不要使用是可选的。quantity 字段和 token_logic 字段必须出现,以便使用 Custom字段。

user_lock可以是任何的 lock script 。该规范会对所使用的 lock 进行限制。
governance_lock_hash 是一个32字节的哈希,它定义了具有管理权限的 token 所有者的 lock script hash。
由 code hash 、type hash、governance lock hash和任何其他 args 组成的唯一的类型脚本( type script )定义了 token class。 token class 由类型脚本指定,而类型脚本又包括 governance lock hash。因此,token class 本质上连接到特定的 lock script ,该脚本可以是单个用户、多个用户或另一个脚本。

Generation 生成

生成模式允许所有者能在同一个 token class 中创建无限个新的 token instance。指派给每个 token 的 instance ID 是使用seed cell 设计模型生成的,这意味着它是随机分配的,并且保证全局唯一。新的 token instance 中的 token 数量在创建时定义,在生成后就不能增加。
Instance ID 按照下列规则去生成

For any new token instance being created, the Instance ID is a hash of the
outpoint of the first input, combined with the output index of the token
instance cell being created.

hash(seed_cell.tx_hash, seed_cell.index, instance_output_index)

通过包含 token instance 的输出索引,可以在单个交易中创建多个物件,并且保证每个物件都有一个全局唯一的 instance ID。

以下是单一个交易中生成两个 token instance 的例子

inputs:
    [Seed Cell]
        data: <*>
        lock: <governance_lock>
        type: <*>
outputs:
    [NFT Cell]
        data:
            <instance_id: hash(seed_cell.tx_hash, seed_cell.index, 0)>
            <quantity>
            <token_logic_hash>
            <custom>
        lock: <*>
        type:
            code_hash: NFT Code Hash (32 bytes)
            hash_type: code
            args: <governance_lock_hash>, *
    [NFT Cell]
        data:
            <instance_id: hash(seed_cell.tx_hash, seed_cell.index, 1)>
            <quantity>
            <token_logic_hash>
            <custom>
        lock: <*>
        type:
            code_hash: NFT Code Hash (32 bytes)
            hash_type: code
            args: <governance_lock_hash>, *

Constraints 约束条件

  • 只有 token class 的所有者可以制造新的物件
    hash(input[i].lock) == governor_lock_script_hash

  • Cell 的 Instance ID 必须是独一无二,而且需由 seed cell 所提供
    hash(seed_cell.tx_hash, seed_cell.index, output.index) == cell.instance_id

  • 如果 quantity 字段已经被使用,他必须要是 16 字节长度的 u128 。这个条件被强制约束:
    if data.length > 32: asset data.length >= 48

  • 如果 token logic 的字段有被使用,那么他们长度一定必须为 32 byte。我们以这个约束来实现:
    if data.length > 48: assert data.length >= 80

  • 如果 token logic 字段被使用了,并且不是填入 0,那么 token logic hash 必须是一个可验证的 cell dep cell_dep[i].data_hash == token_logic_hash

Transfer / Burn 交易/烧币

如果所有者模式在这个交易中没有被侦测到,那么这个交易就会被假定是一笔交易转账或者烧币。然后一组更严格的约束会被使用,在这个约束中这只允许修改 lock script 和 quantity 字段。

假设 Alice 要传三个她的 token 给 Bob:

inputs:
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 10>
            <token_logic: None>
            <custom: None>
        lock: <Alice>
        type: <token_class: XYZ>
outputs:
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 7>
            <token_logic: None>
            <custom: None>
        lock: <Alice>
        type: <token_class: XYZ>
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 3>
            <token_logic: None>
            <custom: None>
        lock: <Bob>
        type: <token_class: XYZ>

Constraints

  • Token instance 只能够被既存的 token instance 创建。
    token_instance_output[i].instance_id == token_instance_input[i].instance_id
  • 在输出端的 token instance 的数量必须要小于或等于输入端,如果在这里没有显示出值,则默认数量为 1
    sum(token_instance_output[…].quantity) <= sum(token_instance_input[…].quantity)
  • Token instances 必须无法改变 token_logic 字段
    token_instance_output[i].token_logic_hash == token_instance_input[i].token_logic_hash

注记:对于 cell 中前 80 个字节外的所有数据都是客制化数据,是是没有任何限制的。任何处理此数据的开发者规则都应该包含在这个 token logic 脚本中。

Update (Owner Mode) 更新(所有者模式)

当交易由所有者创建时,执行将允许对 cell 数据进行 transfer 操作中不允许的其他更改。这里特别指的是,token_logic 字段可以自由地更新,存储在初始 80 字节以外的任何自定义数据也可以自由地修改。
下面是一个所有者的更新操作,ALice 转了她 10 个 token 中的 3 个给 Bob,并且上传了 token_logic 和定制的数据:


inputs:
    [Cell]
        data: None
        lock: <Alice>
        type: None
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 10>
            <token_logic: EDFG>
            <custom: 555>
        lock: <Alice>
        type: <token_class: XYZ owner: Alice>
outputs:
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 7>
            <token_logic: EDFG>
            <custom: 222>
        lock: <Alice>
        type: <token_class: XYZ owner: Alice>
    [NFT Cell]
        data:
            <instance_id: ABCD>
            <quantity: 3>
            <token_logic: HIJK>
            <custom: 333>
        lock: <Bob>
        type: <token_class: XYZ owner: Alice>

Constraints 约束条件

  • Token instances 只能被既存的 instances. 创建
    token_instance_output[i].instance_id == token_instance_input[i].instance_id
  • token instances 输出的数量必须小于等于输出,如果在这里没有出现任何值,则默认数量为 sum(token_instance_output[…].quantity) <= sum(token_instance_input[…].quantity)

Token Logic 执行

Token Logic Script 可以在这些特定的情况下被执行:

  • NFT 的 CELL 的 data 中包含 Token Logic 的值.
  • Token Logic 的 code hash 没有填满零,这表示缺少脚本。
  • 该脚本执行了一个 transfer 或者 burn 的操作
  • 没有侦测到 Owner 模式

Token Logic 不会在 token 生成或更新这两种操作进行的时候执行,因为这将是所需的逻辑变得更加复杂化,也会使得 NFT 物件的管理行为变的复杂化。

Token Logic 字段必须是设定为一个 C 共享的库 (cdylib) 的 Token Logic 脚本的 32 字节的 Blake2b code hash,要获得此哈希,有一个简单的方法是在被编译好的二进制文件上使用 ckb-cli

ckb-cli util blake2b —binary-path ./build/release/token-logic.so
这个二进制文件必须被添加到区块链上的某个 Cell 之中,并且此 Cell 的输出可以以 cell dep 的形式,被包含在一笔 NFT 请求 Token Logic 脚本的交易之中。

Token Logic 的脚本必须遵循源自于 Capsule 的基本 c-sharedlib 的约定格式。目前,Token Logic 脚本必须用 C 编写,因为在Rust 编译器中缺乏对 RISC-V 的 cdylib 目标的支持。一旦添加了支持,那么我们将能够完全支持用 Rust 编写的 Token Logic 脚本 。
Token Logic 脚本的共享库要求一个外部函数,来作为执行的入口点。这个函数会占用包含执行脚本本身的 Token Logic 的 Code hash 的几个字节的数组。

// Rust Definition
fn(token_logic_code_hash: &[u8; 32]) → i32

// C Definition
int32_t token_logic(const char* token_logic_code_hash)

token_logic_code_hash 的值会被包含在 token logic 之中因为这对正统的 NFT 验证来说是必须的。在正常条件下,在执行 token logic 脚本时,只有那些 Token Logic 的值和 token_ logic_code_hash 对上了才会被处理。如果出现不同的 Token Logic 值,那么 cell 就不应该被验证,因为这代表这个值应该被其他的 Token Logic 验证。 然而,这个指导原则并不适用于复杂的 NFT 物件类型的交互

Script Logic Flowchart 脚本逻辑的流程图

这个流程图列出了基本的 NFT 物件的逻辑操作。

Considerations

Token Metadata 代币元数据

和 SUDT 标准相似,没有元数据存在 cell 本身之中。在每个 cell 中包含这些数据是没有意义的,因为这将不必要地占据额外的容量。链上元数据应该存在于单个可以被链下应用程序轻松定位的 cell 之中。在此没有包括如何处理该元数据的标准,因为它超出了本文的范围。

Backwards Compatibility 向后兼容

本标准部分向后兼容于最初的草案标准。如果只使用 Instance ID 创建了一个新的 token instance,省略了quantity、token_logic 和 custom 字段,那么它在功能上与最初的 NFT 草案标准完全相同。如果在 instance ID(32字节)之外存在任何数据,那么应用的约束是不同的

Instance ID and Quantity Restrictions/ Instance ID 和数量限制

这个标准对控制 instance ID 和 Quantity 数值设置了一些无法被 token class 所有者攻破的限制。
这个 NFT 标准允许在任何时候**无限地创建新的 Token instance **。但是,和 SUDT 有所不同的是,任何 token instance 的数量在创建时都是固定的,以后不能再增加了。

为了确保 instance ID 是惟一的,它的创建使用 seed cell 的模式。这有效地从所有者手中夺走了对 instance ID 的控制权。所有者控制何时创建 Token instance ,但他们不能控制 instance ID 是什么。这时候如果数量完全不受限制,那么这实际上就是否定了前面提到的模式。通过同时限制 instance ID 和数量,这个标准保证了 token instance 是惟一的且不可伪造的,即使是 token class 的所有者。

为什么这个特征是重要的,有个真实世界的案例是可收集的游戏卡《Magic The Gathering》。某些稀有卡片的第一版,对收藏者来说是极其珍贵的。然而,这些稀有卡的伪造品存在,原卡发行者的再版印品也存在。限制 instance ID 和数量可以消除任何恶意伪造的可能性,并确保发行者以后的重新印制版不会被误认为是初始版。

Usage Examples 使用范例

下方是一些一般的 NFT 的使用场景,和他如何被用这个标准实现的案例

Topps Garbage Pail Kids 垃圾桶小朋友

Topps 最近以 NFT 的形式,在 WAX 区块链上发布了 Garbage Pail Kids,也就是一种 80 年代很流行的交易收藏卡片。这些是很基本的交易卡,没有任何额外的功能,这使他们可以非常容易的就被这个标准所实现.
DApp 将会为每一张卡片铸造一个独特的 token instance 。在此 Token logic 和客制化数据是必须有的。quantity 字段在这里非常有用,因为它允许用户在一个 cell 中持有同一个 物件的多张卡片。香关联的元数据和图像数据将保存在 Topps 服务器上,这些服务器与特定的 instance ID 匹配。

Multi-Token Extensible NFT - Garbage Pail Kids

CryptoKitties 加密猫

像 CryptoKitties 这样的 dApp 将使用自定义的 token logic 脚本来处理两个 NFT 的 token instance 之间的繁殖操作。在本例中,kitty 的“ DNA ”存储在自定义数据区域中(前 80 个字节之后)。开发人员提供的自定义 token logic script 将确保它不能被直接修改,只能在繁殖这种交易进行的期间,根据特定规则进行更新。
新的 token instance 只能由 Dapp 所有者创建,这意味着如果要创建第三个 kitty,那么新 kitty 的创建必须从所有者那里获取instance ID。这可以很容易地通过 Dapp 提供空鸡蛋的物件来实现,该实例必须与两只 Kitty 结合,以繁殖第三只 kitty 。这里实例 ABC 和 DEF 在 GHI instance 中结合它们的DNA。鸡蛋的 instance 可以批量创建,并使用链上脚本分配,这意味着繁殖过程可以在链上完成,而不需要集中化处理。

另一个在游戏上稍微不同的变化是可以消耗原来的两只 Kitty 来产生第三只 Kitty。这将改变游戏的动态,因为这代表有一只 Kitty 会在繁殖后消失,但如果这是一个游戏,而不是在繁殖后可预期会死亡的密码蜘蛛,那可能是合理的。
在这个案例中,物件 ABC 在 物件 DEF 被消耗的时候被重复使用。这个 Kitty 的 DNA 是根据 token logic 脚本提供的规则而产生的 cell 。

Multi-Token Extensible NFT - CryptoKitties

Resident Evil (Guns and Ammo) 生化危机(枪支和弹药)

如果 Capcom 想要发布一款带基于 NFT 游戏物件的生化危机,像重新装弹药这样的常见动作,可以在没有集中 Dapp 逻辑的情况下在链上完成。

在这个案例中,用户拥有一个叫做物件 DEF 的武器,并且有用物件 ABC 代表的十发弹药。 Token logic 的脚本 RTY 将会允许武器的弹药在弹药被烧毁的交易中被更新。这10个弹药在交易中烧掉,这允许武器的弹药计数器从0更新到10,以便于让玩家重新装子弹。
Multi-Token Extensible NFT - Resident Evil

Reference Implementation 参考实现

参考实现是在 Rust中使用 Capsule 框架编写的,这可以在GitHub上找到。但这个规范仍然是一个草案,代码还没有准备好要实现。

3 Likes

If you are asking how the NFT type script can distinguish between simple or complex transaction inspection used in token logic, I believe the answer is you cannot. There is valid justification for using either in specific conditions.

I was describing another possible variation for handling cells. In CryptoKitties to cats breed to create a third cat. The original two cats are still alive after breeding. This creates a little more complexity in cell management because it is two inputs and three outputs.

As an example, I mention CryptoSpiders as another game. Spiders mate at the end of their lifecycle, and die soon after. It is more simple in cell management because it is two inputs that are consumed, and one output.

This example uses a third NFT egg cell to hatch a new cat. The egg must come from somewhere. A user cannot create it by themselves. When users are playing the game, the website that generates the transactions would automatically give out eggs when needed. This works fine, but this is a centralized solution since all the eggs are under control of the website. Eggs could also be distributed on-chain using a special lock script that has no need for the website. I was indicating that a full decentralized solution is possible under this model, even though I think the more simple centralized solution is sufficient for most.

1 Like

Very sorry for missing this reply.
First of all, thanks for answering.
Ib those days, I also keep considering such scenarios for NFT also discussing with some community members. Cell management like create new NFT through breeding would be an issue.

Case 1 : I have 100 arrows NFT (the same instance ID ) and want to send 30 arrows to three different players without knowing if they have enough ckbytes or not. Maybe here the Approve cell with the ckb indexer could help.

Case 2 : 2 Cats breed one more kitty.
Well,got aspired by regulation byte,not sure whether it is a solution or not :

regulation_byte: 0b 0 0 0 0 0 0 0 0
                    |         | | └- Global control
                    |         | └--- first generation
                    |         └----- second generation 
                    |         
                    └--------------- 1: Definition / 0: Usage

I know this is a very rough idea for a mother(female) cat which may not be considered very well.

But tbh, spending a little capacity to get a new kitty asset must be a desirable behavior that most player is willing to do. See the timing when gas fees rise up, numerous DeFi players still pay, and fortunately, the ckbyte for NFT occupation still could be redeemed theoretically.

Got it, and if such kinds of demand present in the future,I believe there would be specified NFT spec released based on this RFC like regulation sudt .

1 Like

Something like the Approve Cell, Anyone Can Pay, or Open Transaction Lock, should be able to help with this.

Using a system like a regulation byte may be beneficial to specify how an NFT Token Class behaves. It could also be used at the application level, which you indicated in your example, but that is up to the developer of the application to define.

I thought up another way the breeding could be handled which is quite simple. In my examples, I always used the Instance ID for the purpose of identifying a specific cat. That doesn’t have to be the case. An Instance ID could represent a generation of cats, a specific series of cats or the developer could choose to ignore the meaning of the Instance ID completely. If they ignore it, then they would need to specify their own identifier in the custom data, but this also gives them the ability to change it any way they need to.

For developers who do not need guaranteed scarcity trait, the ability to change the Instance ID may be beneficial. I think there should be an option for this, but I’m not sure if that should be part of this standard or a separate standard. I will be doing a second NFT standard regardless. There needs to be a second more simple standard that can be more directly compatible with ERC1155.

1 Like

got it, just realize that instance_id could represent a couple of kitties. That’s cool.
But what it will be if I transfer a baby kitty out of such the series of kitties below to a specific instance ID?
Actually, such kinds of cell capacity management of sUDT or NFT would be an issue deserving to discuss.

1 Like