引语:做有难度的事情,才是成长最快的时候。前段时间,接了一个公司的稍微大点的项目,急着赶进度,本人又没有独立带过队,因此,把自己给搞懵逼了。总是没有多余的时间来做自己想做的事,而且,经常把工作带入生活,这TM真是一个糟糕的事情!这两天,终于把项目上上去了,不管结果怎么样,总算是交差了吧。趁着这空档的时间,写点东西。

  本篇,就来写写关于固定表头和表列的事儿吧。

  相信大家使用excel的时候,肯定都会用到一项冻结的功能,冻结之后,可以让你很方便的查看到各种标题,从而能清楚的查看到当前行的内容。

  这个冻结锁定的需求,来源于页面太长,太宽。

  那么,对于网页版本的冻结锁定,是不是也有相应的功能呢?去网上搜索插件,基本上又都只是固定表头的,并不能固定前几列。不过幸好,不知道从哪里捡到一部分代码,改了一下内部代码,匆忙将功能实现,进入下一步。下面就跟大家分享一下,锁定表头、前几列的这段代码,也可以认为是个小插件,希望在你需要时,能帮上点忙!(实在没有找到作者是谁,如果你知道,请告知我,我一定加上作者姓名)

  独立源码如下:

(function($) {
$.fn.magicTable = function(option) {
$.fn.magicTable.option = {
/* 浮动头部 */
'magicTop': $('#J_MagicTableTop'),
'magicLeft': $('#J_MagicTableLeft'),
/* 可能有隐藏的,所以设定浮动头部的开始索引 */
'leftIndex': 0,
'leftFlg': false,
/* 高度调整 */
"thfix": 0,
"thWidth": 0, //左边显示的宽度
"thHeight": 0,
"thTop": 0,
"thLeft":0,
"thLine": 0,
"removeTotal": false
};
var option = $.extend({}, $.fn.magicTable.option, option); return this.each(function() {
$(this).css({'z-index': '9', 'display': '', 'position': 'relative'}); /*复制活动的表格内容*/
var leftHtml = '';
var leftHtml2 = '';
var leftFlg = option.leftFlg;
var thWidth = option.thWidth;
var thHeight = 0; //th的高度
var thTop = option.thTop; //th距离浏览器顶部的top高度
var thLeft = option.thLeft; //左侧未滚动时的left
var removeTotal = option.removeTotal;//除去最后一行的汇总
var flagLeftLength = 0; //左侧显示浮动层时的临界点 //处理浮动的头部
option.magicTop.html($(this).find('thead').clone()).css({
'width': $(this).width()
}); var trLenght = $(this).find('>tbody>tr').length;
if(removeTotal)
{
trLenght -= 1;
} $(this).find('tr').each(function(i, item) {
var maxHeight = $(this).height();
$(this).find('td').each(function(tdI, tdItem){
var height = $(this).height();
if(height > maxHeight){
maxHeight = height;
}
});
if (i == option.thLine){
thTop = thTop > 0 ? thTop : $(this).find('th:first').offset().top;
thHeight = $(this).height(); //包围th的tr的高度
thLeft = $(this).offset().left; //表格左侧是的left
flagLeftLength = $(this).find('th:eq(' + option.leftIndex + ')').offset().left;
thWidth = flagLeftLength + $(this).find('th:eq(' + option.leftIndex + ')').outerWidth() - thLeft;
} else if (i > option.thLine) {
if (leftFlg && (i <= trLenght)){
var tmpHtml = '';
for (var j = 0; j <= option.leftIndex; j++) {
tmpHtml += '<td style="height:' + maxHeight + 'px;width:' +
$(this).find('td:eq(' + j + ')').innerWidth() + 'px">' + $(this).find('td:eq(' + j + ')').html() + '</td>';
}
leftHtml2 += '<tr>' + tmpHtml + '</tr>';
}
leftHtml = leftHtml + '<tr><td style="height:' + maxHeight + 'px">' +
$(this).find('td:eq(' + option.leftIndex + ')').html() + '</td><tr>';
}
}); if (leftFlg) {
leftHtml = leftHtml2;
option.magicLeft.html(leftHtml);
} /*活动模块*/
function moveSquare(){
if ($(this).scrollTop() >= thTop){
option.magicTop.show().css({'z-index': '999', 'position': 'absolute', 'top': $(this).scrollTop() + option.thfix + 'px'});
} else {
option.magicTop.css({'display': 'none'});
} if ($(this).scrollLeft() >= thLeft) {
option.magicLeft.show().css({
'z-index': '99',
'position': 'absolute',
'top': thTop + thHeight - 1 + 'px',
'left': $(this).scrollLeft() - 1 + 'px',
'width': thWidth + 'px',
});
if ($(this).scrollTop() >= thTop){
option.magicLeft.show().css({
'top': thTop + thHeight - option.thfix - 1 + 'px'
});
}
} else {
option.magicLeft.css({'display': 'none'});
}
} if (document.all) {
window.attachEvent("onscroll", moveSquare);
} else {
window.addEventListener('scroll', moveSquare, false);
} });
}; $.fn.magicTable.setDefaults = function(settings) {
$.extend($.fn.magicTable.option, settings);
};
})(jQuery);

  使用方法:

    1. 在表格之前,添加一个空的表格头table,在表格之后,添加一个空的表格列table,示例如下:

     <table id="J_MagicTableTop" class="table table-bordered data-list" style="display:none;"></table>
