vue3项目开发过程中所遇到的问题积累

本篇文章呢主要是想对自己平时在开发项目时遇到的问题做一下记录,方便自己后续复习,后续会继续更新这个文档的

1、百度地图功能

在这里插入图片描述
实现代码

<template>
    <div class="bmapgl">
      <el-dialog
        :model-value="openMap"
        title="位置选择"
        width="1000px"
        @close="cancel"
      >
        <el-form label-width="80px">
          <el-row>
            <el-col :span="10">
              <el-form-item label="当前地点">
                <el-input
                  size="small"
                  type="text"
                  id="suggestId"
                  v-model="addressInfo.address"
                  placeholder="请输入地点"
                  @blur="onBlurClick"
                />
              </el-form-item>
            </el-col>
            <el-col :span="7">
              <el-form-item label="位置经度">
                <el-input
                  size="small"
                  type="text"
                  v-model="addressInfo.longitude"
                  readonly
                />
              </el-form-item>
            </el-col>
            <el-col :span="7">
              <el-form-item label="位置纬度">
                <el-input
                  size="small"
                  type="text"
                  v-model="addressInfo.latitude"
                  readonly
                />
              </el-form-item>
            </el-col>
          </el-row>
        </el-form>
        <div
          class="baidu"
          ref="mapRef"
          id="baidumap"
          style="width: 100%; height: 450px"
        ></div>
        <template #footer>
          <span class="dialog-footer">
            <el-button @click="cancel">取 消</el-button>
            <el-button type="primary" @click="confirmSelect"> 确 定 </el-button>
          </span>
        </template>
      </el-dialog>
    </div>
  </template>
   
  <script setup >
  import { onMounted, watch, ref, reactive } from "vue";
  import { ElMessage } from "element-plus";
  const emit = defineEmits(["confirmMapAddress"]);
  const props = defineProps({
    openMap:{
      type:Boolean,
      default:false,
    },
    address:{
      type:String,
      default:''
    },
    longitude:{
      type:[Number,String],
    },
    latitude:{
      type:[Number,String]
    }
  })
  let map = ref(null);
  const mapZoom = ref(15);
  const ak = ref("7eVTXNtnM12OxEIly2uL6uBaj9YRtOmy");
  // let mapShow = ref(false);
  let addressInfo = reactive({
    // 地址信息
    longitude: "", // 经度
    latitude: "", // 纬度
    province: "", // 省
    city: "", // 市
    district: "", // 区
    address: "", // 详细地址
  });
  watch(
    () => props.openMap,
    () => {
      if (!props.openMap) {
        map.value && map.value.destroy();
      }else{
        // initMap();
        init()
      }
    },
    { deep: true }
  );
  onMounted(() => {
    init()
    // initMap();
  });
  let geocoder;
  const init = () => {
    map.value = null;
    BMPGL(ak.value).then((BMapGL) =>{
      map.value = new BMapGL.Map("baidumap");
      var zoomCtrl = new BMapGL.ZoomControl(); // 添加缩放控件
      map.value.addControl(zoomCtrl);
      var cityCtrl = new BMapGL.CityListControl(); // 添加城市列表控件
      map.value.addControl(cityCtrl);
      var LocationControl = new BMapGL.LocationControl(); // 添加定位控件,用于获取定位
      map.value.addControl(LocationControl);
      var scaleCtrl = new BMapGL.ScaleControl(); // 添加比例尺控件
      map.value.addControl(scaleCtrl);
      map.value.setMapType(); // 设置地图类型为标准地图模式;
      var localcity = new BMapGL.LocalCity();
      localcity.get((e) => {
        map.value.centerAndZoom(e.name, mapZoom.value);
      });
   
      let point;
      addressInfo.address = props.address
      if( props.longitude !== ''){
        addressInfo.longitude = Number(props.longitude)
      }
      if(props.latitude !== ''){
        addressInfo.latitude = Number(props.latitude)
      }
      //初始化的时候如果有经纬度,需要先在地图上添加点标记
      if (addressInfo.longitude && addressInfo.latitude) {
        point = new BMapGL.Point(addressInfo.longitude, addressInfo.latitude);
        map.value.centerAndZoom(point, mapZoom.value);
        var marker2 = new BMapGL.Marker(point);
        //在地图上添加点标记
        setTimeout(()=> {
          map.value.addOverlay(marker2);
          var opts = {
            width : 200,     // 信息窗口宽度
            height: 80,     // 信息窗口高度
            title : "地址" , // 信息窗口标题
            enableMessage:false,//设置允许信息窗发送短息
          }
          var infoWindow = new BMapGL.InfoWindow(addressInfo.address, opts);  // 创建信息窗口对象 
          map.value.openInfoWindow(infoWindow,point);
        },1000)
      }
   
      map.value.enableScrollWheelZoom(true);
      map.value.setHeading(64.5);
      map.value.setTilt(73);
      geocoder = new BMapGL.Geocoder();

      //点击下拉框的值
      map.value.addEventListener(
        "click",
        function (e) {
          // 判断是否点击了标注点
          if(!e.overlay || !(e.overlay instanceof BMapGL.Marker)){
            map.value.clearOverlays();
            var point1 = new BMapGL.Point(e.latlng.lng, e.latlng.lat);
            // 创建点标记
            var marker1 = new BMapGL.Marker(point1);
            // 在地图上添加点标记
            map.value.addOverlay(marker1);
  
            addressInfo.longitude = e.latlng.lng;
            addressInfo.latitude = e.latlng.lat;
            // var geoc = new BMapGL.Geocoder(); // 创建地址解析器的实例
            geocoder.getLocation(point1, (rs) => {
              let adr = rs.addressComponents;
              addressInfo.address =
                adr.province +
                adr.city +
                adr.district +
                adr.street +
                adr.streetNumber; // 省市区街道门牌号
            });
          }
        }
      );
    })
  }
  const onBlurClick = (event) => {
    addressInfo.address = event.target.value
    if(addressInfo.address && addressInfo.address !== ''){
      geocoder.getPoint(
        addressInfo.address,
        pot => {
          if (pot) {
            addressInfo.longitude = pot.lng;
            addressInfo.latitude = pot.lat;
            map.value.clearOverlays();
            var point1 = new BMapGL.Point(pot.lng, pot.lat);
            map.value.centerAndZoom(point1, mapZoom.value);
            // 创建点标记
            var marker1 = new BMapGL.Marker(point1);
            // 在地图上添加点标记
            map.value.addOverlay(marker1); 
          } else {
            addressInfo.address = ''
            addressInfo.longitude = '';
            addressInfo.latitude = '';
            map.value.clearOverlays();
          }
        },
        {
          // 这里可以设置地址解析的选项
        }
      );
    }else{
      addressInfo.longitude = '';
      addressInfo.latitude = '';
      map.value.clearOverlays();
    }
  }

  const initMap = () => {
    map.value = null;
    BMPGL(ak.value).then((BMapGL) => {
      map.value = new BMapGL.Map("baidumap");
      
      var ac = new BMapGL.Autocomplete({
        //建立一个自动完成的对象
        input: "suggestId",
        location: map.value,
      });
      ac.enableAutoComplete = false
      var zoomCtrl = new BMapGL.ZoomControl(); // 添加缩放控件
      map.value.addControl(zoomCtrl);
      var cityCtrl = new BMapGL.CityListControl(); // 添加城市列表控件
      map.value.addControl(cityCtrl);
      var LocationControl = new BMapGL.LocationControl(); // 添加定位控件,用于获取定位
      map.value.addControl(LocationControl);
      var scaleCtrl = new BMapGL.ScaleControl(); // 添加比例尺控件
      map.value.addControl(scaleCtrl);
      map.value.setMapType(); // 设置地图类型为标准地图模式;
      var localcity = new BMapGL.LocalCity();
      localcity.get((e) => {
        map.value.centerAndZoom(e.name, mapZoom.value);
      });
   
      let point;
      addressInfo.address = props.address
      if(props.address !== ''){
        setTimeout(() => {
          ac.setInputValue(addressInfo.address);
        },1000)
      }
      if( props.longitude !== ''){
        addressInfo.longitude = Number(props.longitude)
      }
      if(props.latitude !== ''){
        addressInfo.latitude = Number(props.latitude)
      }
      //初始化的时候如果有经纬度,需要先在地图上添加点标记
      if (addressInfo.longitude && addressInfo.latitude) {
        point = new BMapGL.Point(addressInfo.longitude, addressInfo.latitude);
        map.value.centerAndZoom(point, mapZoom.value);
        var marker2 = new BMapGL.Marker(point);
        //在地图上添加点标记
        setTimeout(()=> {
          map.value.addOverlay(marker2);
          var opts = {
            width : 200,     // 信息窗口宽度
            height: 80,     // 信息窗口高度
            title : "地址" , // 信息窗口标题
            enableMessage:false,//设置允许信息窗发送短息
          }
          var infoWindow = new BMapGL.InfoWindow(addressInfo.address, opts);  // 创建信息窗口对象 
          map.value.openInfoWindow(infoWindow,point);
        },1000)
      }
   
      map.value.enableScrollWheelZoom(true);
      map.value.setHeading(64.5);
      map.value.setTilt(73);

      //点击下拉框的值
      map.value.addEventListener(
        "click",
        function (e) {
          // 判断是否点击了标注点
          if(!e.overlay || !(e.overlay instanceof BMapGL.Marker)){
            map.value.clearOverlays();
            var point1 = new BMapGL.Point(e.latlng.lng, e.latlng.lat);
            // 创建点标记
            var marker1 = new BMapGL.Marker(point1);
            // 在地图上添加点标记
            map.value.addOverlay(marker1);
  
            addressInfo.longitude = e.latlng.lng;
            addressInfo.latitude = e.latlng.lat;
            var geoc = new BMapGL.Geocoder(); // 创建地址解析器的实例
            geoc.getLocation(point1, (rs) => {
              let adr = rs.addressComponents;
              addressInfo.address =
                adr.province +
                adr.city +
                adr.district +
                adr.street +
                adr.streetNumber; // 省市区街道门牌号
            });
          }
        }
      );
      ac.addEventListener("onconfirm", function (e) {
        addressInfo.longitude = ''
        addressInfo.latitude = ''
        //鼠标点击下拉列表后的事件
        var _value = e.item.value;
        addressInfo.address =
          _value.province +
          _value.city +
          _value.district +
          _value.street +
          _value.business;
        // 搜索
        map.value.clearOverlays(); //清除地图上所有覆盖物
        //智能搜索
        var local = new BMapGL.LocalSearch(map.value, {
          onSearchComplete: () => {
            //获取第一个智能搜索的结果
            const pp = local.getResults().getPoi(0).point;
            map.value.centerAndZoom(pp, mapZoom.value);
            map.value.addOverlay(new BMapGL.Marker(pp)); //添加标注
            addressInfo.longitude = pp.lng;
            addressInfo.latitude = pp.lat;
          },
        });
        local.search(addressInfo.address);
      });
    });
  };
  /**
   * 确认选择
   */
  const confirmSelect = () => {
    if (addressInfo.address == "") {
      ElMessage({
        message: "请选择位置",
        type: "error",
        center: true,
      });
      return;
    }
    emit("confirmMapAddress", addressInfo,false);
    
  };
  /**
   * 取消选择
   */
  const cancel = () => {
    addressInfo.address = ''
    addressInfo.longitude = ''
    addressInfo.latitude = ''
    emit("cancelMap", false);
  };
  function BMPGL(ak) {
    return new Promise(function (resolve, reject) {
      window.init = function () {
        // eslint-disable-next-line
        resolve(BMapGL);
      };
      const script = document.createElement("script");
      script.type = "text/javascript";
      script.src = `https://api.map.baidu.com/api?v=3.0&type=webgl&ak=${ak}&callback=init`;
      script.onerror = reject;
      document.head.appendChild(script);
    });
  }

  </script>
  <style>
  .tangram-suggestion {
    z-index: 99999;
  }
  </style>
  <style scoped lang="scss">
  :deep(.BMap_cpyCtrl) {
    display: none !important;
  }
  :deep(.BMap_cpyCtrl) {
    display: none !important;
  }
   
  :deep(.el-dialog__header),
  :deep(.el-dialog__footer) {
    padding: 15px 20px;
  }
   
  :deep(.el-dialog__body) {
    border-top: 1px solid #e8eaec;
    border-bottom: 1px solid #e8eaec;
    padding: 20px;
  }
  :deep(.el-dialog__headerbtn) {
    top: 0;
    font-size: 18px;
  }
  :deep(.el-dialog) {
    border-radius: 8px;
  }
  </style>

