React 仪器租赁项目

深处莫神
发布于 2022-11-11 23:19
浏览
0收藏

React Vant 组件链接

遇见的错误

警告错误 PascalCase

React 仪器租赁项目 -鸿蒙开发者社区

解决方案:
由于我的组件命名为了Left_nav这种格式的,把组件名给改成了LeftNav成功消除了警告信息。记得组件名第一个字母需得大写,后面用驼峰命名

注册界面

Form表单的使用:

表单

记得先需要初始化表单元素:

const register = () => {
    //初始化表单元素
    const [form] = React.$Vant.Form.useForm()
}
手机号

注意:表单input在vue2不是<input> 而是 Field

{/* 手机号 */}
<div className="wrap-input100 validate-input m-b-10">
    <React.$Vant.Form.Item
        name="mobile"
        label="手机号"
        rules={[
            { required: true, message: '请输入手机号码' },
            { pattern: /^1[3456789]{1}\d{9}$/, message: '请输入正确格式的手机号' }
        ]}
    >
        <React.$Vant.Field placeholder="请输入手机号码" />
    </React.$Vant.Form.Item>
</div>
密码
{/* 密码 */}
<div className="wrap-input100 validate-input m-b-10">
    <React.$Vant.Form.Item
        name="password"
        label="密码"
        rules={[
            { required: true, message: '请输入密码' },
        ]}
    >
        <React.$Vant.Field type="password" placeholder="请输入密码" />
    </React.$Vant.Form.Item>
</div>

注册的提交按钮:

<div className="container-login100-form-btn p-t-10">
    <React.$Vant.Button nativeType="submit" className="login100-form-btn">注 册</React.$Vant.Button>
</div>

链接跳转:

首先:需要初始化路由跳转对象

const register = () => {
    //钩子函数初始化路由跳转对象
    const navigate = React.$Router.useNavigate()
}
<React.$Router.NavLink to='/business/base/login' className="txt1">立即登录</React.$Router.NavLink>

后端:

创建模块:php think build --module rent

创建控制器:php think make:controller rent/business/Base

构建api接口请求,需要安装异步请求工具axios

安装异步请求工具axios
yarn add axios -S

去git拿到封装好的请求服务封装request.js文件,需要改一下请求前缀
React 仪器租赁项目 -鸿蒙开发者社区

需要注意,改完请求的默认前缀之后,需要修改前端的代理配置

api接口请求:

路径 - - rent\src\api\business\base.js

//引入封装的请求服务
import { POST, UPLOAD } from '@/services/request.js'

//导出接口
const base = {
  register(data = {})
  {
    return POST({
      // /rent/business/base/register
      url: '/business/base/register',
      params: data
    })
  },
  login(data = {})
  {
    return POST({
      url: '/business/base/login',
      params: data
    })
  },
}

export default base

前端接收到后端请求的数据信息:

//钩子函数初始化路由跳转对象
const navigate = React.$Router.useNavigate()

const finish = async (values) => {
    var result = await React.$API.login(values)

    if (result.code) {
        React.$Vant.Notify.show({
            type: 'success',
            message: result.msg,
            duration: 1000,
            onClose: () => {

                // 存放cookie的语法
                React.$Cookie.save('LoginAuth', result.data)
                React.$LoginAuth = result.data

                navigate(result.url)
            }
        })

    } else {
        React.$Vant.Notify.show({
            type: 'danger',
            message: result.msg
        })

        return false
    }
}

cookie

安装cookie:

yarn add react-cookies -S

路径 - - rent\src\index.js

挂载cookie:

// 引入cookie
import cookie from 'react-cookies'

//挂载全局自定义属性
React.$Cookie = cookie

将登录信息做一个react全局属性

//将我们的登录信息,做一个React全局属性,如果没有登录就给空对象,如果有登录就给cookie信息
React.$LoginAuth = cookie.load('LoginAuth') ? cookie.load('LoginAuth') : {}