<table class="table table-bordered data-list" id="J_MagicTable">
<thead>
<tr>
<th style="width:80px;">产品</th>
<th style="width:110px;">任务名称</th>
<th>操作</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
<table id="J_MagicTableLeft" class="table table-bordered data-list magic-table-left" style="display:none;"></table>

    2. 添加js绑定事件

        if ($("#J_MagicTable").length > 0) {
var blockHeadingHeight = $("#J_BlockHeading").outerHeight(); //用于设置最上面的间隙
$('#J_MagicTable').magicTable({thfix: blockHeadingHeight, leftIndex: 2, leftFlg: true});
}

  就这样就可以实现,固定表头和前3列的效果了,还是很不错的。

  但是需要注意以下几点:

    1. 表结构一定是table > thead > th 这种结构的,表头中一定是有th这个元素的;

    2. 表头一定要加上width宽度指示,否则将出现严重错位;

    3. 即使是使用了width指示,也会出现错位情况,应该让table>tr>td 设置文字打断, word-break: break-all;

    4. 尽量不要使用colspan属性;

  原理解析:

    其实也很简单,就是利用了一个position: absolute; 起到绝对定位的作用,通过检测当前所处位置,改变他的位置。表头、表列为复制的原表格的属性,不必单独填写;

  有待改进的地方:

    我本人已经作了部分修改,但是鉴于时间关系,没有细改。待完善: 1. 不用指定表头及表列所在的空位,自行创建即可;2. 获取真实td,th的宽度,不必要全部计算设置;

  OK,以上为今天的分享,如果有什么不对的地方,欢迎批评指正。如果你有什么疑问,也可以直接@我,我会尽快回复的!

