nuxt、vue实现PDF和视频文件的上传、下载、预览

news2024/11/24 17:48:03

上传

在这里插入图片描述

上传页面

 <el-form-item :label="(form.ququ3 == 1 ? '参培' : form.ququ3 == 2 ? '授课' : '') + '证明材料'" prop="ququ6">
       <PdfUpload v-model="form.ququ6" :fileType="['pdf', 'mp4', 'avi', 'ts']"></PdfUpload>
</el-form-item>

PdfUpload组件

自定义组件实现v-model,只需要定义props:value属性来接收父组件的v-model绑定的初始值,在子组件改变值时触发$emit(‘input’,值)

<template>
  <div class="upload-file ">
    <el-upload multiple :action="uploadFileUrl" :before-upload="handleBeforeUpload" :file-list="fileList" :limit="limit"
      :on-error="handleUploadError" :on-exceed="handleExceed" :on-success="handleUploadSuccess" :show-file-list="false"
      :headers="headers" class="upload-file-uploader" ref="upload">
      <el-button size="small" type="primary">点击上传</el-button>
      <!-- 上传提示 -->
      <div class="el-upload__tip" slot="tip" v-if="showTip">
        <template v-if="fileSize"> 大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b> </template>
        <template v-if="fileType"> 只能上传PDF文件和视频,格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b> </template>
      </div>
    </el-upload>
    <!-- 文件列表 -->
    <div class="ml-100" style="margin-top: -20px;">
      <transition-group class="upload-file-list el-upload-list el-upload-list--text" name="el-fade-in-linear" tag="ul">
        <li :key="file.url" class="el-upload-list__item ele-upload-list__item-content" v-for="(file, index) in fileList">
          <el-link :href="file.url" :underline="false" target="_blank">
            <!-- <span class="el-icon-document"> {{ getFileName(file.name) }}</span> -->
            <span class="el-icon-document"> {{ file.fileName }}</span>
          </el-link>
          <div class="ele-upload-list__item-content-action ml-60" style="min-width: 40px;">
            <el-link :underline="false" @click="handleDelete(index)" type="primary" icon="el-icon-circle-close"></el-link>
          </div>
        </li>
      </transition-group>
    </div>

  </div>
</template>

<script>
// ******自定义组件实现v-model,只需要定义props:value属性来接收父组件的v-model绑定的初始值,在子组件改变值时触发$emit('input',值)
export default {
  name: "FileUpload",
  props: {
    // 文件值,fileList
    value: [String, Object, Array],
    // 数量限制
    limit: {
      type: Number,
    },
    // 大小限制(MB)
    fileSize: {
      type: Number,
      // default: 500,
    },
    // 文件类型, 例如['png', 'jpg', 'jpeg']
    fileType: {
      type: Array,
      default: () => ['png', 'jpg', 'jpeg'],
    },
    // 是否显示文件大小和类型限制提示文字
    isShowTip: {
      type: Boolean,
      default: true
    },
    // 图片序号
    indexValue: {
      type: Number,
      default: null,
    },
  },
  data() {
    return {
      number: 0,
      uploadList: [],
      uploadFileUrl: '/prod-api' + "/file/upload", // 上传的图片服务器地址
      headers: {
        Authorization: this.$store.state.token,
      },
      fileList: [],
    };
  },
  watch: {
    value: {
      handler(val) {
        if (val) {
          console.log(666, val);
          // 然后将数组转为对象数组
          this.fileList = val
        } else {
          this.fileList = [];
          return [];
        }
      },
      deep: true,
      immediate: true,
    }
  },
  computed: {
    // 是否显示提示
    showTip() {
      return this.isShowTip && (this.fileType || this.fileSize);
    },
  },
  methods: {
    // 上传前校检格式和大小
    handleBeforeUpload(file) {
      console.log('上传前-校验', file, file.name);
      // 校检文件类型
      if (this.fileType) {
        let fileExtension = "";
        if (file.name.lastIndexOf(".") > -1) {
          fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1);
        }
        const isTypeOk = this.fileType.some((type) => {
          if (file.type.indexOf(type) > -1) return true;
          if (fileExtension && fileExtension.indexOf(type) > -1) return true;
          return false;
        });
        if (!isTypeOk) {
          this.$modal.msgError(`文件格式不正确, 请上传${this.fileType.join("/")}格式文件!`);
          return false;
        }
      }
      // 校检文件大小
      if (this.fileSize) {
        const isLt = file.size / 1024 / 1024 < this.fileSize;
        if (!isLt) {
          this.$modal.msgError(`上传文件大小不能超过 ${this.fileSize} MB!`);
          return false;
        }
      }
      this.$modal.loading("正在上传,请稍候...");
      this.number++;
      return true;
    },
    // 文件个数超出
    handleExceed() {
      this.$modal.msgError(`上传文件数量不能超过 ${this.limit} 个!`);
    },
    // 上传失败
    handleUploadError(err) {
      this.$modal.msgError("上传失败,请重试");
      this.$modal.closeLoading()
    },
    // 上传成功回调
    handleUploadSuccess(res) {
      // name为 文件
      console.log('上传成功回调', res, this.indexValue);
      this.uploadList.push({ fileName: res.data.url.split('-')[res.data.url.split('-').length - 1], url: res.data.url, });
      if (this.uploadList.length === this.number) {
        this.fileList = this.fileList.concat(this.uploadList);
        console.log(2222, this.fileList)
        this.uploadList = [];
        this.number = 0;
        // this.$emit("input", this.listToString(this.fileList), this.indexValue);
        this.$emit("input", this.fileList, this.indexValue);
        this.$modal.closeLoading();
      }
    },
    // 删除文件
    handleDelete(index) {
      this.fileList.splice(index, 1);
      this.$emit("input", this.fileList);
    },
    // 获取文件名称
    getFileName(name) {
      if (name.lastIndexOf("/") > -1) {
        return name.slice(name.lastIndexOf("/") + 1);
      } else {
        return "";
      }
    },
    // 对象转成指定字符串分隔
    listToString(list, separator) {
      let strs = "";
      separator = separator || ",";
      for (let i in list) {
        strs += list[i].url + separator;
      }
      return strs != '' ? strs.substr(0, strs.length - 1) : '';
    }
  }
};
</script>