使用cookie:

路径 - - rent\src\components\business\base\index.js

/设置状态数据
const [LoginAuth, setLoginAuth] = React.useState(React.$LoginAuth)
//用钩子函数来代替生命周期
React.useEffect(() => {
    var LoginAuth = React.$Cookie.load('LoginAuth') ? React.$Cookie.load('LoginAuth') : {}

    // console.log(LoginAuth)

    //设置状态数据
    setLoginAuth(LoginAuth)
}, [])  

前端输出:
React 仪器租赁项目 -鸿蒙开发者社区

如果有昵称,则输出昵称,如果没有昵称则输出手机号,如果没有手机号则显示请先登录

const NickName = () => {
    if (LoginAuth.nickname) {
        return (
            <h2>{LoginAuth.nickname}</h2>
        )
    } else if (LoginAuth.mobile) {
        return (
            <h2>{LoginAuth.mobile_text}</h2>
        )
    } else {
        return (
            <h2>请先登录</h2>
        )
    }
}

如果没有登录需要跳转到登录

首先 在路由中组装登录组件

路径 — rent\src\routers\index.js
React 仪器租赁项目 -鸿蒙开发者社区

<Route key={idx} path={son.path} element={<AuthRouter auth={son.auth} component={<son.component />} />}></Route>

一开始点击我的页面的时候,需要判断用户是否有登录,如果没有登录,则点击我的 的时候需要跳转到登录界面

路径 - - rent\src\routers\auth.js

做的一个路由:

import React from 'react'
import {Navigate} from 'react-router-dom'


const AuthRouter = (props) => 
{
    // console.log(props)

    // 根据传递过来的props里面的auth属性来判断路由是否需要登录
    if(props.auth)
    {
        //说明需要登录

        //获取cookie的信息
        var LoginAuth = React.$Cookie.load('LoginAuth') ? React.$Cookie.load('LoginAuth') : {}

        if(!LoginAuth || JSON.stringify(LoginAuth) === "{}")
        {
            //说明没有cookie 意味着没有登录,跳转到登录界面去
            return (
                <Navigate to="/business/base/login" />
            )
        }else
        {
            //说明有cookie,那就显示给他当前访问的页面组件
            return (
                <>
                    {props.component}
                </>
            )
        }
    }else
    {
        //不需要登录
        return (
            <>
                {props.component}
            </>
        )
    }
}

export default AuthRouter

登录的时候需要获取cookie内的信息:

调用login登录接口之后,看是否有用户信息,有信息则登录,并且存放cookie的信息

const finish = async (values) => {
    var result = await React.$API.login(values)

    if (result.code) {
        React.$Vant.Notify.show({
            type: 'success',
            message: result.msg,
            duration: 1000,
            onClose: () => {

                // 存放cookie的语法
                React.$Cookie.save('LoginAuth', result.data)
                React.$LoginAuth = result.data

                navigate(result.url)
            }
        })

    } else {
        React.$Vant.Notify.show({
            type: 'danger',
            message: result.msg
        })

        return false
    }
}

退出登录

组件:

<div className="my_dind">
    <div className="bt">
        <a onClick={logout}>
            <h3><img src="/assets/images/my_x_02.png" alt="" />退出登录</h3>
            <div className="right">
                <img src="/assets/images/right_jiant.png" alt="" />
            </div>
        </a>
    </div>
</div>

使用路由跳转:

//钩子函数初始化路由跳转对象
const navigate = React.$Router.useNavigate()

触发登录事件:onClick={logout}

路径 - - rent\src\components\business\base\index.js

// 退出登录
const logout = () => {
    React.$Vant.Dialog.confirm({
        title: '退出提醒',
        message: '是否确认退出登录'
    }).then(() => {
        //删除cookie,并跳转到登录界面
        React.$Cookie.remove('LoginAuth')
        React.$LoginAuth = {}

        //跳转到登录界面
        navigate('/business/base/login')
    })
        .catch(() => { })
}

