Browse Source

初始化

hfll
前端-胡立永 8 months ago
commit
5a00b1c38c
37 changed files with 8737 additions and 0 deletions
  1. +5
    -0
      .env
  2. +5
    -0
      .env.development
  3. +24
    -0
      .gitignore
  4. +3
    -0
      .vscode/extensions.json
  5. +5
    -0
      README.md
  6. +13
    -0
      index.html
  7. +2241
    -0
      package-lock.json
  8. +28
    -0
      package.json
  9. +123
    -0
      project.md
  10. +1
    -0
      public/vite.svg
  11. +364
    -0
      src/App.vue
  12. +156
    -0
      src/assets/scss/main.css
  13. +1
    -0
      src/assets/scss/main.min.css
  14. +161
    -0
      src/assets/scss/main.scss
  15. +1
    -0
      src/assets/vue.svg
  16. +201
    -0
      src/components/MobileNav.vue
  17. +269
    -0
      src/components/PageHeader.vue
  18. +167
    -0
      src/components/case/caseList.vue
  19. +137
    -0
      src/components/home/ServiceSection.vue
  20. +32
    -0
      src/main.js
  21. +46
    -0
      src/plugins/animation.js
  22. +82
    -0
      src/router/index.js
  23. +150
    -0
      src/stores/casesStore.js
  24. +87
    -0
      src/style.css
  25. +84
    -0
      src/utils/README.md
  26. +46
    -0
      src/utils/api.js
  27. +112
    -0
      src/utils/request.js
  28. +200
    -0
      src/views/blog/Blog.vue
  29. +141
    -0
      src/views/company/About.vue
  30. +478
    -0
      src/views/company/JobDetail.vue
  31. +300
    -0
      src/views/company/Team.vue
  32. +700
    -0
      src/views/pages/CaseDetail.vue
  33. +635
    -0
      src/views/pages/Cases.vue
  34. +307
    -0
      src/views/pages/Contact.vue
  35. +819
    -0
      src/views/pages/Home.vue
  36. +606
    -0
      src/views/pages/Services.vue
  37. +7
    -0
      vite.config.js

+ 5
- 0
.env View File

@ -0,0 +1,5 @@
# API基础URL
VITE_API_BASE_URL=http://api.example.com
# 其他环境变量
# VITE_APP_TITLE=瀚海黎明官网

+ 5
- 0
.env.development View File

@ -0,0 +1,5 @@
# 开发环境API基础URL
VITE_API_BASE_URL=http://localhost:3000
# 其他开发环境变量
# VITE_APP_MODE=development

+ 24
- 0
.gitignore View File

@ -0,0 +1,24 @@
# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
pnpm-debug.log*
lerna-debug.log*
node_modules
dist
dist-ssr
*.local
# Editor directories and files
.vscode/*
!.vscode/extensions.json
.idea
.DS_Store
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw?

+ 3
- 0
.vscode/extensions.json View File

@ -0,0 +1,3 @@
{
"recommendations": ["Vue.volar"]
}

+ 5
- 0
README.md View File

@ -0,0 +1,5 @@
# Vue 3 + Vite
This template should help get you started developing with Vue 3 in Vite. The template uses Vue 3 `<script setup>` SFCs, check out the [script setup docs](https://v3.vuejs.org/api/sfc-script-setup.html#sfc-script-setup) to learn more.
Learn more about IDE Support for Vue in the [Vue Docs Scaling up Guide](https://vuejs.org/guide/scaling-up/tooling.html#ide-support).

+ 13
- 0
index.html View File

@ -0,0 +1,13 @@
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Vite + Vue</title>
</head>
<body>
<div id="app"></div>
<script type="module" src="/src/main.js"></script>
</body>
</html>

+ 2241
- 0
package-lock.json
File diff suppressed because it is too large
View File


+ 28
- 0
package.json View File

@ -0,0 +1,28 @@
{
"name": "hanhai-official-website",
"private": true,
"version": "0.0.0",
"type": "module",
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview"
},
"dependencies": {
"@fortawesome/fontawesome-free": "^6.7.2",
"aos": "^2.3.4",
"axios": "^1.8.4",
"locomotive-scroll": "^4.1.4",
"parallax-js": "^3.1.0",
"pinia": "^2.1.7",
"sass": "^1.86.2",
"vue": "^3.5.13",
"vue-router": "^4.2.5"
},
"devDependencies": {
"@vitejs/plugin-vue": "^5.2.1",
"autoprefixer": "^10.4.16",
"postcss": "^8.4.31",
"vite": "^6.2.0"
}
}

+ 123
- 0
project.md View File

@ -0,0 +1,123 @@
# 瀚海黎明 - 专业软件解决方案
## 网站结构规划
### 1. 首页设计 (带视差滚动效果)
- 顶部导航栏(固定位置)
- Logo
- 导航菜单:首页、服务、案例、关于我们、团队、博客、联系我们
- 语言切换
- 联系按钮
- 英雄区域(Hero Section)
- 大型背景图片/视频(视差效果)
- 简洁有力的标语:"数字化转型的可靠伙伴"
- 副标语:"专注于为企业提供高质量软件开发外包服务"
- CTA按钮:"了解更多" 和 "联系我们"
- 我们的服务(视差滚动)
- 定制软件开发
- 移动应用开发
- Web应用开发
- 企业软件解决方案
- 云服务与DevOps
- UI/UX设计
(每个服务配有图标和简短描述,鼠标悬停效果)
- 我们的优势(视差背景)
- 专业团队
- 质量保证
- 按时交付
- 灵活合作模式
- 技术创新
- 售后支持
(数字+文字组合展示,滚动时有动画效果)
- 精选案例展示(视差滚动)
- 3-4个代表性项目,每个项目包含:
- 项目图片/截图
- 项目名称
- 简短描述
- "查看详情"链接
(滚动时案例卡片有淡入效果)
- 客户评价(视差背景)
- 滚动展示客户评价
- 客户头像、姓名、公司
- 评分星级
- 合作流程(视差滚动)
- 需求分析
- 方案设计
- 开发实施
- 测试验收
- 交付上线
- 持续支持
(流程图形式展示,滚动时逐步显示)
- 页脚
- 版权信息
- 网站地图
- 隐私政策
- 服务条款
- 社交媒体图标
### 2. 服务页面
- 详细介绍各类服务
- 服务流程
- 定价模式
- 常见问题解答
### 3. 案例页面
- 案例分类筛选
- 案例详情展示
- 客户反馈
- 相关案例推荐
### 4. 关于我们
- 公司简介
- 发展历程
- 企业文化
- 荣誉资质
### 5. 团队页面
- 核心团队成员介绍
- 团队文化
- 招聘信息
### 6. 联系页面
- 详细联系方式
- 合作咨询表单
- 办公地点信息
## 视差滚动效果实现建议
1. 使用Parallax.js库实现视差效果
2. 关键区域使用不同深度的视差层
3. 结合滚动触发动画效果
4. 确保移动端兼容性
5. 优化图片加载速度,避免性能问题
## 设计风格建议
- 配色方案:科技蓝+深灰+白色为主,辅以亮色点缀
- 字体选择:无衬线字体,如Roboto、Open Sans等
- 视觉元素:几何图形、线条、科技感图标
- 响应式设计:确保在各种设备上都有良好体验
- 用户体验:平滑的滚动效果、清晰的导航
## 技术栈建议
- 前端框架:Vue3
- 状态管理:Pinia
- 路由管理:Vue Router
- 视差效果:Parallax.js
- 动画:AOS (Animate On Scroll)
- 样式:SCSS
## 网页内容
先全部写模拟数据,图片用网络图片
## 开发建议
- 模块化开发:每个页面一个文件夹
- 组件化设计:每个功能一个组件

+ 1
- 0
public/vite.svg View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>

+ 364
- 0
src/App.vue View File

@ -0,0 +1,364 @@
<script setup>
import { ref, onMounted } from 'vue';
import MobileNav from './components/MobileNav.vue';
//
const isMobileNavOpen = ref(false);
//
const currentLang = ref('CN');
//
function toggleLanguage() {
currentLang.value = currentLang.value === 'CN' ? 'EN' : 'CN';
}
//
function handleLanguageChange(lang) {
currentLang.value = lang;
}
//
function toggleMobileNav() {
isMobileNavOpen.value = !isMobileNavOpen.value;
}
//
function closeMobileNav() {
isMobileNavOpen.value = false;
}
onMounted(() => {
//
});
</script>
<template>
<div class="app">
<!-- 顶部导航栏 -->
<header class="header">
<div class="container">
<div class="logo">
<router-link to="/">瀚海黎明</router-link>
</div>
<nav class="nav">
<ul class="nav-list">
<li><router-link to="/">首页</router-link></li>
<li><router-link to="/services">服务</router-link></li>
<li><router-link to="/cases">案例</router-link></li>
<li><router-link to="/about">关于我们</router-link></li>
<li><router-link to="/team">团队</router-link></li>
<!-- <li><router-link to="/blog">博客</router-link></li> -->
<li><router-link to="/contact">联系我们</router-link></li>
</ul>
</nav>
<div class="nav-actions">
<!-- <button class="lang-switch" @click="toggleLanguage">{{ currentLang === 'CN' ? 'EN' : 'CN' }}</button> -->
<router-link to="/contact" class="contact-btn">联系我们</router-link>
<button class="mobile-menu-btn" @click="toggleMobileNav">
<span></span>
<span></span>
<span></span>
</button>
</div>
</div>
</header>
<!-- 移动端导航 -->
<MobileNav
:is-open="isMobileNavOpen"
@close="closeMobileNav"
@language-change="handleLanguageChange"
/>
<!-- 路由视图 -->
<main>
<router-view v-slot="{ Component }">
<transition name="fade" mode="out-in">
<component :is="Component" />
</transition>
</router-view>
</main>
<!-- 页脚 -->
<footer class="footer">
<div class="container">
<div class="footer-content">
<div class="footer-logo">
<h3>瀚海黎明</h3>
<p>专业软件解决方案提供商</p>
</div>
<div class="footer-links">
<div class="link-group">
<h4>快速链接</h4>
<ul>
<li><router-link to="/">首页</router-link></li>
<li><router-link to="/services">服务</router-link></li>
<li><router-link to="/cases">案例</router-link></li>
<li><router-link to="/about">关于我们</router-link></li>
</ul>
</div>
<div class="link-group">
<h4>服务</h4>
<ul>
<li><a href="#">定制软件开发</a></li>
<li><a href="#">移动应用开发</a></li>
<li><a href="#">Web应用开发</a></li>
<li><a href="#">企业软件解决方案</a></li>
</ul>
</div>
<div class="link-group">
<h4>联系我们</h4>
<ul>
<li>深圳市南山区科技园</li>
<li>info@hanhaisoft.com</li>
<li>+86 755-8888-7777</li>
</ul>
</div>
</div>
</div>
<div class="footer-bottom">
<p>© 2023 瀚海黎明. 保留所有权利.</p>
<div class="footer-nav">
<a href="#">隐私政策</a>
<a href="#">服务条款</a>
<a href="#">网站地图</a>
</div>
</div>
</div>
</footer>
</div>
</template>
<style lang="scss" scoped>
.app {
display: flex;
flex-direction: column;
min-height: 100vh;
max-width: 100vw;
overflow-x: hidden;
}
.header {
position: fixed;
top: 0;
left: 0;
width: 100%;
max-width: 100vw;
background: rgba(255, 255, 255, 0.95);
box-sizing: border-box;
box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
z-index: 1000;
}
.header .container {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15px 20px;
max-width: 1200px;
margin: 0 auto;
box-sizing: border-box;
}
.logo a {
font-size: 24px;
font-weight: bold;
color: #0056b3;
text-decoration: none;
}
.nav-list {
display: flex;
list-style: none;
margin: 0;
padding: 0;
}
.nav-list li {
margin: 0 15px;
}
.nav-list a {
text-decoration: none;
color: #333;
font-weight: 500;
transition: color 0.3s ease;
}
.nav-list a:hover, .nav-list a.router-link-active {
color: #0056b3;
}
.nav-actions {
display: flex;
align-items: center;
}
.lang-switch {
background: none;
border: none;
margin-right: 15px;
cursor: pointer;
font-weight: 500;
}
.contact-btn {
background: #0056b3;
color: white;
border: none;
padding: 8px 20px;
border-radius: 4px;
cursor: pointer;
transition: background 0.3s ease;
text-decoration: none;
display: inline-block;
}
.contact-btn:hover {
background: #003d82;
}
main {
flex: 1;
margin-top: 70px; /* 为固定的header留出空间 */
}
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.3s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}
.footer {
background: #1a1a1a;
color: #fff;
padding: 60px 0 20px;
}
.footer-content {
display: flex;
justify-content: space-between;
margin-bottom: 40px;
}
.footer-logo h3 {
margin: 0 0 10px;
font-size: 24px;
color: #fff;
}
.footer-links {
display: flex;
gap: 60px;
}
.link-group h4 {
margin: 0 0 20px;
font-size: 18px;
color: #fff;
}
.link-group ul {
list-style: none;
padding: 0;
margin: 0;
}
.link-group li {
margin-bottom: 10px;
}
.link-group a {
color: #aaa;
text-decoration: none;
transition: color 0.3s ease;
}
.link-group a:hover {
color: #fff;
}
.footer-bottom {
display: flex;
justify-content: space-between;
align-items: center;
padding-top: 20px;
border-top: 1px solid #333;
}
.footer-nav a {
color: #aaa;
text-decoration: none;
margin-left: 20px;
transition: color 0.3s ease;
}
.footer-nav a:hover {
color: #fff;
}
/* 移动菜单按钮 */
.mobile-menu-btn {
display: none;
flex-direction: column;
justify-content: space-between;
width: 24px;
height: 18px;
background: transparent;
border: none;
cursor: pointer;
padding: 0;
z-index: 10;
}
.mobile-menu-btn span {
display: block;
height: 2px;
width: 100%;
background-color: #333;
transition: all 0.3s ease;
}
/* 响应式设计 */
@media (max-width: 768px) {
.nav-list {
display: none; /* 在移动端隐藏导航列表 */
}
.nav-actions .lang-switch,
.nav-actions .contact-btn {
display: none; /* 在移动端隐藏语言切换和联系按钮 */
}
.mobile-menu-btn {
display: flex; /* 在移动端显示汉堡菜单按钮 */
}
.footer-content, .footer-links {
flex-direction: column;
}
.footer-links {
gap: 30px;
}
.footer-bottom {
flex-direction: column;
text-align: center;
}
.footer-nav {
margin-top: 15px;
}
.footer-nav a {
margin: 0 10px;
}
}
</style>

+ 156
- 0
src/assets/scss/main.css View File

@ -0,0 +1,156 @@
.parallax-container {
position: relative;
overflow: hidden;
}
.parallax-container .parallax-layer {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
will-change: transform;
}
.btn {
display: inline-block;
padding: 12px 24px;
border-radius: 4px;
font-weight: 500;
text-align: center;
cursor: pointer;
transition: all 0.3s ease;
text-decoration: none;
}
.btn.primary {
background-color: #0056b3;
color: white;
border: none;
}
.btn.primary:hover {
background-color: #003d82;
}
.btn.secondary {
background-color: transparent;
color: #0056b3;
border: 1px solid #0056b3;
}
.btn.secondary:hover {
background-color: rgba(0, 86, 179, 0.1);
}
.container {
width: 100%;
max-width: 1200px;
margin: 0 auto;
padding: 0 20px;
}
.card {
background: white;
border-radius: 8px;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.05);
overflow: hidden;
transition: transform 0.3s ease, box-shadow 0.3s ease;
}
.card:hover {
transform: translateY(-5px);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.1);
}
h1, h2, h3, h4, h5, h6 {
font-weight: 700;
line-height: 1.2;
margin-top: 0;
margin-bottom: 0.5em;
color: #333;
}
h1 {
font-size: 2.5rem;
}
@media (min-width: 768px) {
h1 {
font-size: 3rem;
}
}
h2 {
font-size: 2rem;
}
@media (min-width: 768px) {
h2 {
font-size: 2.5rem;
}
}
@keyframes fadeIn {
from {
opacity: 0;
}
to {
opacity: 1;
}
}
@keyframes slideUp {
from {
transform: translateY(20px);
opacity: 0;
}
to {
transform: translateY(0);
opacity: 1;
}
}
.text-center {
text-align: center;
}
.mb-1 {
margin-bottom: 0.25rem;
}
.mb-2 {
margin-bottom: 0.5rem;
}
.mb-3 {
margin-bottom: 1rem;
}
.mb-4 {
margin-bottom: 1.5rem;
}
.mb-5 {
margin-bottom: 3rem;
}
.mt-1 {
margin-top: 0.25rem;
}
.mt-2 {
margin-top: 0.5rem;
}
.mt-3 {
margin-top: 1rem;
}
.mt-4 {
margin-top: 1.5rem;
}
.mt-5 {
margin-top: 3rem;
}

+ 1
- 0
src/assets/scss/main.min.css View File

@ -0,0 +1 @@
.parallax-container{position:relative;overflow:hidden}.parallax-container .parallax-layer{position:absolute;top:0;left:0;width:100%;height:100%;will-change:transform}.btn{display:inline-block;padding:12px 24px;border-radius:4px;font-weight:500;text-align:center;cursor:pointer;transition:all 0.3s ease;text-decoration:none}.btn.primary{background-color:#0056b3;color:white;border:none}.btn.primary:hover{background-color:#003d82}.btn.secondary{background-color:transparent;color:#0056b3;border:1px solid #0056b3}.btn.secondary:hover{background-color:rgba(0,86,179,0.1)}.container{width:100%;max-width:1200px;margin:0 auto;padding:0 20px}.card{background:white;border-radius:8px;box-shadow:0 5px 15px rgba(0,0,0,0.05);overflow:hidden;transition:transform 0.3s ease, box-shadow 0.3s ease}.card:hover{transform:translateY(-5px);box-shadow:0 15px 30px rgba(0,0,0,0.1)}h1,h2,h3,h4,h5,h6{font-weight:700;line-height:1.2;margin-top:0;margin-bottom:0.5em;color:#333}h1{font-size:2.5rem}@media (min-width: 768px){h1{font-size:3rem}}h2{font-size:2rem}@media (min-width: 768px){h2{font-size:2.5rem}}@keyframes fadeIn{from{opacity:0}to{opacity:1}}@keyframes slideUp{from{transform:translateY(20px);opacity:0}to{transform:translateY(0);opacity:1}}.text-center{text-align:center}.mb-1{margin-bottom:0.25rem}.mb-2{margin-bottom:0.5rem}.mb-3{margin-bottom:1rem}.mb-4{margin-bottom:1.5rem}.mb-5{margin-bottom:3rem}.mt-1{margin-top:0.25rem}.mt-2{margin-top:0.5rem}.mt-3{margin-top:1rem}.mt-4{margin-top:1.5rem}.mt-5{margin-top:3rem}

+ 161
- 0
src/assets/scss/main.scss View File

@ -0,0 +1,161 @@
// 主SCSS文件
@use "sass:map";
// 变量定义
$primary-color: #0056b3;
$secondary-color: #003d7a;
$accent-color: #00a8ff;
$text-color: #2c3e50;
$text-light: #5a6a7e;
$light-bg: #f8f9fa;
$dark-bg: #1a1a1a;
$shadow-sm: 0 5px 15px rgba(0, 0, 0, 0.05);
$shadow-lg: 0 15px 30px rgba(0, 0, 0, 0.1);
$shadow-xl: 0 10px 30px rgba(0, 0, 0, 0.3);
// 字体设置
$font-family-base: 'Roboto', 'Open Sans', -apple-system, BlinkMacSystemFont, 'Segoe UI', Helvetica, Arial, sans-serif;
// 断点设置
$breakpoints: (
xs: 0,
sm: 576px,
md: 768px,
lg: 992px,
xl: 1200px
);
// 混合器
@mixin respond-to($breakpoint) {
$value: map.get($breakpoints, $breakpoint);
@if $value != null {
@media (min-width: $value) {
@content;
}
} @else {
@warn "Unknown breakpoint: #{$breakpoint}.";
}
}
// 视差效果相关样式
.parallax-container {
position: relative;
overflow: hidden;
.parallax-layer {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
will-change: transform;
}
}
// 按钮样式
.btn {
display: inline-block;
padding: 12px 24px;
border-radius: 4px;
font-weight: 500;
text-align: center;
cursor: pointer;
transition: all 0.3s ease;
text-decoration: none;
&.primary {
background-color: $primary-color;
color: white;
border: none;
&:hover {
background-color: $secondary-color;
}
}
&.secondary {
background-color: transparent;
color: $primary-color;
border: 1px solid $primary-color;
&:hover {
background-color: rgba($primary-color, 0.1);
}
}
}
// 容器样式
.container {
width: 100%;
max-width: 1200px;
margin: 0 auto;
padding: 0 20px;
}
// 卡片样式
.card {
background: white;
border-radius: 8px;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.05);
overflow: hidden;
transition: transform 0.3s ease, box-shadow 0.3s ease;
&:hover {
transform: translateY(-5px);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.1);
}
}
// 标题样式
h1, h2, h3, h4, h5, h6 {
font-weight: 700;
line-height: 1.2;
margin-top: 0;
margin-bottom: 0.5em;
color: $text-color;
}
h1 {
font-size: 2.5rem;
@include respond-to(md) {
font-size: 3rem;
}
}
h2 {
font-size: 2rem;
@include respond-to(md) {
font-size: 2.5rem;
}
}
// 全局动画
@keyframes fadeIn {
from { opacity: 0; }
to { opacity: 1; }
}
@keyframes slideUp {
from { transform: translateY(20px); opacity: 0; }
to { transform: translateY(0); opacity: 1; }
}
// 辅助类
.text-center {
text-align: center;
}
.mb-1 { margin-bottom: 0.25rem; }
.mb-2 { margin-bottom: 0.5rem; }
.mb-3 { margin-bottom: 1rem; }
.mb-4 { margin-bottom: 1.5rem; }
.mb-5 { margin-bottom: 3rem; }
.mt-1 { margin-top: 0.25rem; }
.mt-2 { margin-top: 0.5rem; }
.mt-3 { margin-top: 1rem; }
.mt-4 { margin-top: 1.5rem; }
.mt-5 { margin-top: 3rem; }

