From 3833764438919ddd2f431502dfc48c42ef999a77 Mon Sep 17 00:00:00 2001 From: Jessica_Faro Date: Fri, 10 Oct 2025 15:36:32 -0300 Subject: [PATCH] loginperfil1 --- src/App.js | 5 +- src/components/Header/Header.css | 107 +++++++++++++++ src/components/Header/Header.jsx | 60 +++++++++ src/pages/ProfilePage.jsx | 206 +++++++++++++++++++++++++++++ src/pages/Support.jsx | 10 ++ src/pages/style/ProfilePage.css | 0 src/pages/style/TrocardePerfil.css | 62 --------- 7 files changed, 387 insertions(+), 63 deletions(-) create mode 100644 src/components/Header/Header.css create mode 100644 src/components/Header/Header.jsx create mode 100644 src/pages/ProfilePage.jsx create mode 100644 src/pages/Support.jsx create mode 100644 src/pages/style/ProfilePage.css delete mode 100644 src/pages/style/TrocardePerfil.css diff --git a/src/App.js b/src/App.js index 13120035..1352f0e1 100644 --- a/src/App.js +++ b/src/App.js @@ -9,6 +9,8 @@ import LandingPage from './pages/LandingPage'; import PerfilFinanceiro from "./perfis/perfil_financeiro/PerfilFinanceiro"; import Perfiladm from "./perfis/Perfil_adm/Perfiladm"; import PerfilMedico from "./perfis/Perfil_medico/PerfilMedico"; +import ProfilePage from "./pages/ProfilePage"; +import Header from "./components/Header/Header"; // Componentes globais de acessibilidade import VlibrasWidget from "./components/VlibrasWidget"; @@ -20,6 +22,7 @@ function App() { +
} /> @@ -30,6 +33,7 @@ function App() { } /> } /> } /> + } /> Página não encontrada} /> @@ -37,4 +41,3 @@ function App() { } export default App; - diff --git a/src/components/Header/Header.css b/src/components/Header/Header.css new file mode 100644 index 00000000..dd15ca08 --- /dev/null +++ b/src/components/Header/Header.css @@ -0,0 +1,107 @@ +/* src/components/Header/Header.css */ +.header-container { + width: 100%; + position: absolute; /* Permite posicionamento livre sobre o conteúdo */ + top: 0; + left: 0; + display: flex; + justify-content: flex-end; /* Alinha os elementos do container à direita */ + padding: 10px 20px; + box-sizing: border-box; + z-index: 1000; /* Garante que fique acima de outros elementos */ +} + +.right-corner-elements { + display: flex; + align-items: center; + gap: 20px; /* Espaço entre o telefone e a seção de perfil */ +} + +/* --- ÍCONE DE TELEFONE --- */ +.phone-icon-container { + font-size: 24px; + cursor: pointer; + padding: 5px; /* Área clicável um pouco maior */ +} +.phone-icon { + display: block; /* Garante que o emoji fique bem centralizado */ +} + +/* --- SEÇÃO DE PERFIL --- */ +.profile-section { + position: relative; + display: flex; + align-items: center; +} + +.profile-picture-container { + width: 40px; + height: 40px; + border-radius: 50%; /* Círculo */ + overflow: hidden; + cursor: pointer; + border: 2px solid #ccc; /* Borda simples */ + box-shadow: 0 0 5px rgba(0, 0, 0, 0.2); +} + +.profile-placeholder { + width: 100%; + height: 100%; + background-color: #A9A9A9; /* Cor cinza escura para o fundo */ + border-radius: 50%; + /* Adicionando um ícone simples de pessoa em branco para simular o ícone */ + position: relative; +} + +.profile-placeholder::after { + content: ''; + position: absolute; + top: 50%; + left: 50%; + transform: translate(-50%, -50%); + width: 60%; + height: 60%; + background-image: url('data:image/svg+xml;utf8,'); + background-size: contain; + background-repeat: no-repeat; + opacity: 0.8; /* Suaviza um pouco o ícone */ +} + +/* --- DROPDOWN (MENU) --- */ +.profile-dropdown { + position: absolute; + top: 50px; /* Posição abaixo da foto de perfil (40px + 10px de espaço) */ + right: 0; + background-color: white; + border: 1px solid #ddd; + border-radius: 5px; + box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15); + display: flex; + flex-direction: column; + z-index: 10; + min-width: 150px; + overflow: hidden; /* Garante que bordas fiquem visíveis */ +} + +.dropdown-button { + background: none; + border: none; + padding: 10px 15px; + text-align: left; + cursor: pointer; + font-size: 14px; + color: #333; + transition: background-color 0.2s; +} + +.dropdown-button:hover { + background-color: #f0f0f0; +} + +.logout-button { + color: #cc0000; /* Cor vermelha para o botão de logout */ +} + +.logout-button:hover { + background-color: #ffe0e0; +} \ No newline at end of file diff --git a/src/components/Header/Header.jsx b/src/components/Header/Header.jsx new file mode 100644 index 00000000..533c1a27 --- /dev/null +++ b/src/components/Header/Header.jsx @@ -0,0 +1,60 @@ +// src/components/Header/Header.jsx +import React, { useState } from 'react'; +import { useNavigate } from 'react-router-dom'; +import './Header.css'; + +const Header = () => { + const [isDropdownOpen, setIsDropdownOpen] = useState(false); + const navigate = useNavigate(); + + const handleProfileClick = () => { + setIsDropdownOpen(!isDropdownOpen); + }; + + const handleViewProfile = () => { + // Redireciona para uma página de perfil (Rota que adicionaremos no App.js) + navigate('/perfil'); + setIsDropdownOpen(false); + }; + + const handleLogout = () => { + // Ação de Logout: Exibe um alerta e redireciona para a tela de Login + alert('Você foi desconectado. Executando ação de logout...'); + setIsDropdownOpen(false); + navigate('/login'); + }; + + const handleSupportClick = () => { + // Funcionalidade de suporte (futuramente implementada em TelefoneSuporte) + alert('Função de Suporte de Telefone em desenvolvimento.'); + }; + + return ( +
+
+ + {/* Ícone de Telefone */} +
+ 📞 +
+ + {/* Seção de Perfil com Dropdown */} +
+
+ {/* O div "profile-placeholder" simula a foto de perfil circular colorida */} +
+
+ + {isDropdownOpen && ( +
+ + +
+ )} +
+
+
+ ); +}; + +export default Header; \ No newline at end of file diff --git a/src/pages/ProfilePage.jsx b/src/pages/ProfilePage.jsx new file mode 100644 index 00000000..ef09ef14 --- /dev/null +++ b/src/pages/ProfilePage.jsx @@ -0,0 +1,206 @@ +// src/pages/ProfilePage.jsx +import React, { useState } from 'react'; +import { useLocation, useNavigate } from 'react-router-dom'; +// import { useAuth } from '../components/utils/AuthProvider'; // <-- NOVO: Se você puder importar isso. + +// --- SIMULAÇÃO DE DADOS DE USUÁRIO --- +// COMO NÃO PODEMOS IMPORTAR O useAuth SEM MEXER EM OUTROS ARQUIVOS, VAMOS USAR ESTA SIMULAÇÃO: +const simulatedUserData = { + // ESTA SIMULAÇÃO DEVERIA SER SUBTITUÍDA PELO SEU CONTEXTO DE AUTENTICAÇÃO REAL. + // O EMAIL REALMENTE LOGADO VEM DO CONTEXTO DE AUTENTICAÇÃO (useAuth) + email: 'admin@squad23.com', + role: 'Administrador' // Vamos forçar um valor para fins de visualização +}; + +const ProfilePage = () => { + const location = useLocation(); + const navigate = useNavigate(); + // const { user } = useAuth(); // Descomente esta linha e comente o bloco simulatedUserData se puder usar o useAuth! + + // --- Lógica de Cargo (AGORA CORRIGIDA PARA PEGAR DA URL SE O CONTEXTO FALHAR) --- + const getRoleFromPath = () => { + const path = location.pathname; + if (path.includes('/admin')) return 'Administrador'; + if (path.includes('/secretaria')) return 'Secretária'; + if (path.includes('/medico')) return 'Médico'; + if (path.includes('/financeiro')) return 'Financeiro'; + return 'Usuário Padrão'; + }; + + // Use a simulação ou o dado real: + const userRole = simulatedUserData.role || getRoleFromPath(); + const userEmail = simulatedUserData.email || 'email.nao.encontrado@mediconnect.com'; + + // --- Estados do Componente --- + + // Se o nome do usuário vier do contexto de autenticação, use-o aqui + const [userName, setUserName] = useState('Admin Padrão'); + const [isEditingName, setIsEditingName] = useState(false); + + // --- Funções de Interação --- + + const handleNameChange = (e) => { + if (e.key === 'Enter') { + setIsEditingName(false); + } + }; + + const handleClose = () => { + navigate(-1); // Volta para a página anterior + }; + + return ( +
+
+ + {/* Botão de Fechar (X) */} + + + {/* 1. Área da Foto de Perfil (Quadrada) */} +
+
+
+ +
+ + {/* 2. Nome do Usuário com Edição */} +
+ {isEditingName ? ( + setUserName(e.target.value)} + onBlur={() => setIsEditingName(false)} + onKeyPress={handleNameChange} + autoFocus + style={styles.nameInput} + /> + ) : ( +

{userName}

+ )} + + +
+ + {/* 3. Email (AGORA EXIBE O VALOR SIMULADO/CORRIGIDO) */} +