修改个人资料

组件:

手机号:

<React.$Vant.Form form={form} onFinish={profile}>
    <React.$Vant.Form.Item
      label="手机号"
      name="mobile"
      initialValue={LoginAuth.mobile}
      rules={[
        {required:true, message: '请输入手机号'}
      ]}
    >
      <React.$Vant.Field disabled />
    </React.$Vant.Form.Item>
</React.$Vant.Form>

密码:

<React.$Vant.Form.Item
  name="password"
  label="密码"
>
  <React.$Vant.Field placeholder="留空,不需要密码" />
</React.$Vant.Form.Item>

邮箱:

<React.$Vant.Form.Item
  name="email"
  label="邮箱"
  initialValue={LoginAuth.email}
  rules={[
    {required:true, message: '请输入邮箱'},
    {type:'email', message: '请输入正确的邮箱格式'}
  ]}
>
  <React.$Vant.Field placeholder="请输入邮箱" />
</React.$Vant.Form.Item>

性别:

Popup:弹出方式 bottom:从底部弹出
picker 下拉选择框
点击性别的时候,设置显示为true - - SetGenderShow(true)},点击取消时则关闭
defaultIndex:默认选中(0,1,2数字)

{/* 性别 */}
<React.$Vant.Form.Item
    label="性别"
    onClick={() => {SetGenderShow(true)}}
  >
  <React.$Vant.Field placeholder="请选择性别" isLink readonly value={LoginAuth.gender_text} />
</React.$Vant.Form.Item>

<React.$Vant.Popup position="bottom" round visible={GenderShow} onClose={() => {SetGenderShow(false)}}>
  <React.$Vant.Picker 
    title="性别" 
    columns={GenderList} 
    defaultIndex={LoginAuth.gender}
    onConfirm={GenderConfirm} 
    onCancel={() => {SetGenderShow(false)}}  
  />
</React.$Vant.Popup>

获取性别数据:

 // 表单内容
  const [form] = React.$Vant.Form.useForm()

  // 性别
  const [GenderShow, SetGenderShow] = React.useState(false)
  const GenderList = [
    {text:'保密', value:0},
    {text:'男', value:1},
    {text:'女', value:2},
  ]

 //点击确认按钮
  const GenderConfirm = (gender) => 
  {
    //隐藏picker
    SetGenderShow(false)

    LoginAuth.gender = gender.value
    LoginAuth.gender_text = gender.text

    SetLoginAuth(LoginAuth)
  }

地区:

安装城市地区数据代码:

//安装城市地区数据
yarn add @vant/area-data -S

引入地区数据:

import { areaList } from '@vant/area-data'

地区数据:

RegionStr—地区 RegionCode—地区码

  //地区
  const [RegionShow, SetRegionShow] = React.useState(false)
  const [region, SetRegion] = React.useState('')
  const [code, SetCode] = React.useState('')

  //初始化地区,获取cookie中的省市区
  const RegionInit = () => 
  {
    var RegionStr = ''
    var RegionCode = ''
    if(LoginAuth.province_text)
    {
      RegionStr += LoginAuth.province_text
      RegionCode = LoginAuth.province
    }
  
    if(LoginAuth.city_text)
    {
      RegionStr += `/${LoginAuth.city_text}`
      RegionCode = LoginAuth.city
    }
  
    if(LoginAuth.district_text)
    {
      RegionStr += `/${LoginAuth.district_text}`
      RegionCode = LoginAuth.district
    }

    SetRegion(RegionStr)
    SetCode(RegionCode)
  }

 //选择地区后,点击确认按钮的时候,调用RegionInit()
  const RegionConfirm = (result) => 
  {
    SetRegionShow(false)
    
    var [province, city, district] = result

    LoginAuth.province = province.code
    LoginAuth.province_text = province.name

    LoginAuth.city = city.code
    LoginAuth.city_text = city.name

    LoginAuth.district = district.code
    LoginAuth.district_text = district.name

    SetLoginAuth(LoginAuth)

    RegionInit()
  }

