My first NFT adventure
About 4 months ago I embarked on my first NFT-adventure. Up till then my only experience experience with block chain technology was buying which ever crypto currency I found interesting.
My first attempt was an ERC20 token, after a chat with some of the guys behind Ember Sword. I entertained som vague idea of using the token as an acces key or certificate of validation - but how on to what I had no idea of. So in reality the token ended up having nothing to it but a name. I followed a tutorial and I have to admit I practically learned next nothing from it besides from the most fundamental of solidity.
A bit later I began to pay some serious attention to art NFTs. The idea of using the chain to combine an immutable codebase with a generative visual expression triggered something in me. I had the good fortune to meet and get some advise from the programmer behind Cranes and Invisible Friends and started to dive into the contract code behind many NFTs. In general I find the "elder", on-chain generative NFTs like Autoglyphs more interesting than the popular SoMe-profile-friendly layer based off-chain generated NFTs. Many of the latter are visually cool and really nice but from a technical point of view I find them a bit boring.
So I decided to try to create something that was
1) stored on the chain
2) integrating or reflecting the chain
4) geometric or non-figurative
5) limits and giveaways implement in code
I have a background in the humanities and have spend a great deal of time in the past researching the impact of early 20th century generative art and concrete art from the 1960s on early computer generated art and net art. So for my first NFT I dived into the treasure chest and decided that Piet Mondrian's colorful squares would be suitable for on-chain generation and storage as svgs.
Mondrian’s squares are painting and posses a texture and of course physicality that svg don’t. Also copying someones art is just plagiarism and I wanted my NFT to reflect the chain as well as just be something visual...
The squares have a stringency to them that have appealed to many mathematical minds and various mathematical challenges based on Mondrian’s art have been presented. One of them is Mondrian Puzzles. Mondrian Puzzles are puzzle that requires rectangles tiling a integer-sided square. All rectangles within the square must be integer sided and pairwise non-congruential. The aim is to fill the square with such rectangles in a way so that the difference between the area of the largest and the area of the smalles rectangles are kept at a minimum. The ultimate challenge consists in finding a tiling that has the lowest score possible. However there are no formulas for the perfect solution - so the most viable solution is using a heuristic approach and just try. So by creating a seed based on the chain's current state this could be the basis for the heuristic - meaning the puzzle would go through multiple heuristics as the chain evolves.
Remix, Hardhat, views and variable limitations
Creating the visual representation of the Mondrian Puzzle was more of a trivial programming challenge than a smart contract challenge. It wasn't until I started to run into contract sizing, gas usage and variable storage it started to become solidity specific and much more interesting.
I started off by using th web based Remix IDE, but soon turned to Truffle and Ganache. It worked out fine for a long time but a tip sent me off to try Hardhat. While Truffle did work well for me I think Hardhard at the time of writing is the better more up to date choice. For my next NFT project I'm definitely going to use Hardhard from the beginning.
In general one of the main challenges when learning solidity and how to use the various development tools is how everything is in rapid evolution. Tutorials and forum-threads are easily outdated after a few months and newer and better Node-packages are being developed fast and a lot of times I ended up reading up on obsolete methods and techniques.
However I learned a lot about storage variables, views, libraries, variable limitations and other quiet solidity specific stuff.
Reflecting the chain
Back to my intention of making the NFT reflect the state of the block chain. After some research I decided to base my random seed on a combination of the token number and the difficulty of the current block. As the Ethereum chain (still) is PoW (Proof-of-work), the difficulty reflects the difficulty of a mathematical problem that the miners must try to solve. The more active miners, the harder is the difficulty.
Using this approach I create the same sequence of pseudo random numbers for a heuristic solution to a mondrian puzzle. When the difficulty goes up or down a new heuristic approach to the mondrian puzzle will be presented. The solution might not be ideal, but it serves the purpose.
Lowering the gas fee
The final smart contract related challenge I ran into was the steep gas fee when deploying. My main contract and library for the creation of the puzzle was about 6M. I spend a lot of time optimizing the code, which meant turning away from good object oriented practice, choosing the suboptimal datatypes and other dodgy measures. Finally after ditching ERC721Enumerable a d rewriting the function it provided my contract was down to 5M and I managed to deploy at a low gas fee.
My Mondrian Puzzles are now available at http://mondrian-puzzles.net (another programmring challenge, that taught me plenty about NodeJS, React and Web3-integration). If you like them I hope you can find room in your wallet for one and time to see it evolve.
For my next project I'm going to try to combine the smart contract with an off-chain generation to create mosaic based portraits of non-existing persons (!). SO stay tuned ;)