Porównaj commity

...

4 Commity

Autor SHA1 Wiadomość Data
Torrin Leonard ce721df8db
Updating Logic documentation 2023-01-01 17:46:31 -08:00
Torrin Leonard 084b7f6ae2
Updating Logic documentation 2023-01-01 17:34:40 -08:00
Torrin Leonard 0bfcb39bf0 Updating __init__.py
Updating __init__.py
Adding support for an order_num offset that allows you to offset the order number of the NFT collection.
2023-01-01 20:33:35 -05:00
Torrin Leonard b3829089a2 Cleaning up methods, adding comments 2023-01-01 20:27:43 -05:00
3 zmienionych plików z 175 dodań i 133 usunięć

Wyświetl plik

@ -434,27 +434,51 @@ You can add and remove Rules in this list using the two + and - buttons: <img wi
Each item in the list will have two text fields labled `Item List 1` and `Item List 2` and a drop down menu where you can select the type of rule:
<img width="552" alt="Screen Shot 2022-04-24 at 3 37 03 PM" src="https://user-images.githubusercontent.com/82110564/164993481-335bcc86-1fd1-4a7f-9e82-58c4a4b31642.png">
![Screenshot 2023-01-01 184011](https://user-images.githubusercontent.com/82110564/210187622-c139346b-fd0c-446f-af71-75cf0b08bd95.png)
The best way to understand how Logic works is to think of it as a sentence, example: ``"Items List 1 Never goes With Items List 2"`` or ``"Items List 1 Only goes With Items List 2"``.
The best way to understand how Logic works is to think of it as a sentence, example: ``"Items List 1 does NOT go with Items List 2"`` or ``"Items List 1 THEN goes with Items List 2"``.
Both `Item Lists` can contain either multiple Variants or Attributes, however this is limited depending on the type of Rule that is selected (See [Rule Types](#rule-types)). All items in the `Item Lists` are seperated by a comma (`,`), NO SPACES!
Both `Item Lists` can contain either multiple Variants or Attributes. However, keep in mind that rules containing Attributes drastically reduce the amount of combinations of a given NFT collection. Likewise with rules that contain large amounts of variants of a given Attribute
It's reccomended if you have a large NFT collection to create a Logic.json file so that your Rules are stored safely. See [Logic JSON Schema](#logic-json-schema).
All items in the `Item Lists` are seperated by a comma (`,`), NO SPACES!
It's reccomended if you have a large NFT collection to create a Logic.json file so that your Rules are stored safely. When using Blender, the settings stored in the Blend_My_NFTs add-on may get lost for various reasons. See [Logic JSON Schema](#logic-json-schema) to learn how to create a Logic.json file.
## Rule Types
There are three rule types:
- ``Never With`` --> If selected, ``Items List 1`` will never appear if ``Items List 2`` are selected. For each NFT DNA that is generated, either ``Items List 1`` or ``Items List 2`` are randomly selected. That selected ``Items List`` is then acted upon depending on if the items in the list are Attributes or Variants:
- If ``Items List`` contains complete Attribute(s), those Attribute(s) will be set to Empty automatically.
- If ``Items List`` contains Variant(s), the other Variants in that Variants Attribute will be randomly or weightedly selected depending on if you have ``Enable Rarity`` selected when you create NFT data.
There are two rule types you can select:
- ``THEN`` --> Items (both Attributes and Variants) in ``Items List 1`` will always appear with Items in ``Item List 2``. The THEN rule works forwards and backwords so if an element in either list are detected, the system will select a Variant from all attributes contained in the other list.
- ``Only With`` --> If selected, ``Items List 1`` will only appear if ``Items List 2`` are selected. If ``Items List 1`` contains complete Attribute(s), those Attribute(s) will be set to Empty automatically. Meaning they will not appear if you export images, animations, or 3D models.
- ``NOT`` --> Items (both Attributes and Variants) in ``Items List 1`` will never appear with Items in ``Item List 2``. The NOT rule works forwards and backwords so if an element in either list are detected, the system will select
- ``Always With`` --> If selected, ``Items List 1`` will always appear if ``Items List 2`` are selected.``Items List 1`` CANNOT contain complete Attribute(s) and is limited to single Variants. The list can contain multiple Variants, however they must be from seperate Attributes.
### What Can Item Lists contain?
Item Lists can contain both Attributes and Variants, there is no limitations to which can be selected for Items List 1 or Items List 2.
### Can Item Lists contain Variants from multiple Attributes?
Yes. You can mix and match Variants from different Attributes for a given rule. Behind the scenes the Logic system keeps track of which Variants in a given list by sorting them under their parent Attribute, this way if you select a full Attribute, or multiple Variants of the same Attribute the Logic system will be able to apply rules to them.
### Is there a limit to the number of Rules I can create?
Yes, the limit isn't a solid number however. It depends on the number of combinations in your collection, the number of rules you have, how many Variants and or Attributes those rules encompase, and if you have Rarity/Materials enabled.
The following makes it easier to understand: Rarity and Logic rules reduce the number of combinations the script can generate, while adding more Variants and Attributes and adding Materials using the Material Randomizer increase the number of combinations the script can generate.
### Can rules conflict with each other?
Yes, I need to come up with examples, however the new system is far less prone to this issue arising. Just keep the rules simple, straightforward and easy to understand and you should be good. Also keep in mind that the more rules you add the higher the chance a rule conflict may arise, and you may see Attribute and Variant behaviour that you do not desire. (This section needs an example)
### How are attributes handled?
The Logic system handles Attributes in two different ways depending on the Rule type selected:
- ``THEN`` --> If a THEN rule states that ``IF <Variant> THEN <Attribute>`` and Variant is selected for a given DNA, a Variant from the Attribute will be selected. However, if the Variant is not selected for a given DNA, the Variants from the stated Attribute will still be selected. THEN rules are more built for situations where you want a given Variant to always appear with another Variant or group of Variants, adding Attributes to this rule is possible, but doesn't really do anything so it's reccommended to keep the THEN rule Attribute-free.
- ``NOT`` --> If a NOT rule states that ``IF <Variant> NOT <Attribute>`` and Variant is selected for a given NFT DNA, the Attribute will be given an "Empty" state, and the DNA slot will be set to 0. This will tell Blend_My_NFTs not to render any Varaint within the Attribute stated in the Rule. If instead the rule is ``IF <Attribute> NOT <Attribute>``
### What is the most important thing to understand about Logic?
Rules now work forwards and backwords, meaning that ``Items List 1`` and ``Items List 2`` are checked twice with each rule, but swapped. This allows for example, the NOT rule to exclude all combinations of two variants, for example if we create a rule ``IF <Variant 1> NOT <Variant 2>`` then Variant 1 will never appear with Variant 2 if either are selected first. This stops all instances of Variants 1 and 2 from appearing with eachother. This was not the case with the old Logic systems, in order to get the same affect you needed two rules, one with first ``IF <Variant 1> NOT <Variant 2>``, then ``IF <Variant 2> NOT <Variant 1>``. This also applies with the THEN rules, for example with the rule ``IF <Variant 1> THEN <Variant 2>``, Variant 2 will always appear with Variant 1, and Variant 1 will always appear with Variant 2.
It's also important to undertsand that the more rules you add to your collection, the less combinations you leave Blend_My_NFTs to generate from. The number of combinations is the total theoretical number of NFTs you could generate with your collection, the more rules you add reduce the number of bossible combinations depending on how they are setup. If the system is not able to find combinations it can get stuck in a never ending loop which can only be stopped by restarting Blender or pressing CTRL + C in the Blender System Console.
### How complicated was it to code the Logic system?
Very complicated. It took about 4 complete overhauls of building it from the ground up before the current system was built. And even then it took me months of testing to modify and perfect it so that it works the way users expect it to work. I (Torrin Leonard) spent a lot of time creating the Logic system the way I understood it would work, the way a programmer would use it. However this was very problematic as it caused a lot of confusion in our community about how the individual rules actually opperate. The current Logic system is a simple IF THEN and IF NOT model that makes it easy for people to understand and implement their NFT collection. Creating this system tested my sanity and my ability to understand what people want and build it in a way they can use a very complicated system easily. It was a very fullfilling learning experience. I'm also honestly releaved with the state it is in now and want to never look at the logic.py file ever again.
**Important:** The more rules you add the higher the chance a rule conflict may arise, and you may see Attribute and Variant behaviour that you do not desire.
## Logic JSON Schema
@ -469,18 +493,22 @@ If you'd like, copy and paste this template into the JSON file you created above
{
"Rule-1":{
"IF": [
"<Variant collection name>"
"<Variant or Attribute collection name>",
"<Variant or Attribute collection name 2>"
],
"THEN":[
"<Attribute or Variant collection name>", "<Attribute or Variant collection name 2>"
"<Attribute or Variant collection name>",
"<Attribute or Variant collection name 2>"
]
}
},
"Rule-2":{
"IF": [
"<Variant collection name>"
"<Attribute or Variant collection name>",
"<Attribute or Variant collection name 2>"
],
"NOT":[
"<Attribute or Variant collection name>", "<Attribute or Variant collection name 2>"
"<Attribute or Variant collection name>",
"<Attribute or Variant collection name 2>"
]
}
}
@ -492,8 +520,6 @@ If you'd like, copy and paste this template into the JSON file you created above
- ``THEN`` A list of Attributes or Variants that always appear IF the ``IF`` Variant is selected.
- ``NOT`` A list of Attributes or Variants that never appear IF the ``IF`` Variant is selected.
* Note: ``NOT`` is not currently stable, it's recommended to only use a Single variant per NOT rule to see consistant results.
## Example Logic.json File
Say we have the following scene in a .blend file:

Wyświetl plik

@ -1,7 +1,7 @@
bl_info = {
"name": "Blend_My_NFTs",
"name": "Blend_My_NFTs - BeastHood Version",
"author": "Torrin Leonard, This Cozy Studio Inc.",
"version": (4, 5, 2),
"version": (4, 6, 0),
"blender": (3, 2, 2),
"location": "View3D",
"description": "A free and opensource Blender add-on that enables you to create thousands of unique images, "
@ -12,8 +12,8 @@ bl_info = {
"category": "Development",
}
BMNFTS_VERSION = "v4.5.2"
LAST_UPDATED = "10:03PM, Dec 13th, 2022"
BMNFTS_VERSION = "v4.6.0"
LAST_UPDATED = "08:31PM, Jan 1st, 2023"
# ======== Import handling ======== #
@ -167,6 +167,8 @@ class BMNFTData:
enable_dry_run: str
order_num_offset: int
custom_fields: dict = None
fail_state: Any = False
failed_batch: Any = None
@ -233,6 +235,7 @@ def get_bmnft_data():
receiver_to=bpy.context.scene.input_tool.receiver_to,
enable_debug=bpy.context.scene.input_tool.enable_debug,
order_num_offset=bpy.context.scene.input_tool.order_num_offset,
log_path=bpy.path.abspath(bpy.context.scene.input_tool.log_path),
enable_dry_run=bpy.context.scene.input_tool.enable_dry_run
@ -352,14 +355,6 @@ def run_as_headless():
if args.batch_data_path:
input.batch_json_save_path = args.batch_data_path
if args.resume_failed_batch:
_fail_state, _failed_batch, _failed_dna, _failed_dna_index = helpers.check_failed_batches(input.batch_json_save_path)
input.fail_state = _fail_state
input.failed_batch = _failed_batch
input.failed_dna= _failed_dna
input.failed_dna_index = _failed_dna_index
if args.operation == 'create-dna':
intermediate.send_to_record(input)
@ -377,14 +372,14 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
nft_name: bpy.props.StringProperty(name="NFT Name")
collection_size: bpy.props.IntProperty(
name="NFT Collection Size",
default=1,
min=1
name="NFT Collection Size",
default=1,
min=1
) # max=(combinations - offset)
nfts_per_batch: bpy.props.IntProperty(
name="NFTs Per Batch",
default=1,
min=1
name="NFTs Per Batch",
default=1,
min=1
) # max=(combinations - offset)
save_path: bpy.props.StringProperty(
@ -396,14 +391,14 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
enable_rarity: bpy.props.BoolProperty(
name="Enable Rarity"
name="Enable Rarity"
)
enable_logic: bpy.props.BoolProperty(
name="Enable Logic"
name="Enable Logic"
)
enable_logic_json: bpy.props.BoolProperty(
name="Use Logic.json instead"
name="Use Logic.json instead"
)
logic_file: bpy.props.StringProperty(
name="Logic File Path",
@ -414,7 +409,7 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
enable_materials: bpy.props.BoolProperty(
name="Enable Materials"
name="Enable Materials"
)
materials_file: bpy.props.StringProperty(
name="Materials File",
@ -426,7 +421,7 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
# Generate NFTs Panel:
image_bool: bpy.props.BoolProperty(
name="Image"
name="Image"
)
image_enum: bpy.props.EnumProperty(
name="Image File Format",
@ -438,7 +433,7 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
animation_bool: bpy.props.BoolProperty(
name="Animation"
name="Animation"
)
animation_enum: bpy.props.EnumProperty(
name="Animation File Format",
@ -454,7 +449,7 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
model_bool: bpy.props.BoolProperty(
name="3D Model"
name="3D Model"
)
model_enum: bpy.props.EnumProperty(
name="3D Model File Format",
@ -474,35 +469,35 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
batch_to_generate: bpy.props.IntProperty(
name="Batch To Generate",
default=1,
min=1
name="Batch To Generate",
default=1,
min=1
)
# Refactor Batches & Create Metadata Panel:
cardano_metadata_bool: bpy.props.BoolProperty(
name="Cardano Cip"
name="Cardano Cip"
)
cardano_description: bpy.props.StringProperty(
name="Cardano description"
name="Cardano description"
)
solana_metadata_bool: bpy.props.BoolProperty(
name="Solana Metaplex"
name="Solana Metaplex"
)
solana_description: bpy.props.StringProperty(
name="Solana description"
name="Solana description"
)
erc721_metadata: bpy.props.BoolProperty(
name="ERC721"
name="ERC721"
)
erc721_description: bpy.props.StringProperty(
name="ERC721 description"
name="ERC721 description"
)
enable_custom_fields: bpy.props.BoolProperty(
name="Enable Custom Metadata Fields"
name="Enable Custom Metadata Fields"
)
custom_fields_file: bpy.props.StringProperty(
name="Custom Fields File",
@ -514,47 +509,50 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
# Other Panel:
enable_auto_save: bpy.props.BoolProperty(
name="Auto Save Before Generation",
description="Automatically saves your Blender file when 'Generate NFTs & Create Metadata' button is clicked"
name="Auto Save Before Generation",
description="Automatically saves your Blender file when 'Generate NFTs & Create Metadata' button is clicked"
)
enable_auto_shutdown: bpy.props.BoolProperty(
name="Auto Shutdown",
description="Automatically shuts down your computer after a Batch is finished Generating"
name="Auto Shutdown",
description="Automatically shuts down your computer after a Batch is finished Generating"
)
specify_time_bool: bpy.props.BoolProperty(
name="Shutdown in a Given Amount of Time",
description="Wait a given amount of time after a Batch is generated before Automatic Shutdown"
name="Shutdown in a Given Amount of Time",
description="Wait a given amount of time after a Batch is generated before Automatic Shutdown"
)
hours: bpy.props.IntProperty(
default=0, min=0
default=0, min=0
)
minutes: bpy.props.IntProperty(
default=0, min=0
default=0, min=0
)
email_notification_bool: bpy.props.BoolProperty(
name="Email Notifications",
description="Receive Email Notifications from Blender once a batch is finished generating"
name="Email Notifications",
description="Receive Email Notifications from Blender once a batch is finished generating"
)
sender_from: bpy.props.StringProperty(
name="From",
default="from@example.com"
name="From",
default="from@example.com"
)
email_password: bpy.props.StringProperty(
name="Password",
subtype='PASSWORD'
name="Password",
subtype='PASSWORD'
)
receiver_to: bpy.props.StringProperty(
name="To",
default="to@example.com"
name="To",
default="to@example.com"
)
enable_debug: bpy.props.BoolProperty(
name="Enable Debug Mode",
description="Allows you to run Blend_My_NFTs without generating any content files and enables debugging "
"console messages saved to a BMNFTs_Log.txt file."
name="Enable Debug Mode",
description="Allows you to run Blend_My_NFTs without generating any content files and enables debugging "
"console messages saved to a BMNFTs_Log.txt file."
)
order_num_offset: bpy.props.IntProperty(
default=0, min=0
)
log_path: bpy.props.StringProperty(
name="Debug Log Path",
@ -565,14 +563,14 @@ class BMNFTS_PGT_Input_Properties(bpy.types.PropertyGroup):
)
enable_dry_run: bpy.props.BoolProperty(
name="Enable Dry Run",
description="Allows you to run Blend_My_NFTs without generating any content files."
name="Enable Dry Run",
description="Allows you to run Blend_My_NFTs without generating any content files."
)
# API Panel properties:
api_key: bpy.props.StringProperty(
name="API Key",
subtype='PASSWORD'
name="API Key",
subtype='PASSWORD'
) # Test code for future features
@ -702,6 +700,7 @@ class ResumeFailedBatch(bpy.types.Operator):
receiver_to=render_settings["receiver_to"],
enable_debug=render_settings["enable_debug"],
order_num_offset=render_settings["order_num_offset"],
log_path=render_settings["log_path"],
enable_dry_run=render_settings["enable_dry_run"],
@ -1045,7 +1044,7 @@ class BMNFTS_PT_Other(bpy.types.Panel):
Other:
A place to store miscellaneous settings, features, and external links that the user may find useful but doesn't
want to get in the way of their work flow.
Export Settings:
This panel gives the user the option to export all settings from the Blend_My_NFTs addon into a config file. Settings
will be read from the config file when running heedlessly.
@ -1113,6 +1112,9 @@ class BMNFTS_PT_Other(bpy.types.Panel):
row.prop(input_tool_scene, "log_path")
row = layout.row()
row = layout.row()
row.prop(input_tool_scene, "order_num_offset")
row = layout.row()
layout.label(text=f"Looking for help?")
@ -1122,9 +1124,9 @@ class BMNFTS_PT_Other(bpy.types.Panel):
row = layout.row()
row.operator(
"wm.url_open",
text="YouTube Tutorials",
icon='URL'
"wm.url_open",
text="YouTube Tutorials",
icon='URL'
).url = "https://www.youtube.com/watch?v=ygKJYz4BjRs&list=PLuVvzaanutXcYtWmPVKu2bx83EYNxLRsX"
row = layout.row()
@ -1137,22 +1139,22 @@ class BMNFTS_PT_Other(bpy.types.Panel):
# ======== Blender add-on register/unregister handling ======== #
classes = (
# Property Group Classes:
BMNFTS_PGT_Input_Properties,
# Property Group Classes:
BMNFTS_PGT_Input_Properties,
# Operator Classes:
CreateData,
ExportNFTs,
ResumeFailedBatch,
RefactorBatches,
ExportSettings,
# Operator Classes:
CreateData,
ExportNFTs,
ResumeFailedBatch,
RefactorBatches,
ExportSettings,
# Panel Classes:
BMNFTS_PT_CreateData,
BMNFTS_PT_GenerateNFTs,
BMNFTS_PT_Refactor,
BMNFTS_PT_Other,
) + custom_metadata_ui_list.classes_Custom_Metadata_UIList + logic_ui_list.classes_Logic_UIList
# Panel Classes:
BMNFTS_PT_CreateData,
BMNFTS_PT_GenerateNFTs,
BMNFTS_PT_Refactor,
BMNFTS_PT_Other,
) + custom_metadata_ui_list.classes_Custom_Metadata_UIList + logic_ui_list.classes_Logic_UIList
def register():

Wyświetl plik

@ -86,70 +86,84 @@ def logic_rarity(variant_list, enable_rarity, a):
return str(variant_num[0])
def apply_rules_to_dna(hierarchy, deconstructed_dna, if_dict, result_dict, result_dict_type, enable_rarity):
def apply_rule_to_dna(hierarchy, deconstructed_dna, if_dict, result_dict, result_dict_type, enable_rarity):
"""
Applies a single given rule to the DNA. This function does not apply multiple rules at the same time.
Then returns the new deconstructed_dna with the single rule applied to it.
"""
# Check if Variants in if_dict are in deconstructed_dna, if so return if_list_selected = True:
if_list_selected = False # True if item in the if_dict (items in the IF dictionary of a rule) are selected
for attribute_index, a in enumerate(deconstructed_dna):
attribute = list(hierarchy.keys())[attribute_index]
for b in hierarchy[attribute]:
if hierarchy[attribute][b]["number"] == a:
if hierarchy[attribute][b]["number"] == a and attribute in if_dict:
a_dna_var = b
if a_dna_var in list(if_dict[attribute].keys()):
if_list_selected = True
break
continue
if attribute in if_dict:
if a_dna_var in list(if_dict[attribute].keys()):
if_list_selected = True
# If Variants in if_dict are selected, set each attribute in 'result_dict' to a random or rarity selected Variant
# from 'result_dict[attribute]' variant_list:
if if_list_selected:
# Invert 'items_returned' if 'NOT' rule is selected:
if result_dict_type == "NOT":
# If Variants in if_dict are selected, select random or rarity variants or set the to Empty depending on the rule.
if result_dict_type == "NOT":
for a in result_dict: # For each Attribute in the NOT rule dictionary
attribute_index = list(hierarchy.keys()).index(a)
attribute = list(hierarchy.keys())[attribute_index]
full_att = list(result_dict[attribute].keys()) == list(
hierarchy[attribute].keys()) # True if full attribute in rules
if if_list_selected:
# If 'a' is a full Attribute and Variants in if_dict selected, set 'a' to empty (0):
if full_att:
deconstructed_dna[attribute_index] = "0"
# Not a full Attribute, invert the variants selected so that we get a list
# of just variants that can be selected. Because the NOT variants are what we don't want selected:
if not full_att:
var_selected_list = list(result_dict[a].keys()) # list of variants from 'NOT'
att_selected_list = list(hierarchy[a].keys()) # full list of variants from hierarchy attribute
# Not a full Attribute, invert the variants selected so that we get a list
# of just variants that can be selected. Because the NOT variants are what we don't want selected:
if not full_att:
var_selected_list = list(result_dict[a].keys()) # list of variants from 'NOT'
att_selected_list = list(hierarchy[a].keys()) # full list of variants from hierarchy attribute
var_selected_list = [i for i in att_selected_list if i not in var_selected_list]
# Invert Variants set in NOT rule:
var_selected_list = [i for i in att_selected_list if i not in var_selected_list]
var_selected_list_complete = {}
for i in var_selected_list:
var_selected_list_complete[i] = get_var_info(i, hierarchy)
result_dict[a] = var_selected_list_complete
var_selected_list_complete = {}
for i in var_selected_list:
var_selected_list_complete[i] = get_var_info(i, hierarchy)
result_dict[a] = var_selected_list_complete
# TODO: Select random or rarity from new result_dict with inverted variants if attribute is not full
variant_list = list(result_dict[a].keys())
deconstructed_dna[int(attribute_index)] = logic_rarity(variant_list, enable_rarity, a)
# Select random or rarity from new result_dict with inverted variants if attribute is not full
variant_list = list(result_dict[a].keys())
deconstructed_dna[int(attribute_index)] = logic_rarity(variant_list, enable_rarity, a)
# If 'a' is a full Attribute and Variants in if_dict selected, set 'a' to empty (0):
if full_att: # Check if Attribute from DNA is in 'result_dict'
deconstructed_dna[attribute_index] = "0"
else: # if result_dict_type == "THEN" basically
for a in result_dict:
attribute_index = list(hierarchy.keys()).index(a)
attribute = list(hierarchy.keys())[attribute_index]
full_att = list(result_dict[attribute].keys()) == list(
hierarchy[attribute].keys()) # True if full attribute in rules
else: # if result_dict_type == "THEN" basically
for a in result_dict:
attribute_index = list(hierarchy.keys()).index(a)
attribute = list(hierarchy.keys())[attribute_index]
variant_list = list(result_dict[a].keys())
variant_list = list(result_dict[a].keys())
# If 'a' is a full Attribute and Variants in if_dict are not selected, set 'a' to empty (0):
# This makes it so Attributes specified in THEN rules will only appear when a given Variant in if_dict is selected.
# if full_att and not if_list_selected:
# deconstructed_dna[attribute_index] = "0"
if attribute in result_dict: # Check if Attribute from DNA is in 'then_dict'
deconstructed_dna[int(attribute_index)] = logic_rarity(variant_list, enable_rarity, a)
# If Variants in if_dict selected, regardless if they make a full variant, select items from result_dict
if if_list_selected:
deconstructed_dna[int(attribute_index)] = logic_rarity(variant_list, enable_rarity, a)
return deconstructed_dna
def get_rule_break_type(hierarchy, deconstructed_dna, if_dict, result_dict, result_dict_type):
"""
Checks if a given rule has been broken by deconstructed_dna.
"""
# Check if Variants in 'if_dict' found in deconstructed_dna:
if_bool = False # True if Variant in 'deconstructed_dna' found in 'if_dict'
for a in if_dict: # Attribute in 'if_dict'
@ -305,7 +319,7 @@ def logicafy_dna_single(hierarchy, single_dna, logic_file, enable_rarity):
if violates_rule:
log.debug(f"======={deconstructed_dna} VIOLATES RULE======")
deconstructed_dna = apply_rules_to_dna(
deconstructed_dna = apply_rule_to_dna(
hierarchy,
deconstructed_dna,
if_dict,
@ -319,7 +333,7 @@ def logicafy_dna_single(hierarchy, single_dna, logic_file, enable_rarity):
original_dna = str(new_dna)
did_reconstruct = True
break
# TODO: This needs to be made more efficient with less repeating code, but it works I guess:
if "NOT" in logic_file[rule]:
result_dict_type = "NOT"
result_dict = create_dicts(hierarchy, logic_file[rule][result_dict_type], result_dict_type)
@ -346,7 +360,7 @@ def logicafy_dna_single(hierarchy, single_dna, logic_file, enable_rarity):
if violates_rule:
log.debug(f"======={deconstructed_dna} VIOLATES RULE======")
deconstructed_dna = apply_rules_to_dna(
deconstructed_dna = apply_rule_to_dna(
hierarchy,
deconstructed_dna,
if_dict,