地区组件:

{/* 地区 */}
<React.$Vant.Form.Item
  label="地区"
  onClick={() => {SetRegionShow(true)}}
>
  <React.$Vant.Field placeholder="请选择地区" isLink readonly value={region} />
</React.$Vant.Form.Item>

<React.$Vant.Popup position="bottom" round visible={RegionShow} onClose={() => {SetRegionShow(false)}}>
  <React.$Vant.Area
    title="请选择地区"
    areaList={areaList}
    value={code}
    onCancel={() => {SetRegionShow(false)}}
    onConfirm={RegionConfirm}
  />
</React.$Vant.Popup>

头像:

头像组件:

Uploader 文件上传 ,maxCount:最多选择一张 initialValue:初始值

头像:

//头像
const [avatar, SetAvatar] = React.useState([
  {url: LoginAuth.avatar_text}
])

{/* 头像 */}
<React.$Vant.Form.Item
  label="头像"
  name="avatar"
  initialValue={[
    {url: LoginAuth.avatar_text}
  ]}
>
  <React.$Vant.Uploader maxCount={1} value={avatar}  />
</React.$Vant.Form.Item>

表单提交:

在页面直接提交

//表单提交
const profile = async (form) =>
{
  // console.log(form);
  // console.log(LoginAuth);

  //组装数据
  var data = {
    id: LoginAuth.id,
    nickname: form.nickname,
    email: form.email,
    gender: LoginAuth.gender,
    province: LoginAuth.province,
    city: LoginAuth.city,
    district: LoginAuth.district,
  }

  //判断密码有填写在去修改
  if(form.password)
  {
    data.password = form.password
  }

  //判断有头像数据,在去更新
  if(form.avatar.length > 0 && form.avatar[0].file)
  {
    data.avatar = form.avatar[0].file
  }

  // console.log(data)

  //调用接口
  var result = await React.$API.profile(data)
 
//如果更新成功
  if(result.code)
  {
    React.$Vant.Notify.show({
      type:'success',
      message: result.msg,
      duration: 1000,
      onClose: () => {
          // 重新覆盖cookie
          React.$Cookie.save('LoginAuth', result.data)
          React.$LoginAuth = result.data

	//返回上一个界面
          navigate(-1)
      }
    })
  }else
  {
 //更新资料失败
    React.$Vant.Notify.show({
      type:'danger',
      message: result.msg
    })
  }
}
修改资料后端

isPost()请求 或者 isAjax()都可以 ,都是axios异步请求

// 修改资料
public function profile()
{
  //isPost()请求 或者 isAjax()都可以

    if($this->request->isAjax())
    {
        $params = $this->request->param();

        $id = $this->request->param('id', 0, 'trim');
        $nickname = $this->request->param('nickname', '', 'trim');
        $email = $this->request->param('email', '', 'trim');
        $gender = $this->request->param('gender', '', 'trim');
        $province = $this->request->param('province', '', 'trim');
        $city = $this->request->param('city', '', 'trim');
        $district = $this->request->param('district', '', 'trim');
        $password = $this->request->param('password', '', 'trim');

        //先确认这个用户是存在
        $business = $this->BusinessModel->find($id);

        if(!$business)
        {
            $this->error('用户不存在');
            exit;
        }

        //组装数据
        $data = [
            'id' => $id,
            'nickname' => $nickname,
            'email' => $email,
            'gender' => $gender,
            'province' => $province,
            'city' => $city,
            'district' => $district,
        ];

        //判断是否有修改过邮箱,如果有修改过邮箱,那么认证状态也要修改
        if($email != $business['email'])
        {
            $data['status'] = 0;
        }

        //判断密码是否要修改
        if(!empty($password))
        {
            //重新生成密码盐
            $salt = build_ranstr();

            $password = md5($password.$salt);

            $data['password'] = $password;
            $data['salt'] = $salt;
        }

        //接收文件上传
        if(isset($_FILES['avatar']) && $_FILES['avatar']['size'] > 0)
        {
            //调用公共方法
            $success = build_upload('avatar');

            if($success['result'])
            {
                //上传成功
                $data['avatar'] = $success['data'];
            }else
            {
                //上传失败
                $this->error($success['msg']);
                exit;
            }
        }

        //准备更新数据库
        $result = $this->BusinessModel->validate('common/Business/Business.ShopProfile')->isUpdate(true)->save($data);

        if($result === FALSE)
        {
            $this->error($this->BusinessModel->getError());
            exit;
        }else
        {
            //更新资料成功
            //删除旧图片,更新cookie
            if(isset($data['avatar']))
            {
                //判断旧图片是否存在,如果存在就删除掉
                @is_file(".".$business['avatar']) && unlink(".".$business['avatar']);
            }

            //查询一次最新的数据出来,并返回
            $update = $this->BusinessModel->find($id);

            $this->success('修改成功', '/business/base/index', $update);
            exit;
        }
    }
}	

