');
}
},
error: function () {
$('#shc-result', layero).html('
' + __('Query failed') + '
');
},
complete: function () {
$btn.prop('disabled', false);
}
});
},
renderSpecialHotCold: function (data, lookback, layero) {
var getColor = function (num) {
return Controller.api.getColorByNum(num);
};
var statusTag = function (status) {
var map = {
'hot': '🔥 热号',
'cold': '❄ 冷号',
'normal': '➜ 温号',
'unknown': '数据不足'
};
return map[status] || '';
};
// 新接口返回 {list: [...], current: {hot: [], cold: [], warm: []}}
var listData = data.list || data;
var current = data.current || null;
if (!listData || listData.length === 0) {
$('#shc-result', layero).html('
暂无数据
');
return;
}
var html = '
';
// 当前冷热号汇总区域
if (current && (current.hot.length > 0 || current.cold.length > 0)) {
var renderNumBall = function (item) {
var color = getColor(item.num);
return '' + item.num + '';
};
html += '
';
html += '
当前热号
';
html += '
';
for (var h = 0; h < current.hot.length; h++) {
html += renderNumBall(current.hot[h]);
}
if (current.hot.length === 0) {
html += '暂无热号';
}
html += '
';
html += '';
html += '
当前冷号
';
html += '
';
for (var c = 0; c < current.cold.length; c++) {
html += renderNumBall(current.cold[c]);
}
if (current.cold.length === 0) {
html += '暂无冷号';
}
html += '
';
html += '
';
}
// 历史记录表格
html += '
' +
'
' +
'
期号
' +
'
特码
' +
'
冷热
' +
'
次数
' +
'
平均
' +
'
排名
' +
'
';
for (var i = 0; i < listData.length; i++) {
var item = listData[i];
var rowClass = '';
if (item.status === 'hot') rowClass = 'style="background:#fff5f5;"';
else if (item.status === 'cold') rowClass = 'style="background:#f5f8ff;"';
html += '
' +
'
' + item.expect + '
' +
'
' +
'' + item.specialNum + '' +
'
' +
'
' + statusTag(item.status) + '
' +
'
' + item.count + '
' +
'
' + item.avgCount + '
' +
'
' + item.rank + '
' +
'
';
}
html += '
';
$('#shc-result', layero).html(html);
},
/**
* 筛号器弹窗
*/
showNumberFilterDialog: function () {
var html = '' +
'
';
$('#nf-range-list', layero).append(html);
},
/**
* 渲染筛号器号码网格
*/
renderNumberFilterGrid: function (layero) {
var colorMap = Controller.api.colorMap;
var html = '';
for (var num = 1; num <= 49; num++) {
var colorHex = Controller.api.getColorByNum(num);
var colorRaw = colorMap[num] || '';
var animal = Controller.api.getAnimalByNum(num);
var colorLabel = '';
if (colorRaw.indexOf('红') !== -1) colorLabel = '红';
else if (colorRaw.indexOf('蓝') !== -1) colorLabel = '蓝';
else if (colorRaw.indexOf('绿') !== -1) colorLabel = '绿';
html += '
' +
'' + num + '' +
'
' + animal + '
' +
'
';
}
$('#nf-numbers', layero).html(html);
},
/**
* 应用筛号器过滤条件
* @param {object} layero Layer弹窗对象
* @param {Array} blockedNums 手动屏蔽的号码列表
*/
applyNumberFilters: function (layero, blockedNums) {
blockedNums = blockedNums || [];
// 收集所有选中的尾号
var excludedTails = [];
$('.nf-tail-select', layero).each(function () {
var val = $(this).val();
if (val !== '' && excludedTails.indexOf(parseInt(val)) === -1) {
excludedTails.push(parseInt(val));
}
});
// 收集被点击(置灰)的生肖
var excludedZodiacs = [];
$('.nf-zodiac.btn-gray', layero).each(function () {
excludedZodiacs.push($(this).data('zodiac'));
});
// 收集被点击(置灰)的波色
var excludedColors = [];
$('.nf-color-btn.btn-gray', layero).each(function () {
excludedColors.push($(this).data('color'));
});
// 收集被点击(置灰)的单双
var excludedParities = [];
$('.nf-parity.btn-gray', layero).each(function () {
excludedParities.push($(this).data('parity'));
});
// 收集所有区间
var ranges = [];
$('.nf-range-row', layero).each(function () {
var $row = $(this);
var min = parseInt($row.find('.nf-range-min').val()) || 1;
var max = parseInt($row.find('.nf-range-max').val()) || 49;
var mode = $row.find('.nf-range-mode').hasClass('btn-info') ? 'include' : 'exclude';
ranges.push({min: min, max: max, mode: mode});
});
$('.nf-number', layero).each(function () {
var $num = $(this);
var num = parseInt($num.data('num'));
var tail = $num.data('tail');
var animal = $num.data('animal');
var color = $num.data('color');
var parity = $num.data('parity');
var hidden = false;
// 尾号筛选:选中多个尾号,任一命中即屏蔽
if (excludedTails.length > 0 && excludedTails.indexOf(tail) !== -1) {
hidden = true;
}
// 单双筛选:选中单或双,匹配则屏蔽
if (excludedParities.indexOf(parity) !== -1) {
hidden = true;
}
// 区间筛选:在区间=白名单(OR)、排除区间=黑名单(OR)
if (!hidden) {
var includeRanges = [];
var excludeRanges = [];
for (var r = 0; r < ranges.length; r++) {
if (ranges[r].mode === 'include') {
includeRanges.push(ranges[r]);
} else {
excludeRanges.push(ranges[r]);
}
}
// 黑名单:任一排除区间命中则屏蔽
for (var r = 0; r < excludeRanges.length; r++) {
if (num >= excludeRanges[r].min && num <= excludeRanges[r].max) {
hidden = true;
break;
}
}
// 白名单:有在区间规则时,号码不在任一区间则屏蔽
if (!hidden && includeRanges.length > 0) {
var inAnyInclude = false;
for (var r = 0; r < includeRanges.length; r++) {
if (num >= includeRanges[r].min && num <= includeRanges[r].max) {
inAnyInclude = true;
break;
}
}
if (!inAnyInclude) {
hidden = true;
}
}
}
// 排除的生肖
if (excludedZodiacs.indexOf(animal) !== -1) {
hidden = true;
}
// 排除的波色
if (excludedColors.indexOf(color) !== -1) {
hidden = true;
}
// 手动屏蔽的号码
if (blockedNums.indexOf(num) !== -1) {
hidden = true;
}
if (hidden) {
$num.css('opacity', '0.25').css('filter', 'grayscale(100%)');
} else {
$num.css('opacity', '1').css('filter', 'none');
}
});
},
bindevent: function () {
Form.api.bindevent($("form[role=form]"));
},
/**
* 通用分析弹窗(波色、生肖、奇偶、大小、尾数)
*/
showAnalysisDialog: function (type) {
var titles = {
colorWave: __('Color Wave'),
zodiac: __('Zodiac'),
oddEven: __('Odd/Even'),
bigSmall: __('Big/Small'),
tailNumbers: __('Tail Numbers')
};
var endpoints = {
colorWave: 'history/colorWaveAnalysis',
zodiac: 'history/zodiacAnalysis',
oddEven: 'history/oddEvenAnalysis',
bigSmall: 'history/bigSmallAnalysis',
tailNumbers: 'history/tailNumbers'
};
var hasType = ['colorWave', 'zodiac', 'oddEven', 'bigSmall', 'tailNumbers'].indexOf(type) !== -1;
var html = '
';
if (hasType) {
html += '
' +
' ' +
' ' +
' ' +
'
';
}
html += '
' +
' ' +
' ' +
' ' +
'
' +
'' +
'
';
Layer.open({
type: 1,
title: titles[type] || type,
area: ['650px', '550px'],
content: html,
shadeClose: true,
success: function (layero, index) {
$('#btn-analysis-' + type, layero).on('click', function () {
var periods = parseInt($('#analysis-periods-' + type, layero).val()) || 30;
var tp = hasType ? $('input[name="analysis-type-' + type + '"]:checked', layero).val() : 'all';
Controller.api.queryAnalysis(periods, tp, type, endpoints[type], layero);
});
if (hasType) {
$('input[name="analysis-type-' + type + '"]', layero).on('change', function () {
var periods = parseInt($('#analysis-periods-' + type, layero).val()) || 30;
Controller.api.queryAnalysis(periods, $(this).val(), type, endpoints[type], layero);
});
}
}
});
},
queryAnalysis: function (periods, type, analysisType, endpoint, layero) {
var $btn = $('#btn-analysis-' + analysisType, layero);
$btn.prop('disabled', true);
$('#analysis-result-' + analysisType, layero).html('
');
}
},
error: function () {
$('#dash-result', layero).html('
' + __('Query failed') + '
');
},
complete: function () {
$btn.prop('disabled', false);
}
});
},
renderDashboard: function (data, layero) {
var getColor = function (color) {
if (!color) return '#95a5a6';
if (color.indexOf('红') !== -1) return '#e74c3c';
if (color.indexOf('蓝') !== -1) return '#3498db';
if (color.indexOf('绿') !== -1) return '#2ecc71';
return '#95a5a6';
};
var hc = data.hotcold;
var cw = data.colorwave;
var zo = data.zodiac;
var oe = data.oddeven;
var bs = data.bigsmall;
var sm = data.sum;
var tn = data.tailnumbers;
var ballHtml = function (item) {
return '
' + item.num + '
' + item.count + '
';
};
var html = '
';
// 冷热号码
html += '
🔥❄️ 冷热号码
';
html += '
热号 Top5
';
for (var i = 0; i < 5; i++) html += ballHtml(hc.hot[i]);
html += '
冷号 Top5
';
for (var i = 0; i < 5; i++) html += ballHtml(hc.cold[i]);
html += '
';
// 波色分析
html += '
🎨 波色比例
';
html += '
';
html += '
' + cw.red + '
红波 ' + cw.red_pct + '%
';
html += '
' + cw.blue + '
蓝波 ' + cw.blue_pct + '%
';
html += '
' + cw.green + '
绿波 ' + cw.green_pct + '%
';
html += '
';
// 生肖分析
html += '
⭐ 生肖排名
';
html += '
';
for (var i = 0; i < Math.min(zo.list.length, 12); i++) {
var z = zo.list[i];
html += '
' + z.animal + '
' + z.count + ' (' + z.percent + '%)
';
}
html += '
';
// 奇偶分析
html += '
⚖️ 奇偶分析
';
html += '
';
html += '
' + oe.odd + ' (' + oe.odd_pct + '%)
奇数
';
html += '
' + oe.even + ' (' + oe.even_pct + '%)
偶数
';
html += '
';
// 大小分析
html += '
📊 大小分析
';
html += '
';
html += '
' + bs.big + ' (' + bs.big_pct + '%)
大数(25-49)
';
html += '
' + bs.small + ' (' + bs.small_pct + '%)
小数(1-24)
';
html += '
';
// 和值
html += '
📈 和值统计
';
html += '
';
html += '
' + sm.avg + '
平均
';
html += '
' + sm.max + '
最大
';
html += '
' + sm.min + '
最小
';
html += '
';
// 尾数
html += '
🔢 尾数频率
';
html += '
';
for (var i = 0; i < tn.all.length; i++) {
var t = tn.all[i];
html += '