vernova/resources/views/projects/show.blade.php
2026-07-26 19:58:27 +03:30

209 lines
12 KiB
PHP

@extends('layouts.app')
@section('content')
<div class="space-y-6">
<!-- Page Header -->
<div class="flex flex-col sm:flex-row sm:items-center sm:justify-between gap-4">
<div class="flex items-center gap-3">
<a href="{{ route('projects.index') }}" class="p-2 text-gray-500 hover:text-gray-900 hover:bg-gray-100 rounded-lg transition-colors">
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M10 19l-7-7m0 0l7-7m-7 7h18"/></svg>
</a>
<div>
<h1 class="text-2xl font-bold text-gray-900">{{ $project->name }}</h1>
<p class="text-sm text-gray-500">{{ $project->code }}</p>
</div>
</div>
<div class="flex items-center gap-2">
<a href="{{ route('projects.edit', $project) }}" class="px-4 py-2 text-sm font-medium text-gray-700 bg-white border border-gray-300 rounded-lg hover:bg-gray-50 transition-colors">
{{ __('common.edit') }}
</a>
<form method="POST" action="{{ route('projects.destroy', $project) }}" class="inline" onsubmit="return confirm('{{ __('common.confirm_delete') }}')">
@csrf @method('DELETE')
<button type="submit" class="px-4 py-2 text-sm font-medium text-red-700 bg-red-50 border border-red-200 rounded-lg hover:bg-red-100 transition-colors">
{{ __('common.delete') }}
</button>
</form>
</div>
</div>
<!-- Project Info Grid -->
<div class="grid grid-cols-1 lg:grid-cols-3 gap-6">
<!-- Main Info -->
<div class="lg:col-span-2 space-y-6">
<!-- Info Card -->
<div class="bg-white rounded-xl border border-gray-200 p-6">
<div class="grid grid-cols-2 md:grid-cols-4 gap-4">
<div>
<p class="text-xs text-gray-500">{{ __('project.status') }}</p>
<span class="inline-flex items-center px-2 py-0.5 rounded-full text-xs font-medium mt-1
{{ $project->status === 'active' ? 'bg-emerald-50 text-emerald-700' :
($project->status === 'planning' ? 'bg-blue-50 text-blue-700' :
($project->status === 'on_hold' ? 'bg-amber-50 text-amber-700' :
($project->status === 'completed' ? 'bg-gray-50 text-gray-700' : 'bg-red-50 text-red-700'))) }}">
{{ $project->status_label }}
</span>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.budget') }}</p>
<p class="text-sm font-medium text-gray-900 mt-1">{{ format_currency((float)$project->budget) }}</p>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.manager') }}</p>
<p class="text-sm font-medium text-gray-900 mt-1">{{ $project->manager?->name ?? '-' }}</p>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.progress') }}</p>
<div class="mt-1">
<div class="flex items-center gap-2">
<div class="flex-1 bg-gray-100 rounded-full h-2">
<div class="h-2 rounded-full bg-teal-500" style="width: {{ $project->progress }}%"></div>
</div>
<span class="text-xs font-medium">{{ $project->progress }}%</span>
</div>
</div>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.start_date') }}</p>
<p class="text-sm text-gray-900 mt-1">{{ $project->start_date ? calendar_date($project->start_date) : '-' }}</p>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.end_date') }}</p>
<p class="text-sm text-gray-900 mt-1">{{ $project->end_date ? calendar_date($project->end_date) : '-' }}</p>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.location') }}</p>
<p class="text-sm text-gray-900 mt-1">{{ $project->location ?? '-' }}</p>
</div>
<div>
<p class="text-xs text-gray-500">{{ __('project.currency') }}</p>
<p class="text-sm text-gray-900 mt-1">{{ $project->defaultCurrency?->code ?? '-' }}</p>
</div>
</div>
@if($project->description)
<div class="mt-4 pt-4 border-t border-gray-100">
<p class="text-xs text-gray-500 mb-1">{{ __('project.description') }}</p>
<p class="text-sm text-gray-700">{{ $project->description }}</p>
</div>
@endif
</div>
@php
$projectEmployees = $project->tasks->pluck('assignee')->filter()->unique('id');
@endphp
<!-- Alpine Tabs: Tasks / Expenses / Employees -->
<div x-data="{ activeTab: 'tasks' }" class="bg-white rounded-xl border border-gray-200">
<div class="border-b border-gray-200">
<nav class="flex -mb-px">
<button @click="activeTab = 'tasks'" :class="activeTab === 'tasks' ? 'border-teal-500 text-teal-600' : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'" class="px-5 py-3 text-sm font-medium border-b-2 transition-colors">
{{ __('task.tasks') }} ({{ $taskStats['total'] }})
</button>
<button @click="activeTab = 'expenses'" :class="activeTab === 'expenses' ? 'border-teal-500 text-teal-600' : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'" class="px-5 py-3 text-sm font-medium border-b-2 transition-colors">
{{ __('expense.expenses') }}
</button>
<button @click="activeTab = 'employees'" :class="activeTab === 'employees' ? 'border-teal-500 text-teal-600' : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'" class="px-5 py-3 text-sm font-medium border-b-2 transition-colors">
{{ __('employee.employees') }}
</button>
</nav>
</div>
<div class="p-5">
<!-- Tasks Tab -->
<div x-show="activeTab === 'tasks'" class="space-y-2">
@forelse($project->tasks as $task)
<div class="flex items-center gap-3 p-3 rounded-lg hover:bg-gray-50 border border-gray-100">
<x-priority-badge :priority="$task->priority" />
<a href="{{ route('tasks.show', $task) }}" class="flex-1 text-sm font-medium text-gray-900 hover:text-teal-600 truncate">{{ $task->title }}</a>
<span class="text-xs px-2 py-0.5 rounded-full
{{ $task->status === 'done' ? 'bg-emerald-50 text-emerald-700' :
($task->status === 'in_progress' ? 'bg-blue-50 text-blue-700' :
($task->status === 'review' ? 'bg-amber-50 text-amber-700' : 'bg-gray-50 text-gray-700')) }}">
{{ $task->status_label }}
</span>
</div>
@empty
<p class="text-sm text-gray-500 text-center py-4">{{ __('task.no_tasks') }}</p>
@endforelse
</div>
<!-- Expenses Tab -->
<div x-show="activeTab === 'expenses'" class="space-y-2">
@forelse($project->expenses as $expense)
<div class="flex items-center gap-3 p-3 rounded-lg border border-gray-100">
<span class="text-sm font-medium text-gray-900 flex-1">{{ $expense->title }}</span>
<span class="text-sm text-gray-600">{{ format_currency((float)$expense->amount, $expense->currency?->code) }}</span>
<span class="text-xs px-2 py-0.5 rounded-full {{ $expense->status === 'approved' ? 'bg-emerald-50 text-emerald-700' : 'bg-amber-50 text-amber-700' }}">{{ $expense->status_label }}</span>
</div>
@empty
<p class="text-sm text-gray-500 text-center py-4">{{ __('expense.no_expenses') }}</p>
@endforelse
</div>
<!-- Employees Tab -->
<div x-show="activeTab === 'employees'" class="space-y-2">
@forelse($projectEmployees as $employee)
<a href="{{ route('employees.show', $employee) }}" class="flex items-center gap-3 p-3 rounded-lg hover:bg-gray-50 border border-gray-100">
<div class="w-8 h-8 bg-teal-50 text-teal-700 rounded-full flex items-center justify-center text-xs font-semibold">
{{ mb_strtoupper(mb_substr($employee->full_name, 0, 1)) }}
</div>
<div class="flex-1">
<p class="text-sm font-medium text-gray-900">{{ $employee->full_name }}</p>
<p class="text-xs text-gray-500">{{ $employee->position ?? $employee->contract_type_label }}</p>
</div>
</a>
@empty
<p class="text-sm text-gray-500 text-center py-4">{{ __('employee.no_employees') }}</p>
@endforelse
</div>
</div>
</div>
</div>
<!-- Sidebar Stats -->
<div class="space-y-6">
<!-- Task Stats -->
<div class="bg-white rounded-xl border border-gray-200 p-5">
<h3 class="text-sm font-semibold text-gray-900 mb-3">{{ __('project.task_overview') }}</h3>
<div class="space-y-2">
<div class="flex items-center justify-between text-sm">
<span class="text-gray-500">{{ __('task.status_pending') }}</span>
<span class="font-medium">{{ $taskStats['pending'] }}</span>
</div>
<div class="flex items-center justify-between text-sm">
<span class="text-gray-500">{{ __('task.status_in_progress') }}</span>
<span class="font-medium">{{ $taskStats['in_progress'] }}</span>
</div>
<div class="flex items-center justify-between text-sm">
<span class="text-gray-500">{{ __('task.status_review') }}</span>
<span class="font-medium">{{ $taskStats['review'] }}</span>
</div>
<div class="flex items-center justify-between text-sm">
<span class="text-gray-500">{{ __('task.status_done') }}</span>
<span class="font-medium">{{ $taskStats['done'] }}</span>
</div>
</div>
</div>
<!-- Team Members -->
<div class="bg-white rounded-xl border border-gray-200 p-5">
<h3 class="text-sm font-semibold text-gray-900 mb-3">{{ __('project.team') }}</h3>
<div class="space-y-2">
@forelse($project->users as $member)
<div class="flex items-center gap-2">
<div class="w-7 h-7 bg-gray-100 rounded-full flex items-center justify-center text-xs font-medium text-gray-600">
{{ mb_strtoupper(mb_substr($member->name, 0, 1)) }}
</div>
<span class="text-sm text-gray-700">{{ $member->name }}</span>
</div>
@empty
<p class="text-sm text-gray-500">{{ __('project.no_team_members') }}</p>
@endforelse
</div>
</div>
</div>
</div>
</div>
@endsection