initMap方法是可以实现检索功能的,但是后面发现检索个人开发注册的时候是有限制的,如果想无限用就要付费了,所以就把检索去除了,就有了现在的init跟失焦事件完成的
刚开始的难点可能在编辑的时候,要回显出来,地址及标注,刚开始的初始想法错了,导致走了不少弯路
最后经同事提醒,发现原来回显的地址已经出来了,只不过是被自动创建给刷新覆盖了,然后发现了这个之后,问题就好解决了
把input框的值重写使用 setInputValue

ac.setInputValue(addressInfo.address)
2、使用elementUI Plus组件上传图片功能

vue页面代码

<el-form-item label="形象图" prop="ticketImage">
    <el-upload
        class="avatar-uploader"
        :action="uploadImgUrl"
        :headers="headers"
        :show-file-list="true"
        list-type="picture-card"
        :on-success="handleAvatarSuccess"
        :before-upload="beforeAvatarUpload"
        :file-list="fileList"
        :limit="1"
        :before-remove="handleAvatarDelete"
        :on-preview="handleAvatarPreview"
        :class="{ hide: fileList.length >= 1 }"
    >
        <el-icon class="avatar-uploader-icon"><Plus /></el-icon>
        <template #tip>
            <div class="el-upload__tip">
                建议上传尺寸750*450,1M以内
            </div>
        </template>
    </el-upload>
    <el-dialog v-model="dialogVisible" title="预览">
        <img w-full :src="form.ticketImage" alt="暂无图片" style="display: block; max-width: 100%; margin: 0 auto" />
    </el-dialog>