<style scoped  >
.upload-file-uploader {
  margin-bottom: 5px;
}

::v-deep .el-upload--picture-card {
  width: 104px;
  height: 104px;
  line-height: 104px;
}

.upload-file-list {
  max-height: 240px !important;
  overflow-y: auto;
}

.upload-file-list .el-upload-list__item {
  line-height: 2;
  margin-bottom: 10px;
  position: relative;
}

.upload-file-list .ele-upload-list__item-content {
  display: flex;
  justify-content: space-between;
  align-items: center;
  color: inherit;
}

.ele-upload-list__item-content-action .el-link {
  margin-right: 10px;
}
</style>

整个上传页面

<template>
  <div id="index" class="flex flex-top w ptb-30">
    <Menu></Menu>
    <div class="flex-1 ml-30  over-hidden">
      <h3 class="mt-20 mb-40">新增培训</h3>
      <el-form style="width:500px" :model="form" :rules="rules" ref="form" label-width="100px" class="demo-form">
        <el-form-item label="培训主题名" prop="ququ1">
          <el-input v-model.trim="form.ququ1" placeholder="请输入培训主题名" clearable />
        </el-form-item>
        <el-form-item label="培训分类" prop="ququ2">
          <el-select v-model="form.ququ2" placeholder="请选择培训分类" style="width: 100%;">
            <el-option label="5" value="5"></el-option>
          </el-select>
        </el-form-item>
        <el-form-item label="所属类别" prop="ququ3">
          <el-radio-group v-model="form.ququ3">
            <el-radio label="1">参培人</el-radio>
            <el-radio label="2">授课人</el-radio>
          </el-radio-group>
        </el-form-item>
        <el-form-item label="参与地点" prop="ququ4">
          <el-input v-model.trim="form.ququ4" placeholder="请输入参与地点" clearable />
        </el-form-item>
        <el-form-item label="起止日期" prop="ququ5">
          <el-date-picker v-model="form.ququ5" type="daterange" range-separator="至" start-placeholder="开始日期"
            end-placeholder="结束日期" value-format="yyyy-MM-dd" style="width: 100%;">
          </el-date-picker>
        </el-form-item>
        <el-form-item :label="(form.ququ3 == 1 ? '参培' : form.ququ3 == 2 ? '授课' : '') + '证明材料'" prop="ququ6">
          <PdfUpload v-model="form.ququ6" :fileType="['pdf', 'mp4', 'avi', 'ts']"></PdfUpload>
        </el-form-item>
        <el-form-item label="备注" prop="ququ7">
          <el-input v-model.trim="form.ququ7" placeholder="请输入备注" clearable type="textarea" />
        </el-form-item>
        <el-form-item>
          <el-button type="primary" @click="submit('form')">提交审核</el-button>
          <el-button type="primary" plain @click="save">保存草稿</el-button>
          <el-button @click="back">返回</el-button>
        </el-form-item>
      </el-form>
    </div>
  </div>