邮箱验证

省略:装api接口,安装路由

在首页页面中:

路径 - - rent老师\src\components\business\base\index.js

const Email = () => {
    // 未认证
    if(LoginAuth.status != 1)
    {
      return (
        <div className="my_dind">
          <div className="bt">
            <React.$Router.NavLink to="/business/base/ems">
              <h3><img src="/assets/images/my_x_01.png" alt="" />邮箱认证</h3>
              <div className="right"> 
                <img src="/assets/images/right_jiant.png" alt="" />
              </div> 
            </React.$Router.NavLink>
          </div>
        </div>
      )
    }else
    {
      return (
        <></>
      )
    }
  }

邮箱组件 + 验证码:

验证码:点击获取验证码的时候,触发send发送事件,并且其为禁止点击,设置定时器进行60s倒计时。

  //设置状态数据
  const [LoginAuth, SetLoginAuth] = React.useState(React.$LoginAuth)
  const [msg, SetMsg] = React.useState('发送验证码')
  const [disabled, SetDisabled] = React.useState(false)

{msg}是上面的const–msg数据
验证码:

<React.$Vant.Form.Item
  name="code"
  label="验证码"
  rules={[
    {required:true, message: '请输入邮箱'}
  ]}
>
  <React.$Vant.Field
    placeholder="请输入邮箱验证码"
    suffix={
      <React.$Vant.Button size="small" type="primary" disabled={disabled} onClick={send}>{msg}</React.$Vant.Button>
    }
  />
</React.$Vant.Form.Item>

点击发送验证码之后,触发send点击事件:


  const send = async () => 
  {

    //先组装数据
    var data = {
      id: LoginAuth.id
    }

   //调用后端sendmsg()发送验证码方法
    var result = await React.$API.sendems(data)

   //如果发送验证码成功
    if(result.code)
    {
      React.$Vant.Notify.show({
        type:'success',
        message: result.msg
      })
    }else
    {
      React.$Vant.Notify.show({
        type:'danger',
        message: result.msg
      })
    }


    //定时器
    var sec = 60
    let T = setInterval(() => {
      // 修改msg内容
      SetMsg(`${sec} s`)
      //设置按钮禁用
      SetDisabled(true)

      //停止定时器
      if(sec <= 0)
      {
        clearInterval(T)
        sec = 60
        SetDisabled(false)
        SetMsg('重新发送验证码')
        return false
      }else
      {
        sec--
      }
    }, 10)
    
  }

后端发送验证码方法:

/**
    * 发送邮箱验证码
    */
