This commit is contained in:
chashaobao
2025-08-24 17:35:13 +08:00
parent 6a2c94c7cf
commit 2cb532c3d7
12 changed files with 148 additions and 71 deletions

View File

@ -1,6 +1,6 @@
@import '@/styles/common.less';
@import '@/styles/variables.less';
.job-card {
&__container {
width: 100%;
@ -11,6 +11,16 @@
border-radius: 16px;
background: #FFFFFF;
margin-bottom: 24px;
position: relative;
}
&__mask {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba(255, 255, 255, 0.4);
}
&__header {
@ -160,4 +170,4 @@
color: @blColorG2;
}
}
}

View File

@ -5,13 +5,13 @@ import React, { useCallback } from 'react';
import { CertificationStatusIcon } from '@/components/certification-status';
import { PageUrl } from '@/constants/app';
import { CITY_CODE_TO_NAME_MAP, COUNTY_CODE_TO_NAME_MAP } from '@/constants/city';
// import { CITY_CODE_TO_NAME_MAP, COUNTY_CODE_TO_NAME_MAP } from '@/constants/city';
import { CertificationStatusType } from '@/constants/company';
import { EMPLOY_TYPE_TITLE_MAP, EmployType } from '@/constants/job';
import { JobInfo } from '@/types/job';
import { LocationInfo } from '@/types/location';
// import { LocationInfo } from '@/types/location';
import { getJobSalary, getJobTitle } from '@/utils/job';
import { calcDistance } from '@/utils/location';
// import { calcDistance } from '@/utils/location';
import { navigateTo, redirectTo } from '@/utils/route';
import './index.less';
@ -23,16 +23,16 @@ interface IProps {
}
const PREFIX = 'job-card';
const getCityDes = (location: LocationInfo) => {
if (!location) {
return '';
}
let des = CITY_CODE_TO_NAME_MAP.get(location.cityCode);
if (location.countyCode) {
des += `-${COUNTY_CODE_TO_NAME_MAP.get(location.countyCode)}`;
}
return des;
};
// const getCityDes = (location: LocationInfo) => {
// if (!location) {
// return '';
// }
// let des = CITY_CODE_TO_NAME_MAP.get(location.cityCode);
// if (location.countyCode) {
// des += `-${COUNTY_CODE_TO_NAME_MAP.get(location.countyCode)}`;
// }
// return des;
// };
function JobCard(props: IProps) {
const { className, data, redirectOpen } = props;
@ -45,7 +45,7 @@ function JobCard(props: IProps) {
publisher,
publisherAvatar,
jobLocation,
distance,
// distance,
isAuthed = false,
} = data;
@ -104,6 +104,7 @@ function JobCard(props: IProps) {
</div>
{/*<div className={`${PREFIX}__city`}>{getCityDes(jobLocation)}</div>*/}
</div>
{data.isRead && <div className={`${PREFIX}__mask`} />}
</div>
);
}

View File