Email: {userEmail}

+ + {/* 4. Cargo (AGORA EXIBE O VALOR SIMULADO/CORRIGIDO) */} +

Cargo: {userRole}

+
+
+
+ ); +}; + +// Estilos Atualizados para Aumentar o Tamanho do Modal +const styles = { + overlay: { + position: 'fixed', + top: 0, + left: 0, + right: 0, + bottom: 0, + backgroundColor: 'rgba(0, 0, 0, 0.5)', + display: 'flex', + justifyContent: 'center', + alignItems: 'center', + zIndex: 1100, + }, + modalContainer: { + position: 'relative', + padding: '50px 70px', // Aumentado o padding + backgroundColor: 'white', + borderRadius: '15px', + boxShadow: '0 8px 30px rgba(0, 0, 0, 0.3)', + display: 'flex', + flexDirection: 'column', + alignItems: 'center', + minWidth: '400px', + width: '60%', // Aumentando a largura para cobrir mais a tela + maxWidth: '500px', // Limite máximo para não ficar gigante em telas grandes + height: 'auto', + }, + closeButton: { + position: 'absolute', + top: '15px', + right: '20px', + background: 'none', + border: 'none', + fontSize: '30px', + cursor: 'pointer', + color: '#666', + lineHeight: '1', + }, + // ... (Os estilos de profilePictureContainer, infoContainer, etc., permanecem iguais) + profilePictureContainer: { + width: '120px', + height: '120px', + borderRadius: '15px', + overflow: 'hidden', + boxShadow: '0 4px 10px rgba(0, 0, 0, 0.15)', + marginBottom: '20px', + }, + profilePicturePlaceholder: { + width: '100%', + height: '100%', + backgroundColor: '#A9A9A9', + backgroundImage: 'url(\'data:image/svg+xml;utf8,\')', + backgroundSize: '80%', + backgroundRepeat: 'no-repeat', + backgroundPosition: 'center', + }, + infoContainer: { + textAlign: 'center', + maxWidth: '400px', + width: '100%', + }, + nameSection: { + display: 'flex', + alignItems: 'center', + justifyContent: 'center', + marginBottom: '10px', + }, + userName: { + margin: '0 5px 0 0', + fontSize: '1.8rem', + color: '#333', + }, + nameInput: { + fontSize: '1.8rem', + padding: '5px', + border: '1px solid #ccc', + borderRadius: '5px', + textAlign: 'center', + marginRight: '5px', + }, + editButton: { + background: 'none', + border: 'none', + cursor: 'pointer', + fontSize: '1.2rem', + marginLeft: '5px', + }, + emailText: { + fontSize: '1rem', + color: '#666', + margin: '5px 0', + }, + roleText: { + fontSize: '1.1rem', + color: '#333', + marginTop: '15px', + paddingTop: '10px', + borderTop: '1px solid #eee', + } +}; + +export default ProfilePage; \ No newline at end of file diff --git a/src/pages/Support.jsx b/src/pages/Support.jsx new file mode 100644 index 00000000..008b4c11 --- /dev/null +++ b/src/pages/Support.jsx @@ -0,0 +1,10 @@ +import React from "react"; + +export default function Support() { + return ( +
+