</el-form-item>

js代码

const uploadList = ref([]);
const baseUrl = import.meta.env.VITE_APP_BASE_API;
const uploadImgUrl = ref(import.meta.env.VITE_APP_BASE_API + '/common/upload'); // 上传的图片服务器地址
const headers = ref({ Authorization: 'Bearer ' + getToken() });
const fileList = ref([]);

const beforeAvatarUpload = (file) => {
    if(file){
        const isLt = file.size / 1024 / 1024 < 1
        if(!isLt){
            proxy.$modal.msgError(`图片大小不能超过 1MB!`);
            return false;
        }
    }
    // if (fileSize) {
	// 	const isLt = file.size / 1024 / 1024 < props.fileSize;
	// 	if (!isLt) {
	// 		proxy.$modal.msgError(`上传头像图片大小不能超过 ${props.fileSize} MB!`);
	// 		return false;
	// 	}
	// }
	proxy.$modal.loading('正在上传图片,请稍候...');
}
const handleAvatarSuccess = (res, file) => {
    if (res.code === 200) {
        form.value.ticketImage = res.fileName
		uploadList.value.push({ name: res.fileName, url: res.url });
		fileList.value = fileList.value.filter((f) => f.url !== undefined).concat(uploadList.value);
        // console.log('fileList.value',fileList.value)
        uploadList.value = []
        proxy.$modal.closeLoading();
	} else {
		
	}
}

const handleAvatarPreview = (file) => {
	dialogVisible.value = true;
}
const handleAvatarDelete = (file) => {
    fileList.value = []
    form.value.ticketImage = ''
}

css(主要是想去除自带的动效)

:deep(.el-date-editor .el-input__prefix) {
  display: none;
}
:deep(.hide .el-upload--picture-card) {
	display: none;
}
.avatar-uploader :deep(.el-upload-list__item) {
    transition: none !important;
}
3、使用elementUI Plus组件中el-date-picker默认回显当前年总回显1970问题

在这里插入图片描述

new Date().getFullYear()
console.log('year',year) // 2024

打印出来是2024,但是页面上回显的确是1970,百度了之后发现要转换一下类型

new Date().getFullYear().toString()

之后就可以了,在此记录一下

  • 4
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

张张Z7

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值