public function sendems()
{
    if($this->request->isAjax())
    {
        //接收id
        $id = $this->request->param('id', 0, 'trim');

        //判断一下 有没有这个人
        $business = $this->BusinessModel->find($id);

        if(!$business)
        {
            $this->error('用户不存在');
            exit;
        }

        $email = trim($business['email']);

        //判断邮箱是否为空
        if(empty($email))
        {
            $this->error('邮箱为空,无法验证,请先更新邮箱地址');
            exit;
        }

        //生成一个新的验证码
        $code = build_ranstr(6);


        //组装数据
        $data = [
            'event' => 'EmailCheck', //自定义
            'email' => $email,
            'code' => $code,
        ];

        //要将发送成功的验证码插入到数据中
        //开启事务
        $this->EMSModel->startTrans();

        //插入数据
        $result = $this->EMSModel->save($data);

        if($result === FALSE)
        {
            $this->error('验证码添加失败');
            exit;
        }
        
        //调用方法
        $success = send_email($email, $code);

        //邮件发送失败
        if(!$success['result'])
        {
            //回滚插入的验证码记录
            $this->EMSModel->rollback();

            $this->error($success['msg']);
            exit;
        }else
        {
            //提交事务
            $this->EMSModel->commit();
            $this->success('验证码发送成功,请注意查收');
            exit;
        }
    }
}

提交表单验证邮箱

表单组件:

<React.$Vant.Form form={form} onFinish={ems}>
    ......
</React.$Vant.Form>

提交后触发ems事件:

const ems = async (form) => 
{    
  // 组装数据
  var data = {
    id: LoginAuth.id,
    code: form.code
  }

  //调用接口
  var result = await React.$API.checkems(data)

  if(result.code)
  {
    React.$Vant.Notify.show({
      type:'success',
      message: result.msg,
      duration: 1000,
      onClose: () => {
          // 重新覆盖cookie
          React.$Cookie.save('LoginAuth', result.data)
          React.$LoginAuth = result.data
          navigate(-1)
      }
    })
  }else
  {
    React.$Vant.Notify.show({
      type:'danger',
      message: result.msg
    })
  }
}

后端验证邮箱的方法:

/**
    * 验证邮箱
    */
public function checkems()
{
    if($this->request->isAjax())
    {
        $id = $this->request->param('id', 0, 'trim');
        $code = $this->request->param('code', 0, 'trim');

        //判断用户是否存在
        $business = $this->BusinessModel->find($id);

        if(!$business)
        {
            $this->error('用户不存在');
            exit;
        }

        if(empty($business['email']))
        {
            $this->error('您的邮箱为空,请先修改邮箱');
            exit;
        }

        if($business['status'])
        {
            $this->error('您已通过邮箱验证,无须重复验证');
            exit;
        }

        //根据条件查询出验证码记录
        $where = [
            'email'=>$business['email'],
            'code' => $code
        ];

        $ems = $this->EMSModel->where($where)->find();

        if(!$ems)
        {
            $this->error("验证码有误,请重新输入");
            exit;
        }
        
        // 验证码的时间 验证码失效时间
        $checktime = $ems['createtime'] + 3600*24;

        if($checktime < time())
        {
            //直接删除
            $this->EMSModel->destroy($ems['id']);

            $this->error('验证码过期');
            exit;
        }

        //更新验证状态
        // 1.更新用户表 2.验证码的删除
        $this->BusinessModel->startTrans();
        $this->EMSModel->startTrans();

        //更新用户表
        $BusessinData = [
            'id' => $business['id'],
            'status' => 1
        ];

        $BusessinStatus = $this->BusinessModel->isUpdate(true)->save($BusessinData);

        if($BusessinStatus === FALSE)
        {
            $this->error('更新用户验证状态失败');
            exit;
        }


        //删除验证记录
        $EMStatus = $this->EMSModel->destroy($ems['id']);

        if($EMStatus === FALSE)
        {
            $this->BusinessModel->rollback();
            $this->error('验证码删除失败');
            exit;
        }

        if($BusessinStatus === FALSE || $EMStatus === FALSE)
        {
            $this->EMSModel->rollback();
            $this->BusinessModel->rollback();
            $this->error('验证失败');
            exit;
        }else
        {
            //提交事务
            $this->BusinessModel->commit();
            $this->EMSModel->commit();

            //查询一次最新的数据出来,并返回
            $update = $this->BusinessModel->find($id);

            $this->success('邮箱验证成功', null, $update);
            exit;
        }
    }
}