Suporte por telefone

+

Funcionalidade de chamada/suporte será implementada em breve.

+
+ ); +} diff --git a/src/pages/style/ProfilePage.css b/src/pages/style/ProfilePage.css new file mode 100644 index 00000000..e69de29b diff --git a/src/pages/style/TrocardePerfil.css b/src/pages/style/TrocardePerfil.css deleted file mode 100644 index 3a253c29..00000000 --- a/src/pages/style/TrocardePerfil.css +++ /dev/null @@ -1,62 +0,0 @@ -.container-perfis { - position: absolute; - top: 80px; - left: 30px; - width: calc(100% - 60px); - display: flex; - flex-direction: column; - align-items: flex-start; - z-index: 60; -} - -.acesso-text { - font-size: 15px; - font-weight: 600; - color: #1e2b57; - margin-bottom: 6px; -} - -/* estilo visual refinado do select */ -.perfil-select { - width: 100%; - padding: 10px 14px; - border-radius: 10px; - border: 1.8px solid #d0d5dd; - background-color: #f9fafc; - color: #1e2b57; - font-weight: 600; - font-size: 14px; - outline: none; - cursor: pointer; - transition: all 0.2s ease; - box-shadow: 0 1px 3px rgba(30, 43, 87, 0.08); -} - -.perfil-select:hover { - border-color: #7a85ff; - background-color: #ffffff; - box-shadow: 0 2px 6px rgba(30, 43, 87, 0.1); -} - -.perfil-select:focus { - border-color: #5a46ff; - box-shadow: 0 0 0 3px rgba(90, 70, 255, 0.2); -} - -.perfil-select option[value=""] { - color: #777; - font-weight: 500; -} - -/* responsivo */ -@media (max-width: 780px) { - .container-perfis { - top: 60px; - left: 20px; - width: calc(100% - 40px); - } - .perfil-select { - font-size: 13px; - padding: 8px 12px; - } -}