@ -1,3 +1,5 @@
import Taro from '@tarojs/taro';
import { List, PullRefresh } from '@taroify/core';
import classNames from 'classnames';
import { isEqual } from 'lodash-es';
@ -5,6 +7,7 @@ import { useCallback, useEffect, useRef, useState } from 'react';
import JobCard from '@/components/job-card';
import ListPlaceholder from '@/components/list-placeholder';
import { EventName } from '@/constants/app';
import { JobType, EmployType, SortType } from '@/constants/job';
import { JobInfo, GetJobsRequest } from '@/types/job';
import { logWithPrefix } from '@/utils/common';
@ -58,6 +61,23 @@ function JobList(props: IJobListProps) {
const prevRequestProps = useRef<IRequestProps>({});
const onListEmptyRef = useRef(onListEmpty);
const handleReadJob = useCallback(
(jobId: string) => {
const index = dataList.findIndex(d => String(d.id) === jobId);
if (index < 0) {
return;
}
const job = dataList[index];
if (!job || job.isRead) {
return;
}
log('auto mark read', jobId);
dataList.splice(index, 1, { ...job, isRead: true });
setDataList([...dataList]);
},
[dataList]
);
const handleRefresh = useCallback(async () => {
log('start pull refresh');
try {
@ -109,6 +129,13 @@ function JobList(props: IJobListProps) {
onListEmptyRef.current = onListEmpty;
}, [onListEmpty]);
useEffect(() => {
Taro.eventCenter.on(EventName.VIEW_JOB_SUCCESS, handleReadJob);
return () => {
Taro.eventCenter.off(EventName.VIEW_JOB_SUCCESS, handleReadJob);
};
}, [handleReadJob]);
useEffect(() => {
log('request params changed');
requestProps.current = {

View File

@ -39,9 +39,7 @@ function JoinEntry({ onBindSuccess }: JoinEntryProps) {
</Button>
)}
</div>
{visible && (
<LoginDialog disableCheck onCancel={() => setVisible(false)} onSuccess={onBindSuccess} needPhone={needPhone} />
)}
{visible && <LoginDialog onCancel={() => setVisible(false)} onSuccess={onBindSuccess} needPhone={needPhone} />}
</>
);
}

View File

@ -8,7 +8,51 @@
background: #6d3df5;
color: #fff;
&__simple {
&-simple {
padding: 39px 35px;
height: 120px;
box-sizing: border-box;
&__bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
border-radius: 16px;
height: 100%;
}
&__content {
.flex-row();
line-height: 42px;
position: relative;
z-index: 1;
}
&__title {
font-size: 26px;
color: #FFFFFF;
}
&__money {
font-weight: 800;
margin-left: 12px;
font-size: 44px;
}
&__button {
position: absolute;
z-index: 2;
top: 44px;
right: 24px;
font-size: 28px;
line-height: 32px;
&-image {
width: 24px;
height: 24px;
display: inline-block;
margin-left: 8px;
}
}
}
&__bg {
@ -28,20 +72,7 @@
z-index: 1;
}
&__button {
position: absolute;
z-index: 2;
top: 44px;
right: 56px;
font-size: 24px;
line-height: 24px;
&-image {
width: 20px;
height: 20px;
display: inline-block;
margin-left: 4px;
}
}
&__title {
font-style: normal;
font-weight: 400;

View File

@ -144,24 +144,37 @@ export default function PartnerKanban({ simple }: PartnerKanbanProps) {
useEffect(() => {
getProfitStats();
}, []);
if (simple) {
return (
<div className={`${PREFIX} ${PREFIX}-simple`}>
<Image
className={`${PREFIX}-simple__bg`}
src="https://publiccdn.neighbourhood.com.cn/img/partner_bg.png"
mode="aspectFill"
/>
<div className={`${PREFIX}-simple__content`}>
<div className={`${PREFIX}-simple__title`}>()</div>
<div className={`${PREFIX}-simple__money`}>{formatMoney(total)}</div>
</div>
<div className={`${PREFIX}-simple__button`} onClick={handleNavigate}>
<Image
className={`${PREFIX}-simple__button-image`}
mode="aspectFit"
src={require('@/statics/svg/caret-right.svg')}
/>
</div>
</div>
);
}
return (
<div className={`${PREFIX} ${simple ? `${PREFIX}__simple` : ''}`}>
<div className={PREFIX}>
<Image
className={`${PREFIX}__bg`}
src="https://publiccdn.neighbourhood.com.cn/img/partner_bg.png"
mode="aspectFill"
/>
<div className={`${PREFIX}__content`}>
{simple && (
<div className={`${PREFIX}__button`} onClick={handleNavigate}>
<Image
className={`${PREFIX}__button-image`}
mode="aspectFit"
src={require('@/statics/svg/caret-right.svg')}
/>
</div>
)}
<div className={`${PREFIX}__total`}>
<div className={`${PREFIX}__title`}></div>
<div className={`${PREFIX}__money`}>{formatMoney(total)}</div>
@ -183,25 +196,21 @@ export default function PartnerKanban({ simple }: PartnerKanbanProps) {
<div className={`${PREFIX}__money`}>{formatMoney(stats.availableProfit)}</div>
</div>
</div>
{!simple && (
<div className={`${PREFIX}__buttons`}>
<Button className={`${PREFIX}__withdraw`} onClick={handleViewWithdraw}>
</Button>
<Button className={`${PREFIX}__record`} onClick={handleNavigateRecord}>
</Button>
</div>
)}
<div className={`${PREFIX}__buttons`}>
<Button className={`${PREFIX}__withdraw`} onClick={handleViewWithdraw}>
</Button>
<Button className={`${PREFIX}__record`} onClick={handleNavigateRecord}>
</Button>
</div>
</div>
{!simple && <TipDialog open={tipOpen} onClose={handleTipClose} />}
{!simple && (
<WithdrawDialog
count={Math.min(Number(formatMoney(stats.availableBalance)), 200)}
open={withdrawOpen}
onClose={handleWithdrawClose}
/>
)}
<TipDialog open={tipOpen} onClose={handleTipClose} />
<WithdrawDialog
count={Math.min(Number(formatMoney(stats.availableBalance)), 200)}
open={withdrawOpen}
onClose={handleWithdrawClose}
/>
</div>
);
}

View File

@ -24,6 +24,7 @@ export enum EventName {
SELECT_MY_PUBLISH_JOB = 'select_my_publish_job',
EXIT_CHAT_PAGE = 'exit_chat_page',
VIEW_MATERIAL_SUCCESS = 'view_material_success',
VIEW_JOB_SUCCESS = 'view_job_success',
}
export enum OpenSource {

View File

@ -18,7 +18,8 @@ import {
ALL_SORT_TYPES,
EMPLOY_TYPE_TITLE_MAP,
EmployType,
JOB_TABS, JobSourceType,
JOB_TABS,
JobSourceType,
JobType,
SORT_TYPE_TITLE_MAP,
SortType,
@ -143,12 +144,7 @@ function JobFragment(props: IProps) {
return (
<div className={`${PREFIX}__container`}>
<div className={`${PREFIX}__top-search-bar`}>
<SearchInput
disabled
className={`${PREFIX}__search`}
placeholder="试试 女装"
onClick={handleClickSearch}
/>
<SearchInput disabled className={`${PREFIX}__search`} placeholder="试试 女装" onClick={handleClickSearch} />
<div className={classNames(`${PREFIX}__employType-select`)} onClick={handleClickEmployTypeSelect}>
<div className="title">
{employType && employType !== EmployType.All ? EMPLOY_TYPE_TITLE_MAP[employType] : '类型'}

View File

@ -1,5 +1,6 @@
// export const DOMAIN = 'http://192.168.60.191:8082';
export const DOMAIN = process.env.BRAND === 'dev' ? 'https://dev.neighbourhood.cn' : 'https://neighbourhood.cn';
// export const DOMAIN = 'https://dev.neighbourhood.cn';
export const BASE_URL = `${DOMAIN}/api`;
export enum API {

View File

@ -286,6 +286,7 @@ export default function JobDetail() {
if (!jobId) {
return;
}
Taro.eventCenter.trigger(EventName.VIEW_JOB_SUCCESS, jobId);
try {
const res = await requestJobDetail(jobId);
setData(res);

View File

@ -17,6 +17,7 @@ export interface JobInfo {
distance?: number; // 距离。一期没有
isAuthed?: boolean; // 是否认证
companyName?: string;
isRead?: boolean;
}
export interface CreateJobInfo extends Pick<JobInfo, 'title' | 'employType' | 'jobDescription'> {