Files
web_work/app/Core/View.php
kirill.khorkov d2c15ec37f [MVC] Полная миграция на MVC архитектуру
- Создано ядро MVC: App, Router, Controller, Model, View, Database
- Созданы модели: User, Product, Category, Cart, Order
- Созданы контроллеры: Home, Auth, Product, Cart, Order, Page, Admin
- Созданы layouts и partials для представлений
- Добавлены все views для страниц
- Настроена маршрутизация с чистыми URL
- Обновлена конфигурация Docker и Apache для mod_rewrite
- Добавлена единая точка входа public/index.php
2026-01-03 11:48:14 +03:00

185 lines
4.9 KiB
PHP

<?php
namespace App\Core;
/**
* View - класс для рендеринга представлений
*/
class View
{
private static string $viewsPath = '';
/**
* Установить путь к директории представлений
*/
public static function setViewsPath(string $path): void
{
self::$viewsPath = rtrim($path, '/');
}
/**
* Получить путь к директории представлений
*/
public static function getViewsPath(): string
{
if (empty(self::$viewsPath)) {
self::$viewsPath = dirname(__DIR__) . '/Views';
}
return self::$viewsPath;
}
/**
* Отрендерить представление
*/
public static function render(string $view, array $data = [], ?string $layout = 'main'): string
{
$viewPath = self::getViewsPath() . '/' . str_replace('.', '/', $view) . '.php';
if (!file_exists($viewPath)) {
throw new \Exception("Представление не найдено: {$viewPath}");
}
// Извлекаем данные в переменные
extract($data);
// Буферизируем вывод контента
ob_start();
require $viewPath;
$content = ob_get_clean();
// Если есть layout, оборачиваем контент
if ($layout !== null) {
$layoutPath = self::getViewsPath() . '/layouts/' . $layout . '.php';
if (!file_exists($layoutPath)) {
throw new \Exception("Layout не найден: {$layoutPath}");
}
ob_start();
require $layoutPath;
$content = ob_get_clean();
}
return $content;
}
/**
* Отрендерить partial (часть шаблона)
*/
public static function partial(string $partial, array $data = []): string
{
$partialPath = self::getViewsPath() . '/partials/' . $partial . '.php';
if (!file_exists($partialPath)) {
throw new \Exception("Partial не найден: {$partialPath}");
}
extract($data);
ob_start();
require $partialPath;
return ob_get_clean();
}
/**
* Экранирование HTML
*/
public static function escape(string $value): string
{
return htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
}
/**
* Сокращенный алиас для escape
*/
public static function e(string $value): string
{
return self::escape($value);
}
/**
* Форматирование цены
*/
public static function formatPrice($price): string
{
return number_format((float)$price, 0, '', ' ') . ' ₽';
}
/**
* Форматирование даты
*/
public static function formatDate(string $date, string $format = 'd.m.Y'): string
{
return date($format, strtotime($date));
}
/**
* Форматирование даты и времени
*/
public static function formatDateTime(string $date, string $format = 'd.m.Y H:i'): string
{
return date($format, strtotime($date));
}
/**
* Получить flash-сообщения
*/
public static function getFlashMessages(): array
{
$messages = $_SESSION['flash'] ?? [];
unset($_SESSION['flash']);
return $messages;
}
/**
* Проверить, авторизован ли пользователь
*/
public static function isAuthenticated(): bool
{
return isset($_SESSION['isLoggedIn']) && $_SESSION['isLoggedIn'] === true;
}
/**
* Проверить, является ли пользователь администратором
*/
public static function isAdmin(): bool
{
return self::isAuthenticated() && isset($_SESSION['isAdmin']) && $_SESSION['isAdmin'] === true;
}
/**
* Получить данные текущего пользователя
*/
public static function currentUser(): ?array
{
if (!self::isAuthenticated()) {
return null;
}
return [
'id' => $_SESSION['user_id'] ?? null,
'email' => $_SESSION['user_email'] ?? '',
'full_name' => $_SESSION['full_name'] ?? '',
'is_admin' => $_SESSION['isAdmin'] ?? false,
'login_time' => $_SESSION['login_time'] ?? null
];
}
/**
* Генерация URL
*/
public static function url(string $path): string
{
return '/' . ltrim($path, '/');
}
/**
* Генерация URL для ассетов
*/
public static function asset(string $path): string
{
return '/assets/' . ltrim($path, '/');
}
}