contract CryptoFlower is ERC721Token, Ownable {

    // Disallowing transfers
    bool transfersAllowed = false;

    // Storage of flower generator
    mapping (uint256 => bytes7) genes;
    mapping (uint256 => string) dedication;

    // event definitions
    event FlowerAwarded(address indexed owner, uint256 tokenID, bytes7 gen);
    event FlowerDedicated(uint256 tokenID, string wording);

    /*
     *  @dev Constructor
     *  @param string _name simple setter for the token.name variable
     *  @param string _symbol simple setter for the token.symbol variable
     */
    constructor(string _name, string _symbol)
    ERC721Token(_name, _symbol)
    public {}

    /*
     *  @dev Minting function calling token._mint procedure
     *  @param address beneficiary is the destination of the token ownership
     *  @param bytes32 generator is a hash generated by the fundraiser contract
     *  @param uint karma is a genome influencer which will help to get a higher bonus gene
     *  @return bool - true
     */
    function mint(address beneficiary, bytes32 generator, uint karma) onlyOwner external returns (bool)  {
        /*
         *  Interpretation mechanism [variant (value interval)]
         *  Flower:             1 (0-85); 2 (86-170); 3 (171-255);
         *  Bloom:              1 (0-51); 2 (52-102); 3 (103-153); 4 (154-204); 5 (205-255)
         *  Stem:               1 (0-85); 2 (86-170); 3 (171-255);
         *  Special:            None (0-222);1 (223-239); 2 (240-255);
         *  Color Bloom:        hue variation
         *  Color Stem:         hue variation
         *  Color Background:   hue variation
         */

        bytes1[7] memory genome;
        genome[0] = generator[0];
        genome[1] = generator[1];
        genome[2] = generator[2];
        if (uint(generator[3]) + karma >= 255) {
            genome[3] = bytes1(255);
        } else {
            genome[3] = bytes1(uint(generator[3]) + karma);
        }
        genome[4] = generator[4];
        genome[5] = generator[5];
        genome[6] = generator[6];

        genes[lastID() + 1] = bytesToBytes7(genome);
        emit FlowerAwarded(beneficiary, lastID() + 1, genes[lastID() + 1]);
        _mint(beneficiary, lastID() + 1);
        return true;
    }

    /*
     *  @dev function that enables to add one-off additional text to the token
     *  @param uint256 tokenID of the token an owner wants to add dedication text to
     *  @param string wording of the dedication to be shown with the flower
     */
    function addDedication(uint256 tokenID, string wording)
    onlyOwnerOf(tokenID)
    public {
        require(bytes(dedication[tokenID]).length == 0);
        dedication[tokenID] = wording;
        emit FlowerDedicated(tokenID, wording);
    }

    /*
     *  Helper functions
     */

    /*
     *  @dev function returning tokenID of the last token issued
     *  @return uint256 - the tokenID
     */
    function lastID() view public returns (uint256)  {
        return allTokens.length - 1;
    }

    /*
     *  @dev CryptoFlower specific function returning the genome of a token
     *  @param uint256 tokenID to look up the genome
     *  @return bytes7 genome of the token
     */
    function getGen(uint256 tokenID) public view returns(bytes7) {
        return genes[tokenID];
    }

    /*
     *  @dev function transforming a genom byte array to bytes7 type
     *  @param bytes1[7] b - an array of 7 single bytes representing individual genes
     *  @return bytes7 the compact type
     */
    function bytesToBytes7(bytes1[7] b) private pure returns (bytes7) {
        bytes7 out;

        for (uint i = 0; i < 7; i++) {
          out |= bytes7(b[i] & 0xFF) >> (i * 8);
        }

        return out;
    }

    /**
   * @dev Checks msg.sender can transfer a token, by being owner, approved, or operator
   * @param _tokenId uint256 ID of the token to validate
   */
    modifier canTransfer(uint256 _tokenId) {
        require(transfersAllowed);
        require(isApprovedOrOwner(msg.sender, _tokenId));
        _;
    }
}
/*
 *  @title CryptoFlower
 *  @dev This is a constrained but compliant ERC725 token implementation with additional genome sequence for each token
 *  @dev rewrites the CanTransfer modifier of OZs' implementation in order to disable transfers
 */
function addDedication(uint256 tokenID, string wording)
onlyOwnerOf(tokenID)
public {
    require(bytes(dedication[tokenID]).length == 0);
    dedication[tokenID] = wording;
    emit FlowerDedicated(tokenID, wording);
}

/*
 *  @dev function that enables to add one-off additional text to the token
 *  @param uint256 tokenID of the token an owner wants to add dedication text to
 *  @param string wording of the dedication to be shown with the flower
 */