</template>
<script>

export default {
  data() {
    return {
      form: {
        ququ1: '',
        ququ2: '',
        ququ3: '',
        ququ4: '',
        ququ5: '',
        ququ6: [],
        ququ7: '',
      },
      rules: {
        ququ1: {
          required: true,
          message: '请输入主题名',
          trigger: ['blur']
        },
        ququ2: {
          required: true,
          message: '请选择培训分类',
          trigger: ['change']
        },
        ququ3: {
          required: true,
          message: '请选择所属类别',
          trigger: ['change']
        },
        ququ5: {
          required: true,
          message: '请选择起止日期',
          trigger: ['change']
        },
        ququ6: {
          required: true,
          message: '请上传证明材料',
          trigger: ['change']
        },
      }
    };
  },
  mounted() {
    if (localStorage.getItem('form')) {
      this.$confirm('检测到您有保存的草稿,需要使用吗?', '提示', {
        confirmButtonText: '使用',
        cancelButtonText: '删除',
        type: 'warning'
      }).then(() => {
        this.form = JSON.parse(localStorage.getItem('form'))
      }).catch(() => {
        localStorage.removeItem('form')
      });
    }
  },
  methods: {
    submit(formName) {
      this.$refs[formName].validate((valid) => {
        if (valid) {
          this.$axios.get('/exam/info/queryErrorQuestionQuantity').then(res => {
            this.back()
            localStorage.removeItem('form')
          })
        } else {
          return false;
        }
      });
    },
    resetForm(formName) {
      this.$refs[formName].resetFields();
    },
    back() {
      this.$router.back()
    },
    save() {
      console.log(this.form.ququ6.map(item => item.url))
      localStorage.setItem('form', JSON.stringify(this.form))
    },
  },
};
</script>
<style scoped></style>

预览和下载

在这里插入图片描述

在这里插入图片描述

预览页面

 <el-button @click="downLoad(item)" type="primary" size="mini">下载</el-button>
 <el-button @click="preview(item)" type="danger" size="mini">预览</el-button>


	downLoad(item) {
      let url = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/6a12b9ca-3ae9-435b-b023-0f9c119afad3-1.mp4"
      let url1 = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/53aa1f60-0735-4203-86b2-c2b8b019e8d9-我的哈哈.pdf"

      fetch(url).then(res => res.blob()).then(blob => { // 将链接地址字符内容转变成blob地址
        const a = document.createElement('a')
        a.href = URL.createObjectURL(blob)
        a.download = url.split('-')[url.split('-').length - 1]  // 下载文件的名字
        document.body.appendChild(a)
        a.click()
      })
    },
    preview(item) {
      let url = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/6a12b9ca-3ae9-435b-b023-0f9c119afad3-1.mp4"
      let url1 = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/53aa1f60-0735-4203-86b2-c2b8b019e8d9-我的哈哈.pdf"
      window.open(url1)
    }

整个列表加详情弹窗页面



