Spaces:
Sleeping
Sleeping
File size: 13,645 Bytes
6e887ea 51fc11d 4d02c23 6e887ea 461aeae 51fc11d 461aeae 4d02c23 5838efa 461aeae 4d02c23 461aeae 4d02c23 a9a44ea 461aeae 84b5f6c 461aeae 4d02c23 84b5f6c 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 84b5f6c 461aeae 84b5f6c 461aeae 4d02c23 84b5f6c 4d02c23 84b5f6c 4d02c23 84b5f6c 461aeae 84b5f6c 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae a9a44ea 461aeae 4d02c23 84b5f6c 461aeae 4d02c23 461aeae 4d02c23 9d4c47a 461aeae 5838efa 4d02c23 5838efa 461aeae 5838efa 4d02c23 461aeae 4d02c23 461aeae 6e887ea eb284a9 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 eb284a9 461aeae 4d02c23 eb284a9 461aeae 4d02c23 461aeae eb284a9 5838efa 4d02c23 461aeae 3f1040a 461aeae eb284a9 461aeae 58f4530 461aeae 58f4530 4d02c23 461aeae 4d02c23 461aeae 4d02c23 3f1040a 4d02c23 461aeae 84b5f6c 4d02c23 3f1040a 4d02c23 84b5f6c 461aeae 4d02c23 461aeae eb284a9 461aeae eb284a9 4d02c23 84b5f6c 4d02c23 9d4c47a 461aeae 84b5f6c 9d4c47a 461aeae a9a44ea 3f1040a 4d02c23 5838efa 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 a9a44ea 4d02c23 461aeae a9a44ea 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 84b5f6c a9a44ea 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 9d4c47a 461aeae 4d02c23 461aeae 4d02c23 9d4c47a 4d02c23 461aeae 4d02c23 461aeae 4d02c23 461aeae 4d02c23 9d4c47a 84b5f6c 4d02c23 461aeae 4d02c23 461aeae 2c12be3 461aeae 4d02c23 461aeae 4d02c23 461aeae 6e887ea 461aeae 6e887ea 461aeae |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 |
import gradio as gr
import torch
import time
from transformers import AutoTokenizer, AutoModelForCausalLM, pipeline
print("🚀 ЗАГРУЖАЮ ОПТИМИЗИРОВАННУЮ СИСТЕМУ...")
# ================== ИСПОЛЬЗУЕМ ТОЛЬКО TINYLLAMA ==================
# Она быстрая, уже работает, занимает мало памяти
MODEL_NAME = "TinyLlama/TinyLlama-1.1B-Chat-v1.0"
# Глобальные переменные для кэша
_tokenizer = None
_model = None
_translator = None
def load_system():
"""Загружаем только одну модель - TinyLlama"""
global _tokenizer, _model, _translator
print("📦 Загружаю TinyLlama (самая быстрая для CPU)...")
try:
# Токенизатор
_tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME)
_tokenizer.pad_token = _tokenizer.eos_token
# Модель с оптимизациями для CPU
_model = AutoModelForCausalLM.from_pretrained(
MODEL_NAME,
torch_dtype=torch.float32, # Используем float32 для CPU
device_map="auto",
low_cpu_mem_usage=True,
offload_folder="./offload" # Выгружаем на диск если не хватает RAM
)
print("✅ TinyLlama загружена и оптимизирована для CPU!")
# Переводчик
print("🌐 Загружаю переводчик...")
_translator = pipeline(
"translation_ru_to_en",
model="Helsinki-NLP/opus-mt-ru-en",
device="cpu"
)
print("✅ Переводчик готов!")
return True
except Exception as e:
print(f"❌ Ошибка загрузки: {e}")
return False
# ================== ПРАВИЛЬНЫЕ ПРОМТ-ШАБЛОНЫ ==================
def get_enhancement_prompt(user_input: str) -> str:
"""Создаем ПРАВИЛЬНЫЙ промт для улучшения, а не для рассказа"""
return f"""<|system|>
Ты помощник для создания промтов к AI-генератору изображений Dreamlike Photoreal 2.0.
ТВОЯ ЗАДАЧА: Взять короткое описание и добавить КОНКРЕТНЫЕ детали для фотореалистичной генерации.
ДОБАВЬ:
1. Описание внешности (если есть персонаж)
2. Детали окружения
3. Освещение и время суток
4. Атмосферу и настроение
5. Стиль изображения
НЕ пиши рассказ, НЕ добавляй сюжет. Только описание для генератора изображений.
Примеры правильных улучшений:
• "девушка в лесу" → "Молодая девушка с рыжими волосами в белом платье стоит в магическом лесу на закате, золотые лучи солнца пробиваются сквозь листву, атмосферное освещение, фотореалистично, детализированно"
• "город ночью" → "Футуристический город ночью с неоновыми вывесками, мокрые улицы отражают свет, киберпанк стиль, детализированная архитектура, фотореалистично"</s>
<|user|>
Улучши это описание для генерации фотореалистичного изображения: "{user_input}"</s>
<|assistant|>
Улучшенное описание:"""
# ================== БЫСТРАЯ ГЕНЕРАЦИЯ ==================
def enhance_prompt_fast(user_input: str) -> str:
"""Быстро улучшаем промт с TinyLlama"""
if _model is None or _tokenizer is None:
return user_input + " [система не загружена]"
try:
# Создаем правильный промт
system_prompt = get_enhancement_prompt(user_input)
# Токенизация (ограничиваем длину)
inputs = _tokenizer(
system_prompt,
return_tensors="pt",
max_length=256,
truncation=True,
padding=True
)
# Быстрая генерация с оптимизированными параметрами
with torch.no_grad():
outputs = _model.generate(
**inputs,
max_new_tokens=120, # Не больше 120 новых токенов
temperature=0.8,
do_sample=True,
top_p=0.9,
repetition_penalty=1.1,
pad_token_id=_tokenizer.eos_token_id,
eos_token_id=_tokenizer.eos_token_id,
no_repeat_ngram_size=3 # Избегаем повторений
)
# Декодируем
response = _tokenizer.decode(outputs[0], skip_special_tokens=True)
# Извлекаем только улучшенную часть
if "Улучшенное описание:" in response:
enhanced = response.split("Улучшенное описание:")[-1].strip()
else:
# Fallback: удаляем системный промт
enhanced = response.replace(system_prompt, "").strip()
# Очищаем от метаданных
for marker in ["<|endoftext|>", "</s>", "<|assistant|>", "<|user|>", "<|system|>"]:
enhanced = enhanced.split(marker)[0].strip()
# Если результат слишком короткий, добавляем базовые улучшения
if len(enhanced.split()) < 5:
enhanced = f"{user_input}, фотореалистично, высокое качество, детализированно, красивое освещение"
return enhanced[:400] # Ограничиваем длину
except Exception as e:
print(f"Ошибка генерации: {e}")
return f"{user_input}, фотореалистично, высокое качество, детализированно"
def generate_negative_prompt_smart(english_prompt: str) -> str:
"""Умный негативный промт"""
base = [
"blurry", "ugly", "deformed", "bad anatomy",
"bad proportions", "extra limbs", "mutated hands",
"poorly drawn hands", "text", "watermark", "signature",
"worst quality", "low quality", "jpeg artifacts"
]
prompt_lower = english_prompt.lower()
# Добавляем контекстные исключения
if any(word in prompt_lower for word in ["realistic", "photoreal", "photo"]):
base.extend(["cartoon", "anime", "painting", "drawing", "illustration", "3d render"])
if any(word in prompt_lower for word in ["bright", "light", "sun"]):
base.extend(["dark", "dull", "underexposed", "gloomy"])
if any(word in prompt_lower for word in ["portrait", "face", "person"]):
base.extend(["asymmetric eyes", "cloned face", "malformed limbs"])
# Убираем дубликаты
unique = []
for term in base:
if term not in unique:
unique.append(term)
return ", ".join(unique)
def process_pipeline(user_input: str):
"""Полный пайплайн обработки"""
start_time = time.time()
if not user_input.strip():
return "Введите промт", "", "", "⏳ Введите промт"
print(f"⚡ Обработка: {user_input}")
# 1. Улучшаем промт (максимум 5 секунд)
gen_start = time.time()
enhanced_ru = enhance_prompt_fast(user_input)
gen_time = time.time() - gen_start
# 2. Переводим
trans_start = time.time()
try:
if _translator:
translated = _translator(enhanced_ru[:300])[0]['translation_text']
else:
translated = enhanced_ru
except:
translated = enhanced_ru
trans_time = time.time() - trans_start
# 3. Улучшаем английский для Dreamlike
dreamlike_keywords = ", photorealistic, high quality, detailed, 8K, professional photography"
if "photorealistic" not in translated.lower():
translated += dreamlike_keywords
# 4. Негативный промт
negative_start = time.time()
negative_en = generate_negative_prompt_smart(translated)
negative_time = time.time() - negative_start
# 5. Статистика
total_time = time.time() - start_time
info = f"""
⚡ БЫСТРАЯ ОБРАБОТКА:
• Генерация: {gen_time:.1f} сек
• Перевод: {trans_time:.1f} сек
• Негативный промт: {negative_time:.1f} сек
• Всего: {total_time:.1f} сек
📊 СТАТИСТИКА:
• Модель: TinyLlama-1.1B (оптимизирована для CPU)
• Длина промта: {len(translated.split())} слов
• Статус: ✅ Готово к использованию в Dreamlike
"""
return enhanced_ru, translated, negative_en, info.strip()
# ================== ПРОСТОЙ ИНТЕРФЕЙС ==================
with gr.Blocks(title="AI Улучшитель промтов для Dreamlike", theme=gr.themes.Soft()) as demo:
# Заголовок
gr.Markdown("""
# 🚀 УЛЬТРА-БЫСТРЫЙ AI УЛУЧШИТЕЛЬ ПРОМТОВ
### Оптимизирован для CPU • TinyLlama • Мгновенная обработка
""")
# Статус загрузки
status = gr.Textbox(
label="🔄 Статус системы",
value="Загружаю систему...",
interactive=False
)
# Основной интерфейс
with gr.Column(visible=False) as main_ui:
# Ввод
input_prompt = gr.Textbox(
label="🎯 Введите промт на русском",
placeholder="Пример: девушка в магическом лесу на закате",
lines=2
)
# Кнопка
process_btn = gr.Button("⚡ УЛУЧШИТЬ ПРОМТ", variant="primary", size="lg")
# Результаты
gr.Markdown("### 📝 УЛУЧШЕННЫЙ ПРОМТ (русский)")
output_ru = gr.Textbox(
label="",
lines=3,
interactive=True
)
gr.Markdown("### 🌐 ДЛЯ DREAMLIKE (английский)")
with gr.Row():
output_en = gr.Textbox(
label="🎨 Основной промт",
lines=3,
interactive=True
)
output_neg = gr.Textbox(
label="🚫 Negative Prompt",
lines=3,
interactive=True
)
# Информация
output_info = gr.Textbox(
label="📊 СТАТИСТИКА",
lines=4,
interactive=False
)
# Примеры
gr.Markdown("### 🧪 БЫСТРЫЕ ПРИМЕРЫ")
examples = gr.Examples(
examples=[
["девушка в магическом лесу на закате"],
["киберпанк улица ночью с неоновыми вывесками"],
["космонавт играет на гитаре на луне"],
["кошка в шляпе читает газету в кафе"],
["дракон на вершине горы"]
],
inputs=[input_prompt],
outputs=[output_ru, output_en, output_neg, output_info],
fn=process_pipeline,
label="Кликните для теста:"
)
# Обработчики
def process_and_update(prompt):
return process_pipeline(prompt)
process_btn.click(
fn=process_and_update,
inputs=[input_prompt],
outputs=[output_ru, output_en, output_neg, output_info]
)
input_prompt.submit(
fn=process_and_update,
inputs=[input_prompt],
outputs=[output_ru, output_en, output_neg, output_info]
)
# Функция инициализации
def initialize_system():
if load_system():
return "✅ СИСТЕМА ГОТОВА! TinyLlama загружена и оптимизирована.\n⚡ Введите промт и нажмите кнопку.", gr.update(visible=True)
else:
return "❌ Ошибка загрузки. Попробуйте перезапустить Space.", gr.update(visible=False)
# Загружаем при старте
demo.load(
fn=initialize_system,
outputs=[status, main_ui]
)
# ================== ЗАПУСК ==================
if __name__ == "__main__":
demo.launch(
server_name="0.0.0.0",
server_port=7860
) |