固定表头/锁定前几列的代码参考[JS篇]的更多相关文章

  1. 前端面试题(一)JS篇

    内置类型 JS 中分为七种内置类型,七种内置类型又分为两大类型:基本类型和对象(Object). 基本类型有六种: null,undefined,boolean,number,string,symbo ...

  2. 解决react使用antd table组件固定表头后,表头和表体列不对齐以及配置fixed固定左右侧后行高度不对齐

    一.固定表头后表体列和表头不对齐 此问题可能在antd3.24.0版本之前都存在,反正3.16.2版本是存在这个问题的,如果是3.24.0之前的版本估计只能通过修改css样式解决. 按照官网说的: 1 ...

  3. HTML table固定表头

    最近尝试了几种HTML的table固定表头的方法..额...各有利弊,但很尴尬..... 1.thead和tbody的display设置为block; 这种可以实现,但是需要提前设置好每个th和td的 ...

  4. table固定前两列和最后一列,其他滑动显示

    网上搜的基本都是4个table做的,数据处理比较麻烦,写了个一个table的,此示例只固定了前两列和最后一列,和网上的不太一样. 网上搜的基本都是4个table做的,数据处理比较麻烦,写了个一个tab ...

  5. vue表格实现固定表头首列

    前言 最近在做vue移动端项目,需要做一个可以固定表头首列的表格,而且由于一些原因不能使用任何UI插件,网上找了很久也没什么好方法,所以在解决了问题之后,写下了这篇文章供后来人参考,文章有什么错漏的问 ...

  6. bootstrap-table固定表头固定列

    1.引入 bootstrap依赖于jquery bootstrap-table依赖于bootstrap,所以都需要引入 2. bootstrap-table有两种方式,html.js <tabl ...

  7. html table 固定表头和列

    /**************************************************************** jQuery 插件. 功能: 固定表格标题行或列头 Version: ...

  8. bootstrap table 怎么实现前两列固定冻结?

    $("#Table").bootstrapTable('destroy').bootstrapTable({ pagination: true,//分页 minimumCountC ...

  9. 原生javascript 固定表头原理与源码

    我在工作中需要固定表头这个功能,我不想去找,没意思.于是就写了一个,我写的是angularjs 自定义指令 起了个 "fix-header" ,有人叫  "freeze- ...

随机推荐

  1. 【BZOJ2756】奇怪的游戏(二分,最小割)

    题意: Blinker最近喜欢上一个奇怪的游戏.这个游戏在一个 N*M 的棋盘上玩,每个格子有一个数.每次 Blinker 会选择两个相邻的格子,并使这两个数都加上 1.现在 Blinker 想知道最 ...

  2. Redis 软件和配置

    Redis 下载 1.通过CMD命令进入redis 文件目录 2.运行[redis-server redis.windows.conf]

  3. PHP--目录处理

    __file___ dirname(): dirname()与__file__的组合:dirname(__file__)

  4. python学习之——小闹钟(持续完善ing)

    "啊,坏了,我忘了那啥啥了~~~" 为了不坏了,动手做一个小闹钟吧,一点点完善的过程一定美好极了,必像等待培育许久的花儿绽放一样,不多说,加油,期待↖(^ω^)↗ #! /usr/ ...

  5. 常用UML模型简要小结

    关系: 关联(组合,生命周期相同:聚合,物以类聚),依赖,泛化(继承),实现 还有 包含,细化复用已有用例:扩展,非必要主要的用例 图: 1.用例图:就是描述一个功能场景(集合),其实用例编写(前后置 ...

  6. .net WebApi中使用swagger

    我在WebApi中使用swagger的时候发现会出现很多问题,搜索很多地方都没找到完全解决问题的方法,后面自己解决了,希望对于遇到同样问题朋友有帮助.我将先一步一步的演示项目中解决swagger遇到问 ...

  7. sqlite query用法

    本文转自http://blog.csdn.net/double2hao/article/details/50281273,在此感谢作者 query(table, columns, selection, ...

  8. c#开发Mongo笔记第五篇

    现在增删查改算是都完成了,但是查询算是有点不完美的,相信现在用juqeryeasyui这一类的插件的人应该也不少吧,这样的话前台展示需要JSON格式的数据, 好在mogno驱动提供toJson()的函 ...

  9. Ubuntu上如何卸载Vmware产品

    每次升级完Kernel之后启动Vmplayer都需要重新编译一些模块,经常出现编译失败的情况,为了重新安装程序,得先卸载掉之前已安装的. 首先,执行如下命令确认正在运行的产品名称(如Workstati ...

  10. Android相机使用(系统相机、自定义相机、大图片处理)

    本博文主要是介绍了android上使用相机进行拍照并显示的两种方式,并且由于涉及到要把拍到的照片显示出来,该例子也会涉及到Android加载大图片时候的处理(避免OOM),还有简要提一下有些人Surf ...