+ 1
- 0
src/assets/vue.svg View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="37.07" height="36" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 198"><path fill="#41B883" d="M204.8 0H256L128 220.8L0 0h97.92L128 51.2L157.44 0h47.36Z"></path><path fill="#41B883" d="m0 0l128 220.8L256 0h-51.2L128 132.48L50.56 0H0Z"></path><path fill="#35495E" d="M50.56 0L128 133.12L204.8 0h-47.36L128 51.2L97.92 0H50.56Z"></path></svg>

+ 201
- 0
src/components/MobileNav.vue View File

@ -0,0 +1,201 @@
<script setup>
import { ref } from 'vue';
import { useRouter } from 'vue-router';
// props
const props = defineProps({
isOpen: {
type: Boolean,
required: true
}
});
//
const emit = defineEmits(['close', 'languageChange']);
//
const currentLang = ref('CN');
//
function toggleLanguage() {
currentLang.value = currentLang.value === 'CN' ? 'EN' : 'CN';
emit('languageChange', currentLang.value);
}
//
function closeMenu() {
emit('close');
}
//
const router = useRouter();
//
function navigateTo(path) {
router.push(path);
closeMenu();
}
</script>
<template>
<div class="mobile-nav" :class="{ 'is-open': isOpen }">
<div class="mobile-nav-overlay" @click="closeMenu"></div>
<div class="mobile-nav-content">
<div class="mobile-nav-header">
<div class="logo">瀚海黎明</div>
<button class="close-btn" @click="closeMenu">
<span>&times;</span>
</button>
</div>
<nav class="mobile-nav-menu">
<ul>
<li><a @click="navigateTo('/')">首页</a></li>
<li><a @click="navigateTo('/services')">服务</a></li>
<li><a @click="navigateTo('/cases')">案例</a></li>
<li><a @click="navigateTo('/about')">关于我们</a></li>
<li><a @click="navigateTo('/team')">团队</a></li>
<li><a @click="navigateTo('/contact')">联系我们</a></li>
</ul>
</nav>
<div class="mobile-nav-footer">
<button class="lang-switch" @click="toggleLanguage">{{ currentLang === 'CN' ? 'EN' : 'CN' }}</button>
<button class="contact-btn" @click="navigateTo('/contact')">联系我们</button>
</div>
</div>
</div>
</template>
<style scoped>
.mobile-nav {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: 2000;
visibility: hidden;
opacity: 0;
transition: visibility 0.3s, opacity 0.3s;
}
.mobile-nav.is-open {
visibility: visible;
opacity: 1;
}
.mobile-nav-overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(0, 0, 0, 0.5);
}
.mobile-nav-content {
position: absolute;
top: 0;
right: 0;
width: 80%;
max-width: 320px;
height: 100%;
background-color: white;
box-shadow: -2px 0 10px rgba(0, 0, 0, 0.1);
display: flex;
flex-direction: column;
transform: translateX(100%);
transition: transform 0.3s ease;
}
.is-open .mobile-nav-content {
transform: translateX(0);
}
.mobile-nav-header {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15px 20px;
border-bottom: 1px solid #eee;
}
.logo {
font-size: 20px;
font-weight: bold;
color: #0056b3;
}
.close-btn {
background: none;
border: none;
font-size: 24px;
cursor: pointer;
color: #333;
}
.mobile-nav-menu {
flex: 1;
overflow-y: auto;
padding: 20px 0;
}
.mobile-nav-menu ul {
list-style: none;
padding: 0;
margin: 0;
}
.mobile-nav-menu li {
margin: 0;
}
.mobile-nav-menu a {
display: block;
padding: 12px 20px;
color: #333;
text-decoration: none;
transition: background-color 0.3s;
cursor: pointer;
}
.mobile-nav-menu a:hover {
background-color: #f5f5f5;
color: #0056b3;
}
.mobile-nav-footer {
padding: 20px;
border-top: 1px solid #eee;
display: flex;
flex-direction: column;
gap: 10px;
}
.lang-switch {
background: none;
border: 1px solid #ddd;
padding: 8px;
border-radius: 4px;
cursor: pointer;
font-weight: 500;
transition: background 0.3s ease;
}
.lang-switch:hover {
background: #f5f5f5;
}
.contact-btn {
background: #0056b3;
color: white;
border: none;
padding: 10px;
border-radius: 4px;
cursor: pointer;
transition: background 0.3s ease;
}
.contact-btn:hover {
background: #003d82;
}
</style>

+ 269
- 0
src/components/PageHeader.vue View File

@ -0,0 +1,269 @@
<script setup>
import { computed, onMounted, onUnmounted } from 'vue';
import { useRoute } from 'vue-router';
import { initParallax } from '../plugins/animation';
//
const props = defineProps({
title: {
type: String,
required: true
},
subtitle: {
type: String,
default: ''
},
backgroundImage: {
type: String,
default: 'https://images.unsplash.com/photo-1522071901873-411886a10004?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
},
height: {
type: String,
default: '60vh'
}
});
//
const route = useRoute();
const currentRouteName = computed(() => route.name);
//
const breadcrumbMap = {
'Home': '首页',
'About': '关于我们',
'Team': '团队',
'Services': '服务',
'Cases': '案例',
'Blog': '博客',
'Contact': '联系我们'
};
onMounted(() => {
// Parallax.js
initParallax();
});
</script>
<template>
<section class="page-header parallax-container" :style="{ height: height }">
<!-- 视差背景 -->
<div class="parallax-bg" data-depth="0.2" :style="{ backgroundImage: `url(${backgroundImage})` }"></div>
<!-- 渐变叠加层 -->
<div class="overlay"></div>
<div class="container">
<!-- 面包屑导航 -->
<div class="breadcrumb" data-aos="fade-right" data-aos-delay="100">
<router-link to="/" class="breadcrumb-item">首页</router-link>
<span class="separator">/</span>
<span class="current">{{ breadcrumbMap[currentRouteName] || title }}</span>
</div>
<!-- 标题内容 -->
<div class="header-content">
<h1 data-aos="fade-up">{{ title }}</h1>
<p v-if="subtitle" data-aos="fade-up" data-aos-delay="200">{{ subtitle }}</p>
<!-- 插槽用于扩展按钮 -->
<slot name="header-cta"></slot>
</div>
</div>
</section>
</template>
<style scoped>
.page-header {
position: relative;
overflow: hidden;
display: flex;
align-items: center;
justify-content: center;
color: white;
text-align: center;
}
.page-header .container {
position: relative;
z-index: 2;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
height: 100%;
width: 100vw;
max-width: 100%;
margin: 0;
padding: 0 20px;
left: 0;
right: 0;
pointer-events: auto; /* 确保容器可以正确传递点击事件 */
}
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-size: cover;
background-position: center;
background-repeat: no-repeat;
z-index: -1;
transform: translateZ(-5px) scale(1.5);
/* 确保在所有浏览器中正确渲染 */
backface-visibility: hidden;
perspective: 1000;
-webkit-backface-visibility: hidden;
-webkit-perspective: 1000;
/* 确保背景图片始终可见 */
opacity: 1 !important;
visibility: visible !important;
/* 确保鼠标事件可以穿透到下层元素 */
pointer-events: none;
}
/* 渐变叠加层 */
.overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to bottom, rgba(0,0,0,0.5), rgba(0,0,0,0.7));
z-index: 1;
/* 确保鼠标事件可以穿透到下层元素 */
pointer-events: none;
}
/* 面包屑导航 */
.breadcrumb {
position: absolute;
top: 30px;
left: 30px;
font-size: 0.9rem;
color: rgba(255, 255, 255, 0.8);
text-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);
align-self: flex-start;
z-index: 2;
}
.breadcrumb-item {
color: white;
text-decoration: none;
transition: color 0.3s ease;
}
.breadcrumb-item:hover {
color: var(--accent-color);
}
.separator {
margin: 0 8px;
opacity: 0.7;
}
.current {
font-weight: 500;
}
/* 标题内容 */
.header-content {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
z-index: 5; /* 提高z-index确保内容在最上层 */
width: 100%;
text-align: center;
margin: 0 auto;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
pointer-events: auto; /* 确保内容可以接收点击事件 */
}
.header-content h1 {
font-size: 3.5rem;
font-weight: 800;
color: #fff;
margin-bottom: 20px;
text-shadow: 0 2px 8px rgba(0, 0, 0, 0.6);
letter-spacing: 1px;
}
.header-content p {
font-size: 1.6rem;
margin: 0 auto 30px;
text-shadow: 0 2px 4px rgba(0, 0, 0, 0.4);
font-weight: 300;
}
/* 按钮样式 */
:deep(.header-cta) {
margin-top: 10px;
position: relative;
z-index: 10;
pointer-events: auto; /* 确保按钮可以接收点击事件 */
}
:deep(.btn-outline) {
display: inline-block;
padding: 12px 30px;
border: 2px solid white;
border-radius: 30px;
color: white;
font-weight: 600;
text-decoration: none;
transition: all 0.3s ease;
text-shadow: none;
position: relative;
z-index: 20;
cursor: pointer;
pointer-events: auto;
}
:deep(.btn-outline:hover) {
background-color: white;
color: var(--primary-color);
transform: translateY(-3px);
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.2);
}
/* 响应式调整 */
@media (max-width: 768px) {
.page-header {
height: 50vh !important;
}
.header-content h1 {
font-size: 2.5rem;
}
.header-content p {
font-size: 1.2rem;
margin-bottom: 20px;
}
.breadcrumb {
top: 20px;
left: 20px;
font-size: 0.8rem;
}
:deep(.btn-outline) {
padding: 10px 25px;
}
}
@media (max-width: 480px) {
.page-header {
height: 40vh !important;
}
.header-content h1 {
font-size: 1.8rem;
}
}
</style>

+ 167
- 0
src/components/case/caseList.vue View File

@ -0,0 +1,167 @@
<script setup>
import { ref, onMounted, computed } from 'vue';
import { useRoute, useRouter } from 'vue-router';
//
const route = useRoute();
const router = useRouter();
//
const viewRelatedCase = (id) => {
router.push(`/cases/${id}`);
};
//
const props = defineProps({
cases: {
type: Array,
required: true
},
});
</script>
<template>
<!-- 相关案例 -->
<div class="related-grid">
<div v-for="caseItem in cases" :key="caseItem.id" class="related-case-card" data-aos="fade-up"
@click="viewRelatedCase(caseItem.id)">
<div class="case-image">
<img :src="caseItem.image" :alt="caseItem.title">
<div class="case-overlay">
<span class="view-more">查看详情 <i class="fas fa-arrow-right"></i></span>
</div>
</div>
<div class="case-content">
<div class="case-category">{{ caseItem.category }}</div>
<h3>{{ caseItem.title }}</h3>
<p>{{ caseItem.description }}</p>
</div>
</div>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
.related-grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));
gap: 30px;
@media (max-width: 768px) {
grid-template-columns: 1fr;
}
}
.related-case-card {
background: white;
border-radius: 10px;
overflow: hidden;
box-shadow: $shadow-sm;
transition: all 0.3s ease;
cursor: pointer;
height: 100%;
display: flex;
flex-direction: column;
&:hover {
transform: translateY(-10px);
box-shadow: $shadow-lg;
.case-image img {
transform: scale(1.05);
}
.case-overlay {
opacity: 1;
}
.view-more {
transform: translateY(0);
}
}
}
.case-image {
position: relative;
height: 220px;
overflow: hidden;
img {
width: 100%;
height: 100%;
object-fit: cover;
transition: transform 0.5s ease;
}
.case-overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba($primary-color, 0.7);
display: flex;
align-items: center;
justify-content: center;
opacity: 0;
transition: opacity 0.3s ease;
}
.view-more {
color: white;
font-weight: 500;
display: flex;
align-items: center;
gap: 8px;
transform: translateY(20px);
transition: transform 0.3s ease 0.1s;
i {
transition: transform 0.2s ease;
}
&:hover i {
transform: translateX(5px);
}
}
}
.case-content {
padding: 25px;
flex-grow: 1;
display: flex;
flex-direction: column;
}
.case-category {
display: inline-block;
padding: 5px 12px;
background-color: rgba($primary-color, 0.1);
color: $primary-color;
border-radius: 20px;
font-size: 0.8rem;
font-weight: 500;
margin-bottom: 15px;
}
.case-content h3 {
font-size: 1.4rem;
color: $text-color;
margin-bottom: 10px;
transition: color 0.3s ease;
}
.case-content p {
color: $text-light;
font-size: 0.95rem;
line-height: 1.6;
margin-bottom: 20px;
flex-grow: 1;
}
</style>

+ 137
- 0
src/components/home/ServiceSection.vue View File

@ -0,0 +1,137 @@
<script setup>
//
const services = [
{
id: 1,
icon: 'https://cdn-icons-png.flaticon.com/512/2920/2920277.png',
title: '定制软件开发',
description: '根据您的业务需求,量身定制专属软件解决方案',
delay: 100
},
{
id: 2,
icon: 'https://cdn-icons-png.flaticon.com/512/2586/2586488.png',
title: '移动应用开发',
description: '打造高性能、用户友好的iOS和Android应用',
delay: 200
},
{
id: 3,
icon: 'https://cdn-icons-png.flaticon.com/512/1055/1055687.png',
title: 'Web应用开发',
description: '开发响应式、现代化的Web应用和网站',
delay: 300
},
{
id: 4,
icon: 'https://cdn-icons-png.flaticon.com/512/1935/1935765.png',
title: '企业软件解决方案',
description: '提供ERP、CRM等企业级软件解决方案',
delay: 400
},
{
id: 5,
icon: 'https://cdn-icons-png.flaticon.com/512/4727/4727266.png',
title: '云服务与DevOps',
description: '云架构设计、部署和DevOps自动化服务',
delay: 500
},
{
id: 6,
icon: 'https://cdn-icons-png.flaticon.com/512/1055/1055666.png',
title: 'UI/UX设计',
description: '创造直观、美观且用户友好的界面设计',
delay: 600
}
];
</script>
<template>
<section class="services-section" data-aos="fade-up">
<div class="section-header">
<h2>我们的服务</h2>
<p>为您的业务提供全方位的软件解决方案</p>
</div>
<div class="services-grid">
<div
v-for="service in services"
:key="service.id"
class="service-card"
data-aos="fade-up"
:data-aos-delay="service.delay"
>
<div class="service-icon">
<img :src="service.icon" :alt="service.title" />
</div>
<h3>{{ service.title }}</h3>
<p>{{ service.description }}</p>
</div>
</div>
</section>
</template>
<style lang="scss" scoped>
.services-section {
padding: 100px 20px;
background-color: #f8f9fa;
.section-header {
text-align: center;
margin-bottom: 50px;
h2 {
font-size: 2.5rem;
color: #2c3e50;
margin-bottom: 15px;
}
p {
font-size: 1.2rem;
color: #7f8c8d;
}
}
.services-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: 30px;
margin-top: 40px;
max-width: 1200px;
margin-left: auto;
margin-right: auto;
.service-card {
background: white;
border-radius: 8px;
padding: 30px;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.05);
transition: transform 0.3s ease, box-shadow 0.3s ease;
text-align: center;
&:hover {
transform: translateY(-10px);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.1);
}
.service-icon {
margin-bottom: 20px;
img {
width: 80px;
height: 80px;
}
}
h3 {
font-size: 1.5rem;
margin-bottom: 15px;
color: #2c3e50;
}
p {
color: #7f8c8d;
}
}
}
}
</style>

+ 32
- 0
src/main.js View File

@ -0,0 +1,32 @@
import { createApp } from 'vue'
import { createPinia } from 'pinia'
import './style.css'
import App from './App.vue'
// 导入路由配置
import router from './router'
// 导入动画效果初始化函数
import initAnimations from './plugins/animation'
// 导入SCSS样式
import './assets/scss/main.scss'
// 导入FontAwesome图标库
import '@fortawesome/fontawesome-free/css/all.min.css'
// 创建Pinia实例
const pinia = createPinia()
// 创建Vue应用实例
const app = createApp(App)
// 使用插件
app.use(router)
app.use(pinia)
// 初始化动画效果
initAnimations()
// 挂载应用
app.mount('#app')

+ 46
- 0
src/plugins/animation.js View File

@ -0,0 +1,46 @@
// 导入动画和视差效果库
import AOS from 'aos';
import 'aos/dist/aos.css';
import Parallax from 'parallax-js';
// 初始化AOS动画库
export function initAOS() {
AOS.init({
duration: 800, // 动画持续时间
easing: 'ease', // 动画曲线
once: true, // 动画是否只播放一次
offset: 120, // 触发偏移量
delay: 0, // 延迟时间
anchorPlacement: 'top-bottom', // 锚点位置
});
}
// 初始化Parallax.js视差效果
export function initParallax() {
// 获取所有带有parallax-container类的元素
const scenes = document.querySelectorAll('.parallax-container');
// 为每个元素创建视差实例
scenes.forEach(scene => {
new Parallax(scene, {
relativeInput: true,
clipRelativeInput: true,
hoverOnly: false,
inputElement: document.documentElement
});
});
}
// 导出一个函数用于在Vue应用中初始化所有动画效果
export default function initAnimations() {
// 在DOM加载完成后初始化
window.addEventListener('DOMContentLoaded', () => {
initAOS();
initParallax();
});
// 在窗口大小改变时刷新AOS
window.addEventListener('resize', () => {
AOS.refresh();
});
}