<template>
  <div id="index" class="flex flex-top w ptb-30">
    <Menu></Menu>
    <div class="flex-1 ml-30  over-hidden">
      <!-- 搜索 -->
      <el-form :model="queryParams" ref="queryForm" size="small" :inline="true">
        <el-form-item label="培训名称" prop="ququ1">
          <el-input v-model.trim="queryParams.ququ1" placeholder="请输入培训名称" clearable @keyup.enter.native="getList(1)" />
        </el-form-item>
        <el-form-item label="起止日期" prop="ququ2">
          <el-date-picker v-model="queryParams.ququ2" type="daterange" range-separator="至" start-placeholder="开始日期"
            end-placeholder="结束日期" value-format="yyyy-MM-dd">
          </el-date-picker>
        </el-form-item>
        <el-form-item label="培训地点" prop="ququ3">
          <el-input v-model.trim="queryParams.ququ3" placeholder="请输入培训地点" clearable @keyup.enter.native="getList(1)" />
        </el-form-item>
        <el-form-item>
          <el-button type="primary" icon="el-icon-search" size="mini" @click="getList(1)">查询</el-button>
          <el-button size="mini" @click="resetQuery">重置</el-button>
        </el-form-item>
      </el-form>
      <!-- 新增 -->
      <el-row>
        <el-col :span="24" class="flex_r">
          <el-button type="success" icon="el-icon-plus" size="mini" @click="add">新增</el-button>
        </el-col>
      </el-row>

      <!-- tab  -->
      <el-tabs v-model="tab" @tab-click="getList(1)">
        <el-tab-pane label="全部培训" name="1">
        </el-tab-pane>
        <el-tab-pane label="已通过审批" name="2">
        </el-tab-pane>
        <el-tab-pane label="未通过审批" name="3">
        </el-tab-pane>
      </el-tabs>
      <!-- 表格 -->
      <el-table :data="tableData" border>
        <el-table-column prop="paperName" align="center" min-width="140" label="培训名称" :show-overflow-tooltip="true">
        </el-table-column>
        <el-table-column prop="paperName" align="center" min-width="140" label="培训分类" :show-overflow-tooltip="true">
        </el-table-column>
        <el-table-column prop="practiceType" align="center" min-width="90" label="所属类别">
          <template slot-scope="scope">
            <el-tag size="small">
              {{ scope.row.practiceType == 1 ? '参培人' : '授课人' }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column prop="paperName" align="center" min-width="100" label="培训地点" :show-overflow-tooltip="true">
        </el-table-column>
        <el-table-column prop="startTime" align="center" min-width="120" label="开始时间">
        </el-table-column>
        <el-table-column prop="endTime" align="center" min-width="120" label="结束时间">
        </el-table-column>
        <el-table-column prop="practiceType" align="center" min-width="90" label="审批状态">
          <template slot-scope="scope">
            <el-tag :type="scope.row.practiceType == 1 ? '' : scope.row.practiceType == 2 ? 'success' : 'danger'">
              {{ scope.row.practiceType == 1 ? '审核中' : scope.row.practiceType == 2 ? '已通过' : '未通过' }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column label="操作" align="center" fixed="right" min-width="100">
          <template slot-scope="scope">
            <el-button @click="toDetail(scope.row)" size="mini" type="text" icon="el-icon-document-copy">详情</el-button>
          </template>
        </el-table-column>
      </el-table>
      <!-- 分页 -->
      <div class="center mtb-20">
        <el-pagination :hide-on-single-page="true" background layout="prev, pager, next" :total="total * 1"
          :current-page.sync="page" @current-change="getList" :page-size="this.pageSize">
        </el-pagination>
      </div>
    </div>

    <!-- 详情弹窗 -->
    <el-dialog title="培训详情" :visible.sync="show" width="1000px">
      <el-card shadow="hover" class="flex-1 ml-20 scroll pd-10">
        <el-descriptions title="培训详情">
          <el-descriptions-item label="培训主题名">kooriookami</el-descriptions-item>
          <el-descriptions-item label="培训分类">18100000000</el-descriptions-item>
          <el-descriptions-item label="提交时间">苏州市</el-descriptions-item>
          <el-descriptions-item label="本人所属类别">
            <el-tag size="small">学校</el-tag>
          </el-descriptions-item>
          <el-descriptions-item label="培训起止日期">江苏省苏州市吴中区吴中大道 1188</el-descriptions-item>
          <el-descriptions-item label="参与地点">江苏省苏州市吴中区吴中大道 1188</el-descriptions-item>
          <el-descriptions-item label="备注">江苏省苏州市吴中区吴中大道 1188</el-descriptions-item>
        </el-descriptions>
      </el-card>
      <el-card shadow="hover" class="flex-1 ml-20 scroll pd-10 mt-30">
        <h3 class="mb-20">附件记录</h3>
        <div class="flex mb-10" v-for="(item, i) in 6">
          <div>23243232.png</div>
          <div>
            <el-button @click="downLoad(item)" type="primary" size="mini">下载</el-button>
            <el-button @click="preview(item)" type="danger" size="mini">预览</el-button>
          </div>
        </div>
      </el-card>
    </el-dialog>
  </div>
</template>
<script>

export default {
  data() {
    return {
      tab: '1',
      page: 1,
      pageSize: 10,
      total: 0,
      tableData: [],
      // 搜索
      queryParams: {
        ququ1: "",
        ququ2: "",
        ququ3: "",
      },

      //详情
      show: false,
    };
  },
  mounted() {
    this.getList()
  },
  methods: {
    getList(page) {
      console.log(this.queryParams.ququ2)
      if (page == 1) {
        this.page = 1;
      }
      this.$axios.get('/exam/practiceHistory/record/listPc', {
        params: {
          pageNum: this.page,
          pageSize: this.pageSize,
          tab: this.tab,
          ...this.queryParams
        }
      }).then(res => {
        this.tableData = res.rows;
        this.total = res.total;
      });
    },
    /** 重置按钮操作 */
    resetQuery() {
      this.$refs['queryForm'].resetFields();
      this.queryParams.ququ2 = ''
      this.getList(1)
    },
    add() {
      this.$router.push({ path: "/train/add" });
    },

    toDetail(row) {
      this.show = true
    },
    downLoad(item) {
      let url = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/6a12b9ca-3ae9-435b-b023-0f9c119afad3-1.mp4"
      let url1 = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/53aa1f60-0735-4203-86b2-c2b8b019e8d9-我的哈哈.pdf"

      fetch(url).then(res => res.blob()).then(blob => { // 将链接地址字符内容转变成blob地址
        const a = document.createElement('a')
        a.href = URL.createObjectURL(blob)
        a.download = url.split('-')[url.split('-').length - 1]  // 下载文件的名字
        document.body.appendChild(a)
        a.click()
      })
    },
    preview(item) {
      let url = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/6a12b9ca-3ae9-435b-b023-0f9c119afad3-1.mp4"
      let url1 = "https://cscec83-learnplatform.oss-cn-shanghai.aliyuncs.com/test/2023-11-27/53aa1f60-0735-4203-86b2-c2b8b019e8d9-我的哈哈.pdf"
      window.open(url1)
    }
  },
};
</script>
<style scoped></style>


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1258607.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

虚幻学习笔记—文本内容处理

一、前言 本文使用的虚幻引擎5.3.2&#xff0c;在虚幻中已经集成了很多可以直接处理多样化文本的蓝图&#xff0c;比如格式化动态显示、浮点数多样化等。 二、实现 2.1、格式化文本显示动态内容&#xff1a;在设置某个文本时可以使用“Format Text”蓝图设置自定义可以的显示…

广州华锐互动:VR虚拟现实内容创作工具带来全新的应用场景

随着科技的不断发展&#xff0c;低代码编辑工具已经成为了一种越来越受欢迎的开发方式。它可以帮助开发人员快速构建应用程序&#xff0c;降低开发成本&#xff0c;提高开发效率&#xff0c;而VR虚拟现实内容创作工具带来了全新的应用场景。 VR虚拟现实内容创作工具是广州华锐互…

Python办公神器:教你如何快速分拆、删页、合并PDF文件

哈喽大家好&#xff0c;我是了不起&#xff0c;今天教你如何用Python快速分拆、删页、合并PDF文件 介绍 有时我们可能需要对PDF文件进行一些处理&#xff0c;例如分拆、删页、合并等。这些操作在一些专业的PDF软件中可能比较容易实现&#xff0c;但是如果我们想要用Python来自…

C++STL——string类详解及其模拟实现

CSTL——string类 1. STL简介 STL全称standard template libaray&#xff0c;译为标准模板库 需要注意&#xff0c;STL不是C的标准库&#xff0c;而是C标准库的重要组成部分STL是一个包含众多数据结构和算法的软件框架 下面展示STL的六大组件&#xff1a; 本章&#xff0c;我…

强化学习中的深度Q网络

深度 Q 网络&#xff08;Deep Q-Network&#xff0c;DQN&#xff09;是一种结合了深度学习和强化学习的方法&#xff0c;用于解决离散状态和离散动作空间的强化学习问题。DQN 的核心思想是使用深度神经网络来近似 Q 函数&#xff0c;从而学习复杂环境中的最优策略。 以下是 DQN…

二叉树进阶OJ题

目录 一、前序遍历非递归 二、中序遍历非递归 三、后序遍历非递归 四、二叉树转链表 五、二叉树的最近公共祖先 六、二叉树的层序遍历1 七、二叉树的层序遍历2 一、前序遍历非递归 题目描述&#xff1a;写出二叉树前序遍历的非递归形式。 链接&#xff1a;前序遍历 思…

css之svg 制作圆及旋转

1.代码 <template><div class"loading-box"><div class"circle-container"><svg width"75" height"75" class"move-left-to-right"><circle cx"37.5" cy"37.5" r"26&…

leetcode42接雨水问题

接雨水 题目描述 题目分析 核心思想&#xff1a; 代码 java版本&#xff1a; package com.pxx.leetcode.trapRainWaterDoublePoniter;public class Solution1 {public int trap(int[] height) {if (height.length 0) {return 0;}int n height.length;int left 0;int righ…

Linux之高级IO

目录 IO基本概念五种IO模型钓鱼人例子五种IO模型高级IO重要概念同步通信 VS 异步通信阻塞 VS 非阻塞其他高级IO阻塞IO非阻塞IO IO基本概念 I/O&#xff08;input/output&#xff09;也就是输入和输出&#xff0c;在著名的冯诺依曼体系结构当中&#xff0c;将数据从输入设备拷贝…

2023亚马逊云科技re:Invent,与全球合作伙伴探索更多发展可能

一年一度的全球云计算、科技圈的狂欢“Party”又双叒叕要来了&#xff01;2023年11月27日&#xff0c;2023亚马逊云科技re:Invent正式向全球云计算从业者、合作伙伴发出邀请&#xff0c;相聚拉斯维加斯&#xff0c;共同开启一场创新探索之旅&#xff01; 全球合作伙伴相约拉斯维…

ffmpeg开发 环境配置

ffmpeg开发简图 1 下载ffmpeg开发包 https://ffmpeg.org/download.html 包含三个版本&#xff1a;Static、Shared以及Dev Static --- 包含3个应用程序&#xff1a;ffmpeg.exe , ffplay.exe , ffprobe.exe&#xff0c;体积都很大&#xff0c;相关的DLL已经被编译到exe里面去…

【Java】ThreadPoolExecutor类参数简述

ThreadPoolExecutor类继承自AbstractExecutorService类&#xff0c;而AbstractExecutorService实现了ExecutorService接口 ThreadPoolExecutor类是Executor类中重要的实现类 1、ThreadPoolExecutor构造方法参数 在手册中&#xff0c; 一共有四种参数列表不同的构造方法。我们…

【文末送书】程序员如何化解35岁危机?

欢迎关注博主 Mindtechnist 或加入【智能科技社区】一起学习和分享Linux、C、C、Python、Matlab&#xff0c;机器人运动控制、多机器人协作&#xff0c;智能优化算法&#xff0c;滤波估计、多传感器信息融合&#xff0c;机器学习&#xff0c;人工智能等相关领域的知识和技术。关…

网易云音频数据如何爬取?

在当今数字化时代&#xff0c;音频数据的获取和处理变得越来越重要。本文将详细介绍如何使用Objective-C语言构建音频爬虫程序&#xff0c;以爬取网易云音乐为案例。我们将从Objective-C的基础知识开始&#xff0c;逐步深入到爬取思路分析、构建爬虫框架、完整爬取代码等方面&a…

android trace文件的抓取与查看方法

本地手机抓取trace 解压android trace文件的抓取与查看方法 找到config.pbtx文件&#xff0c;连接手机push进去 # push config.pbtx &#xff0c;/data/local/tmp/为自定义push到的目录 adb push config.pbtx /data/local/tmp/ adb shell # 抓取trace&#xff0c; /data/loc…

Redis原理之五种数据类型笔记

目录 String List Set ZSet ​ Hash String List Set ZSet Hash

CTF图片隐写

1.题目给出的zip文件给出提示如下。 2.用 ARCHPR爆破出密码。 3.解压后发现1.png&#xff0c;为图片隐写。 4.使用010editor打开图片&#xff0c;发现缺少png文件头。 010editor官方下载链接&#xff1a;sweetscape.com/download/010editor/ 5.添加文件头保存。 6.使用图片隐写…

vue3+highlight.js代码高亮插件使用

先安装 npm install highlight.jsmain.js中引入&#xff0c;并注册自定义指令 ..... import hljs from highlight.js window.hljs hljs import highlight.js/styles/atom-one-light.css import highlight.js/lib/common import mitt from mitt .....app.directive(highlight…

HTML5+CSS3+JS小实例:九宫格图片鼠标移入移出方向感知特效

实例:九宫格图片鼠标移入移出方向感知特效 技术栈:HTML+CSS+JS 效果: 源码: 【HTML】 <!DOCTYPE html> <html><head><meta http-equiv="content-type" content="text/html; charset=utf-8"><meta name="viewport&…

鲲鹏测评:电视盒子什么品牌好?双十二口碑电视盒子品牌排行榜

最近我们收到很多网友的私信不知道电视盒子怎么选&#xff0c;想要我们推荐双十二值得入手的电视盒子&#xff0c;本年度我们已经共计测评过18款电视盒子&#xff0c;通过对比测评结果&#xff0c;我们整理了电视盒子品牌排行榜&#xff0c;双十二想买电视盒子的朋友们可不要错…