Skip to content

Blender addon

Blender addons can be enabled in File/Preferences, add-ons tab.

Blender addons require bl_info.
they only show in the addon manager if they are in the addon folder.
in the site package folder they are just normal py modules.

see Blender extensions

some helper functions regarding addons

import bpy  
import addon_utils  
from pathlib import Path  
import shutil  
import logging  


def is_installed(name):  
    """check if plugin is installed, use plugin_name from manifest, checking folder name in addons"""  
    local_script_dir = bpy.utils.script_path_user()  
    local_addons_dir = Path(local_script_dir) / "addons"  
    return (local_addons_dir / name).exists()  


def installed_plugins():  
    """return list of installed plugins"""  
    # Blender names returned are from the operator, but plugin_name in the manifest refers to the blender folder name  
    # todo ideally we return a name thats useable in the pluggest install commands  
    return [mod.bl_info.get("name") for mod in addon_utils.modules()]  


def enabled_plugins() -> list[str]:  
    """return list of enabled plugins"""  
    # Blender names returned are from the operator, but plugin_name in the manifest refers to the blender folder name  
    # todo ideally we return a name thats useable in the pluggest install commands  
    return bpy.context.preferences.addons.keys()  


def disabled_plugins() -> list[str]:  
    """return list of disabled plugins"""  
    # Blender names returned are from the operator, but plugin_name in the manifest refers to the blender folder name  
    # todo ideally we return a name thats useable in the pluggest install commands  
    return [p for p in installed_plugins() if p not in enabled_plugins()]  


def disable_plugin(name):  
    """disable plugin by name"""  
    bpy.ops.preferences.addon_disable(module=name)  


def enable_plugin(name):  
    """enable plugin by name"""  
    bpy.ops.preferences.addon_enable(module=name)  


def install_plugin(plugin_paths: list[Path]) -> bool:  # todo , force=False, enable=True):  
    """install plugin from path"""  
    # If the “overwrite” parameter is True, the add-on will be reinstalled, even if it has not been previously removed.  

    # manifest is named io_xray    # but subdir is io_scene_xray    # resulting in clashes. we cant just rename the subdir, might break code inside.    # so we need to track the "name" with plugin_name in the manifest  
    # todo fix only support 1 plugin  
    plugin_path = plugin_paths[0]  
    if len(plugin_paths) > 1:  
        raise NotImplemented("Only 1 plugin can be installed at a time for now")  

    local_script_dir = bpy.utils.script_path_user()  
    local_addons_dir = Path(local_script_dir) / "addons"  
    new_plugin_path = local_addons_dir / plugin_path.name  
    shutil.move(str(plugin_path), str(new_plugin_path.parent))  # copy plugin_path to local_addons_dir  

    # check if plugin folder was copied, by checking if any files are in new_plugin_path    if not any(new_plugin_path.iterdir()):  
        logging.warning(f"Failed to install plugin {plugin_path.name}")  
        return False  
    else:  
        return True  


def uninstall_plugin(name):  
    """uninstall plugin by name"""  
    if not name:  
        logging.warning("No plugin name given")  
        return  
    bpy.ops.preferences.addon_remove(module=name)  


def open_install_dir():  
    """Open the directory where plugins are installed"""  
    local_script_dir = bpy.utils.script_path_user()  
    local_addons_dir = Path(local_script_dir) / "addons"  
    bpy.ops.wm.path_open(filepath=str(local_addons_dir))

Blender Python