zhuguifei
2026-03-10 2c1fd10c6fbabb8e9f0e9f07fe66fb36c008e883
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
/**
* jQuery EasyUI 1.3.6
* Copyright (c) 2009-2014 www.jeasyui.com. All rights reserved.
*
* Licensed under the GPL or commercial licenses
* To use it on other terms please contact author: info@jeasyui.com
* http://www.gnu.org/licenses/gpl.txt
* http://www.jeasyui.com/license_commercial.php
*
* jQuery EasyUI tabs Extensions 1.0 beta
* jQuery EasyUI tabs 组件扩展
* jeasyui.extensions.tabs.js
* 二次开发 流云
* 最近更新:2014-04-09
*
* 依赖项:
*   1、jquery.jdirk.js v1.0 beta late
*   2、jeasyui.extensions.js v1.0 beta late
*   3、jeasyui.extensions.menu.js v1.0 beta late
*   4、jeasyui.extensions.panel.js v1.0 beta late
*   5、jeasyui.extensions.window.js v1.0 beta late
*   6、jeasyui.extensions.dialog.js v1.0 beta late
*
* Copyright (c) 2013-2014 ChenJianwei personal All rights reserved.
* http://www.chenjianwei.org
*/
(function ($, undefined) {
 
 
    $.fn.tabs.extensions = {};
 
 
    function initTabsPanelPaddingTopLine(target) {
        var t = $(target), opts = $.data(target, "tabs").options, position = opts.tabPosition;
        if ($.isNumeric(opts.lineHeight) && opts.lineHeight > 0) {
            if (!$.array.contains(["top", "bottom", "left", "right"], position)) { position = "top"; }
            t.children("div.tabs-panels").css("padding-" + position, opts.lineHeight.toString() + "px").children().children().css("border-" + position + "-width", "1px");
        }
    };
 
 
    var _onContextMenu = $.fn.tabs.defaults.onContextMenu;
    var onContextMenu = function (e, title, index) {
        if ($.isFunction(_onContextMenu)) { _onContextMenu.apply(this, arguments); }
        var t = $(this), opts = t.tabs("options");
        if (opts.enableConextMenu) {
            e.preventDefault();
            var panel = t.tabs("getTab", index),
                panelOpts = panel.panel("options"),
                leftTabs = t.tabs("leftClosableTabs", index),
                rightTabs = t.tabs("rightClosableTabs", index),
                otherTabs = t.tabs("otherClosableTabs", index),
                allTabs = t.tabs("closableTabs"),
                selected = t.tabs("isSelected", index),
                m0 = {
                    text: '在新页面中打开', iconCls: 'icon-standard-shape-move-forwards', disabled: panelOpts.href && panelOpts.iniframe ? false : true,
                    handler: function () { t.tabs("jumpTab", index); }
                },
                m1 = {
                    text: "显示 Option", iconCls: "icon-standard-application-form", disabled: opts.showOption ? false : true, children: [
                        { text: "选项卡组 Option", iconCls: "icon-standard-tab-go", handler: function () { t.tabs("showOption"); } },
                        { text: "该选项卡 Option", iconCls: "icon-standard-tab", handler: function () { t.tabs("showOption", index); } }
                    ]
                },
                m2 = {
                    text: "关闭选项卡", iconCls: "icon-standard-application-form-delete", disabled: panelOpts.closable ? false : true,
                    handler: function () { t.tabs("closeClosable", index); }
                },
                m3 = {
                    text: "关闭其他选项卡", iconCls: "icon-standard-cancel", disabled: otherTabs.length ? false : true,
                    handler: function () { t.tabs("closeOtherClosable", index); }
                },
                m4 = {
                    text: "刷新选项卡", iconCls: "icon-standard-table-refresh", disabled: panelOpts.refreshable && panelOpts.href ? false : true,
                    handler: function () { t.tabs("refresh", index); }
                },
                m5 = {
                    text: "关闭左侧选项卡", iconCls: "icon-standard-tab-close-left", disabled: leftTabs.length ? false : true,
                    handler: function () { t.tabs("closeLeftClosable", index); }
                },
                m6 = {
                    text: "关闭右侧选项卡", iconCls: "icon-standard-tab-close-right", disabled: rightTabs.length ? false : true,
                    handler: function () { t.tabs("closeRightClosable", index); }
                },
                m7 = {
                    text: "关闭所有选项卡", iconCls: "icon-standard-cross", disabled: allTabs.length ? false : true,
                    handler: function () { t.tabs("closeAllClosable"); }
                },
                m8 = {
                    text: "新建选项卡", iconCls: "icon-standard-tab-add", disabled: opts.enableNewTabMenu ? false : true,
                    handler: function () { t.tabs("newTab", index); }
                },
                m9 = {
                    text: "重复选项卡", iconCls: "icon-standard-control-repeat", disabled: panelOpts.repeatable ? false : true,
                    handler: function () { t.tabs("repeat", index); }
                };
            var items = [];
            if ($.array.likeArray(opts.contextMenu) && !$.util.isString(opts.contextMenu)) { $.array.merge(items, opts.contextMenu); }
            if (opts.enableJumpTabMenu) { $.array.merge(items, "-", m0); }
            if (opts.showOption) { $.array.merge(items, "-", m1); }
            $.array.merge(items, panelOpts.closable ? ["-", m2, m3] : ["-", m3]);
            if (panelOpts.refreshable) { $.array.merge(items, "-", m4); }
            $.array.merge(items, "-", m5, m6, m7);
            if (panelOpts.repeatable || opts.enableNewTabMenu) {
                var mm = [];
                if (opts.enableNewTabMenu) { mm.push(m8); }
                if (panelOpts.repeatable) { mm.push(m9); }
                $.array.merge(items, "-", mm);
            }
            items = parseContextMenuMap(e, title, index, items, t);
            if (items[0] == "-") { $.array.removeAt(items, 0); }
            $.easyui.showMenu({ left: e.pageX, top: e.pageY, items: items });
        }
    };
    function parseContextMenuMap(e, title, index, menus, tabs) {
        return $.array.map(menus, function (value) {
            if (!value || $.util.isString(value)) { return value; }
            var ret = $.extend({}, value);
            ret.id = $.isFunction(value.id) ? value.id.call(ret, e, title, index, tabs) : value.id;
            ret.text = $.isFunction(value.text) ? value.text.call(ret, e, title, index, tabs) : value.text;
            ret.iconCls = $.isFunction(value.iconCls) ? value.iconCls.call(ret, e, title, index, tabs) : value.iconCls;
            ret.disabled = $.isFunction(value.disabled) ? value.disabled.call(ret, e, title, index, tabs) : value.disabled;
            ret.hideOnClick = $.isFunction(value.hideOnClick) ? value.hideOnClick.call(ret, e, title, index, tabs) : value.hideOnClick;
            ret.onclick = $.isFunction(value.onclick) ? function (e, item, menu) { value.onclick.call(this, e, title, index, tabs, item, menu); } : value.onclick;
            ret.handler = $.isFunction(value.handler) ? function (e, item, menu) { value.handler.call(this, e, title, index, tabs, item, menu); } : value.handler;
            if (ret.children && ret.children.length) { ret.children = parseContextMenuMap(e, title, index, ret.children, tabs); }
            return ret;
        });
    };
 
 
    var _updateTab = $.fn.tabs.methods.update;
    function updateTab(target, param) {
        param = $.extend({ tab: null, options: null }, param);
        var tabs = $(target), opts = $.data(target, "tabs").options,
            index = tabs.tabs("getTabIndex", param.tab),
            panelOpts = $.union({}, param.options, $.fn.tabs.extensions.panelOptions),
            tools = panelOpts.tools,
            onLoad = panelOpts.onLoad, onError = panelOpts.onError,
            updateProgress = $.array.contains(["mask", "progress", "none"], opts.updateProgress) ? opts.updateProgress : "mask",
            loading = function () {
                if (updateProgress == "mask") {
                    $.easyui.loading({ topMost: true, msg: panelOpts.loadingMessage });
                } else if (updateProgress == "progress") {
                    $.easyui.messager.progress({ title: "操作提醒", msg: panelOpts.loadingMessage, interval: 100 });
                }
            },
            loaded = function () {
                if (updateProgress == "mask") {
                    $.easyui.loaded({ topMost: true });
                } else if (updateProgress == "progress") {
                    $.easyui.messager.progress("close");
                }
            },
            refreshButton = {
                iconCls: "icon-mini-refresh", handler: function () {
                    var title = $(this).parent().prev().find("span.tabs-title").text();
                    if (title) { $.util.exec(function () { tabs.tabs("refresh", title); }); }
                }
            };
        if (panelOpts.refreshable) {
            if ($.util.likeArrayNotString(panelOpts.tools)) {
                panelOpts.tools = $.array.merge([], panelOpts.tools, refreshButton);
            } else {
                panelOpts.tools = [refreshButton];
            }
        }
        if (updateProgress != "none" && !$.string.isNullOrWhiteSpace(panelOpts.href) && (panelOpts.selected || tabs.tabs("getSelected") == param.tab)) {
            loading();
            panelOpts.onLoad = function () {
                if ($.isFunction(onLoad)) { onLoad.apply(this, arguments); }
                $.util.exec(loaded);
                $(this).panel("options").onLoad = onLoad;
            };
            panelOpts.onError = function () {
                if ($.isFunction(onError)) { onError.apply(this, arguments); }
                $.util.exec(loaded);
                $(this).panel("options").onError = onError;
            };
        }
        var ret = _updateTab.call(tabs, tabs, { tab: param.tab, options: panelOpts });
        var tab = tabs.tabs("getTab", index);
        panelOpts = tab.panel("options");
        panelOpts.tools = tools;
        initTabsPanelPaddingTopLine(target);
        if (panelOpts.closeOnDblClick && panelOpts.closable) {
            tabs.find(">div.tabs-header>div.tabs-wrap>ul.tabs>li").eq(index).off("dblclick.closeOnDblClick").on("dblclick.closeOnDblClick", function () {
                tabs.tabs("close", panelOpts.title);
            }).attr("title", "双击此选项卡标题可以将其关闭");
        }
        return ret;
    };
 
    function refreshTab(target, which) {
        var tabs = $(target), opts = tabs.tabs("options"),
            panel = tabs.tabs("getTab", which), panelOpts = panel.panel("options"),
            index = tabs.tabs("getTabIndex", panel);
        if ($.string.isNullOrWhiteSpace(panelOpts.href) && $.string.isNullOrWhiteSpace(panelOpts.content)) { return; }
        tabs.tabs("update", { tab: panel, options: panelOpts });
        if ($.isFunction(opts.onRefresh)) { opts.onRefresh.call(target, opts.title, index); }
    };
 
    function isSelected(target, which) {
        var tabs = $(target), selected = tabs.tabs("getSelected"), index = tabs.tabs("getTabIndex", selected);
        var thisTab = tabs.tabs("getTab", which), thisIndex = tabs.tabs("getTabIndex", thisTab);
        return thisIndex == index;
    };
 
    function isClosable(target, which) {
        var tabs = $(target), panel = tabs.tabs("getTab", which), panelOpts = panel.panel("options");
        return panelOpts.closable;
    };
 
    function newTab(target, which) {
        var content = $("<table></table>").css({ width: "95%", height: "100%" }),
            txtTitle = $("<input type='text' style='width: 98%;'/>"),
            txtHref = $("<input type='text' style='width: 98%;'/>"),
            ckRefreshable = $("<input id='refreshable' type='checkbox' checked='true' />"),
            ckIniframe = $("<input id='iniframe' type='checkbox' />"),
            lblRefreshable = $("<label>是否可刷新</label>"),
            lblIniframe = $("<label>是否嵌至 IFRAME(浏览器内部窗体) 中</label>");
 
        var tr1 = $("<tr></tr>").append("<td width='24%' align='right'>选项卡标题:</td>").appendTo(content);
        var tr2 = $("<tr></tr>").append("<td width='24%' align='right'>路径(href):</td>").appendTo(content);
        var tr3 = $("<tr></tr>").appendTo(content);
        $("<td></td>").append(txtTitle).appendTo(tr1);
        $("<td></td>").append(txtHref).appendTo(tr2);
        $("<td width='24%' align='right'></td>").append(ckRefreshable).append(lblRefreshable).appendTo(tr3);
        $("<td align='right'></td>").append(ckIniframe).append(lblIniframe).appendTo(tr3);
 
        which = which || 0;
        var tabs = $(target),
            index = $.isNumeric(which) ? which : tabs.tabs("getTabIndex", tabs.tabs("getTab", which)),
            header = tabs.find(">div.tabs-header>div.tabs-wrap>ul.tabs>li:eq(" + index + ")"),
            offset = header.offset(), position = $.extend({}, { left: offset.left + 10, top: offset.top + 10 });
        var dialogOptions = $.extend({
            iconCls: "icon-standard-application-form",
            title: "新建选项卡 - 设置参数",
            width: 400,
            height: 165,
            maximizable: false,
            resizable: false,
            autoVCenter: false,
            autoHCenter: false,
            enableSaveButton: false,
            topMost: false,
            applyButtonIndex: 1,
            applyButtonText: "打开",
            onApply: function (dia) {
                var title = txtTitle.val(), href = txtHref.val();
                href = href || $.fn.tabs.extensions.panelOptions.href;
                if ($.string.isNullOrWhiteSpace(title)) { title = "新建选项卡"; }
                var i = 0; while (tabs.tabs("getTab", title = title + (i ? i : ""))) { i++; }
                if ($.string.isNullOrWhiteSpace(href)) { $.easyui.messager.show("操作提醒", "请输入要创建的选项卡的路径!", "info"); txtHref.focus(); return; }
                var iniframe = ckIniframe.prop("checked"), refreshable = ckRefreshable.prop("checked");
                tabs.tabs("add", { title: title, href: href, refreshable: refreshable, closable: true, iniframe: iniframe });
                dia.dialog("close");
            },
            content: content
        }, position);
        var dia = $.easyui.showDialog(dialogOptions);
        $.util.exec(function () {
            var enter = dia.find(">div.dialog-button>a:first");
            txtTitle.keydown(function (e) { if (e.which == 13) { txtHref.focus(); } });
            txtHref.keydown(function (e) { if (e.which == 13) { ckRefreshable.focus(); } });
            ckRefreshable.keydown(function (e) { if (e.which == 13) { ckIniframe.focus(); } });
            ckIniframe.keydown(function (e) { if (e.which == 13) { enter.focus(); } });
            lblRefreshable.click(function () { ckRefreshable.click(); });
            lblIniframe.click(function () { ckIniframe.click(); });
            enter.focus();
            txtTitle.focus();
        });
    };
 
    function repeatTab(target, which) {
        var tabs = $(target), panel = tabs.tabs("getTab", which), panelOpts = panel.panel("options");
        var opts = $.extend({}, panelOpts, { selected: true, closable: true }), i = 2, title = opts.title;
        while (tabs.tabs("getTab", opts.title = title + "-" + i.toString())) { i++; }
        tabs.tabs("add", opts);
    };
 
    function getTabOption(target, which) {
        var t = $(target), tab = t.tabs("getTab", which), tabOpts = tab.panel("options");
        return tabOpts;
    };
 
    function getSelectedOption(target) {
        var t = $(target), tab = t.tabs("getSelected"), tabOpts = tab.panel("options");
        return tabOpts;
    };
 
    function getSelectedIndex(target) {
        var t = $(target), tab = t.tabs("getSelected"), index = t.tabs("getTabIndex", tab);
        return index;
    };
 
    function getSelectedTitle(target) {
        var t = $(target), tabOpts = t.tabs("getSelectedOption"), title = tabOpts.title;
        return title;
    };
 
    function leftTabs(target, which) {
        var tabs = $(target), index = $.isNumeric(which) ? which : tabs.tabs("getTabIndex", tabs.tabs("getTab", which)),
            panels = tabs.tabs("tabs");
        return $.array.range(panels, 0, index);
    };
 
    function rightTabs(target, which) {
        var tabs = $(target), index = $.isNumeric(which) ? which : tabs.tabs("getTabIndex", tabs.tabs("getTab", which)),
            panels = tabs.tabs("tabs");
        return $.array.range(panels, index + 1);
    };
 
    function otherTabs(target, which) {
        var tabs = $(target), index = $.isNumeric(which) ? which : tabs.tabs("getTabIndex", tabs.tabs("getTab", which)),
            panels = tabs.tabs("tabs");
        return $.array.merge($.array.range(panels, 0, index), $.array.range(panels, index + 1));
    };
 
    function closableFinder(val) {
        if ($.util.isJqueryObject(val) && val.length) {
            var state = $.data(val[0], "panel");
            return state && state.options && state.options.closable;
        } else { return false; }
    };
 
    function closableTabs(target) {
        var tabs = $(target), panels = tabs.tabs("tabs");
        return $.array.filter(panels, closableFinder);
    };
 
    function leftClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("leftTabs", which);
        return $.array.filter(panels, closableFinder);
    };
 
    function rightClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("rightTabs", which);
        return $.array.filter(panels, closableFinder);
    };
 
    function otherClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("otherTabs", which);
        return $.array.filter(panels, closableFinder);
    };
 
    function closeLeftTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("leftTabs", which);
        $.each(panels, function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeRightTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("rightTabs", which);
        $.each(panels, function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeOtherTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("otherTabs", which);
        $.each(panels, function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeAllTabs(target) {
        var tabs = $(target), panels = tabs.tabs("tabs");
        $.each($.array.clone(panels), function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeClosableTab(target, which) {
        var tabs = $(target), panel = tabs.tabs("getTab", which);
        if (panel && panel.panel("options").closable) {
            var index = $.isNumeric(which) ? which : tabs.tabs("getTabIndex", panel);
            tabs.tabs("close", index);
        }
    };
 
    function closeLeftClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("leftClosableTabs", which);
        $.each($.array.clone(panels), function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeRightClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("rightClosableTabs", which);
        $.each($.array.clone(panels), function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeOtherClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("otherClosableTabs", which);
        $.each($.array.clone(panels), function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function closeAllClosableTabs(target, which) {
        var tabs = $(target), panels = tabs.tabs("closableTabs", which);
        $.each($.array.clone(panels), function () { tabs.tabs("close", tabs.tabs("getTabIndex", this)); });
    };
 
    function showOption(target, which) {
        var t = $(target), opts, pos;
        if (which != null && which != undefined) {
            var p = t.tabs("getTab", which);
            opts = p.panel("options");
            pos = p.panel("header").offset();
        } else {
            opts = t.tabs("options");
            pos = t.offset();
        }
        $.extend(pos, { left: pos.left + 25, top: pos.top + 15 });
        $.easyui.showOption(opts, pos);
    };
 
    function moveTab(tabTarget, param) {
        if (!param || param.source == undefined || param.target == undefined || !param.point) { return; }
        var source = param.source, target = param.target,
            point = $.array.contains(["before", "after"], param.point) ? param.point : "before",
            t = $(tabTarget), tabs = t.tabs("tabs"),
            sourcePanel = t.tabs("getTab", source), targetPanel = t.tabs("getTab", target),
            sourceIndex = t.tabs("getTabIndex", sourcePanel),
            sourceHeader = sourcePanel.panel("header"), targetHeader = targetPanel.panel("header");
        if (!sourcePanel || !targetPanel) { return; }
 
        $.array.removeAt(tabs, sourceIndex);
        var targetIndex = $.array.indexOf(tabs, targetPanel);
        $.array.insert(tabs, point == "before" ? targetIndex : targetIndex + 1, sourcePanel);
 
        sourcePanel = sourcePanel.panel("panel"); targetPanel = targetPanel.panel("panel");
        targetPanel[point](sourcePanel); targetHeader[point](sourceHeader);
    };
 
    function insertTab(tabTarget, options) {
        var target = options.target, t = $(tabTarget);
        options.target = undefined;
        t.tabs("add", options);
        var tabs = t.tabs("tabs");
        t.tabs("move", { source: tabs.length - 1, target: target, point: "before" });
    };
 
    function setTitle(target, param) {
        if (!param || !(param.which || $.isNumeric(param.which)) || !param.title) { return; }
        var t = $(target), tab = t.tabs("getTab", param.which);
        tab.panel("setTitle", param.title);
    };
 
    function jumpTab(target, which) {
        var t = $(target),
            tab = (which == null || which == undefined) ? t.tabs("getSelected") : t.tabs("getTab", which),
            opts = tab.panel("options");
        if (opts.url) {//&& opts.iniframe
            window.open(opts.url, "_blank");
        } else {
            $.easyui.messager.show("\"" + opts.title + "\" 选项卡不可在新页面中打开。");
        }
    };
 
    var panelOptions = $.fn.tabs.extensions.panelOptions = $.extend({}, $.fn.panel.defaults, {
 
        //  该选项卡的 href 是否在 iframe 中打开。
        iniframe: false,
 
        //  该选项卡是否具有重复打开功能
        repeatable: false,
 
        //  该选项卡是否具有刷新功能。
        refreshable: true,
 
        //  双击选项卡标题是否能将其关闭,当该选项卡 closable: true 时,该属性有效。
        closeOnDblClick: true,
 
        href: null,
 
        iconCls: "icon-standard-application-form"
    });
    var methods = $.fn.tabs.extensions.methods = {
        //  覆盖 easyui-tabs 的原生方法 update,以支持扩展的功能;
        update: function (jq, param) { return jq.each(function () { updateTab(this, param); }); },
 
        //  刷新指定的选项卡;该方法定义如下参数:
        //      which:  表示被刷新的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        refresh: function (jq, which) { return jq.each(function () { refreshTab(this, which); }); },
 
        //  判断指定的选项卡是否被选中;该方法定义如下参数:
        //      which:  要判断的选项卡的 索引号 或者 标题。
        //  返回值:如果指定的选项卡被选中,则返回 true,否则返回 false。
        isSelected: function (jq, which) { return isSelected(jq[0], which); },
 
        //  判断指定的选项卡是否可关闭(closable:true);该方法定义如下参数:
        //      which:  要判断的选项卡的 索引号 或者 标题。
        //  返回值:如果指定的选项卡可被关闭(closable:true),则返回 true,否则返回 false。
        isClosable: function (jq, which) { return isClosable(jq[0], which); },
 
        //  弹出一个 easyui-dialog,可以在该 dialog 中输入参数以在当前选项卡组件中创建一个新的选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题,可选,默认为 0;该参数用于指示弹出的 easyui-dialog 出现的位置。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        newTab: function (jq, which) { return jq.each(function () { newTab(this, which); }); },
 
        //  创建一个和指定选项卡相同内容的新选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        repeat: function (jq, which) { return jq.each(function () { repeatTab(this, which); }); },
 
        //  获取指定选项卡的属性值集合(option);
        getTabOption: function (jq, which) { return getTabOption(jq[0], which); },
 
        //  获取当前选中的选项卡的属性值集合 (option);
        getSelectedOption: function (jq) { return getSelectedOption(jq[0]); },
 
        //  获取当前选中的选项卡的索引号;
        getSelectedIndex: function (jq) { return getSelectedIndex(jq[0]); },
 
        //  获取当前选中的选项卡的标题。
        getSelectedTitle: function (jq) { return getSelectedTitle(jq[0]); },
 
        //  获取指定选项卡的左侧所有选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果指定选项卡左侧没有其他选项卡,则返回一个空数组。
        leftTabs: function (jq, which) { return leftTabs(jq[0], which); },
 
        //  获取指定选项卡的右侧所有选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果指定选项卡右侧没有其他选项卡,则返回一个空数组。
        rightTabs: function (jq, which) { return rightTabs(jq[0], which); },
 
        //  获取当前选项卡控件中除指定选项卡页在的其他所有选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果当前选项卡控件除指定的选项卡页外没有其他选项卡,则返回一个空数组。
        otherTabs: function (jq, which) { return otherTabs(jq[0], which); },
 
        //  获取所有可关闭的选项卡页元素集合;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果没有可关闭的选项卡,则返回一个空数组。
        closableTabs: function (jq) { return closableTabs(jq[0]); },
 
        //  获取指定选项卡左侧的所有可关闭的选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果指定选项卡左侧没有可关闭的选项卡,则返回一个空数组。
        leftClosableTabs: function (jq, which) { return leftClosableTabs(jq[0], which); },
 
        //  获取指定选项卡右侧的所有可关闭的选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果指定选项卡右侧没有可关闭的选项卡,则返回一个空数组。
        rightClosableTabs: function (jq, which) { return rightClosableTabs(jq[0], which); },
 
        //  获取当前选项卡控件中除指定选项卡页在的其他所有可关闭的选项卡元素;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回一个数组,数组中的每一项都是一个表示选项卡页的 panel(jQuery) 对象;
        //      如果当前选项卡控件除指定的选项卡页外没有其他可关闭的选项卡,则返回一个空数组。
        otherClosableTabs: function (jq, which) { return otherClosableTabs(jq[0], which); },
 
        //  关闭指定选项卡左侧的所有选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeLeft: function (jq, which) { return jq.each(function () { closeLeftTabs(this, which); }); },
 
        //  关闭指定选项卡右侧的所有选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeRight: function (jq, which) { return jq.each(function () { closeRightTabs(this, which); }); },
 
        //  关闭除指定选项卡外的其他所有选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeOther: function (jq, which) { return jq.each(function () { closeOtherTabs(this, which); }); },
 
        //  关闭所有选项卡;
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeAll: function (jq) { return jq.each(function () { closeAllTabs(this); }); },
 
        //  指定指定的选项卡,但是如果该选项卡不可被关闭(closable:false),则不执行任何动作;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeClosable: function (jq, which) { return jq.each(function () { closeClosableTab(this, which); }); },
 
        //  指定指定的选项卡左侧的所有可关闭的选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeLeftClosable: function (jq, which) { return jq.each(function () { closeLeftClosableTabs(this, which); }); },
 
        //  指定指定的选项卡右侧的所有可关闭的选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeRightClosable: function (jq, which) { return jq.each(function () { closeRightClosableTabs(this, which); }); },
 
        //  指定除指定选项卡外的所有可关闭的选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeOtherClosable: function (jq, which) { return jq.each(function () { closeOtherClosableTabs(this, which); }); },
 
        //  指定所有可关闭的选项卡;该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        closeAllClosable: function (jq) { return jq.each(function () { closeAllClosableTabs(this); }); },
 
        //  以 easyui-dialog 的方式弹出一个 dialog 对话框窗体,该窗体中显示指定选项卡的所有属性值(options);该方法定义如下参数:
        //      which:  指定的选项卡的 索引号 或者 标题。该参数可选;如果不定义该参数,则显示选项卡组的 options 信息。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        showOption: function (jq, which) { return jq.each(function () { showOption(this, which); }); },
 
        //  将指定的 easyui-tabs tab-panel 选项卡页移动至另一位置;该方法定义如下参数:
        //      param:  这是一个 JSON-Object 对象,该对象定义如下属性:
        //          source: Integer 或 String 类型值,表示要移动的 tab-panel 的索引号或者标题 title 值;
        //          target: Integer 或 String 类型值,表示移动目标位置的 tab-panel 的索引号或者标题 title 值;
        //          point:  移动到目标位置的方式,String 类型值,仅限于定义为如下值:
        //              "before":   表示把 source 选项卡移动至 target 选项卡的前面,默认值;
        //              "after":    表示把 source 选项卡移动至 target 选项卡的后面;
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        move: function (jq, param) { return jq.each(function () { moveTab(this, param); }); },
 
        //  在当前 easyui-tabs 组件上创建一个新的选项卡,并将其移动至指定选项卡的前一格位置;该方法定义如下参数:
        //      options:  表示要创建的新选项卡的属性;是一个 JSON-Object 对象;
        //          该对象的各项属性参考 easyui-tabs 中 add 方法的参数 options,并在此基础上增加了如下属性:
        //          target: Integer 或 String 类型值,表示移动位置的 tab-panel 的索引号或者标题 title 值;
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        insert: function (jq, options) { return jq.each(function () { insertTab(this, options); }); },
 
        //  重设指定选项卡的标题名;该方法定义如下参数:
        //      param:  这是一个 JSON-Object 对象,该对象定义如下属性:
        //          which: 需要重设标题名的选项卡的 索引号(index) 或者原标题名(title);
        //          title: 新的标题名;
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        setTitle: function (jq, param) { return jq.each(function () { setTitle(this, param); }); },
 
        //  将执行的选项卡在新页面中打开;该方法定义如下参数:
        //      which:  可选值参数;表示需要在新页面打开的的选项卡的 索引号(index) 或者原标题名(title);如果未传入该参数,则对当前选中的选项卡进行操作。
        //  返回值:返回当前选项卡控件 easyui-tabs 的 jQuery 对象。
        jumpTab: function (jq, which) { return jq.each(function () { jumpTab(this, which); }); }
    };
    var defaults = $.fn.tabs.extensions.defaults = {
        //  增加 easyui-tabs 的自定义扩展属性,该属性表示当前选项卡标题栏和选项卡的 pane-body 之间的空白区域高(宽)度(px);
        //  该参数是一个 Number 数值,默认为 2.
        lineHeight: 2,
 
        //  是否启用点击选项卡头的右键菜单。
        enableConextMenu: true,
 
        //  是否启用 “创建新选项卡” 的右键菜单。
        enableNewTabMenu: false,
 
        //  是否启用 "在新页面中打开" 选项卡的右键菜单。
        enableJumpTabMenu: false,
 
        //  定义 easyui-tabs 的 onRefresh 事件,当调用 easyui-tabs 的 refresh 方法后,将触发该事件。
        onRefresh: function (title, index) { },
 
        //  定义当 enableContextMenu 为 true 时,右键点击选项卡标题时候弹出的自定义右键菜单项内容;
        //  这是一个数组格式对象,数组中的每一项都是一个 menu-item 元素;该 menu-item 元素格式定义如下:
        //      id:         表示菜单项的 id;
        //      text:       表示菜单项的显示文本;
        //      iconCls:    表示菜单项的左侧显示图标;
        //      disabled:   表示菜单项是否被禁用(禁用的菜单项点击无效);
        //      hideOnClick:    表示该菜单项点击后整个右键菜单是否立即自动隐藏;
        //      bold:           Boolean 类型值,默认为 false;表示该菜单项是否字体加粗;
        //      style:          JSON-Object 类型值,默认为 null;表示要附加到该菜单项的样式;
        //      handler:    表示菜单项的点击事件,该事件函数格式为 function(e, title, index, tabs, item, menu),其中 this 指向菜单项本身
        contextMenu: null,
 
        //  覆盖 easyui-tabs 的原生事件属性 onContextMenu,以支持相应扩展功能。
        //onContextMenu: onContextMenu, //2014-8-26 注释tabs右击事件 by leejean
 
        //  增加 easyui-tabs 的自定义扩展属性;该属性表示当右键点击选项卡头时,是否显示 "显示该选项卡的 option" 菜单项。
        //  Boolean 类型值,默认为 false。
        showOption: false,
 
        //  增加 easyui-tabs 的自定义扩展属性;该属性表示或者更新选项卡时,显示的遮蔽层进度条类型。
        //  String 类型值,可选的值限定范围如下:
        //      "mask": 表示遮蔽层 mask-loading 进度显示,默认值
        //      "progress": 表示调用 $.messager.progress 进行进度条效果显示
        //      "none": 表示不显示遮蔽层和进度条
        updateProgress: "mask"
    };
 
    $.extend($.fn.tabs.defaults, defaults);
    $.extend($.fn.tabs.methods, methods);
 
 
 
 
    function closeCurrentTab(target, iniframe) {
        iniframe = iniframe && !$.util.isUtilTop ? true : false;
        var current = $(target),
            currentTabs = current.currentTabs(),
            index;
        if (!iniframe && currentTabs.length) {
            index = current.currentTabIndex();
            if (index > -1) { currentTabs.tabs("close", index); }
        } else {
            var jq = $.util.parent.$;
            current = jq($.util.currentFrame);
            currentTabs = current.currentTabs();
            if (currentTabs.length) {
                index = current.currentTabIndex();
                if (index > -1) { currentTabs.tabs("close", index); }
            }
        }
    };
 
    function refreshCurrentTab(target, iniframe) {
        iniframe = iniframe && !$.util.isUtilTop ? true : false;
        var current = $(target),
            currentTabs = current.currentTabs(),
            index;
        if (!iniframe && currentTabs.length) {
            index = current.currentTabIndex();
            if (index > -1) { currentTabs.tabs("refresh", index); }
        } else {
            var jq = $.util.parent.$;
            current = jq($.util.currentFrame);
            currentTabs = current.currentTabs();
            if (currentTabs.length) {
                index = current.currentTabIndex();
                if (index > -1) { currentTabs.tabs("refresh", index); }
            }
        }
    };
 
    $.fn.extend({
        //  扩展 jQuery 对象的实例方法;用于关闭当前对象所在的 easyui-tabs 当前选项卡(支持当前选项卡页面为 iframe 加载的情况)。
        //  该方法定义如下参数:
        //      iniframe: Boolean 类型值,表示是否为关闭当前对象所在的父级页面的选项卡;默认为 false。
        //          如果当前页面为顶级页面,
        //          或者当前对象在 iframe 中但是不在当前iframe中的某个 easyui-tabs 内,则参数参数 inframe 无效。
        //  返回值:返回当前 jQuery 链式对象(实际上返回的 jQuery 对象中,所包含的元素已经被销毁,因为其容器 tab-panel 被关闭销毁了)。
        closeCurrentTab: function (iniframe) { return this.each(function () { closeCurrentTab(this, iniframe); }); },
 
        //  扩展 jQuery 对象的实例方法;用于刷新当前对象所在的 easyui-tabs 当前选项卡(支持当前选项卡页面为 iframe 加载的情况)。
        //  该方法定义如下参数:
        //      iniframe: Boolean 类型值,表示是否为刷新当前对象所在的父级页面的选项卡;默认为 false。
        //          如果当前页面为顶级页面,
        //          或者当前对象在 iframe 中但是不在当前iframe中的某个 easyui-tabs 内,则参数参数 inframe 无效。
        //  返回值:返回当前 jQuery 链式对象。
        refreshCurrentTab: function (iniframe) { return this.each(function () { refreshCurrentTab(this, iniframe); }); }
    });
 
 
})(jQuery);