# This file is part of stable-diffusion-webui (https://github.com/sd-webui/stable-diffusion-webui/). # Copyright 2022 sd-webui team. # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU Affero General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU Affero General Public License for more details. # You should have received a copy of the GNU Affero General Public License # along with this program. If not, see . # base webui import and utils. import collections.abc #from webui_streamlit import st import gfpgan import hydralit as st # streamlit imports from streamlit import StopException, StreamlitAPIException from streamlit.runtime.scriptrunner import script_run_context #streamlit components section from streamlit_server_state import server_state, server_state_lock import hydralit_components as hc from hydralit import HydraHeadApp import streamlit_nested_layout #other imports import warnings import json import base64 import os, sys, re, random, datetime, time, math, glob, toml import gc from PIL import Image, ImageFont, ImageDraw, ImageFilter from PIL.PngImagePlugin import PngInfo from scipy import integrate import torch from torchdiffeq import odeint import k_diffusion as K import math, requests import mimetypes import numpy as np from numpy import asarray import pynvml import threading import torch, torchvision from torch import autocast from torchvision import transforms import torch.nn as nn from omegaconf import OmegaConf import yaml from pathlib import Path from contextlib import nullcontext from einops import rearrange, repeat from ldm.util import instantiate_from_config from retry import retry from slugify import slugify import skimage import piexif import piexif.helper from tqdm import trange from ldm.models.diffusion.ddim import DDIMSampler from ldm.util import ismap from abc import ABC, abstractmethod from typing import Dict, Union from io import BytesIO from packaging import version #import librosa from logger import logger, set_logger_verbosity, quiesce_logger #from loguru import logger # Temp imports #from basicsr.utils.registry import ARCH_REGISTRY # end of imports #--------------------------------------------------------------------------------------------------------------- # we make a log file where we store the logs logger.add("logs/log_{time:MM-DD-YYYY!UTC}.log", rotation="8 MB", compression="zip", level='INFO') # Once the file is too old, it's rotated logger.add(sys.stderr, diagnose=True) logger.add(sys.stdout) logger.enable("") # try: # this silences the annoying "Some weights of the model checkpoint were not used when initializing..." message at start. from transformers import logging logging.set_verbosity_error() except: pass # remove some annoying deprecation warnings that show every now and then. warnings.filterwarnings("ignore", category=DeprecationWarning) warnings.filterwarnings("ignore", category=UserWarning) # this is a fix for Windows users. Without it, javascript files will be served with text/html content-type and the bowser will not show any UI mimetypes.init() mimetypes.add_type('application/javascript', '.js') # some of those options should not be changed at all because they would break the model, so I removed them from options. opt_C = 4 opt_f = 8 def load_configs(): if not "defaults" in st.session_state: st.session_state["defaults"] = {} st.session_state["defaults"] = OmegaConf.load("configs/webui/webui_streamlit.yaml") if (os.path.exists("configs/webui/userconfig_streamlit.yaml")): user_defaults = OmegaConf.load("configs/webui/userconfig_streamlit.yaml") if "version" in user_defaults.general: if version.parse(user_defaults.general.version) < version.parse(st.session_state["defaults"].general.version): logger.error("The version of the user config file is older than the version on the defaults config file. " "This means there were big changes we made on the config." "We are removing this file and recreating it from the defaults in order to make sure things work properly.") os.remove("configs/webui/userconfig_streamlit.yaml") st.experimental_rerun() else: logger.error("The version of the user config file is older than the version on the defaults config file. " "This means there were big changes we made on the config." "We are removing this file and recreating it from the defaults in order to make sure things work properly.") os.remove("configs/webui/userconfig_streamlit.yaml") st.experimental_rerun() try: st.session_state["defaults"] = OmegaConf.merge(st.session_state["defaults"], user_defaults) except KeyError: st.experimental_rerun() else: OmegaConf.save(config=st.session_state.defaults, f="configs/webui/userconfig_streamlit.yaml") loaded = OmegaConf.load("configs/webui/userconfig_streamlit.yaml") assert st.session_state.defaults == loaded if (os.path.exists(".streamlit/config.toml")): st.session_state["streamlit_config"] = toml.load(".streamlit/config.toml") if st.session_state["defaults"].daisi_app.running_on_daisi_io: if os.path.exists("scripts/modeldownload.py"): import modeldownload modeldownload.updateModels() if "keep_all_models_loaded" in st.session_state.defaults.general: with server_state_lock["keep_all_models_loaded"]: server_state["keep_all_models_loaded"] = st.session_state["defaults"].general.keep_all_models_loaded else: st.session_state["defaults"].general.keep_all_models_loaded = False with server_state_lock["keep_all_models_loaded"]: server_state["keep_all_models_loaded"] = st.session_state["defaults"].general.keep_all_models_loaded load_configs() # #if st.session_state["defaults"].debug.enable_hydralit: #navbar_theme = {'txc_inactive': '#FFFFFF','menu_background':'#0e1117','txc_active':'black','option_active':'red'} #app = st.HydraApp(title='Stable Diffusion WebUI', favicon="", use_cookie_cache=False, sidebar_state="expanded", layout="wide", navbar_theme=navbar_theme, #hide_streamlit_markers=False, allow_url_nav=True , clear_cross_app_sessions=False, use_loader=False) #else: #app = None # should and will be moved to a settings menu in the UI at some point grid_format = [s.lower() for s in st.session_state["defaults"].general.grid_format.split(':')] grid_lossless = False grid_quality = 100 if grid_format[0] == 'png': grid_ext = 'png' grid_format = 'png' elif grid_format[0] in ['jpg', 'jpeg']: grid_quality = int(grid_format[1]) if len(grid_format) > 1 else 100 grid_ext = 'jpg' grid_format = 'jpeg' elif grid_format[0] == 'webp': grid_quality = int(grid_format[1]) if len(grid_format) > 1 else 100 grid_ext = 'webp' grid_format = 'webp' if grid_quality < 0: # e.g. webp:-100 for lossless mode grid_lossless = True grid_quality = abs(grid_quality) # should and will be moved to a settings menu in the UI at some point save_format = [s.lower() for s in st.session_state["defaults"].general.save_format.split(':')] save_lossless = False save_quality = 100 if save_format[0] == 'png': save_ext = 'png' save_format = 'png' elif save_format[0] in ['jpg', 'jpeg']: save_quality = int(save_format[1]) if len(save_format) > 1 else 100 save_ext = 'jpg' save_format = 'jpeg' elif save_format[0] == 'webp': save_quality = int(save_format[1]) if len(save_format) > 1 else 100 save_ext = 'webp' save_format = 'webp' if save_quality < 0: # e.g. webp:-100 for lossless mode save_lossless = True save_quality = abs(save_quality) # this should force GFPGAN and RealESRGAN onto the selected gpu as well os.environ["CUDA_DEVICE_ORDER"]="PCI_BUS_ID" # see issue #152 os.environ["CUDA_VISIBLE_DEVICES"] = str(st.session_state["defaults"].general.gpu) # functions to load css locally OR remotely starts here. Options exist for future flexibility. Called as st.markdown with unsafe_allow_html as css injection # TODO, maybe look into async loading the file especially for remote fetching def local_css(file_name): with open(file_name) as f: st.markdown(f'', unsafe_allow_html=True) def remote_css(url): st.markdown(f'', unsafe_allow_html=True) def load_css(isLocal, nameOrURL): if(isLocal): local_css(nameOrURL) else: remote_css(nameOrURL) def set_page_title(title): """ Simple function to allows us to change the title dynamically. Normally you can use `st.set_page_config` to change the title but it can only be used once per app. """ st.sidebar.markdown(unsafe_allow_html=True, body=f"""