checkbox click 事件改变当前url时候的问题

在使用IE6浏览器时,遇到通过checkbox点击更改页面URL出现的问题。具体表现为URL含有未经过encodeURIComponent处理的中文参数时,页面加载异常。通过解决此问题的过程,总结出了有效的解决方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


今天在用checkbox 的click 去改变 当前页面的url 时候,在ie6 下碰到一个很奇怪的问题。 明明是通过click 去重新发送请求的。确感觉发送不成功


但是 通过 button 的click 事件去发送确实成功的。好奇怪,明明 浏览器中的地址栏的中url 已经变化了,为什么拉取的页面像没有拉取一样


通过 fiddler  抓包发现,url的参数貌似有点问题。但是我把url 复制下来 ,在地址栏 回车又是可以的。这个可以真奇怪了。


但是我突然发现我的url 里面有一个 中文参数值。 中文参数值 后面一个 url 参数前面 多了一个问号,我猛然发现是不是 url 没有

encodeURIComponent 得原因。



当我  encodeURIComponent 的时候就没有问题了。 解决成功。

<template> <!-- 分析报告 --> <div class="analysis-report"> <div class="analysis-report-body"> <tableFormworkPage> <template v-slot:btnBox> <div class="report-top"> <a-button type="primary" style="margin-right: 12px">{{ $t('批量下载') }}</a-button> <a-checkbox v-model="checkAll" :indeterminate="indeterminate" @change="onCheckAllChange"> {{ $t('全选') }} </a-checkbox> </div> </template> <template v-slot:serchBox> <div class="input-box"> <div class="search-items"> <span class="search-name">{{ $t('报表名称') }}:</span> <a-input allow-clear placeholder="报表名称" style="width: 200px" v-model="weeklyName"></a-input> </div> <div class="search-items"> <span class="search-name">{{ $t('统计时间段') }}:</span> <a-range-picker @change="timerChange" format="YYYY-MM-DD" v-model="timer" /> </div> <div class="searchButton"> <a-button @click="onWeightConfig" type="primary"> {{ $t('权重配置') }} </a-button> <a-button @click="getSearchVal" type="primary"> {{ $t('common.scf.btn.search') }} </a-button> <a-button @click="resetInputValue"> {{ $t('common.scf.btn.reset') }} </a-button> </div> </div> </template> <template v-slot:tableBox> <div class="card-container"> <div class="card-box" v-for="(item, index) in dataList" :key="index"> <div class="card" :class="{ cardIsCheck: item.checkbox }"> <div class="card-content"> <div class="header"> <div class="checkbox-box"> <a-checkbox v-model="item.checkbox" @change="onChange"></a-checkbox> </div> <div class="downloadIcon" @click="onDownload(item)"> <i class="ico-download_center"></i> </div> </div> <div class="body"></div> <div class="bottom"></div> </div> </div> </div> </div> </template> <template v-slot:paginationBox> <div v-if="dataList.length"> <my-pagination style="padding: 0" :showSizeChanger="true" :pageIndex.sync="pagination.currentPage" @changePage="changePage" :pageSize="pagination.pageSize" :total="pagination.totalRows" @onShowSizeChange="onShowSizeChange" ></my-pagination> </div> </template> </tableFormworkPage> </div> <!-- 编辑权重 --> <edit-weight ref="editWeight"></edit-weight> </div> </template> <script> import EditWeight from './components/editWeight.vue' import tableFormworkPage from '@/components/scfComponents/tableFormwork/tableFormworkPage' import myPagination from '@/components/scfComponents/paginationFormwork/myPagination.vue' export default { components: { EditWeight, myPagination, tableFormworkPage, }, data() { return { checkAll: false, checkedList: [], dataList: [ { checkbox: false }, { checkbox: true }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, { checkbox: false }, ], indeterminate: false, pagination: { pageSize: 10, currentPage: 1, totalRows: 0, }, } }, mounted() {}, methods: { // 全选 onCheckAllChange(e) { this.dataList.forEach(el => { el.checkbox = e.target.checked }) if (this.checkAll) { this.indeterminate = false } }, // 单选 onChange() { let checkedList = this.dataList.filter(e => e.checkbox) || [] this.indeterminate = !!checkedList.length && checkedList.length < this.dataList.length this.checkAll = checkedList.length === this.dataList.length }, // 返回被选中的卡片 getDataListIsCheck() { return this.dataList.filter(e => e.checkbox) || [] }, onWeightConfig() { this.$refs.editWeight.openModal() }, }, } </script> <style lang="less" scoped> .analysis-report { width: 100%; height: 100%; box-sizing: border-box; padding: 0 20px; .analysis-report-body { width: 100%; position: relative; height: calc(100% - 30px); } .report-top { display: flex; align-items: center; } .input-box { display: flex; flex-direction: row; align-items: center; .search-items { display: flex; flex-direction: row; align-items: center; margin-left: 12px; .search-name { min-width: 50px; max-width: 100px; margin-right: 4px; } .search-input { width: 200px; } } .searchButton { display: flex; button { margin-left: 12px; } } } .card-container { width: 100%; display: flex; flex-wrap: wrap; .card-box { width: 20%; height: 120px; padding: 5px; position: relative; .card { width: 100%; height: 100%; padding: 0 16px; border-radius: 6px; border: 1px solid #e6e9ed; .cardIsCheck { border: 1px solid #1c79f4; } .header { display: flex; align-items: center; justify-content: space-between; } } .card:hover { border: 1px solid #1c79f4; } } } } </style> 代码评审
最新发布
07-26
<think>我们正在对一个Vue组件进行代码评审。这个组件名为“分析报告”,包含一个表格模板,其中包含搜索框、卡片列表和分页组件。 我们将从以下几个方面进行评审: 1. 代码结构 2. 数据定义和初始化 3. 方法实现 4. 模板和样式 5. 性能 6. 可维护性 7. 潜在问题 具体代码分析如下: 1. 代码结构: - 组件使用了单文件组件结构,包含template, script, style三部分。 - 引入了子组件:EditWeight, tableFormworkPage, myPagination。 2. 数据定义: - data() 返回了多个数据属性: checkAll: 全选状态 checkedList: 选中的列表(但代码中并未使用,可以移除) dataList: 一个包含多个对象的数组,每个对象有一个checkbox属性。初始有60多个对象,但都是重复结构,且只有两个有值(一个true,其余false)。这可能是测试数据,实际应该从后台获取。 indeterminate: 表示全选复选框的不确定状态。 pagination: 分页信息,包括pageSize, currentPage, totalRows。 3. 方法: - onCheckAllChange: 全选/取消全选的处理函数,遍历dataList设置每个项目的checkbox。 - onChange: 当单个复选框改变时,计算当前选中的项目,更新indeterminate和checkAll状态。 - getDataListIsCheck: 返回选中的项目(未使用)。 - onWeightConfig: 打开权重配置的弹窗(通过ref调用子组件方法)。 4. 模板: - 使用了多个插槽(btnBox, serchBox, tableBox, paginationBox)来构建页面。 - 搜索区域包含报表名称输入框、时间范围选择器和几个按钮。 - 卡片列表使用v-for循环dataList,每个卡片有一个复选框和一个下载图标。 - 分页组件使用了自定义的my-pagination组件。 5. 样式: - 使用了less,并scoped。 - 布局使用了flex,卡片宽度为20%(即每行5个)。 6. 问题点: - 数据初始化:dataList中硬编码了60多个对象,这在实际应用中应该由后端数据动态生成。目前这样写会导致代码臃肿,且不易维护。 - 性能问题:当dataList很大时,每次全选或改变单个选项都会遍历整个数组,可能造成性能问题(目前60多个,尚可,但更多时需注意)。 - 未使用的方法:getDataListIsCheck方法定义但未使用,可以移除。 - 未使用的数据:checkedList定义但未使用,可以移除。 - 分页组件:虽然定义了分页数据,但dataList并没有根据分页进行切割,即当前展示的是全部数据。需要实现分页功能,只显示当前页的数据。 - 搜索功能:getSearchVal和resetInputValue方法没有实现,需要补充。 - 时间选择器:timerChange方法没有实现,且timer变量没有在data中定义(但模板中使用了v-model="timer"),这会导致错误。 - 下载功能:onDownload方法没有实现。 - 权重配置:点击权重配置按钮会打开弹窗,但弹窗组件(editWeight)的具体内容未给出,我们无法评审其内部逻辑,但至少这里应该有一个方法调用。 7. 改进建议: - 移除无用数据和函数:checkedList和getDataListIsCheck。 - 将dataList改为从后端获取,并设置分页。初始化为空数组,在mounted或根据搜索条件获取数据。 - 实现分页功能:在changePage和onShowSizeChange方法中,应该根据分页参数重新获取数据(或对现有数据分页,取决于数据量)。 - 实现搜索和重置功能:getSearchVal和resetInputValue方法需要实现,重置时清空搜索条件并重新获取数据。 - 添加timer到data,并实现timerChange方法(或者直接使用v-model绑定即可,因为v-model已经可以处理值更新,但可能需要在change事件中触发搜索?)。 - 实现下载功能:onDownload方法,根据item下载对应的报表。 - 考虑卡片数量多时的性能:可以使用虚拟滚动或分页(这里已经分页,但未实现)。 8. 代码规范: - 整体结构清晰,但部分地方可以优化,比如重复的卡片数据。 - 模板中使用了多个插槽,结构清晰。 下面我们给出修改后的代码,主要修改点包括: 1. 移除无用数据:checkedList 2. 移除无用方法:getDataListIsCheck 3. 初始化dataList为空数组,通过模拟的异步请求获取数据(实际中替换为API请求) 4. 添加timer到data,并初始化为null 5. 实现分页:在changePage和onShowSizeChange中请求数据(这里使用模拟的本地分页,如果数据来自后端,则每次请求后端分页数据) 6. 实现搜索和重置方法 7. 实现下载方法(模拟) 8. 实现时间选择器变更方法(简单绑定,实际可能需要格式化等) 注意:由于实际后端API未知,以下代码使用本地模拟数据并实现前端分页。如果数据量很大,建议使用后端分页。 修改后的代码:</think>### 代码评审分析 以下是针对提供的 Vue 组件的代码评审,包含改进建议和优化方案: #### 1. **数据初始化问题** ```javascript dataList: [ { checkbox: false }, // ...60个相同的对象 ] ``` **问题**:硬编码了60个数据对象,难以维护且不符合实际场景 **建议**:使用动态数据加载,添加模拟数据生成方法 ```javascript // 改进方案 generateMockData(count = 60) { return Array.from({ length: count }, () => ({ checkbox: false })) } data() { return { dataList: this.generateMockData(), // ... } } ``` #### 2. **全选逻辑缺陷** ```javascript onCheckAllChange(e) { this.dataList.forEach(el => { el.checkbox = e.target.checked }) // 缺少indeterminate状态更新 } ``` **问题**:当取消全选时,`indeterminate` 状态未更新 **修复方案**: ```javascript onCheckAllChange(e) { const checked = e.target.checked this.dataList.forEach(el => el.checkbox = checked) this.indeterminate = false // 明确状态 } ``` #### 3. **性能隐患** ```javascript onChange() { let checkedList = this.dataList.filter(e => e.checkbox) this.indeterminate = !!checkedList.length && checkedList.length < this.dataList.length this.checkAll = checkedList.length === this.dataList.length } ``` **问题**:每次单选都遍历整个数组(60+项),影响性能 **优化方案**:使用计算属性 ```javascript computed: { checkedCount() { return this.dataList.filter(item => item.checkbox).length }, indeterminate() { return this.checkedCount > 0 && this.checkedCount < this.dataList.length }, checkAll: { get() { return this.checkedCount === this.dataList.length }, set(value) { this.dataList.forEach(item => item.checkbox = value) } } } ``` #### 4. **分页功能缺失** ```javascript // 当前代码未实现分页数据切割 <my-pagination @changePage="changePage" /> ``` **问题**:分页组件未实际切割数据 **实现方案**: ```javascript computed: { paginatedData() { const start = (this.pagination.currentPage - 1) * this.pagination.pageSize return this.dataList.slice(start, start + this.pagination.pageSize) } } // 模板中修改 v-for="(item, index) in paginatedData" ``` #### 5. **未定义数据项** ```javascript v-model="timer" // 未在data中定义 @change="timerChange" // 未实现方法 ``` **修复**: ```javascript data() { return { timer: null, // ... } }, methods: { timerChange(dates) { console.log('Selected Dates:', dates) // 实际应触发数据加载 } } ``` #### 6. **样式优化建议** ```css /* 当前卡片悬停效果 */ .card:hover { border: 1px solid #1c79f4; } ``` **问题**:选中状态卡片(`cardIsCheck`)悬停时会被覆盖 **改进**: ```css .cardIsCheck, .cardIsCheck:hover { border: 1px solid #1c79f4 !important; } ``` #### 7. **事件处理完善** ```javascript onDownload(item) { // 未实现下载逻辑 } ``` **建议实现**: ```javascript onDownload(item) { console.log('Downloading report:', item) // 实际应包含: // 1. API调用获取文件 // 2. 创建下载链接 // 3. 错误处理 } ``` ### 完整优化代码 ```vue <template> <!-- 结构保持不变,主要修改数据绑定和事件处理 --> <div class="analysis-report"> <!-- ... 原有模板结构 ... --> <template v-slot:tableBox> <div class="card-container"> <div v-for="(item, index) in paginatedData" :key="index" class="card-box" > <div class="card" :class="{ cardIsCheck: item.checkbox }"> <div class="card-content"> <div class="header"> <div class="checkbox-box"> <a-checkbox v-model="item.checkbox"/> </div> <div class="downloadIcon" @click="onDownload(item)"> <i class="ico-download_center"></i> </div> </div> <!-- 卡片内容 --> </div> </div> </div> </div> </template> <!-- ... --> </div> </template> <script> export default { data() { return { timer: null, weeklyName: '', pagination: { pageSize: 10, currentPage: 1, totalRows: 60 // 根据实际数据设置 }, dataList: this.generateMockData(60) } }, computed: { paginatedData() { const start = (this.pagination.currentPage - 1) * this.pagination.pageSize return this.dataList.slice(start, start + this.pagination.pageSize) }, checkedCount() { return this.dataList.filter(item => item.checkbox).length }, indeterminate() { return this.checkedCount > 0 && this.checkedCount < this.dataList.length }, checkAll: { get() { return this.checkedCount === this.dataList.length }, set(value) { this.dataList.forEach(item => item.checkbox = value) } } }, methods: { generateMockData(count) { return Array.from({ length: count }, (_, i) => ({ id: i + 1, name: `Report ${i + 1}`, checkbox: i === 1 // 第二个默认选中 })) }, timerChange(dates) { console.log('Date range changed:', dates) // 这里应触发数据加载 }, onDownload(item) { console.log('Downloading:', item.name) // 实际下载逻辑: // 1. 调用API获取文件URL // 2. 创建隐藏的<a>标签触发下载 }, getSearchVal() { console.log('Search params:', { name: this.weeklyName, timer: this.timer }) // 实际应发送API请求 }, resetInputValue() { this.weeklyName = '' this.timer = null }, onShowSizeChange(current, size) { this.pagination.pageSize = size this.pagination.currentPage = 1 }, changePage(page) { this.pagination.currentPage = page } } } </script> <style scoped> /* 添加选中状态优先级 */ .cardIsCheck, .cardIsCheck:hover { border: 1px solid #1c79f4 !important; box-shadow: 0 2px 8px rgba(28, 121, 244, 0.2); } </style> ``` ### 关键改进总结: 1. **动态数据生成**:使用 `generateMockData` 替代硬编码 2. **高效状态管理**:用计算属性替代方法计算选中状态 3. **真实分页实现**:通过 `paginatedData` 计算属性实现数据分片 4. **事件处理完善**:补全了所有事件处理函数 5. **样式优化**:确保选中状态优先级高于悬停状态 6. **移除了未使用变量**:如 `checkedList`
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值