+ 82
- 0
src/router/index.js View File

@ -0,0 +1,82 @@
import { createRouter, createWebHistory } from 'vue-router'
// 导入页面组件
const Home = () => import('../views/pages/Home.vue')
const Services = () => import('../views/pages/Services.vue')
const Cases = () => import('../views/pages/Cases.vue')
const CaseDetail = () => import('../views/pages/CaseDetail.vue')
const About = () => import('../views/company/About.vue')
const Team = () => import('../views/company/Team.vue')
const JobDetail = () => import('../views/company/JobDetail.vue')
const Blog = () => import('../views/blog/Blog.vue')
const Contact = () => import('../views/pages/Contact.vue')
// 定义路由
const routes = [
{
path: '/',
name: 'Home',
component: Home
},
{
path: '/services',
name: 'Services',
component: Services
},
{
path: '/cases',
name: 'Cases',
component: Cases
},
{
path: '/cases/:id',
name: 'CaseDetail',
component: CaseDetail
},
{
path: '/about',
name: 'About',
component: About
},
{
path: '/team',
name: 'Team',
component: Team
},
{
path: '/jobs/:id',
name: 'JobDetail',
component: JobDetail
},
{
path: '/blog',
name: 'Blog',
component: Blog
},
{
path: '/contact',
name: 'Contact',
component: Contact
}
]
// 创建路由实例
const router = createRouter({
history: createWebHistory(),
routes,
// 平滑滚动行为
scrollBehavior(to, from, savedPosition) {
if (savedPosition) {
return savedPosition
} else if (to.hash) {
return {
el: to.hash,
behavior: 'smooth'
}
} else {
return { top: 0, behavior: 'smooth' }
}
}
})
export default router

+ 150
- 0
src/stores/casesStore.js View File