文章列表

做上拉加载,下拉刷新效果

需要用到分页,先引入:

const [page, SetPage] = React.useState(1)

文章列表组件:

触发下拉加载,下拉刷新 :refresh事件

{/* 文章列表 */}
<React.$Vant.PullRefresh
    onRefresh={refresh}
>
    <React.$Vant.List className="catelist" finished={finished} onLoad={load} offset={5} loading={loading} autoCheck={false}>
        <Items />
    </React.$Vant.List>
</React.$Vant.PullRefresh>
</div>

refresh事件:

设置定时器:1s后完成,并且提示信息,先需要把列表数据和分页数据清空

// 刷新
const refresh = async () => 
{
//清空列表数据
    SetList([])
  //设置分页数据为第一页,刷新后回到第一页
    SetPage(1)
    SetFinished(false)
    return new Promise((resolve) => {
        setTimeout(() => {
    
	//调用ListData()函数
            ListData()
            React.$Vant.Toast.info('刷新成功')
            resolve(true)
        }, 1000)
    })
}

页面详细信息

解析数据库的html标签输出

react输出描述内容 用dangerouslySetInnerHTML 解析html标签:

<div className="wom_de" dangerouslySetInnerHTML={{__html:info.description}}></div>

页面上下篇

组件使用:

<div className="shangxia_piab">
    <PrevCate />
    <NextCate />
</div>

上一篇 方法:

首先,每次点击外部的时候,都是需要获取id,因此初始化路由参数对象 - - 获取id

    const [id, SetID] = useState(searchParams.get('id'))
const PrevCate = () => 
{
  //定义ToPrev,链接跳转后 刷新navigate(0)
    let ToPrev = () =>
    {
        SetID(prev.id)
        navigate(`/business/category/info?id=${prev.id}`)
        navigate(0)
    }

  //如果有数据 ,则点击返回上一篇
    if(prev)
    {
        return (
            <p>上一篇:
                <a onClick={ToPrev}>{prev.name}</a>
            </p>
        )
    }else
    {
        return (
            <p>上一篇:已经到顶了</p>
        )
    }
}

下一篇同理。

数据输出时

   //初始化路由参数对象
    const [info, SetInfo] = React.useState({})

组件:info.()输出信息 –

<div className="bt">
    <h2>{info.name}</h2>
    <div className="text">
        <span>{info.createtime_text}</span>
        <span>文章作者:{info.nickname}</span>
    </div>
</div>

轮播图

轮播图组件:

{/* banner 图片 */}
<div className="banner_shouy">
  <React.$Vant.Swiper>
    {Banner()}
  </React.$Vant.Swiper>
</div>

Banner方法:

const Banner = () => {
  if (hot) {
    return hot.map((item, index) => {
      return (
        <React.$Vant.Swiper.Item key={index}>
          <React.$Router.NavLink to={`/business/category/info?id=${item.id}`}>
            <img alt="" src={item.image_text} />
          </React.$Router.NavLink>
        </React.$Vant.Swiper.Item>
      )
    })
  }
}

产品中心

React 仪器租赁项目 -鸿蒙开发者社区

组件:

<React.$Vant.ActionBar>
  <React.$Vant.ActionBar.Icon text="首页" icon={<React.$Icon.ShopO  />} onClick={home} />
  {check()}
  <React.$Vant.ActionBar.Button type="danger" text="立即租赁" onClick={lease} />
</React.$Vant.ActionBar>

首页跳转:

const home = () =>
{
  navigate('/')
}

收藏:
走验证场景验证器:

模型:

/**
    * 验证场景
    */
protected $scene = [
    //我们根据业务场景 分配了不同 验证模式 自定义
    'category' => ['busid', 'cateid'],
    'product' => ['busid', 'proid']
];  

控制器:

$result = $this->CollectionModel->validate('common/Business/Collection.category')->save($data);

收藏与取消收藏:

因为收藏与取消收藏是需要登录后才可以进行的操作,并且还需要知道操作是进行的是收藏 还是 取消收藏。

组件用checked :
React 仪器租赁项目 -鸿蒙开发者社区

添加 collection:

const [collection, SetCollection] = React.useState(false)

collection从后端产品中获取的数据:
React 仪器租赁项目 -鸿蒙开发者社区

const check = () =>
{
  if(collection)
  {
    return (
      <React.$Vant.ActionBar.Icon text="已收藏" icon={<React.$Icon.Star color="#f44336" />} onClick={cancel} />
    )
  }else
  {
    return (
      <React.$Vant.ActionBar.Icon text="收藏" icon={<React.$Icon.StarO  />} onClick={Collection} />
    )
  }
}

收藏:

调用后端接口:

// 收藏
const Collection = async () =>
{
  if(!LoginAuth || JSON.stringify(LoginAuth) === "{}")
  {
    React.$Vant.Toast.info('请先登录')
    return false
  }

  //组装数据
  var data = {
    busid: LoginAuth.id,
    proid: pid
  }

  var result = await React.$API.ProductCollection(data)

  if(result.code)
  {
    React.$Vant.Notify.show({
      type:'success',
      message: result.msg,
      duration: 1000,
      onClose: () => {            
          SetCollection(true)
      }
    })
  }else
  {
    React.$Vant.Notify.show({
      type:'danger',
      message: result.msg
    })
  }
}

收藏的后端代码:

// 收藏方法
public function collection()
{
    if($this->request->isPost())
    {
        $proid = $this->request->param('proid', 0, 'trim');
        $busid = $this->request->param('busid', 0, 'trim');

        //先找出商品是否存在
        $product = $this->ProductModel->find($proid);

        if(!$product)
        {
            $this->error('收藏商品不存在');
            exit;
        }

        //组装数据
        $data = [
            'busid' => $busid,
            'proid' => $proid
        ];

        $result = $this->CollectionModel->validate('common/Business/Collection.product')->save($data);

        if($result === FALSE)
        {
            $this->error($this->CollectionModel->getError());
            exit;
        }else
        {
            $this->success('收藏成功');
            exit;
        }
    }
}

取消收藏调用接口:

//取消收藏
let cancel = async () => 
{
    //组装数据
    var data = {
    proid: pid,
    busid: LoginAuth.id
    }

    var result = await React.$API.ProductCancel(data)

    if(result.code)
    {
        React.$Vant.Notify.show({
            type:'success',
            message: result.msg,
            duration: 1000,
            onClose: () => {            
                SetCollection(false)
            }
        })
    }else
    {
        React.$Vant.Notify.show({
            type:'danger',
            message: result.msg
        })
    }
}

取消收藏的后端代码:

// 取消收藏方法
public function cancel()
{
    $proid = $this->request->param('proid', 0, 'trim');
    $busid = $this->request->param('busid', 0, 'trim');

    //先找出商品是否存在
    $product = $this->ProductModel->find($proid);

    if(!$product)
    {
        $this->error('收藏商品不存在');
        exit;
    }

    //组装数据
    $where = [
        'busid' => $busid,
        'proid' => $proid
    ];

    //删除记录
    $result = $this->CollectionModel->destroy($where);

    if($result === FALSE)
    {
        $this->error($this->CollectionModel->getError());
        exit;
    }else
    {
        $this->success('取消收藏成功');
        exit;
    }
}

分类
标签
已于2022-11-18 22:09:01修改
收藏
回复
举报
回复
    相关推荐