前言:传一个uint32类型的值,通过 按位或操作符(|)来设置ui_control的值,通过按位与操作符(&)来检测是否显示或隐藏
简单介绍一下两个概念:
按位与操作符和按位或操作符都是二进制位运算符。
-
按位与操作符(&):对于每一个二进制位,只有当两个操作数的对应位都为1时,结果的对应位才为1,否则为0。例如,5(二进制101) & 3(二进制011)的结果是1(二进制001)。
-
按位或操作符(|):对于每一个二进制位,只要两个操作数的对应位有一个为1时,结果的对应位就为1,否则为0。例如,5(二进制101) | 3(二进制011)的结果是7(二进制111)。
这两种操作符在计算机编程中常用于位操作,如设置位标志、清除位标志、切换位标志等。
一、demo1:路由传一个ui_control,用高16位设置允许修改,修改位用第17位检测
var ui_control = 0;
ui_control = (ui_control | (1 << 17));
console.log(ui_control) // 131072
这时候ui_control参数传131072,在页面中做检测看是否允许修改
var uiControl = Number(new URLSearchParams(location.search).get('uiControl'))
if ((control & (1 << 17)) !== 0) {
console.log("1 表示允许修改");
} else {
console.log("0 表示不允许修改");
}
二、demo2:路由传一个ui_control,同时控制修改和导出权限,修改位用第17位检测,导出位用第16位检测
既允许修改也允许导出
var ui_control = 0;
ui_control = (ui_control | (1 << 17));
ui_control = (ui_control | (1 << 16));
console.log(ui_control) // 196608
这时候ui_control参数传196608,通过与运算检测第16位导出是否为1,第17位修改是否为1,就能知道是否有对应权限了
咱们封装一个方法出来
// keys 传一个检测权限的key,比如下面Edit编辑,Export导出
const getUiControlBinaryContent = (keys) => {
var uicontrol = Number(new URLSearchParams(location.search).get('uiControl'))
let uint32 = new Uint32Array(1);
uint32[0] = uicontrol;
const action = new Map<string, any>([
['Edit', checkUnitBuffer(uint32[0], 17)], // 第17位
['Export', checkUnitBuffer(uint32[0], 16)], // 第16位
]);
return keys ? action.get(keys) : 0;
};
// 与或位控制
const checkUnitBuffer = (control: number, idx: number) => {
if (!idx) return 0;
if ((control & (1 << idx)) !== 0) {
return 1; // 表示有该操作权限
} else {
return 0; // 表示没有该操作权限
}
};
这样的话在这些操作的地方就直接能调用getUiControlBinaryContent方法传对应key值就可以知道是否有权限了
上面的demo1和demo2是高16位的检测,接下来我们简单说一下低16位的检测
三、举个例子:低0,1,2,3,4位控制,高16,17位控制总结
1、设置ui_control:我这里用简单的html元素来展示,你们按照自己的库来做就行,最终的UI_Control就是路由上要传的参数
/**
* unit32 生成 ui_control
* ● 是否修改:ui_control & (1 << 17)
● 是否导出:ui_control & (1 << 16)
● 是否显示思维导图:ui_control & (1 << 4)
● 是否显示原文:ui_control & (1 << 3)
● 是否显示章节概率:ui_control & (1 << 2)
● 是否显示全文总结:ui_control & (1 << 1)
● 是否显示视频:ui_control & 1
*/
function onCreateUiControl() {
var ui_control = 0;
const Edit = document.getElementById("Edit");
const Export1 = document.getElementById("Export");
const VideoPre = document.getElementById("VideoPre");
const MindMap = document.getElementById("MindMap");
const AllText = document.getElementById("AllText");
const ChapterOverviewt = document.getElementById("ChapterOverviewt");
const FullTextSummary = document.getElementById("FullTextSummary");
if (Edit.checked) ui_control = (ui_control | (1 << 17));
if (Export1.checked) ui_control = (ui_control | (1 << 16));
if (VideoPre.checked) ui_control = (ui_control | 1);
if (MindMap.checked) ui_control = (ui_control | (1 << 4));
if (AllText.checked) ui_control = (ui_control | (1 << 3));
if (ChapterOverviewt.checked) ui_control = (ui_control | (1 << 2));
if (FullTextSummary.checked) ui_control = (ui_control | (1 << 1));
document.getElementById("ui_control").value = ui_control;
// TODO 这个最终的ui_control就是你设置的上面某些功能的权限了
console.log("ui_control", ui_control);
}
2、检测ui_control权限:调用getUiControlBinaryContent(key)传对应keys值做检测
/**
* UI控制使用16位位运算 https://tool.oschina.net/hexconvert
* 每一位可以看作一个开关,1表示开,0表示关。
* 右移操作符>>和按位与操作符&来获取每一位的值。如果某一位的值为1,那么对应的开关就是开,如果某一位的值为0,那么对应的开关就是关。
* ● 是否修改:ui_control & (1 << 17)
● 是否导出:ui_control & (1 << 16)
● 是否显示思维导图:ui_control & (1 << 4)
● 是否显示原文:ui_control & (1 << 3)
● 是否显示章节概率:ui_control & (1 << 2)
● 是否显示全文总结:ui_control & (1 << 1)
● 是否显示视频:ui_control & 1
*/
const getUiControlBinaryContent = (keys) => {
var uicontrol = Number(new URLSearchParams(location.search).get('uiControl'))
let uint32 = new Uint32Array(1);
uint32[0] = uicontrol;
const action = new Map<string, any>([
['Edit', checkUnitBuffer(uint32[0], 17)],
['Export', checkUnitBuffer(uint32[0], 16)],
['VideoPre', checkUnitVideo(uint32[0], 1)],
['MindMap', checkUnitBuffer(uint32[0], 4)],
['AllText', checkUnitBuffer(uint32[0], 3)],
['ChapterOverviewt', checkUnitBuffer(uint32[0], 2)],
['FullTextSummary', checkUnitBuffer(uint32[0], 1)]
]);
return keys ? action.get(keys) : 0;
};
// 与或位控制
const checkUnitBuffer = (control: number, idx: number) => {
if (!idx) return 0;
if ((control & (1 << idx)) !== 0) {
return 1;
} else {
return 0;
}
};
总结:路由上设置ui_control,通过第几位用按位或来设置具体值,用按位与来解析是否有权限