@ -0,0 +1,150 @@
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'
// 定义案例数据存储
export const useCasesStore = defineStore('cases', () => {
// 案例数据
const casesList = ref([
{
id: 1,
title: '企业资源管理系统',
description: '为某制造企业开发的一套完整ERP系统,实现了生产、销售、库存等全流程管理',
image: 'https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统',
client: '某制造业集团',
completionDate: '2023年6月',
services: ['系统架构设计', '数据库优化', '前端开发', '后端开发', '系统集成'],
challenge: '客户面临的主要挑战是多个业务系统之间数据孤岛问题,导致信息流通不畅,管理效率低下。同时,随着业务规模扩大,原有系统已无法满足日益增长的业务需求。',
solution: '我们为客户设计并实现了一套全面的企业资源管理系统,整合了生产、销售、采购、库存、财务等多个模块。系统采用微服务架构,确保了各模块之间的松耦合与高内聚,同时保证了系统的可扩展性和稳定性。我们还为客户定制了数据分析和决策支持功能,帮助管理层快速获取业务洞察。',
results: '系统上线后,客户的运营效率提升了35%,信息处理时间缩短了60%,库存周转率提高了25%,大幅降低了运营成本。同时,实时的数据分析功能帮助客户更快速地响应市场变化,提升了企业的竞争力。',
testimonial: '微隐软件工作室的团队展现了卓越的专业能力和服务态度。他们不仅理解我们的业务需求,还能提供创新的技术解决方案。新系统极大地提升了我们的运营效率,是我们数字化转型的重要一步。',
testimonialAuthor: '张总 - 客户CIO',
gallery: [
'https://images.unsplash.com/photo-1454165804606-c3d57bc86b40?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551434678-e076c223a692?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 2,
title: '电商平台重构',
description: '帮助某电商企业重构其线上平台,提升用户体验和系统性能,实现销售额提升30%',
image: 'https://images.unsplash.com/photo-1556742049-0cfed4f6a45d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用',
client: '某知名电商企业',
completionDate: '2023年9月',
services: ['用户体验设计', '前端重构', '后端优化', '性能调优', '安全加固'],
challenge: '客户的电商平台面临用户体验不佳、系统响应缓慢、移动端适配不足等问题,导致用户流失和转化率下降。同时,随着业务量增长,系统稳定性也面临挑战。',
solution: '我们对客户的电商平台进行了全面重构,采用了现代化的前端框架和响应式设计,优化了用户界面和交互流程。在后端,我们重构了核心服务,引入了微服务架构和缓存机制,提升了系统性能和可扩展性。同时,我们还加强了系统的安全性,实现了全面的HTTPS和数据加密。',
results: '重构后的平台页面加载速度提升了65%,用户停留时间增加了40%,转化率提高了25%,最终带来了30%的销售额增长。系统的稳定性也得到了显著提升,即使在促销高峰期也能保持良好的性能。',
testimonial: '微隐软件工作室的团队展现了卓越的技术实力和创新思维。他们不仅解决了我们平台的技术问题,还从用户体验和业务角度提供了宝贵建议。重构后的平台获得了用户的一致好评,为我们带来了实质性的业务增长。',
testimonialAuthor: '李总 - 客户产品总监',
gallery: [
'https://images.unsplash.com/photo-1556740758-90de374c12ad?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1556740772-1a741d976155?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1556761175-129418cb2dfe?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 3,
title: '医疗服务APP',
description: '为连锁医疗机构开发的患者服务APP,实现在线挂号、问诊和健康管理等功能',
image: 'https://images.unsplash.com/photo-1576091160550-2173dba999ef?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '移动应用',
client: '某连锁医疗机构',
completionDate: '2023年12月',
services: ['移动应用开发', 'UI/UX设计', '后端API开发', '数据安全', '系统集成'],
challenge: '客户希望通过数字化手段提升患者服务体验,减少排队等待时间,同时提高医疗资源利用效率。传统的线下预约和就诊流程繁琐,患者满意度不高。',
solution: '我们为客户开发了一款功能全面的医疗服务APP,支持在线挂号、远程问诊、检查报告查询、健康档案管理等功能。APP采用了直观的用户界面和流畅的交互设计,确保各年龄段用户都能轻松使用。在技术层面,我们实现了与医院HIS系统的无缝集成,并采用了严格的数据加密和隐私保护措施。',
results: 'APP上线后,患者预约效率提升了80%,平均等待时间减少了65%,患者满意度提高了45%。同时,医生的工作效率也得到了提升,资源利用率增加了30%。APP已成为客户数字化医疗服务的核心平台。',
testimonial: '微隐软件工作室深入理解了医疗行业的特殊需求,为我们打造了一款既专业又易用的医疗服务APP。他们在确保数据安全和系统稳定性方面表现出色,为我们的患者提供了便捷、高效的服务体验。',
testimonialAuthor: '王院长 - 客户医疗总监',
gallery: [
'https://images.unsplash.com/photo-1576091160399-112ba8d25d1d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1579684385127-1ef15d508118?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1583324113626-70df0f4deaab?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 4,
title: '金融数据可视化平台',
description: '为金融机构开发的数据分析和可视化平台,帮助决策者快速洞察市场趋势',
image: 'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用',
client: '某投资管理公司',
completionDate: '2024年2月',
services: ['数据分析', '可视化设计', '前端开发', 'API集成', '实时数据处理'],
challenge: '客户需要一个能够整合多源金融数据,并提供直观、实时的可视化分析工具,帮助投资分析师和决策者快速识别市场趋势和投资机会。',
solution: '我们为客户开发了一个功能强大的金融数据可视化平台,整合了市场数据、公司财报、宏观经济指标等多种数据源。平台提供了丰富的图表类型和分析工具,支持自定义仪表盘和报告。我们采用了高性能的前端渲染技术和实时数据处理架构,确保了大数据量下的流畅体验。',
results: '平台上线后,客户的数据分析效率提升了70%,决策周期缩短了50%,投资组合表现超过了基准指数15%。平台的预测模型准确率达到了85%,为客户提供了显著的竞争优势。',
testimonial: '微隐软件工作室交付的数据可视化平台超出了我们的预期。他们不仅具备出色的技术能力,还展现了对金融行业的深刻理解。平台直观的界面和强大的分析功能极大地提升了我们的决策效率和准确性。',
testimonialAuthor: '赵总 - 客户投资总监',
gallery: [
'https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1590283603385-17ffb3a7f29f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 5,
title: '智慧校园系统',
description: '为教育机构打造的一体化校园管理系统,涵盖教学、行政、学生服务等多个模块',
image: 'https://images.unsplash.com/photo-1523240795612-9a054b0db644?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统',
client: '某知名高校',
completionDate: '2023年8月',
services: ['系统规划', '软件开发', '数据迁移', '用户培训', '持续支持'],
challenge: '客户面临的挑战是多个独立系统并行运行,数据不一致,管理效率低下。学生和教职工需要在多个系统间切换,用户体验不佳。',
solution: '我们为客户设计并实现了一套集成化的智慧校园系统,整合了教务管理、学生服务、行政办公、资源管理等多个模块。系统采用了统一的用户界面和数据标准,实现了单点登录和数据共享。我们还开发了移动端应用,方便师生随时随地访问系统功能。',
results: '系统上线后,管理效率提升了50%,数据处理错误减少了80%,用户满意度提高了60%。系统的自助服务功能减轻了行政人员的工作负担,让他们能够专注于更有价值的任务。',
testimonial: '微隐软件工作室的团队展现了卓越的项目管理和技术能力。他们深入理解了我们复杂的业务需求,并提供了一套既全面又易用的解决方案。新系统极大地改善了我们的管理效率和服务质量。',
testimonialAuthor: '陈校长 - 客户负责人',
gallery: [
'https://images.unsplash.com/photo-1523050854058-8df90110c9f1?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1562774053-701939374585?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1577896851231-70ef18881754?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 6,
title: '品牌官网设计',
description: '为高端品牌设计的响应式官方网站,展现品牌形象并提升用户转化率',
image: 'https://images.unsplash.com/photo-1561070791-2526d30994b5?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'UI/UX设计',
client: '某高端消费品牌',
completionDate: '2024年1月',
services: ['品牌策略', 'UI/UX设计', '前端开发', 'CMS实现', 'SEO优化'],
challenge: '客户的原有网站设计过时,无法有效展现品牌高端形象,且缺乏移动端适配,导致用户体验不佳和转化率低下。',
solution: '我们为客户重新设计了品牌官网,采用了现代简约的设计风格,突出品牌的高端定位。网站采用了响应式设计,确保在各种设备上都能提供出色的用户体验。我们还优化了产品展示和购买流程,降低了用户转化的摩擦。在技术层面,我们实现了高性能的前端架构和易用的内容管理系统。',
results: '新网站上线后,用户停留时间增加了45%,页面跳出率降低了30%,转化率提升了35%。网站的加载速度提高了60%,搜索引擎排名也有显著提升。客户的品牌形象得到了有效提升,线上销售额增长了40%。',
testimonial: '微隐软件工作室的设计团队展现了卓越的创意和专业能力。他们不仅理解我们的品牌价值,还能将其完美地转化为视觉设计。新网站获得了客户和合作伙伴的一致好评,成为了我们品牌传播的重要窗口。',
testimonialAuthor: '林总 - 客户市场总监',
gallery: [
'https://images.unsplash.com/photo-1542744094-3a31f272c490?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1542744173-8659239e9452?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1542744173-05336fcc7ad4?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
}
])
// 获取单个案例的方法
const getCaseById = (id) => {
return casesList.value.find(item => item.id === id) || null
}
// 获取相关案例的方法
const getRelatedCases = (currentCaseId, category) => {
return casesList.value
.filter(item =>
item.id !== currentCaseId &&
item.category === category
)
.slice(0, 3)
}
return {
casesList,
getCaseById,
getRelatedCases
}
})

+ 87
- 0
src/style.css View File

@ -0,0 +1,87 @@
:root {
font-family: 'Roboto', 'Open Sans', system-ui, Avenir, Helvetica, Arial, sans-serif;
line-height: 1.5;
font-weight: 400;
color-scheme: light dark;
color: #333333;
background-color: #ffffff;
font-synthesis: none;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
/* 自定义变量 */
:root {
--primary-color: #0066cc; /* 科技蓝 */
--secondary-color: #333333; /* 深灰 */
--accent-color: #00aaff; /* 亮色点缀 */
--background-color: #ffffff; /* 白色 */
--text-color: #333333; /* 文本颜色 */
}
/* 基础样式 */
body {
margin: 0;
padding: 0;
font-family: 'Roboto', 'Open Sans', sans-serif;
color: var(--text-color);
background-color: var(--background-color);
overflow-x: hidden; /* 防止水平滚动条 */
}
a {
color: var(--primary-color);
text-decoration: none;
transition: color 0.3s ease;
}
a:hover {
color: var(--accent-color);
}
/* 容器样式 */
.container {
width: 100%;
max-width: 1200px;
margin: 0 auto;
padding: 0 1rem;
}
/* 视差滚动相关样式 */
.parallax-container {
position: relative;
overflow: hidden;
height: 100vh;
}
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 120%;
background-size: cover;
background-position: center;
transform: translateZ(0);
will-change: transform;
}
/* 响应式设计 */
@media (max-width: 768px) {
.container {
padding: 0 1.5rem;
}
}
/* 动画过渡效果 */
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.5s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}

+ 84
- 0
src/utils/README.md View File

@ -0,0 +1,84 @@
# API请求工具使用说明
## 简介
本项目使用Axios封装了HTTP请求,并集中管理API接口,便于维护和使用。
## 文件结构
- `request.js`: Axios实例配置和请求/响应拦截器
- `api.js`: 集中管理所有API接口
## 使用方法
### 在组件中使用
```javascript
<script setup>
import { ref, onMounted } from 'vue'
import api from '@/utils/api'
// 定义响应式数据
const homeData = ref(null)
const loading = ref(false)
const error = ref(null)
// 获取首页数据
const fetchHomeData = async () => {
loading.value = true
error.value = null
try {
// 调用API
const res = await api.getHomeData()
homeData.value = res.data
} catch (err) {
error.value = err.message || '获取数据失败'
console.error('获取首页数据失败:', err)
} finally {
loading.value = false
}
}
// 页面加载时获取数据
onMounted(() => {
fetchHomeData()
})
</script>
```
### 添加新的API接口
在`api.js`文件中添加新的接口定义:
```javascript
// 在api对象中添加新接口
const api = {
// 现有接口...
// 新增接口
getNewData: (params) => get('/new-endpoint', params),
submitNewForm: (data) => post('/new-form', data),
}
```
### 自定义请求配置
所有请求方法都支持传入自定义配置:
```javascript
// 带自定义配置的请求
api.getCustomData = (params) => get('/custom', params, {
timeout: 5000,
headers: {
'Custom-Header': 'value'
}
})
```
## 注意事项
1. API基础URL通过环境变量`VITE_API_BASE_URL`配置
2. 默认已配置请求超时时间为15秒
3. 默认已配置token认证,会自动从localStorage获取token并添加到请求头
4. 响应拦截器会自动处理常见的HTTP错误状态码

+ 46
- 0
src/utils/api.js View File

@ -0,0 +1,46 @@
import { get, post, put, del } from './request'
// API接口管理
const api = {
// 示例接口
// 获取首页数据
getHomeData: () => get('/home'),
// 获取关于我们数据
getAboutData: () => get('/about'),
// 获取服务列表
getServices: () => get('/services'),
// 获取案例列表
getCases: (params) => get('/cases', params),
// 获取案例详情
getCaseDetail: (id) => get(`/cases/${id}`),
// 获取团队成员
getTeamMembers: () => get('/team'),
// 获取博客列表
getBlogs: (params) => get('/blogs', params),
// 获取博客详情
getBlogDetail: (id) => get(`/blogs/${id}`),
// 提交联系表单
submitContact: (data) => post('/contact', data),
// 用户相关接口
user: {
// 登录
login: (data) => post('/user/login', data),
// 注册
register: (data) => post('/user/register', data),
// 获取用户信息
getInfo: () => get('/user/info'),
// 更新用户信息
updateInfo: (data) => put('/user/info', data)
}
}
export default api

+ 112
- 0
src/utils/request.js View File

@ -0,0 +1,112 @@
import axios from 'axios'
// 创建axios实例
const service = axios.create({
// 设置基础URL,如果有环境变量可以使用环境变量
baseURL: import.meta.env.VITE_API_BASE_URL || '',
// 请求超时时间
timeout: 15000,
// 请求头设置
headers: {
'Content-Type': 'application/json;charset=utf-8'
}
})
// 请求拦截器
service.interceptors.request.use(
config => {
// 在发送请求之前做些什么
// 例如:可以在这里统一添加token
const token = localStorage.getItem('token')
if (token) {
config.headers['Authorization'] = `Bearer ${token}`
}
return config
},
error => {
// 对请求错误做些什么
console.error('请求错误:', error)
return Promise.reject(error)
}
)
// 响应拦截器
service.interceptors.response.use(
response => {
// 对响应数据做点什么
const res = response.data
// 根据自己的业务逻辑判断响应是否成功
// 这里假设后端返回的数据格式为 { code: 200, data: {}, message: '' }
if (res.code && res.code !== 200) {
// 处理业务错误
console.error('业务错误:', res.message || '未知错误')
return Promise.reject(new Error(res.message || '未知错误'))
}
return res
},
error => {
// 对响应错误做点什么
let message = '网络错误'
if (error.response) {
// 请求已发出,但服务器响应的状态码不在 2xx 范围内
switch (error.response.status) {
case 401:
message = '未授权,请重新登录'
// 可以在这里处理登出逻辑
break
case 403:
message = '拒绝访问'
break
case 404:
message = '请求的资源不存在'
break
case 500:
message = '服务器内部错误'
break
default:
message = `请求错误: ${error.response.status}`
}
} else if (error.request) {
// 请求已发出,但没有收到响应
message = '服务器未响应'
} else {
// 请求配置有误
message = error.message
}
console.error('响应错误:', message)
return Promise.reject(error)
}
)
// 封装GET请求
export function get(url, params, config = {}) {
return service.get(url, {
params,
...config
})
}
// 封装POST请求
export function post(url, data, config = {}) {
return service.post(url, data, config)
}
// 封装PUT请求
export function put(url, data, config = {}) {
return service.put(url, data, config)
}
// 封装DELETE请求
export function del(url, params, config = {}) {
return service.delete(url, {
params,
...config
})
}
// 导出axios实例
export default service

+ 200
- 0
src/views/blog/Blog.vue View File

@ -0,0 +1,200 @@
<script setup>
import { onMounted } from 'vue';
onMounted(() => {
//
});
</script>
<template>
<div class="blog-page">
<section class="page-header parallax-container">
<div class="parallax-bg"></div>
<div class="header-content">
<h1 data-aos="fade-up">博客</h1>
<p data-aos="fade-up" data-aos-delay="200">了解行业动态和技术趋势</p>
</div>
</section>
<section class="blog-content">
<div class="container">
<div class="blog-grid">
<div class="blog-card" data-aos="fade-up">
<div class="blog-image">
<img src="https://images.unsplash.com/photo-1486312338219-ce68d2c6f44d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80" alt="博客图片">
</div>
<div class="blog-info">
<div class="blog-meta">
<span class="date">2023-06-15</span>
<span class="category">技术</span>
</div>
<h2>人工智能在企业软件中的应用趋势</h2>
<p>随着人工智能技术的快速发展越来越多的企业开始将AI融入到自己的软件系统中...</p>
<a href="#" class="read-more">阅读更多</a>
</div>
</div>
<!-- 其他博客文章 -->
</div>
<div class="blog-sidebar" data-aos="fade-left">
<div class="sidebar-widget">
<h3>分类</h3>
<ul class="categories">
<li><a href="#">技术 (12)</a></li>
<li><a href="#">行业动态 (8)</a></li>
<li><a href="#">案例分析 (5)</a></li>
<li><a href="#">公司新闻 (3)</a></li>
</ul>
</div>
<div class="sidebar-widget">
<h3>热门文章</h3>
<ul class="popular-posts">
<li>
<a href="#">如何选择适合您企业的CRM系统</a>
<span class="post-date">2023-05-20</span>
</li>
<!-- 其他热门文章 -->
</ul>
</div>
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
.page-header {
height: 60vh;
position: relative;
overflow: hidden;
display: flex;
align-items: center;
justify-content: center;
color: white;
text-align: center;
}
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('https://images.unsplash.com/photo-1499750310107-5fef28a66643?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80');
background-size: cover;
background-position: center;
z-index: -1;
transform: translateZ(-5px) scale(1.5);
}
.blog-content {
padding: 80px 0;
background-color: $light-bg;
}
.container {
max-width: 1200px;
margin: 0 auto;
padding: 0 20px;
display: flex;
}
.blog-grid {
flex: 2;
display: grid;
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
gap: 30px;
}
.blog-sidebar {
flex: 1;
margin-left: 40px;
}
.blog-card {
background: white;
border-radius: 8px;
overflow: hidden;
box-shadow: $shadow-sm;
transition: transform 0.3s ease;
&:hover {
transform: translateY(-10px);
}
.blog-image img {
width: 100%;
height: 200px;
object-fit: cover;
}
.blog-info {
padding: 20px;
}
}
.blog-meta {
display: flex;
justify-content: space-between;
margin-bottom: 10px;
font-size: 14px;
color: $text-light;
}
.read-more {
display: inline-block;
margin-top: 15px;
color: $primary-color;
text-decoration: none;
font-weight: 500;
}
.sidebar-widget {
background: white;
padding: 20px;
border-radius: 8px;
margin-bottom: 30px;
box-shadow: $shadow-sm;
h3 {
margin-top: 0;
padding-bottom: 10px;
border-bottom: 1px solid #eee;
}
}
.categories, .popular-posts {
list-style: none;
padding: 0;
li {
padding: 10px 0;
border-bottom: 1px solid #eee;
&:last-child {
border-bottom: none;
}
}
a {
text-decoration: none;
color: $text-color;
transition: color 0.3s ease;
&:hover {
color: $primary-color;
}
}
}
.post-date {
display: block;
font-size: 12px;
color: $text-light;
margin-top: 5px;
}
</style>

+ 141
- 0
src/views/company/About.vue View File

@ -0,0 +1,141 @@
<script setup>
import { onMounted } from 'vue';
import PageHeader from '../../components/PageHeader.vue';
onMounted(() => {
//
});
</script>
<template>
<div class="about-page">
<PageHeader
title="关于我们"
subtitle="了解瀚海黎明的故事与使命"
backgroundImage="https://images.unsplash.com/photo-1522071820081-009f0129c71c?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
/>
<section class="company-intro">
<div class="container">
<div class="intro-content" data-aos="fade-up">
<h2>公司简介</h2>
<p>瀚海黎明成立于2020年是一家专注于为企业提供高质量软件开发外包服务的技术公司我们的团队由经验丰富的软件工程师设计师和项目经理组成致力于通过技术创新帮助企业实现数字化转型</p>
<p>多年来我们已成功为金融医疗教育零售等多个行业的客户提供了定制化的软件解决方案帮助他们提升运营效率降低成本增强市场竞争力</p>
</div>
</div>
</section>
<section class="company-history" data-aos="fade-up">
<div class="container">
<h2>发展历程</h2>
<div class="timeline" v-for="(item, index) in 5">
<div class="timeline-item" data-aos="fade-right">
<div class="year">2020</div>
<div class="event">
<h3>公司成立</h3>
<p>瀚海黎明在深圳正式成立开始提供软件开发服务</p>
</div>
</div>
</div>
</div>
</section>
<section class="company-culture" data-aos="fade-up">
<div class="container">
<h2>企业文化</h2>
<div class="culture-values">
<div class="value-item" data-aos="fade-up" data-aos-delay="100">
<div class="value-icon"><!-- 图标 --></div>
<h3>创新</h3>
<p>不断探索新技术为客户创造更大价值</p>
</div>
<!-- 其他价值观 -->
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 页面头部样式已移至PageHeader组件 */
.company-intro {
padding: 80px 0;
background-color: white;
}
.company-history {
padding: 80px 0;
background-color: $light-bg;
}
.timeline {
position: relative;
max-width: 800px;
margin: 40px auto 0;
padding: 20px 0;
&::before {
content: '';
position: absolute;
top: 0;
bottom: 0;
left: 50%;
width: 2px;
background: $primary-color;
transform: translateX(-50%);
}
.timeline-item {
position: relative;
margin-bottom: 50px;
display: flex;
align-items: center;
.year {
flex: 0 0 100px;
text-align: right;
font-size: 24px;
font-weight: bold;
color: $primary-color;
padding-right: 30px;
}
.event {
flex: 1;
background: white;
padding: 20px;
border-radius: 8px;
box-shadow: $shadow-sm;
margin-left: 30px;
}
}
}
.company-culture {
padding: 80px 0;
background-color: white;
.culture-values {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
gap: 30px;
margin-top: 40px;
.value-item {
text-align: center;
padding: 30px;
background: $light-bg;
border-radius: 8px;
transition: transform 0.3s ease;
&:hover {
transform: translateY(-10px);
}
}
}
}
</style>

+ 478
- 0
src/views/company/JobDetail.vue View File

@ -0,0 +1,478 @@
<script setup>
import { ref, onMounted } from 'vue';
import { useRoute } from 'vue-router';
import PageHeader from '../../components/PageHeader.vue';
//
const route = useRoute();
const jobId = route.params.id;
//
const jobDetail = ref(null);
//
const jobsData = [
{
id: 1,
title: '高级前端开发工程师',
description: '负责公司产品的前端架构设计和开发工作',
department: '技术部',
location: '上海',
type: '全职',
salary: '25k-35k',
responsibilities: [
'负责公司产品的前端架构设计和开发工作',
'参与产品需求分析和技术方案设计',
'编写高质量、可维护的前端代码',
'优化前端性能,提升用户体验',
'与后端开发团队协作,完成产品功能开发',
'指导初级工程师,进行代码审查'
],
requirements: [
'本科及以上学历,计算机相关专业',
'5年以上前端开发经验,熟悉Vue、React等主流框架',
'精通HTML5、CSS3、JavaScript等前端技术',
'熟悉前端工程化、模块化开发',
'具有良好的代码风格和编程习惯',
'有大型Web应用开发经验者优先',
'良好的沟通能力和团队协作精神'
],
benefits: [
'具有市场竞争力的薪资',
'五险一金、年终奖金',
'弹性工作时间',
'定期团队建设活动',
'职业发展培训机会',
'舒适的办公环境'
],
applicationProcess: [
'简历筛选',
'技术笔试',
'技术面试',
'HR面试',
'录用通知'
]
},
{
id: 2,
title: '后端开发工程师',
description: '负责服务端API开发和数据库设计',
department: '技术部',
location: '上海',
type: '全职',
salary: '20k-30k',
responsibilities: [
'负责服务端API开发和数据库设计',
'参与系统架构设计和技术选型',
'编写高质量、高性能的后端代码',
'优化系统性能,保证系统稳定性',
'与前端开发团队协作,完成产品功能开发'
],
requirements: [
'本科及以上学历,计算机相关专业',
'3年以上后端开发经验,熟悉Node.js、Java、Python等语言',
'熟悉关系型数据库和NoSQL数据库',
'了解常用设计模式和架构模式',
'具有良好的代码风格和编程习惯',
'有分布式系统开发经验者优先',
'良好的沟通能力和团队协作精神'
],
benefits: [
'具有市场竞争力的薪资',
'五险一金、年终奖金',
'弹性工作时间',
'定期团队建设活动',
'职业发展培训机会',
'舒适的办公环境'
],
applicationProcess: [
'简历筛选',
'技术笔试',
'技术面试',
'HR面试',
'录用通知'
]
},
{
id: 3,
title: '产品助理',
description: '协助产品经理进行需求分析和产品规划',
department: '产品部',
location: '上海',
type: '全职',
salary: '10k-15k',
responsibilities: [
'协助产品经理进行需求分析和产品规划',
'参与用户调研和竞品分析',
'编写产品需求文档和原型设计',
'跟进产品开发进度,协调各部门资源',
'收集用户反馈,提出产品优化建议'
],
requirements: [
'本科及以上学历,计算机或设计相关专业优先',
'1-3年产品相关工作经验',
'熟悉产品设计流程和方法',
'具备良好的沟通能力和团队协作精神',
'有较强的学习能力和执行力',
'熟悉原型设计工具如Axure、Sketch等'
],
benefits: [
'具有市场竞争力的薪资',
'五险一金、年终奖金',
'弹性工作时间',
'定期团队建设活动',
'职业发展培训机会',
'舒适的办公环境'
],
applicationProcess: [
'简历筛选',
'笔试测评',
'专业面试',
'HR面试',
'录用通知'
]
},
{
id: 4,
title: '市场营销专员',
description: '负责公司产品的市场推广和品牌建设',
department: '市场部',
location: '上海',
type: '全职',
salary: '8k-15k',
responsibilities: [
'负责公司产品的市场推广和品牌建设',
'策划并执行市场营销活动',
'管理社交媒体账号,提升品牌影响力',
'分析市场数据,优化营销策略',
'撰写营销文案和宣传材料'
],
requirements: [
'本科及以上学历,市场营销相关专业优先',
'1-3年市场营销相关工作经验',
'具备良好的文案写作能力和创意思维',
'熟悉各类社交媒体平台和营销工具',
'有较强的沟通能力和团队协作精神',
'有互联网产品营销经验者优先'
],
benefits: [
'具有市场竞争力的薪资',
'五险一金、年终奖金',
'弹性工作时间',
'定期团队建设活动',
'职业发展培训机会',
'舒适的办公环境'
],
applicationProcess: [
'简历筛选',
'笔试测评',
'专业面试',
'HR面试',
'录用通知'
]
}
];
//
const getJobDetail = () => {
// API
// 使
const job = jobsData.find(job => job.id === parseInt(jobId));
if (job) {
jobDetail.value = job;
} else {
// 404
console.error('职位不存在');
}
};
//
const applyForJob = () => {
alert('申请功能正在开发中,请稍后再试!');
};
onMounted(() => {
getJobDetail();
});
</script>
<template>
<div class="job-detail-page">
<PageHeader
title="职位详情"
subtitle="加入我们,共创未来"
backgroundImage="https://images.unsplash.com/photo-1521737852567-6949f3f9f2b5?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
/>
<section class="job-detail" v-if="jobDetail" data-aos="fade-up">
<div class="container">
<div class="job-header">
<h2>{{ jobDetail.title }}</h2>
<div class="job-meta">
<span><i class="fas fa-building"></i> {{ jobDetail.department }}</span>
<span><i class="fas fa-map-marker-alt"></i> {{ jobDetail.location }}</span>
<span><i class="fas fa-briefcase"></i> {{ jobDetail.type }}</span>
<span><i class="fas fa-money-bill-wave"></i> {{ jobDetail.salary }}</span>
</div>
</div>
<div class="job-content">
<div class="job-section">
<h3><i class="fas fa-tasks"></i> 工作职责</h3>
<ul>
<li v-for="(item, index) in jobDetail.responsibilities" :key="index">{{ item }}</li>
</ul>
</div>
<div class="job-section">
<h3><i class="fas fa-user-check"></i> 任职要求</h3>
<ul>
<li v-for="(item, index) in jobDetail.requirements" :key="index">{{ item }}</li>
</ul>
</div>
<div class="job-section">
<h3><i class="fas fa-gift"></i> 薪资福利</h3>
<ul>
<li v-for="(item, index) in jobDetail.benefits" :key="index">{{ item }}</li>
</ul>
</div>
<div class="job-section">
<h3><i class="fas fa-clipboard-list"></i> 申请流程</h3>
<div class="application-process">
<div class="process-step" v-for="(step, index) in jobDetail.applicationProcess" :key="index">
<div class="step-number">{{ index + 1 }}</div>
<div class="step-text">{{ step }}</div>
</div>
</div>
</div>
<div class="job-apply">
<button class="btn-primary" @click="applyForJob">立即申请</button>
</div>
</div>
</div>
</section>
<section class="not-found" v-else data-aos="fade-up">
<div class="container">
<h2>职位不存在</h2>
<p>抱歉您查找的职位不存在或已被删除</p>
<router-link to="/team" class="btn-primary">返回职位列表</router-link>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
.job-detail {
padding: 80px 0;
background-color: white;
.container {
max-width: 900px;
margin: 0 auto;
}
.job-header {
margin-bottom: 40px;
text-align: center;
h2 {
font-size: 2.5rem;
margin-bottom: 20px;
color: $primary-color;
}
.job-meta {
display: flex;
justify-content: center;
flex-wrap: wrap;
gap: 20px;
span {
display: flex;
align-items: center;
color: $text-light;
font-size: 1rem;
i {
margin-right: 8px;
color: $primary-color;
}
}
}
}
.job-content {
background-color: $light-bg;
border-radius: 8px;
padding: 40px;
box-shadow: $shadow-sm;
}
.job-section {
margin-bottom: 40px;
h3 {
font-size: 1.5rem;
margin-bottom: 20px;
color: $primary-color;
display: flex;
align-items: center;
i {
margin-right: 10px;
}
}
ul {
list-style-type: none;
padding-left: 0;
li {
position: relative;
padding-left: 25px;
margin-bottom: 12px;
line-height: 1.6;
&:before {
content: '✓';
position: absolute;
left: 0;
color: $primary-color;
font-weight: bold;
}
}
}
}
.application-process {
display: flex;
justify-content: space-between;
flex-wrap: wrap;
margin-top: 20px;
.process-step {
flex: 1;
min-width: 120px;
text-align: center;
padding: 0 10px;
position: relative;
margin-bottom: 30px;
&:not(:last-child):after {
content: '';
position: absolute;
top: 25px;
right: -10px;
width: 100%;
height: 2px;
background-color: $primary-color;
z-index: 0;
}
.step-number {
width: 50px;
height: 50px;
border-radius: 50%;
background-color: $primary-color;
color: white;
display: flex;
align-items: center;
justify-content: center;
font-size: 1.2rem;
font-weight: bold;
margin: 0 auto 15px;
position: relative;
z-index: 1;
}
.step-text {
font-size: 0.9rem;
}
}
}
.job-apply {
text-align: center;
margin-top: 40px;
.btn-primary {
padding: 12px 30px;
font-size: 1.1rem;
background-color: $primary-color;
color: white;
border: none;
border-radius: 4px;
cursor: pointer;
transition: background-color 0.3s ease;
&:hover {
background-color: darken($primary-color, 10%);
}
}
}
}
.not-found {
padding: 100px 0;
text-align: center;
h2 {
font-size: 2rem;
margin-bottom: 20px;
}
p {
margin-bottom: 30px;
color: $text-light;
}
.btn-primary {
display: inline-block;
padding: 12px 30px;
background-color: $primary-color;
color: white;
text-decoration: none;
border-radius: 4px;
transition: background-color 0.3s ease;
&:hover {
background-color: darken($primary-color, 10%);
}
}
}
@media (max-width: 768px) {
.job-detail {
.job-header {
.job-meta {
flex-direction: column;
align-items: center;
gap: 10px;
}
}
.job-content {
padding: 20px;
}
.application-process {
flex-direction: column;
.process-step {
margin-bottom: 20px;
&:not(:last-child):after {
display: none;
}
}
}
}
}
</style>

+ 300
- 0
src/views/company/Team.vue View File

@ -0,0 +1,300 @@
<script setup>
import { onMounted, ref } from 'vue';
import PageHeader from '../../components/PageHeader.vue';
//
const teamMembers = ref([
{
id: 1,
name: '张明',
position: '创始人 & CEO',
bio: '拥有15年软件开发和团队管理经验,曾在多家知名科技公司担任技术负责人',
photo: 'https://images.unsplash.com/photo-1507003211169-0a1dd7228f2d?ixlib=rb-1.2.1&auto=format&fit=crop&w=634&q=80',
social: [
{ type: 'linkedin', url: 'https://linkedin.com/' },
{ type: 'github', url: 'https://github.com/' },
{ type: 'twitter', url: 'https://twitter.com/' }
]
},
{
id: 2,
name: '李婷',
position: '技术总监',
bio: '计算机科学博士,专注于人工智能和大数据领域,拥有多项技术专利',
photo: 'https://images.unsplash.com/photo-1494790108377-be9c29b29330?ixlib=rb-1.2.1&auto=format&fit=crop&w=634&q=80',
social: [
{ type: 'linkedin', url: 'https://linkedin.com/' },
{ type: 'github', url: 'https://github.com/' }
]
},
{
id: 3,
name: '王强',
position: '产品经理',
bio: '10年产品设计和管理经验,擅长用户体验设计和产品策略规划',
photo: 'https://images.unsplash.com/photo-1472099645785-5658abf4ff4e?ixlib=rb-1.2.1&auto=format&fit=crop&w=634&q=80',
social: [
{ type: 'linkedin', url: 'https://linkedin.com/' },
{ type: 'twitter', url: 'https://twitter.com/' }
]
},
{
id: 4,
name: '陈静',
position: 'UI/UX设计师',
bio: '毕业于中央美术学院,曾参与多个国际设计奖项的评选,对用户体验有独到见解',
photo: 'https://images.unsplash.com/photo-1438761681033-6461ffad8d80?ixlib=rb-1.2.1&auto=format&fit=crop&w=634&q=80',
social: [
{ type: 'linkedin', url: 'https://linkedin.com/' },
{ type: 'dribbble', url: 'https://dribbble.com/' },
{ type: 'behance', url: 'https://www.behance.net/' }
]
}
]);
//
const culturePhotos = ref([
'https://images.unsplash.com/photo-1522202176988-66273c2fd55f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1556761175-4b46a572b786?ixlib=rb-1.2.1&auto=format&fit=crop&w=1267&q=80',
'https://images.unsplash.com/photo-1519389950473-47ba0277781c?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]);
//
const jobOpenings = ref([
{
id: 1,
title: '高级前端开发工程师',
description: '负责公司产品的前端架构设计和开发工作',
link: '/jobs/1'
},
{
id: 2,
title: '后端开发工程师',
description: '负责服务端API开发和数据库设计',
link: '/jobs/2'
},
{
id: 3,
title: '产品助理',
description: '协助产品经理进行需求分析和产品规划',
link: '/jobs/3'
},
{
id: 4,
title: '市场营销专员',
description: '负责公司产品的市场推广和品牌建设',
link: '/jobs/4'
}
]);
</script>
<template>
<div class="team-page">
<PageHeader
title="我们的团队"
subtitle="认识瀚海黎明背后的专业人才"
backgroundImage="https://images.unsplash.com/photo-1522071901873-411886a10004?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
/>
<section class="team-members">
<div class="container">
<h2 data-aos="fade-up">核心团队</h2>
<div class="members-grid">
<div
v-for="member in teamMembers"
:key="member.id"
class="member-card"
data-aos="fade-up"
:data-aos-delay="100 + (member.id - 1) * 100"
>
<div class="member-photo">
<img :src="member.photo" :alt="member.name">
</div>
<div class="member-info">
<h3>{{ member.name }}</h3>
<p class="position">{{ member.position }}</p>
<p class="bio">{{ member.bio }}</p>
<div class="social-links">
<a
v-for="(social, index) in member.social"
:key="index"
:href="social.url"
target="_blank"
rel="noopener noreferrer"
>
<i :class="`fab fa-${social.type}`"></i>
</a>
</div>
</div>
</div>
</div>
</div>
</section>
<section class="team-culture" data-aos="fade-up">
<div class="container">
<h2>团队文化</h2>
<div class="culture-content">
<p>我们相信优秀的团队文化是公司成功的基石在瀚海黎明我们倡导开放协作创新的工作环境鼓励每位团队成员充分发挥自己的才能和创造力</p>
<div class="culture-photos">
<div
v-for="(photo, index) in culturePhotos"
:key="index"
class="culture-photo"
data-aos="zoom-in"
:data-aos-delay="index * 100"
>
<img :src="photo" alt="团队活动照片">
</div>
</div>
</div>
</div>
</section>
<section class="join-us" data-aos="fade-up">
<div class="container">
<h2>加入我们</h2>
<p>我们始终在寻找优秀的人才加入团队如果你热爱技术追求卓越欢迎加入瀚海黎明</p>
<div class="job-openings">
<div
v-for="(job, index) in jobOpenings"
:key="index"
class="job-card"
data-aos="fade-up"
:data-aos-delay="100 + index * 100"
>
<h3>{{ job.title }}</h3>
<p>{{ job.description }}</p>
<router-link :to="job.link" class="btn-apply">查看详情</router-link>
</div>
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 页面头部样式已移至PageHeader组件 */
.team-members {
padding: 80px 0;
background-color: white;
}
.members-grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
gap: 40px;
margin-top: 50px;
}
.member-card {
background: white;
border-radius: 8px;
overflow: hidden;
box-shadow: $shadow-sm;
transition: transform 0.3s ease;
&:hover {
transform: translateY(-10px);
}
.member-photo img {
width: 100%;
height: 300px;
object-fit: cover;
}
.member-info {
padding: 20px;
}
}
.position {
color: $primary-color;
font-weight: 500;
margin-bottom: 10px;
}
.social-links {
display: flex;
gap: 15px;
margin-top: 15px;
a {
color: $text-light;
font-size: 18px;
transition: color 0.3s ease;
&:hover {
color: $primary-color;
}
}
}
.team-culture {
padding: 80px 0;
background-color: $light-bg;
.culture-photos {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 20px;
margin-top: 30px;
.culture-photo {
border-radius: 8px;
overflow: hidden;
box-shadow: $shadow-sm;
height: 200px;
img {
width: 100%;
height: 100%;
object-fit: cover;
transition: transform 0.5s ease;
&:hover {
transform: scale(1.05);
}
}
}
}
}
.join-us {
padding: 80px 0;
background-color: white;
.job-openings {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
gap: 30px;
margin-top: 40px;
.job-card {
padding: 30px;
background: $light-bg;
border-radius: 8px;
transition: transform 0.3s ease, box-shadow 0.3s ease;
&:hover {
transform: translateY(-5px);
box-shadow: $shadow-lg;
}
}
}
}
.btn-apply {
display: inline-block;
margin-top: 15px;
color: $primary-color;
text-decoration: none;
font-weight: 500;
}
</style>

+ 700
- 0
src/views/pages/CaseDetail.vue View File

@ -0,0 +1,700 @@
<script setup>
import { ref, onMounted, computed } from 'vue';
import { useRoute, useRouter } from 'vue-router';
import PageHeader from '../../components/PageHeader.vue';
import caseList from '../../components/case/caseList.vue';
//
const route = useRoute();
const router = useRouter();
// ID
const caseId = computed(() => Number(route.params.id));
// (API)
const casesList = ref([
{
id: 1,
title: '企业资源管理系统',
description: '为某制造企业开发的一套完整ERP系统,实现了生产、销售、库存等全流程管理',
image: 'https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统',
client: '某制造业集团',
completionDate: '2023年6月',
services: ['系统架构设计', '数据库优化', '前端开发', '后端开发', '系统集成'],
challenge: '客户面临的主要挑战是多个业务系统之间数据孤岛问题,导致信息流通不畅,管理效率低下。同时,随着业务规模扩大,原有系统已无法满足日益增长的业务需求。',
solution: '我们为客户设计并实现了一套全面的企业资源管理系统,整合了生产、销售、采购、库存、财务等多个模块。系统采用微服务架构,确保了各模块之间的松耦合与高内聚,同时保证了系统的可扩展性和稳定性。我们还为客户定制了数据分析和决策支持功能,帮助管理层快速获取业务洞察。',
results: '系统上线后,客户的运营效率提升了35%,信息处理时间缩短了60%,库存周转率提高了25%,大幅降低了运营成本。同时,实时的数据分析功能帮助客户更快速地响应市场变化,提升了企业的竞争力。',
testimonial: '微隐软件工作室的团队展现了卓越的专业能力和服务态度。他们不仅理解我们的业务需求,还能提供创新的技术解决方案。新系统极大地提升了我们的运营效率,是我们数字化转型的重要一步。',
testimonialAuthor: '张总 - 客户CIO',
gallery: [
'https://images.unsplash.com/photo-1454165804606-c3d57bc86b40?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551434678-e076c223a692?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 2,
title: '电商平台重构',
description: '帮助某电商企业重构其线上平台,提升用户体验和系统性能,实现销售额提升30%',
image: 'https://images.unsplash.com/photo-1556742049-0cfed4f6a45d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用',
client: '某知名电商企业',
completionDate: '2023年9月',
services: ['用户体验设计', '前端重构', '后端优化', '性能调优', '安全加固'],
challenge: '客户的电商平台面临用户体验不佳、系统响应缓慢、移动端适配不足等问题,导致用户流失和转化率下降。同时,随着业务量增长,系统稳定性也面临挑战。',
solution: '我们对客户的电商平台进行了全面重构,采用了现代化的前端框架和响应式设计,优化了用户界面和交互流程。在后端,我们重构了核心服务,引入了微服务架构和缓存机制,提升了系统性能和可扩展性。同时,我们还加强了系统的安全性,实现了全面的HTTPS和数据加密。',
results: '重构后的平台页面加载速度提升了65%,用户停留时间增加了40%,转化率提高了25%,最终带来了30%的销售额增长。系统的稳定性也得到了显著提升,即使在促销高峰期也能保持良好的性能。',
testimonial: '微隐软件工作室的团队展现了卓越的技术实力和创新思维。他们不仅解决了我们平台的技术问题,还从用户体验和业务角度提供了宝贵建议。重构后的平台获得了用户的一致好评,为我们带来了实质性的业务增长。',
testimonialAuthor: '李总 - 客户产品总监',
gallery: [
'https://images.unsplash.com/photo-1556740758-90de374c12ad?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1556740772-1a741d976155?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1556761175-129418cb2dfe?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 3,
title: '医疗服务APP',
description: '为连锁医疗机构开发的患者服务APP,实现在线挂号、问诊和健康管理等功能',
image: 'https://images.unsplash.com/photo-1576091160550-2173dba999ef?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '移动应用',
client: '某连锁医疗机构',
completionDate: '2023年12月',
services: ['移动应用开发', 'UI/UX设计', '后端API开发', '数据安全', '系统集成'],
challenge: '客户希望通过数字化手段提升患者服务体验,减少排队等待时间,同时提高医疗资源利用效率。传统的线下预约和就诊流程繁琐,患者满意度不高。',
solution: '我们为客户开发了一款功能全面的医疗服务APP,支持在线挂号、远程问诊、检查报告查询、健康档案管理等功能。APP采用了直观的用户界面和流畅的交互设计,确保各年龄段用户都能轻松使用。在技术层面,我们实现了与医院HIS系统的无缝集成,并采用了严格的数据加密和隐私保护措施。',
results: 'APP上线后,患者预约效率提升了80%,平均等待时间减少了65%,患者满意度提高了45%。同时,医生的工作效率也得到了提升,资源利用率增加了30%。APP已成为客户数字化医疗服务的核心平台。',
testimonial: '微隐软件工作室深入理解了医疗行业的特殊需求,为我们打造了一款既专业又易用的医疗服务APP。他们在确保数据安全和系统稳定性方面表现出色,为我们的患者提供了便捷、高效的服务体验。',
testimonialAuthor: '王院长 - 客户医疗总监',
gallery: [
'https://images.unsplash.com/photo-1576091160399-112ba8d25d1d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1579684385127-1ef15d508118?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1583324113626-70df0f4deaab?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 4,
title: '金融数据可视化平台',
description: '为金融机构开发的数据分析和可视化平台,帮助决策者快速洞察市场趋势',
image: 'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用',
client: '某投资管理公司',
completionDate: '2024年2月',
services: ['数据分析', '可视化设计', '前端开发', 'API集成', '实时数据处理'],
challenge: '客户需要一个能够整合多源金融数据,并提供直观、实时的可视化分析工具,帮助投资分析师和决策者快速识别市场趋势和投资机会。',
solution: '我们为客户开发了一个功能强大的金融数据可视化平台,整合了市场数据、公司财报、宏观经济指标等多种数据源。平台提供了丰富的图表类型和分析工具,支持自定义仪表盘和报告。我们采用了高性能的前端渲染技术和实时数据处理架构,确保了大数据量下的流畅体验。',
results: '平台上线后,客户的数据分析效率提升了70%,决策周期缩短了50%,投资组合表现超过了基准指数15%。平台的预测模型准确率达到了85%,为客户提供了显著的竞争优势。',
testimonial: '微隐软件工作室交付的数据可视化平台超出了我们的预期。他们不仅具备出色的技术能力,还展现了对金融行业的深刻理解。平台直观的界面和强大的分析功能极大地提升了我们的决策效率和准确性。',
testimonialAuthor: '赵总 - 客户投资总监',
gallery: [
'https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1590283603385-17ffb3a7f29f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 5,
title: '智慧校园系统',
description: '为教育机构打造的一体化校园管理系统,涵盖教学、行政、学生服务等多个模块',
image: 'https://images.unsplash.com/photo-1523240795612-9a054b0db644?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统',
client: '某知名高校',
completionDate: '2023年8月',
services: ['系统规划', '软件开发', '数据迁移', '用户培训', '持续支持'],
challenge: '客户面临的挑战是多个独立系统并行运行,数据不一致,管理效率低下。学生和教职工需要在多个系统间切换,用户体验不佳。',
solution: '我们为客户设计并实现了一套集成化的智慧校园系统,整合了教务管理、学生服务、行政办公、资源管理等多个模块。系统采用了统一的用户界面和数据标准,实现了单点登录和数据共享。我们还开发了移动端应用,方便师生随时随地访问系统功能。',
results: '系统上线后,管理效率提升了50%,数据处理错误减少了80%,用户满意度提高了60%。系统的自助服务功能减轻了行政人员的工作负担,让他们能够专注于更有价值的任务。',
testimonial: '微隐软件工作室的团队展现了卓越的项目管理和技术能力。他们深入理解了我们复杂的业务需求,并提供了一套既全面又易用的解决方案。新系统极大地改善了我们的管理效率和服务质量。',
testimonialAuthor: '陈校长 - 客户负责人',
gallery: [
'https://images.unsplash.com/photo-1523050854058-8df90110c9f1?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1562774053-701939374585?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1577896851231-70ef18881754?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
},
{
id: 6,
title: '品牌官网设计',
description: '为高端品牌设计的响应式官方网站,展现品牌形象并提升用户转化率',
image: 'https://images.unsplash.com/photo-1561070791-2526d30994b5?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'UI/UX设计',
client: '某高端消费品牌',
completionDate: '2024年1月',
services: ['品牌策略', 'UI/UX设计', '前端开发', 'CMS实现', 'SEO优化'],
challenge: '客户的原有网站设计过时,无法有效展现品牌高端形象,且缺乏移动端适配,导致用户体验不佳和转化率低下。',
solution: '我们为客户重新设计了品牌官网,采用了现代简约的设计风格,突出品牌的高端定位。网站采用了响应式设计,确保在各种设备上都能提供出色的用户体验。我们还优化了产品展示和购买流程,降低了用户转化的摩擦。在技术层面,我们实现了高性能的前端架构和易用的内容管理系统。',
results: '新网站上线后,用户停留时间增加了45%,页面跳出率降低了30%,转化率提升了35%。网站的加载速度提高了60%,搜索引擎排名也有显著提升。客户的品牌形象得到了有效提升,线上销售额增长了40%。',
testimonial: '微隐软件工作室的设计团队展现了卓越的创意和专业能力。他们不仅理解我们的品牌价值,还能将其完美地转化为视觉设计。新网站获得了客户和合作伙伴的一致好评,成为了我们品牌传播的重要窗口。',
testimonialAuthor: '林总 - 客户市场总监',
gallery: [
'https://images.unsplash.com/photo-1542744094-3a31f272c490?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1542744173-8659239e9452?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
'https://images.unsplash.com/photo-1542744173-05336fcc7ad4?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80'
]
}
]);
//
const currentCase = computed(() => {
return casesList.value.find(item => item.id === caseId.value) || null;
});
//
const relatedCases = computed(() => {
if (!currentCase.value) return [];
return casesList.value
.filter(item =>
item.id !== currentCase.value.id &&
item.category === currentCase.value.category
)
.slice(0, 3);
});
//
const goBackToList = () => {
router.push('/cases');
};
//
const viewRelatedCase = (id) => {
router.push(`/cases/${id}`);
};
onMounted(() => {
//
if (!currentCase.value) {
router.push('/cases');
}
//
window.scrollTo({
top: 0,
behavior: 'smooth'
});
});
</script>
<template>
<div v-if="currentCase" class="case-detail-page">
<!-- 页面头部 -->
<PageHeader :title="currentCase.title" :subtitle="currentCase.description" :backgroundImage="currentCase.image"
height="70vh">
<template #header-cta>
<div class="header-cta" data-aos="fade-up" data-aos-delay="400">
<button @click="goBackToList" class="btn-outline">
<i class="fas fa-arrow-left"></i> 返回案例列表
</button>
</div>
</template>
</PageHeader>
<!-- 案例概览 -->
<section class="case-overview">
<div class="container">
<div class="overview-grid">
<div class="overview-item" data-aos="fade-up">
<h4>客户</h4>
<p>{{ currentCase.client }}</p>
</div>
<div class="overview-item" data-aos="fade-up" data-aos-delay="100">
<h4>类别</h4>
<p>{{ currentCase.category }}</p>
</div>
<div class="overview-item" data-aos="fade-up" data-aos-delay="200">
<h4>完成时间</h4>
<p>{{ currentCase.completionDate }}</p>
</div>
<div class="overview-item services" data-aos="fade-up" data-aos-delay="300">
<h4>服务内容</h4>
<div class="services-list">
<span v-for="(service, index) in currentCase.services" :key="index" class="service-tag">
{{ service }}
</span>
</div>
</div>
</div>
</div>
</section>
<!-- 案例详情 -->
<section class="case-content">
<div class="container">
<div class="content-grid">
<div class="content-main">
<div class="content-section" data-aos="fade-up">
<h3>项目挑战</h3>
<p>{{ currentCase.challenge }}</p>
</div>
<div class="content-section" data-aos="fade-up">
<h3>解决方案</h3>
<p>{{ currentCase.solution }}</p>
</div>
<div class="content-section" data-aos="fade-up">
<h3>项目成果</h3>
<p>{{ currentCase.results }}</p>
</div>
</div>
<div class="content-sidebar">
<div class="testimonial" data-aos="fade-left">
<div class="quote-icon">
<i class="fas fa-quote-left"></i>
</div>
<blockquote>
{{ currentCase.testimonial }}
</blockquote>
<div class="testimonial-author-wrapper">
<div class="testimonial-avatar">
<i class="fas fa-user"></i>
</div>
<div class="testimonial-author">
{{ currentCase.testimonialAuthor }}
</div>
</div>
</div>
</div>
</div>
</div>
</section>
<!-- 项目图库 -->
<section class="case-gallery">
<div class="container">
<h2 class="section-title" data-aos="fade-up">项目展示</h2>
<div class="gallery-grid">
<div v-for="(image, index) in currentCase.gallery" :key="index" class="gallery-item"
data-aos="fade-up" :data-aos-delay="index * 100">
<img :src="image" :alt="`${currentCase.title} - 图片 ${index + 1}`">
</div>
</div>
</div>
</section>
<!-- 相关案例 -->
<section class="related-cases" v-if="relatedCases.length > 0">
<div class="container">
<h2 class="section-title" data-aos="fade-up">相关案例</h2>
<caseList :cases="relatedCases" />
</div>
</section>
<!-- CTA部分 -->
<section class="cta-section" data-aos="fade-up">
<div class="container">
<div class="cta-content">
<div class="cta-icon" data-aos="zoom-in" data-aos-delay="200">
<i class="fas fa-lightbulb"></i>
</div>
<h2 data-aos="fade-up" data-aos-delay="300">有类似的项目需求</h2>
<p data-aos="fade-up" data-aos-delay="400">我们的团队随时准备为您提供专业的技术支持和服务</p>
<div class="cta-buttons" data-aos="fade-up" data-aos-delay="500">
<a href="/contact" class="btn-primary">立即咨询 <i class="fas fa-arrow-right"></i></a>
<button @click="goBackToList" class="btn-outline">浏览更多案例</button>
</div>
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 页面头部样式 */
.header-cta {
display: flex;
justify-content: center;
margin-top: 30px;
}
.btn-outline {
display: inline-flex;
align-items: center;
gap: 8px;
padding: 12px 25px;
background: transparent;
color: white;
border: 2px solid white;
border-radius: 30px;
font-weight: 500;
text-decoration: none;
transition: all 0.3s ease;
cursor: pointer;
&:hover {
background: rgba(255, 255, 255, 0.1);
transform: translateY(-3px);
}
}
/* 案例概览样式 */
.case-overview {
padding: 60px 0;
background-color: $light-bg;
}
.overview-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 30px;
}
.overview-item {
h4 {
font-size: 1.1rem;
color: $text-color;
margin-bottom: 10px;
font-weight: 600;
}
p {
color: $text-light;
font-size: 1rem;
}
&.services {
grid-column: 1 / -1;
}
}
.services-list {
display: flex;
flex-wrap: wrap;
gap: 10px;
}
.service-tag {
display: inline-block;
padding: 6px 15px;
background: white;
border-radius: 20px;
font-size: 0.9rem;
color: $text-color;
box-shadow: $shadow-sm;
}
/* 案例内容样式 */
.case-content {
padding: 80px 0;
background-color: white;
}
.content-grid {
display: grid;
grid-template-columns: 2fr 1fr;
gap: 50px;
@media (max-width: 768px) {
grid-template-columns: 1fr;
}
}
.content-section {
margin-bottom: 40px;
h3 {
font-size: 1.8rem;
color: $text-color;
margin-bottom: 20px;
position: relative;
padding-bottom: 15px;
&:after {
content: '';
position: absolute;
bottom: 0;
left: 0;
width: 60px;
height: 3px;
background: $primary-color;
}
}
p {
color: $text-light;
line-height: 1.8;
font-size: 1.05rem;
}
}
.testimonial {
background: white;
padding: 40px 30px 30px;
border-radius: 12px;
position: relative;
box-shadow: $shadow-lg;
border-left: 4px solid $primary-color;
transition: transform 0.3s ease, box-shadow 0.3s ease;
margin-top: 25px;
@media (max-width: 768px) {
padding: 35px 25px 25px;
margin-top: 40px;
}
&:hover {
transform: translateY(-5px);
box-shadow: $shadow-xl;
}
blockquote {
font-style: italic;
line-height: 1.8;
font-size: 1.1rem;
color: $text-color;
margin: 0 0 20px 0;
position: relative;
z-index: 1;
@media (max-width: 768px) {
font-size: 1rem;
}
}
&::before {
content: '"';
position: absolute;
top: 10px;
right: 20px;
font-size: 120px;
color: rgba($primary-color, 0.05);
font-family: serif;
line-height: 1;
z-index: 0;
@media (max-width: 768px) {
font-size: 100px;
top: 5px;
right: 15px;
}
}
.testimonial-author-wrapper {
margin-top: 15px;
padding-top: 15px;
border-top: 1px solid rgba($text-light, 0.1);
position: relative;
z-index: 1;
display: flex;
align-items: center;
}
.testimonial-avatar {
width: 40px;
height: 40px;
border-radius: 50%;
background-color: rgba($primary-color, 0.1);
display: flex;
align-items: center;
justify-content: center;
margin-right: 12px;
i {
color: $primary-color;
font-size: 1.2rem;
}
}
.testimonial-author {
font-weight: 600;
color: $primary-color;
font-size: 1rem;
line-height: 1.4;
}
}
.quote-icon {
position: absolute;
top: -20px;
left: 20px;
width: 40px;
height: 40px;
background: $primary-color;
border-radius: 50%;
display: flex;
align-items: center;
justify-content: center;
box-shadow: 0 4px 10px rgba(0, 0, 0, 0.15);
i {
color: white;
font-size: 1.2rem;
}
}
/* 相关案例样式 */
.related-cases {
padding: 80px 0;
background-color: $light-bg;
}
.section-title {
text-align: center;
margin-bottom: 50px;
font-size: 2.2rem;
color: $text-color;
position: relative;
padding-bottom: 15px;
&:after {
content: '';
position: absolute;
bottom: 0;
left: 50%;
transform: translateX(-50%);
width: 80px;
height: 3px;
background: $primary-color;
}
}
/* CTA部分样式 */
.cta-section {
background: linear-gradient(135deg, $primary-color, $secondary-color);
background-size: 200% 200%;
color: white;
padding: 80px 0;
text-align: center;
margin-top: 40px;
position: relative;
overflow: hidden;
box-shadow: 0 -10px 30px rgba(0, 0, 0, 0.1);
animation: gradientBG 15s ease infinite;
}
@keyframes gradientBG {
0% {
background-position: 0% 50%;
}
50% {
background-position: 100% 50%;
}
100% {
background-position: 0% 50%;
}
}
.cta-section::before {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('data:image/svg+xml;charset=utf8,%3Csvg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1440 320"%3E%3Cpath fill="%23ffffff" fill-opacity="0.05" d="M0,96L48,112C96,128,192,160,288,186.7C384,213,480,235,576,213.3C672,192,768,128,864,128C960,128,1056,192,1152,213.3C1248,235,1344,213,1392,202.7L1440,192L1440,320L1392,320C1344,320,1248,320,1152,320C1056,320,960,320,864,320C768,320,672,320,576,320C480,320,384,320,288,320C192,320,96,320,48,320L0,320Z"%3E%3C/path%3E%3C/svg%3E');
background-size: cover;
background-position: center;
opacity: 0.1;
z-index: 0;
}
.cta-content {
position: relative;
z-index: 1;
}
.cta-icon {
margin-bottom: 25px;
i {
font-size: 3.5rem;
color: #fff;
background: rgba(255, 255, 255, 0.1);
width: 100px;
height: 100px;
line-height: 100px;
border-radius: 50%;
display: inline-block;
box-shadow: 0 10px 20px rgba(0, 0, 0, 0.1);
transition: all 0.3s ease;
&:hover {
transform: translateY(-5px) scale(1.05);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.2);
background: rgba(255, 255, 255, 0.2);
}
}
}
.cta-content h2 {
font-size: 2.5rem;
margin-bottom: 20px;
font-weight: 700;
text-shadow: 0 2px 10px rgba(0, 0, 0, 0.2);
color: #fff;
}
.cta-content p {
font-size: 1.2rem;
opacity: 0.9;
max-width: 600px;
margin: 0 auto 30px;
line-height: 1.6;
}
.cta-buttons {
display: flex;
justify-content: center;
gap: 20px;
margin-top: 30px;
@media (max-width: 576px) {
flex-direction: column;
align-items: center;
}
.btn-primary {
padding: 14px 32px;
font-size: 1.1rem;
font-weight: 600;
background-color: #fff;
color: $primary-color;
border: none;
border-radius: 30px;
box-shadow: 0 8px 15px rgba(0, 0, 0, 0.2);
transition: all 0.3s ease;
display: inline-flex;
align-items: center;
text-decoration: none;
i {
margin-left: 8px;
transition: transform 0.3s ease;
}
&:hover {
transform: translateY(-3px);
box-shadow: 0 12px 20px rgba(0, 0, 0, 0.3);
i {
transform: translateX(5px);
}
}
}
.btn-outline {
background: transparent;
color: white;
border: 2px solid rgba(255, 255, 255, 0.6);
padding: 14px 32px;
font-size: 1.1rem;
font-weight: 600;
border-radius: 30px;
transition: all 0.3s ease;
&:hover {
background: rgba(255, 255, 255, 0.1);
border-color: white;
transform: translateY(-3px);
}
}
}
</style>

+ 635
- 0
src/views/pages/Cases.vue View File

@ -0,0 +1,635 @@
<script setup>
import { ref, onMounted } from 'vue';
import { useRouter } from 'vue-router';
import PageHeader from '../../components/PageHeader.vue';
//
const casesList = ref([
{
id: 1,
title: '企业资源管理系统',
description: '为某制造企业开发的一套完整ERP系统,实现了生产、销售、库存等全流程管理',
image: 'https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统'
},
{
id: 2,
title: '电商平台重构',
description: '帮助某电商企业重构其线上平台,提升用户体验和系统性能,实现销售额提升30%',
image: 'https://images.unsplash.com/photo-1556742049-0cfed4f6a45d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用'
},
{
id: 3,
title: '医疗服务APP',
description: '为连锁医疗机构开发的患者服务APP,实现在线挂号、问诊和健康管理等功能',
image: 'https://images.unsplash.com/photo-1576091160550-2173dba999ef?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '移动应用'
},
{
id: 4,
title: '金融数据可视化平台',
description: '为金融机构开发的数据分析和可视化平台,帮助决策者快速洞察市场趋势',
image: 'https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'Web应用'
},
{
id: 5,
title: '智慧校园系统',
description: '为教育机构打造的一体化校园管理系统,涵盖教学、行政、学生服务等多个模块',
image: 'https://images.unsplash.com/photo-1523240795612-9a054b0db644?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: '企业系统'
},
{
id: 6,
title: '品牌官网设计',
description: '为高端品牌设计的响应式官方网站,展现品牌形象并提升用户转化率',
image: 'https://images.unsplash.com/photo-1561070791-2526d30994b5?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80',
category: 'UI/UX设计'
}
]);
//
const currentFilter = ref('全部');
//
const filteredCases = ref([]);
//
const categories = ['全部', 'Web应用', '移动应用', '企业系统', 'UI/UX设计'];
//
const filterCases = (category) => {
currentFilter.value = category;
if (category === '全部') {
filteredCases.value = casesList.value;
} else {
filteredCases.value = casesList.value.filter(item => item.category === category);
}
};
//
const router = useRouter();
//
const viewCaseDetails = (id) => {
//
router.push(`/cases/${id}`);
};
onMounted(() => {
//
filterCases('全部');
});
</script>
<template>
<div class="cases-page">
<PageHeader
title="成功案例"
subtitle="我们为各行业客户提供的优质解决方案"
backgroundImage="https://images.unsplash.com/photo-1504384308090-c894fdcc538d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
height="70vh"
>
<template #header-cta>
<div class="header-cta" data-aos="fade-up" data-aos-delay="400">
<a href="#cases-grid" class="btn-primary">浏览案例</a>
<a href="/contact" class="btn-outline">联系我们</a>
</div>
</template>
</PageHeader>
<section class="cases-filter">
<div class="container">
<div class="section-header" data-aos="fade-up">
<h2>我们的项目</h2>
<p>浏览我们为不同行业客户提供的解决方案</p>
</div>
<div class="filter-buttons" data-aos="fade-up">
<button
v-for="category in categories"
:key="category"
:class="['filter-btn', currentFilter === category ? 'active' : '']"
@click="filterCases(category)"
>
{{ category }}
</button>
</div>
</div>
</section>
<section id="cases-grid" class="cases-grid">
<div class="container">
<div class="grid">
<div
v-for="caseItem in filteredCases"
:key="caseItem.id"
class="case-card"
data-aos="fade-up"
>
<div class="case-image">
<div class="category-tag">{{ caseItem.category }}</div>
<img :src="caseItem.image" :alt="caseItem.title">
</div>
<div class="case-content">
<h3>{{ caseItem.title }}</h3>
<p>{{ caseItem.description }}</p>
<button @click="viewCaseDetails(caseItem.id)" class="btn-details">查看详情</button>
</div>
</div>
</div>
<div v-if="filteredCases.length === 0" class="no-results" data-aos="fade-up">
<div class="empty-state">
<i class="empty-icon"></i>
<h3>暂无相关案例</h3>
<p>请尝试选择其他类别查看</p>
</div>
</div>
</div>
</section>
<section class="cta-section" data-aos="fade-up">
<div class="container">
<div class="cta-content">
<div class="cta-icon" data-aos="zoom-in" data-aos-delay="200">
<i class="fas fa-rocket"></i>
</div>
<h2 data-aos="fade-up" data-aos-delay="300">准备好开始您的项目了吗</h2>
<p data-aos="fade-up" data-aos-delay="400">我们的团队随时准备为您提供专业的技术支持和服务</p>
<div class="cta-buttons" data-aos="fade-up" data-aos-delay="500">
<a href="/contact" class="btn-primary">立即咨询 <i class="fas fa-arrow-right"></i></a>
<a href="tel:+8612345678901" class="btn-outline">电话联系</a>
</div>
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 页面头部样式 */
.page-header {
height: 70vh;
position: relative;
overflow: hidden;
display: flex;
align-items: center;
color: white;
text-align: center;
perspective: 1000px;
}
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('https://images.unsplash.com/photo-1504384308090-c894fdcc538d?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80');
background-size: cover;
background-position: center;
z-index: -1;
transform: translateZ(-5px) scale(1.5);
filter: brightness(0.9) contrast(1.1);
}
.overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to right, rgba(0,0,0,0.7), rgba(0,0,0,0.4));
z-index: -1;
}
.breadcrumb {
position: absolute;
top: 30px;
left: 30px;
padding: 10px 0;
font-size: 14px;
a {
color: #fff;
text-decoration: none;
transition: color 0.3s ease;
&:hover {
color: $primary-color;
}
}
}
.header-content {
max-width: 800px;
margin: 0 auto;
padding: 0 20px;
}
.header-content {
h1 {
font-size: 3.5rem;
font-weight: 700;
margin-bottom: 20px;
text-shadow: 0 2px 10px rgba(0,0,0,0.3);
}
p {
font-size: 1.2rem;
margin-bottom: 30px;
opacity: 0.9;
}
}
.header-cta {
display: flex;
justify-content: center;
gap: 15px;
margin-top: 30px;
}
.btn-primary, .btn-outline {
display: inline-block;
padding: 12px 30px;
border-radius: 30px;
font-weight: 500;
text-decoration: none;
transition: all 0.3s ease;
}
.btn-primary {
background: $primary-color;
color: white;
border: 2px solid $primary-color;
&:hover {
background: $secondary-color;
border-color: $secondary-color;
transform: translateY(-3px);
}
}
.btn-outline {
background: transparent;
color: white;
border: 2px solid white;
&:hover {
background: rgba(255,255,255,0.1);
transform: translateY(-3px);
}
}
/* 筛选部分样式 */
.cases-filter {
padding: 60px 0 40px;
background-color: $light-bg;
}
.section-header {
text-align: center;
margin-bottom: 30px;
h2 {
font-size: 2.2rem;
color: $text-color;
margin-bottom: 15px;
}
p {
color: $text-light;
max-width: 600px;
margin: 0 auto;
}
}
.filter-buttons {
display: flex;
justify-content: center;
flex-wrap: wrap;
gap: 15px;
margin-top: 20px;
.filter-btn {
padding: 10px 25px;
background: white;
border: 1px solid #ddd;
border-radius: 30px;
cursor: pointer;
transition: all 0.3s ease;
font-size: 15px;
&.active,
&:hover {
background: $primary-color;
color: white;
border-color: $primary-color;
box-shadow: 0 5px 15px rgba($primary-color, 0.2);
}
}
}
/* 案例网格样式 */
.cases-grid {
padding: 60px 0;
background-color: #fff;
.grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(350px, 1fr));
gap: 30px;
}
}
.case-card {
border-radius: 12px;
overflow: hidden;
box-shadow: $shadow-sm;
transition: transform 0.3s ease, box-shadow 0.3s ease;
background: white;
position: relative;
&:hover {
transform: translateY(-10px);
box-shadow: $shadow-lg;
.case-image img {
transform: scale(1.05);
}
}
.case-image {
position: relative;
overflow: hidden;
img {
width: 100%;
height: 250px;
object-fit: cover;
transition: transform 0.5s ease;
}
}
.category-tag {
position: absolute;
top: 15px;
right: 15px;
background: rgba($primary-color, 0.8);
color: white;
padding: 5px 12px;
border-radius: 20px;
font-size: 12px;
font-weight: 500;
z-index: 1;
}
.case-content {
padding: 25px;
background: white;
h3 {
font-size: 1.3rem;
margin-bottom: 10px;
color: $text-color;
}
p {
color: $text-light;
margin-bottom: 15px;
line-height: 1.6;
}
}
}
.btn-details {
display: inline-block;
padding: 8px 20px;
background: transparent;
border: 1px solid $primary-color;
color: $primary-color;
border-radius: 30px;
font-weight: 500;
cursor: pointer;
transition: all 0.3s ease;
&:hover {
background: $primary-color;
color: white;
}
}
/* 空状态样式 */
.no-results {
padding: 50px 0;
text-align: center;
.empty-state {
padding: 40px;
background: $light-bg;
border-radius: 10px;
h3 {
margin: 15px 0;
color: $text-color;
}
p {
color: $text-light;
}
}
}
/* CTA部分样式 */
.cta-section {
background: linear-gradient(135deg, #0056b3, #00337f);
background-size: 200% 200%;
color: white;
padding: 80px 0;
text-align: center;
margin-top: 40px;
position: relative;
overflow: hidden;
box-shadow: 0 -10px 30px rgba(0,0,0,0.1);
animation: gradientBG 15s ease infinite;
}
@keyframes gradientBG {
0% { background-position: 0% 50%; }
50% { background-position: 100% 50%; }
100% { background-position: 0% 50%; }
}
.cta-section::before {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('data:image/svg+xml;charset=utf8,%3Csvg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1440 320"%3E%3Cpath fill="%23ffffff" fill-opacity="0.05" d="M0,96L48,112C96,128,192,160,288,186.7C384,213,480,235,576,213.3C672,192,768,128,864,128C960,128,1056,192,1152,213.3C1248,235,1344,213,1392,202.7L1440,192L1440,320L1392,320C1344,320,1248,320,1152,320C1056,320,960,320,864,320C768,320,672,320,576,320C480,320,384,320,288,320C192,320,96,320,48,320L0,320Z"%3E%3C/path%3E%3C/svg%3E');
background-size: cover;
background-position: center;
opacity: 0.1;
z-index: 0;
}
.cta-content {
position: relative;
z-index: 1;
}
.cta-icon {
margin-bottom: 25px;
}
.cta-icon i {
font-size: 3.5rem;
color: #fff;
background: rgba(255,255,255,0.1);
width: 100px;
height: 100px;
line-height: 100px;
border-radius: 50%;
display: inline-block;
box-shadow: 0 10px 20px rgba(0,0,0,0.1);
transition: all 0.3s ease;
}
.cta-icon i:hover {
transform: translateY(-5px) scale(1.05);
box-shadow: 0 15px 30px rgba(0,0,0,0.2);
background: rgba(255,255,255,0.2);
}
.cta-content h2 {
font-size: 2.5rem;
margin-bottom: 20px;
font-weight: 700;
text-shadow: 0 2px 10px rgba(0,0,0,0.2);
color: #fff;
}
.cta-content p {
font-size: 1.2rem;
opacity: 0.9;
max-width: 600px;
margin: 0 auto 30px;
line-height: 1.6;
}
.cta-buttons {
display: flex;
justify-content: center;
gap: 20px;
margin-top: 30px;
}
.cta-buttons .btn-primary {
padding: 14px 32px;
font-size: 1.1rem;
font-weight: 600;
box-shadow: 0 8px 15px rgba(0,0,0,0.2);
transition: all 0.3s ease;
}
.cta-buttons .btn-primary i {
margin-left: 8px;
transition: transform 0.3s ease;
}
.cta-buttons .btn-primary:hover i {
transform: translateX(5px);
}
.cta-buttons .btn-outline {
background: transparent;
color: white;
border: 2px solid rgba(255,255,255,0.6);
padding: 14px 32px;
font-size: 1.1rem;
font-weight: 600;
transition: all 0.3s ease;
}
.cta-buttons .btn-outline:hover {
background: rgba(255,255,255,0.1);
border-color: white;
transform: translateY(-3px);
box-shadow: 0 8px 15px rgba(0,0,0,0.1);
}
/* 响应式样式 */
@media (max-width: 768px) {
.page-header {
height: 60vh;
}
.header-content h1 {
font-size: 2.5rem;
}
.grid {
grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
}
.header-cta {
flex-direction: column;
align-items: center;
gap: 10px;
}
.btn-primary, .btn-outline {
width: 80%;
text-align: center;
}
.cta-content h2 {
font-size: 2rem;
}
.cta-content p {
font-size: 1.1rem;
padding: 0 15px;
}
.cta-buttons {
flex-direction: column;
align-items: center;
width: 100%;
gap: 15px;
}
.cta-buttons .btn-primary,
.cta-buttons .btn-outline {
width: 80%;
max-width: 300px;
}
.cta-icon i {
width: 80px;
height: 80px;
line-height: 80px;
font-size: 2.8rem;
}
}
@media (max-width: 480px) {
.header-content h1 {
font-size: 2rem;
}
.filter-buttons {
gap: 10px;
}
.filter-btn {
padding: 8px 15px;
font-size: 14px;
}
}
</style>

+ 307
- 0
src/views/pages/Contact.vue View File

@ -0,0 +1,307 @@
<script setup>
import { onMounted, ref } from 'vue';
import PageHeader from '../../components/PageHeader.vue';
import { initAOS } from '../../plugins/animation';
// 使
const companyLocation = {
lng: 113.9430, //
lat: 22.5350 //
};
//
const tencentMap = ref(null);
//
const initTencentMap = () => {
// API
if (typeof TMap === 'undefined') {
console.error('腾讯地图API未加载');
return;
}
//
const map = new TMap.Map('company-map', {
center: new TMap.LatLng(companyLocation.lat, companyLocation.lng), //
zoom: 16, //
viewMode: '2D' // 2D
});
//
const marker = new TMap.MultiMarker({
map: map,
styles: {
//
'normal': new TMap.MarkerStyle({
width: 25,
height: 35,
anchor: { x: 12.5, y: 35 }
})
},
geometries: [{
id: 'company',
styleId: 'normal',
position: new TMap.LatLng(companyLocation.lat, companyLocation.lng),
properties: {
title: '瀚海黎明软件技术有限公司'
}
}]
});
//
const infoWindow = new TMap.InfoWindow({
map: map,
position: new TMap.LatLng(companyLocation.lat, companyLocation.lng),
content: '<div style="padding:10px;">' +
'<h4 style="margin:0 0 5px 0;">瀚海黎明软件技术有限公司</h4>' +
'<p style="margin:0;">深圳市南山区科技园南区高新南七道数字技术大厦8楼</p>' +
'</div>',
offset: { x: 0, y: -35 }
});
//
infoWindow.close();
//
marker.on('click', function(evt) {
infoWindow.open();
infoWindow.setPosition(evt.geometry.position);
});
//
tencentMap.value = map;
};
// API
const loadTencentMapScript = (key) => {
return new Promise((resolve, reject) => {
//
if (window.TMap) {
resolve();
return;
}
// API
if (typeof TMap !== 'undefined') {
console.error('腾讯地图API已加载');
return;
}
// script
const script = document.createElement('script');
script.type = 'text/javascript';
// API
// https://lbs.qq.com/dev/console/key/manage
script.src = 'https://map.qq.com/api/gljs?v=1.exp&key=' + key;
script.onload = resolve;
script.onerror = reject;
//
document.head.appendChild(script);
});
};
onMounted(() => {
//
initAOS();
//
loadTencentMapScript("XMBBZ-BCPCV-SXPPQ-5Y7MY-PHZXK-YFFVU")
.then(() => {
//
initTencentMap();
})
.catch(error => {
console.error('加载腾讯地图API失败:', error);
});
});
</script>
<template>
<div class="contact-page">
<PageHeader
title="联系我们"
subtitle="随时为您提供专业支持与服务"
backgroundImage="https://images.unsplash.com/photo-1423666639041-f56000c27a9a?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
/>
<section class="contact-info">
<div class="container">
<div class="info-grid">
<div class="info-card" data-aos="fade-up">
<div class="info-icon"><!-- 图标 --></div>
<h3>地址</h3>
<p>深圳市南山区科技园南区高新南七道数字技术大厦8楼</p>
</div>
<div class="info-card" data-aos="fade-up" data-aos-delay="100">
<div class="info-icon"><!-- 图标 --></div>
<h3>电话</h3>
<p>+86 755-8888-7777</p>
</div>
<div class="info-card" data-aos="fade-up" data-aos-delay="200">
<div class="info-icon"><!-- 图标 --></div>
<h3>邮箱</h3>
<p>info@hanhaisoft.com</p>
</div>
</div>
</div>
</section>
<section class="contact-form" data-aos="fade-up">
<div class="container">
<h2>发送消息</h2>
<p>如果您有任何问题或需求请随时与我们联系</p>
<form class="form">
<div class="form-group">
<label for="name">姓名</label>
<input type="text" id="name" placeholder="请输入您的姓名">
</div>
<div class="form-group">
<label for="email">邮箱</label>
<input type="email" id="email" placeholder="请输入您的邮箱">
</div>
<div class="form-group">
<label for="phone">电话</label>
<input type="tel" id="phone" placeholder="请输入您的电话号码">
</div>
<div class="form-group">
<label for="subject">主题</label>
<input type="text" id="subject" placeholder="请输入消息主题">
</div>
<div class="form-group full-width">
<label for="message">消息</label>
<textarea id="message" rows="6" placeholder="请输入您的消息内容"></textarea>
</div>
<button type="submit" class="submit-btn">发送消息</button>
</form>
</div>
</section>
<section class="map-section">
<div class="map-container" data-aos="fade-up">
<!-- 腾讯地图容器 -->
<div id="company-map"></div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 页面头部样式已移至PageHeader组件 */
.contact-info {
padding: 80px 0;
background-color: white;
}
.container {
max-width: 1200px;
margin: 0 auto;
padding: 0 20px;
}
.info-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: 30px;
.info-card {
padding: 30px;
background: $light-bg;
border-radius: 8px;
text-align: center;
transition: transform 0.3s ease, box-shadow 0.3s ease;
&:hover {
transform: translateY(-10px);
box-shadow: $shadow-lg;
}
}
}
.contact-form {
padding: 80px 0;
background-color: $light-bg;
text-align: center;
.form {
max-width: 800px;
margin: 40px auto 0;
display: grid;
grid-template-columns: repeat(2, 1fr);
gap: 20px;
.form-group {
text-align: left;
&.full-width {
grid-column: span 2;
}
label {
display: block;
margin-bottom: 8px;
font-weight: 500;
}
input, textarea {
width: 100%;
padding: 12px 15px;
border: 1px solid #ddd;
border-radius: 4px;
font-size: 16px;
}
textarea {
resize: vertical;
}
}
.submit-btn {
grid-column: span 2;
background: $primary-color;
color: white;
border: none;
padding: 15px 30px;
font-size: 16px;
border-radius: 4px;
cursor: pointer;
transition: background 0.3s ease;
&:hover {
background: $secondary-color;
}
}
}
}
.map-section {
padding: 0 0 80px;
.map-container {
height: 600px;
background: $light-bg;
border-radius: 8px;
overflow: hidden;
box-shadow: $shadow-sm;
#company-map {
height: 100%;
width: calc(100% - 40px);
margin: 20px auto;
max-width: calc(1200px - 40px);
}
}
}
</style>

+ 819
- 0
src/views/pages/Home.vue View File

@ -0,0 +1,819 @@
<script setup>
//
import { onMounted, ref } from 'vue';
import { useRouter } from 'vue-router';
import { initParallax, initAOS } from '../../plugins/animation.js';
//
import ServiceSection from '../../components/home/ServiceSection.vue';
//
const router = useRouter();
//
const serviceSection = ref(null);
//
const scrollToServices = () => {
// 使DOM
const element = document.querySelector('.services-section');
if (element) {
element.scrollIntoView({ behavior: 'smooth' });
}
};
//
const navigateToContact = () => {
router.push('/contact');
};
onMounted(() => {
//
initAOS();
initParallax();
});
</script>
<template>
<div class="home">
<!-- 英雄区域带视差效果 -->
<section class="hero-section parallax-container">
<!-- 添加一个注释确保视差容器不会阻止按钮点击 -->
<div class="parallax-bg" data-depth="0.4"></div>
<div class="hero-overlay"></div>
<div class="hero-content hero-content-fixed" data-aos="fade-up" data-aos-duration="1000">
<h1 class="hero-title">数字化转型的<span class="highlight">可靠伙伴</span></h1>
<p class="hero-subtitle" data-aos="fade-up" data-aos-delay="200">专注于为企业提供高质量软件开发服务</p>
<div class="cta-buttons" data-aos="fade-up" data-aos-delay="400">
<button class="btn primary" @click="scrollToServices">了解更多</button>
<button class="btn secondary" @click="navigateToContact">联系我们</button>
</div>
</div>
</section>
<!-- 我们的服务视差滚动 -->
<ServiceSection />
<!-- 我们的优势视差背景 -->
<section class="advantages-section parallax-container">
<div class="parallax-bg" data-depth="0.1"></div>
<div class="overlay-dark"></div>
<div class="container hero-content-fixed">
<div class="section-content">
<div class="section-header" data-aos="fade-up">
<h2 style="color: #fff;">我们的优势</h2>
<p>为什么选择瀚海黎明</p>
</div>
<div class="advantages-grid" data-aos="fade-up" data-aos-delay="100">
<div class="advantage-card" data-aos="fade-right" data-aos-delay="100">
<div class="advantage-number">01</div>
<h3>专业团队</h3>
<p>由经验丰富的开发人员设计师和项目经理组成的精英团队</p>
</div>
<div class="advantage-card" data-aos="fade-right" data-aos-delay="200">
<div class="advantage-number">02</div>
<h3>质量保证</h3>
<p>严格的质量控制流程确保交付高质量的软件产品</p>
</div>
<div class="advantage-card" data-aos="fade-right" data-aos-delay="300">
<div class="advantage-number">03</div>
<h3>按时交付</h3>
<p>高效的项目管理确保项目按时按预算完成</p>
</div>
<div class="advantage-card" data-aos="fade-left" data-aos-delay="400">
<div class="advantage-number">04</div>
<h3>灵活合作模式</h3>
<p>根据客户需求提供灵活的合作方式和定价模式</p>
</div>
<div class="advantage-card" data-aos="fade-left" data-aos-delay="500">
<div class="advantage-number">05</div>
<h3>技术创新</h3>
<p>持续关注最新技术趋势为客户提供创新解决方案</p>
</div>
<div class="advantage-card" data-aos="fade-left" data-aos-delay="600">
<div class="advantage-number">06</div>
<h3>售后支持</h3>
<p>提供全面的售后支持和维护服务确保系统稳定运行</p>
</div>
</div>
</div>
</div>
</section>
<!-- 精选案例展示视差滚动 -->
<section class="cases-section" data-aos="fade-up">
<div class="section-header">
<h2>精选案例</h2>
<p>我们的成功项目展示</p>
</div>
<div class="cases-grid">
<div class="case-card" data-aos="fade-up" data-aos-delay="100">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80"
alt="企业管理系统" />
</div>
<div class="case-content">
<h3>企业资源管理系统</h3>
<p>为某大型制造企业开发的一体化ERP系统整合了生产销售库存和财务管理</p>
<a href="#" class="btn-link">查看详情</a>
</div>
</div>
<div class="case-card" data-aos="fade-up" data-aos-delay="200">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1526498460520-4c246339dccb?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80"
alt="电子商务平台" />
</div>
<div class="case-content">
<h3>电子商务平台</h3>
<p>为零售客户开发的全渠道电商平台支持PC端移动端和小程序多端访问</p>
<a href="#" class="btn-link">查看详情</a>
</div>
</div>
<div class="case-card" data-aos="fade-up" data-aos-delay="300">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1551288049-bebda4e38f71?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80"
alt="医疗管理系统" />
</div>
<div class="case-content">
<h3>医疗管理系统</h3>
<p>为医疗机构开发的患者管理系统提高了医疗服务效率和患者满意度</p>
<a href="#" class="btn-link">查看详情</a>
</div>
</div>
<div class="case-card" data-aos="fade-up" data-aos-delay="400">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1454165804606-c3d57bc86b40?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80"
alt="金融分析平台" />
</div>
<div class="case-content">
<h3>金融分析平台</h3>
<p>为金融机构开发的数据分析平台提供实时市场分析和风险评估</p>
<a href="#" class="btn-link">查看详情</a>
</div>
</div>
</div>
</section>
<!-- 客户评价视差背景 -->
<section class="testimonials-section parallax-container">
<div class="parallax-bg" data-depth="0.1"></div>
<div class="section-content">
<div class="section-header" data-aos="fade-up">
<h2>客户评价</h2>
<p>听听我们的客户怎么说</p>
</div>
<div class="testimonials-slider" data-aos="fade-up">
<div class="testimonial-card">
<div class="testimonial-rating">
<span></span><span></span><span></span><span></span><span></span>
</div>
<p class="testimonial-text">"瀚海黎明团队的专业素养和技术能力给我们留下了深刻印象。他们不仅按时交付了高质量的产品,还提供了持续的技术支持。"</p>
<div class="testimonial-author">
<img src="https://randomuser.me/api/portraits/men/32.jpg" alt="张总" class="author-avatar" />
<div class="author-info">
<h4>张总</h4>
<p>某科技有限公司 CEO</p>
</div>
</div>
</div>
<div class="testimonial-card">
<div class="testimonial-rating">
<span></span><span></span><span></span><span></span><span></span>
</div>
<p class="testimonial-text">"与瀚海黎明的合作非常愉快。他们理解我们的业务需求,并将其转化为了一个功能强大且用户友好的系统。"</p>
<div class="testimonial-author">
<img src="https://randomuser.me/api/portraits/women/44.jpg" alt="李经理"
class="author-avatar" />
<div class="author-info">
<h4>李经理</h4>
<p>某医疗集团 IT总监</p>
</div>
</div>
</div>
<div class="testimonial-card">
<div class="testimonial-rating">
<span></span><span></span><span></span><span></span><span></span>
</div>
<p class="testimonial-text">"瀚海黎明团队的响应速度和解决问题的能力令人印象深刻。他们不仅是技术提供商,更是我们业务发展的战略伙伴。"</p>
<div class="testimonial-author">
<img src="https://randomuser.me/api/portraits/men/67.jpg" alt="王董事" class="author-avatar" />
<div class="author-info">
<h4>王董事</h4>
<p>某金融服务公司 董事长</p>
</div>
</div>
</div>
</div>
</div>
</section>
<!-- 合作流程视差滚动 -->
<section class="process-section" data-aos="fade-up">
<div class="section-header">
<h2>合作流程</h2>
<p>简单高效的项目合作流程</p>
</div>
<div class="process-flow">
<div class="process-step" data-aos="fade-right" data-aos-delay="100">
<div class="step-number">01</div>
<div class="step-content">
<h3>需求分析</h3>
<p>深入了解您的业务需求和目标确定项目范围和技术方案</p>
</div>
</div>
<div class="process-step" data-aos="fade-right" data-aos-delay="200">
<div class="step-number">02</div>
<div class="step-content">
<h3>方案设计</h3>
<p>制定详细技术方案和项目计划包括功能规格UI设计和技术架构</p>
</div>
</div>
<div class="process-step" data-aos="fade-right" data-aos-delay="300">
<div class="step-number">03</div>
<div class="step-content">
<h3>开发实施</h3>
<p>按照敏捷开发方法迭代开发并定期交付可测试的版本</p>
</div>
</div>
<div class="process-step" data-aos="fade-left" data-aos-delay="400">
<div class="step-number">04</div>
<div class="step-content">
<h3>测试验收</h3>
<p>进行全面的功能测试性能测试和安全测试确保产品质量</p>
</div>
</div>
<div class="process-step" data-aos="fade-left" data-aos-delay="500">
<div class="step-number">05</div>
<div class="step-content">
<h3>交付上线</h3>
<p>系统部署上线提供用户培训和文档确保平稳过渡</p>
</div>
</div>
<div class="process-step" data-aos="fade-left" data-aos-delay="600">
<div class="step-number">06</div>
<div class="step-content">
<h3>持续支持</h3>
<p>提供持续的技术支持和系统维护确保系统稳定运行</p>
</div>
</div>
</div>
</section>
</div>
</template>
<style scoped>
/* 全局样式 */
.section-header {
text-align: center;
margin-bottom: 50px;
}
.section-header h2 {
font-size: 2.5rem;
color: #2c3e50;
margin-bottom: 15px;
}
.section-header p {
font-size: 1.2rem;
color: #7f8c8d;
}
.btn {
padding: 14px 32px;
border-radius: 30px;
font-weight: 600;
cursor: pointer !important; /* 确保鼠标悬停时显示小手 */
transition: all 0.4s cubic-bezier(0.165, 0.84, 0.44, 1);
border: none;
margin: 0;
position: relative;
overflow: hidden;
font-size: 1rem;
letter-spacing: 1px;
box-shadow: 0 4px 10px rgba(0, 0, 0, 0.2);
z-index: 30; /* 确保按钮在最上层 */
pointer-events: auto; /* 确保可以接收鼠标事件 */
}
.btn.primary {
background-color: #3498db;
color: white;
}
.btn.primary:hover {
background-color: #2980b9;
transform: translateY(-3px);
box-shadow: 0 6px 15px rgba(0, 0, 0, 0.3);
}
.btn.primary:active {
transform: translateY(-1px);
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.2);
}
.btn.secondary {
background-color: transparent;
color: white;
border: 2px solid white;
box-shadow: 0 4px 10px rgba(0, 0, 0, 0.1);
}
.btn.secondary:hover {
background-color: rgba(255, 255, 255, 0.15);
transform: translateY(-3px);
box-shadow: 0 6px 15px rgba(0, 0, 0, 0.2);
}
.btn.secondary:active {
transform: translateY(-1px);
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.15);
}
.btn-link {
color: #3498db;
text-decoration: none;
font-weight: 600;
position: relative;
cursor: pointer;
}
.btn-link:after {
content: '';
position: absolute;
width: 0;
height: 2px;
bottom: -5px;
left: 0;
background-color: #3498db;
transition: width 0.3s ease;
}
.btn-link:hover:after {
width: 100%;
}
/* 英雄区域样式 */
.hero-section {
height: 100vh;
position: relative;
overflow: hidden;
display: flex;
align-items: center;
justify-content: center;
color: white;
text-align: center;
}
/* 确保视差容器不会阻止点击事件 */
.parallax-container {
pointer-events: none; /* 默认不接收鼠标事件,让事件穿透到下层元素 */
}
/* 确保视差容器中的内容可以接收点击事件 */
.parallax-container .hero-content,
.parallax-container .hero-content * {
pointer-events: auto; /* 恢复内容区域的鼠标事件 */
}
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('https://images.unsplash.com/photo-1451187580459-43490279c0fa?ixlib=rb-1.2.1&auto=format&fit=crop&w=1352&q=80');
background-size: cover;
background-position: center;
z-index: -2;
transform: scale(1.1);
/* 轻微放大背景,增强视差效果 */
transition: transform 0.5s ease;
}
.hero-overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to right, rgba(0, 0, 0, 0.7), rgba(0, 0, 0, 0.4));
z-index: -1;
}
.hero-content {
z-index: 1;
padding: 0 20px;
text-align: center;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
width: calc(100% - 40px);
/* 使用!important确保transform属性不被AOS动画库覆盖 */
}
/* 添加额外的样式来修复AOS动画结束后的位置问题 */
[data-aos].aos-animate {
transform: none;
}
/* 特定针对hero-content中的元素恢复正确的transform */
.hero-content[data-aos].aos-animate {
transform: translate(-50%, -50%) !important;
}
/* 添加固定定位样式确保hero-content始终居中 */
.hero-content-fixed {
position: absolute !important;
top: 50% !important;
left: 50% !important;
transform: translate(-50%, -50%) !important;
width: calc(100% - 40px) !important;
z-index: 10 !important; /* 提高z-index确保内容在最上层 */
pointer-events: auto !important; /* 确保可以接收鼠标事件 */
}
.hero-title {
font-size: 4rem;
font-weight: 700;
margin-bottom: 20px;
text-shadow: 0 2px 10px rgba(0, 0, 0, 0.5);
letter-spacing: 1px;
color: #fff;
}
.hero-title .highlight {
color: #3498db;
position: relative;
}
.hero-title .highlight::after {
content: '';
position: absolute;
bottom: -5px;
left: 0;
width: 100%;
height: 3px;
background-color: #3498db;
}
.hero-subtitle {
font-size: 1.6rem;
margin-bottom: 40px;
text-shadow: 0 2px 5px rgba(0, 0, 0, 0.5);
font-weight: 300;
line-height: 1.5;
}
.cta-buttons {
display: flex;
justify-content: center;
gap: 20px;
position: relative;
z-index: 20; /* 确保按钮在最上层 */
pointer-events: auto; /* 确保可以接收鼠标事件 */
}
/* 服务部分样式已移至ServiceSection.vue组件 */
/* 优势部分样式 */
.advantages-section {
position: relative;
padding: 100px 20px;
color: white;
overflow: hidden;
text-align: center;
/* 确保文本居中 */
display: flex;
flex-direction: column;
align-items: center;
/* 确保子元素水平居中 */
width: 100%;
/* 确保宽度占满容器 */
box-sizing: border-box;
/* 确保padding不会增加元素总宽度 */
}
.advantages-section .container {
width: 100%;
max-width: 1200px;
margin: 0 auto;
position: relative;
z-index: 2;
}
.advantages-section .parallax-bg {
background-image: url('https://images.unsplash.com/photo-1504639725590-34d0984388bd?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80');
filter: brightness(0.3);
/* 降低亮度以增加对比度 */
}
.overlay-dark {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to right, rgba(0, 0, 0, 0.7), rgba(0, 0, 0, 0.5));
z-index: 0;
}
.section-content {
position: relative;
z-index: 2;
/* 提高z-index确保内容在叠加层之上 */
max-width: 1200px;
margin: 0 auto;
width: 100%;
/* 确保宽度占满容器 */
padding: 0 15px;
/* 添加内边距,确保在小屏幕上内容不会贴边 */
display: flex;
flex-direction: column;
align-items: center;
/* 确保子元素水平居中 */
box-sizing: border-box;
/* 确保padding不会增加元素总宽度 */
left: 0;
/* 确保不会有偏移 */
right: 0;
/* 确保不会有偏移 */
margin-left: auto;
margin-right: auto;
text-align: center;
/* 确保文本居中 */
}
.advantages-grid {
display: grid;
gap: 30px;
margin-top: 40px;
justify-content: center;
/* 确保网格居中 */
max-width: 1200px;
margin-left: auto;
margin-right: auto;
width: 100%;
/* 确保宽度占满容器 */
grid-template-columns: repeat(3, 1fr);
/* 固定为3列布局 */
box-sizing: border-box;
/* 确保padding不会增加元素总宽度 */
}
@media (max-width: 992px) {
.advantages-grid {
grid-template-columns: repeat(2, 1fr);
/* 中等屏幕2列 */
}
}
@media (max-width: 768px) {
.advantages-grid {
grid-template-columns: 1fr;
/* 小屏幕1列 */
}
}
.advantage-card {
background: rgba(0, 0, 0, 0.5);
/* 更深的背景色以增加对比度 */
backdrop-filter: blur(10px);
border-radius: 8px;
padding: 30px;
transition: transform 0.3s ease;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.3);
/* 添加阴影增强可见性 */
border: 1px solid rgba(255, 255, 255, 0.1);
/* 添加细边框增强可见性 */
}
.advantage-card:hover {
transform: translateY(-10px);
background: rgba(0, 0, 0, 0.6);
/* 悬停时背景更深 */
}
.advantage-number {
font-size: 3rem;
font-weight: 700;
color: rgba(52, 152, 219, 0.7);
/* 使用品牌蓝色,增加可见性 */
margin-bottom: 15px;
text-shadow: 0 2px 5px rgba(0, 0, 0, 0.5);
/* 添加文字阴影 */
}
.advantage-card h3 {
font-size: 1.5rem;
margin-bottom: 15px;
color: #ffffff;
/* 确保标题为纯白色 */
text-shadow: 0 2px 4px rgba(0, 0, 0, 0.5);
/* 添加文字阴影增强可读性 */
}
.advantage-card p {
color: rgba(255, 255, 255, 0.9);
/* 段落文字颜色 */
line-height: 1.6;
/* 增加行高提高可读性 */
font-size: 1rem;
/* 设置合适的字体大小 */
text-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);
/* 轻微文字阴影 */
}
/* 案例部分样式 */
.cases-section {
padding: 100px 20px;
background-color: #f8f9fa;
}
.cases-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(500px, 1fr));
gap: 30px;
margin-top: 40px;
max-width: 1200px;
margin-left: auto;
margin-right: auto;
}
.case-card {
background: white;
border-radius: 8px;
overflow: hidden;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.05);
transition: transform 0.3s ease, box-shadow 0.3s ease;
}
.case-card:hover {
transform: translateY(-10px);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.1);
}
.case-image img {
width: 100%;
height: 300px;
object-fit: cover;
transition: transform 0.5s ease;
}
.case-card:hover .case-image img {
transform: scale(1.05);
}
.case-content {
padding: 25px;
}
.case-content h3 {
font-size: 1.5rem;
margin-bottom: 15px;
color: #2c3e50;
}
.case-content p {
color: #7f8c8d;
margin-bottom: 20px;
}
/* 客户评价部分样式 */
.testimonials-section {
position: relative;
padding: 100px 20px;
color: white;
overflow: hidden;
}
.testimonials-section .parallax-bg {
background-image: url('https://images.unsplash.com/photo-1557682250-33bd709cbe85?ixlib=rb-1.2.1&auto=format&fit=crop&w=1500&q=80');
filter: brightness(0.4);
}
.testimonials-slider {
display: flex;
flex-wrap: wrap;
gap: 30px;
justify-content: center;
max-width: 1200px;
margin: 0 auto;
}
.testimonial-card {
background: rgba(255, 255, 255, 0.1);
backdrop-filter: blur(10px);
border-radius: 8px;
padding: 30px;
flex: 1;
min-width: 300px;
max-width: 400px;
}
.testimonial-rating {
color: #f1c40f;
font-size: 1.5rem;
margin-bottom: 20px;
}
.testimonial-text {
font-style: italic;
margin-bottom: 20px;
line-height: 1.6;
}
.testimonial-author {
display: flex;
align-items: center;
}
.author-avatar {
width: 60px;
height: 60px;
border-radius: 50%;
margin-right: 15px;
object-fit: cover;
}
.author-info h4 {
font-size: 1.2rem;
margin-bottom: 5px;
}
.author-info p {
opacity: 0.8;
font-size: 0.9rem;
}
/* 合作流程部分样式 */
.process-section {
padding: 100px 20px;
background-color: #f8f9fa;
}
.process-flow {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: 30px;
margin-top: 40px;
max-width: 1200px;
margin-left: auto;
margin-right: auto;
}
.process-step {
display: flex;
background: white;
border-radius: 8px;
padding: 30px;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.05);
transition: transform 0.3s ease, box-shadow 0.3s ease;
}
.process-step:hover {
transform: translateY(-10px);
box-shadow: 0 15px 30px rgba(0, 0, 0, 0.1);
}
.step-number {
font-size: 2.5rem;
font-weight: 700;
color: #3498db;
margin-right: 20px;
line-height: 1;
}
.step-content h3 {
font-size: 1.5rem;
margin-bottom: 10px;
color: #2c3e50;
}
.step-content p {
color: #7f8c8d;
}
/* 响应式调整 */
@media (max-width: 768px) {
.hero-content h1 {
font-size: 2.5rem;
}
.hero-content p {
font-size: 1.2rem;
}
.cases-grid {
grid-template-columns: 1fr;
}
.process-step {
flex-direction: column;
}
.step-number {
margin-right: 0;
margin-bottom: 15px;
}
}
</style>

+ 606
- 0
src/views/pages/Services.vue View File

@ -0,0 +1,606 @@
<script setup>
import { onMounted } from 'vue';
import { initAOS } from '../../plugins/animation';
import PageHeader from '../../components/PageHeader.vue';
onMounted(() => {
//
initAOS();
// FontAwesome
if (!document.getElementById('font-awesome-css')) {
const link = document.createElement('link');
link.id = 'font-awesome-css';
link.rel = 'stylesheet';
link.href = 'https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.4/css/all.min.css';
document.head.appendChild(link);
}
});
</script>
<template>
<div class="services-page">
<PageHeader title="我们的服务" subtitle="为您的业务提供全方位的软件解决方案"
backgroundImage="https://images.unsplash.com/photo-1454165804606-c3d57bc86b40?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80"
height="70vh">
<template #header-cta>
<div class="header-cta" data-aos="fade-up" data-aos-delay="300">
<a href="#services-detail" class="btn-outline">了解详情</a>
</div>
</template>
</PageHeader>
<section id="services-detail" class="services-detail">
<div class="container">
<div class="service-item" data-aos="fade-up">
<div class="service-icon">
<i class="fas fa-laptop-code"></i>
</div>
<div class="service-content">
<h2>定制软件开发</h2>
<p>我们提供端到端的定制软件开发服务从需求分析到设计开发测试和部署确保软件完全符合您的业务需求</p>
<ul>
<li>业务流程自动化</li>
<li>企业资源规划(ERP)系统</li>
<li>客户关系管理(CRM)系统</li>
<li>数据分析与报表系统</li>
</ul>
</div>
</div>
<div class="service-item" data-aos="fade-up" data-aos-delay="100">
<div class="service-icon">
<i class="fas fa-mobile-alt"></i>
</div>
<div class="service-content">
<h2>移动应用开发</h2>
<p>我们开发高性能用户友好的移动应用帮助您的业务在移动端获得更多机会</p>
<ul>
<li>iOS和Android原生应用</li>
<li>跨平台应用开发</li>
<li>移动电商解决方案</li>
<li>企业移动办公应用</li>
</ul>
</div>
</div>
<div class="service-item" data-aos="fade-up" data-aos-delay="200">
<div class="service-icon">
<i class="fas fa-globe"></i>
</div>
<div class="service-content">
<h2>网站设计与开发</h2>
<p>我们创建美观响应式的网站确保在所有设备上都能提供出色的用户体验</p>
<ul>
<li>企业官网设计与开发</li>
<li>电子商务网站</li>
<li>内容管理系统</li>
<li>网站性能优化</li>
</ul>
</div>
</div>
<div class="service-item" data-aos="fade-up" data-aos-delay="300">
<div class="service-icon">
<i class="fas fa-cloud"></i>
</div>
<div class="service-content">
<h2>云服务与DevOps</h2>
<p>我们提供全面的云服务解决方案帮助您的业务实现数字化转型</p>
<ul>
<li>云迁移与部署</li>
<li>持续集成与部署(CI/CD)</li>
<li>容器化与微服务架构</li>
<li>云基础设施管理</li>
</ul>
</div>
</div>
</div>
</section>
<section class="service-process" data-aos="fade-up">
<div class="container">
<h2>我们的服务流程</h2>
<div class="process-steps">
<div class="step" data-aos="fade-right" data-aos-delay="100">
<div class="step-number">01</div>
<h3>需求分析</h3>
<p>深入了解您的业务需求和目标确定项目范围和技术要求</p>
</div>
<div class="step" data-aos="fade-right" data-aos-delay="200">
<div class="step-number">02</div>
<h3>方案设计</h3>
<p>制定详细的技术方案和项目计划确保解决方案符合您的业务目标</p>
</div>
<div class="step" data-aos="fade-right" data-aos-delay="300">
<div class="step-number">03</div>
<h3>开发实现</h3>
<p>采用敏捷开发方法快速迭代定期交付可用的软件版本</p>
</div>
<div class="step" data-aos="fade-right" data-aos-delay="400">
<div class="step-number">04</div>
<h3>测试验收</h3>
<p>全面的功能测试性能测试和安全测试确保软件质量</p>
</div>
<div class="step" data-aos="fade-right" data-aos-delay="500">
<div class="step-number">05</div>
<h3>部署上线</h3>
<p>专业的部署服务确保系统平稳上线并提供详细的使用文档</p>
</div>
</div>
</div>
</section>
<section class="case-studies" data-aos="fade-up">
<div class="container">
<h2>成功案例</h2>
<p class="section-desc">我们为各行业客户提供了成功的软件解决方案</p>
<div class="cases-grid">
<div class="case-card" data-aos="fade-up" data-aos-delay="100">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1460925895917-afdab827c52f?ixlib=rb-1.2.1&auto=format&fit=crop&w=500&q=80"
alt="金融行业案例">
</div>
<div class="case-content">
<h3>某大型金融机构</h3>
<p>为客户开发了全面的风险管理系统帮助其提高了30%的风险识别率</p>
<a href="#" class="read-more">查看详情</a>
</div>
</div>
<div class="case-card" data-aos="fade-up" data-aos-delay="200">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1576091160550-2173dba999ef?ixlib=rb-1.2.1&auto=format&fit=crop&w=500&q=80"
alt="医疗行业案例">
</div>
<div class="case-content">
<h3>医疗健康集团</h3>
<p>开发了患者管理系统帮助医院提高了40%的工作效率</p>
<a href="#" class="read-more">查看详情</a>
</div>
</div>
<div class="case-card" data-aos="fade-up" data-aos-delay="300">
<div class="case-image">
<img src="https://images.unsplash.com/photo-1556740738-b6a63e27c4df?ixlib=rb-1.2.1&auto=format&fit=crop&w=500&q=80"
alt="零售行业案例">
</div>
<div class="case-content">
<h3>全国连锁零售企业</h3>
<p>开发了全渠道零售系统帮助客户销售额提升25%</p>
<a href="#" class="read-more">查看详情</a>
</div>
</div>
</div>
</div>
</section>
<section class="contact-section parallax-container">
<div class="parallax-bg"></div>
<div class="container">
<div class="contact-content" data-aos="fade-up">
<h2 data-aos="zoom-in" data-aos-delay="100">准备好开始您的项目了吗</h2>
<p data-aos="fade-up" data-aos-delay="200">联系我们获取专业的软件解决方案</p>
<div class="contact-buttons" data-aos="fade-up" data-aos-delay="300">
<a href="/contact" class="btn-primary"><i class="fas fa-paper-plane"></i> 联系我们</a>
<a href="tel:+8612345678901" class="btn-secondary"><i class="fas fa-phone-alt"></i> 服务热线</a>
</div>
<div class="quick-contact" data-aos="fade-up" data-aos-delay="400">
<span><i class="fas fa-envelope"></i> info@hanhaisoftware.com</span>
</div>
</div>
</div>
</section>
</div>
</template>
<style lang="scss" scoped>
/* 导入全局SCSS变量 */
@use '../../assets/scss/main.scss' as *;
/* 使用全局变量 */
/* 容器样式 */
.container {
max-width: 1200px;
margin: 0 auto;
padding: 0 20px;
}
/* 服务详情部分 */
.services-detail {
padding: 80px 0;
.service-item {
display: flex;
margin-bottom: 60px;
padding: 30px;
background: white;
border-radius: 8px;
box-shadow: $shadow-sm;
transition: transform 0.3s ease, box-shadow 0.3s ease;
&:hover {
transform: translateY(-5px);
box-shadow: $shadow-lg;
}
.service-icon {
flex: 0 0 100px;
display: flex;
align-items: center;
justify-content: center;
font-size: 3rem;
color: $primary-color;
margin-right: 30px;
}
.service-content {
flex: 1;
h2 {
font-size: 1.8rem;
margin-bottom: 15px;
color: $text-color;
}
p {
margin-bottom: 20px;
color: $text-light;
line-height: 1.6;
}
ul {
padding-left: 20px;
li {
margin-bottom: 10px;
color: $text-light;
}
}
}
}
}
/* 服务流程部分 */
.service-process {
padding: 80px 0;
background-color: $light-bg;
text-align: center;
h2 {
font-size: 2.5rem;
margin-bottom: 30px;
color: $text-color;
}
.process-steps {
display: flex;
justify-content: space-between;
margin-top: 50px;
flex-wrap: wrap;
.step {
flex: 1;
min-width: 200px;
padding: 0 20px;
text-align: center;
margin-bottom: 30px;
.step-number {
font-size: 48px;
font-weight: bold;
color: $primary-color;
margin-bottom: 20px;
}
h3 {
font-size: 1.5rem;
margin-bottom: 15px;
color: $text-color;
}
p {
color: $text-light;
line-height: 1.6;
}
}
}
}
/* 案例研究部分 */
.case-studies {
padding: 80px 0;
text-align: center;
h2 {
font-size: 2.5rem;
margin-bottom: 15px;
color: $text-color;
}
.section-desc {
max-width: 700px;
margin: 0 auto 50px;
color: $text-light;
}
.cases-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: 30px;
margin-top: 40px;
.case-card {
background: white;
border-radius: 8px;
overflow: hidden;
box-shadow: $shadow-sm;
transition: transform 0.3s ease, box-shadow 0.3s ease;
&:hover {
transform: translateY(-10px);
box-shadow: $shadow-lg;
}
.case-image {
img {
width: 100%;
height: 200px;
object-fit: cover;
}
}
.case-content {
padding: 20px;
text-align: left;
h3 {
font-size: 1.5rem;
margin-bottom: 10px;
color: $text-color;
}
p {
color: $text-light;
margin-bottom: 15px;
line-height: 1.6;
}
.read-more {
display: inline-block;
color: $primary-color;
font-weight: 600;
text-decoration: none;
transition: color 0.3s ease;
&:hover {
color: $secondary-color;
}
}
}
}
}
}
/* 联系部分 */
.contact-section {
position: relative;
padding: 120px 0;
color: white;
text-align: center;
overflow: hidden;
display: flex;
align-items: center;
min-height: 60vh;
.parallax-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-image: url('https://images.unsplash.com/photo-1557804506-669a67965ba0?ixlib=rb-1.2.1&auto=format&fit=crop&w=1350&q=80');
background-size: cover;
background-position: center;
background-attachment: fixed;
filter: brightness(0.3);
transform: scale(1.1);
transition: transform 0.5s ease;
}
&:hover {
.parallax-bg {
transform: scale(1);
}
}
.contact-content {
position: relative;
z-index: 1;
padding: 30px;
border-radius: 10px;
background-color: rgba(0, 0, 0, 0.2);
backdrop-filter: blur(5px);
box-shadow: $shadow-xl;
max-width: 800px;
margin: 0 auto;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
h2 {
font-size: 2.8rem;
margin-bottom: 20px;
text-shadow: 0 2px 5px rgba(0, 0, 0, 0.5);
font-weight: 700;
}
p {
font-size: 1.3rem;
margin-bottom: 30px;
text-shadow: 0 1px 3px rgba(0, 0, 0, 0.3);
}
.contact-buttons {
display: flex;
justify-content: center;
gap: 20px;
margin-bottom: 25px;
}
.quick-contact {
margin-top: 20px;
font-size: 1.1rem;
span {
display: inline-block;
padding: 8px 15px;
background-color: rgba(255, 255, 255, 0.1);
border-radius: 20px;
margin: 0 5px;
transition: all 0.3s ease;
&:hover {
background-color: rgba(255, 255, 255, 0.2);
transform: translateY(-3px);
}
i {
margin-right: 8px;
color: $primary-color;
}
}
}
}
}
/* 按钮样式 */
.btn-primary,
.btn-secondary {
display: inline-flex;
align-items: center;
justify-content: center;
padding: 14px 32px;
border-radius: 30px;
text-decoration: none;
font-weight: 600;
transition: all 0.3s ease;
box-shadow: $shadow-sm;
&:hover {
transform: translateY(-5px);
box-shadow: 0 10px 20px rgba(0, 0, 0, 0.3);
}
i {
margin-right: 8px;
}
}
.btn-primary {
background-color: $primary-color;
color: white;
&:hover {
background-color: $secondary-color;
}
}
.btn-secondary {
background-color: rgba(255, 255, 255, 0.15);
color: white;
border: 1px solid rgba(255, 255, 255, 0.3);
&:hover {
background-color: rgba(255, 255, 255, 0.25);
}
}
/* 响应式设计 */
@media (max-width: 992px) {
.process-steps {
flex-direction: column;
}
.step {
margin-bottom: 40px;
}
.service-item {
flex-direction: column;
.service-icon {
margin-right: 0;
margin-bottom: 20px;
}
}
}
@media (max-width: 768px) {
.page-header {
height: 60vh;
}
.header-content {
h1 {
font-size: 2.5rem;
}
p {
font-size: 1.2rem;
margin-bottom: 20px;
}
}
.breadcrumb {
top: 20px;
left: 20px;
font-size: 0.8rem;
}
.btn-outline {
padding: 10px 25px;
}
.cases-grid {
grid-template-columns: 1fr;
}
.contact-section {
padding: 80px 0;
.contact-content {
padding: 20px;
h2 {
font-size: 2.2rem;
}
p {
font-size: 1.1rem;
}
.contact-buttons {
flex-direction: column;
gap: 15px;
}
.quick-contact {
span {
display: block;
margin: 10px auto;
max-width: 280px;
}
}
}
}
.btn-primary,
.btn-secondary {
width: 100%;
padding: 12px 20px;
}
}
</style>

+ 7
- 0
vite.config.js View File

@ -0,0 +1,7 @@
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
// https://vite.dev/config/
export default defineConfig({
plugins: [vue()],
})

Loading…
Cancel
Save