mirror of
https://github.com/modernw/App-Installer-For-Windows-8.x-Reset.git
synced 2026-04-11 17:57:19 +10:00
Updated manager and added appx manifest reader.
This commit is contained in:
@@ -12,6 +12,18 @@
|
||||
DarkModeBackgroundColor='#001629' />
|
||||
</VisualElements>
|
||||
</Application>
|
||||
<Application Id='Manager'>
|
||||
<VisualElements
|
||||
DisplayName='Package Manager'
|
||||
Logo='Settings.Assets\Logo.png'
|
||||
SmallLogo='Settings.Assets\SmallLogo.png'
|
||||
ForegroundText='light'
|
||||
BackgroundColor='#159d9d'>
|
||||
<DefaultTile ShowName='allLogos' />
|
||||
<SplashScreen Image="VisualElements\splash\settings\splashscreen.png"
|
||||
BackgroundColor="#159d9d" DarkModeBackgroundColor='#2e1e5c' />
|
||||
</VisualElements>
|
||||
</Application>
|
||||
<Application Id='Settings'>
|
||||
<VisualElements
|
||||
DisplayName='Settings'
|
||||
|
||||
Binary file not shown.
@@ -170,7 +170,7 @@
|
||||
element.style.animation = generateAnimeString(swKeyFrames, uMillisecond, swTimingFunc, uDelayMs, swIteration, swDirection, swFillMode, swPlayState);
|
||||
element.addEventListener("animationend", function() {
|
||||
element.style.animation = "";
|
||||
complete();
|
||||
complete(element);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
396
shared/html/js/appbar.js
Normal file
396
shared/html/js/appbar.js
Normal file
@@ -0,0 +1,396 @@
|
||||
(function(global) {
|
||||
"use strict";
|
||||
|
||||
// 基类:提供 element 管理与基础 dispose 行为
|
||||
function PMAppBarBaseMember() {
|
||||
var _element = null;
|
||||
Object.defineProperty(this, "element", {
|
||||
configurable: true, // <- 关键:允许子类重定义该属性
|
||||
enumerable: false,
|
||||
get: function() { return _element; },
|
||||
set: function(value) {
|
||||
_element = value;
|
||||
try {
|
||||
if (_element) {
|
||||
// 让 DOM 节点可以反查到对应的 member
|
||||
_element.appBarMember = this;
|
||||
}
|
||||
} catch (e) {}
|
||||
}
|
||||
});
|
||||
// 可被子类或外部调用来从 DOM 中移除自身
|
||||
this.dispose = function() {
|
||||
try {
|
||||
if (this.element && this.element.parentNode) {
|
||||
this.element.parentNode.removeChild(this.element);
|
||||
}
|
||||
} catch (e) {}
|
||||
};
|
||||
}
|
||||
|
||||
function PMAppBarCommand() {
|
||||
PMAppBarBaseMember.call(this);
|
||||
var _button = document.createElement("button");
|
||||
var _iconcontainer = document.createElement("span");
|
||||
var _iconnode = document.createElement("span");
|
||||
var _labelnode = document.createElement("span");
|
||||
_button.appendChild(_iconcontainer);
|
||||
_iconcontainer.appendChild(_iconnode);
|
||||
_button.appendChild(_labelnode);
|
||||
_button.classList.add("win-command");
|
||||
_button.setAttribute("role", "menuitem");
|
||||
_iconcontainer.classList.add("win-commandicon");
|
||||
_iconcontainer.classList.add("win-commandring");
|
||||
_iconnode.classList.add("win-commandimage");
|
||||
_labelnode.classList.add("win-label");
|
||||
_iconcontainer.tabIndex = -1;
|
||||
_iconnode.tabIndex = -1;
|
||||
_labelnode.tabIndex = -1;
|
||||
_button.classList.add("win-global");
|
||||
Windows.UI.Event.Util.addEvent(_button, "keydown", function(event) {
|
||||
if (event.keyCode === 13) {
|
||||
_button.click();
|
||||
}
|
||||
});
|
||||
Object.defineProperty(this, "element", {
|
||||
get: function() { return _button; },
|
||||
set: function(value) { _button = value; }
|
||||
});
|
||||
Object.defineProperty(this, "icon", {
|
||||
get: function() { return _iconnode.innerHTML; },
|
||||
set: function(value) { _iconnode.innerHTML = value; }
|
||||
});
|
||||
Object.defineProperty(this, "label", {
|
||||
get: function() { return _labelnode.textContent; },
|
||||
set: function(value) { _labelnode.textContent = value; }
|
||||
});
|
||||
Object.defineProperty(this, "onclick", {
|
||||
get: function() { return _button.onclick; },
|
||||
set: function(value) { _button.onclick = value; }
|
||||
});
|
||||
Object.defineProperty(this, "selectable", {
|
||||
get: function() { return _button.classList.contains("win-selectable"); },
|
||||
set: function(value) {
|
||||
try { Windows.UI.Event.Util.removeEvent(this.element, "click", selectHandler); } catch (e) {}
|
||||
_button.classList.toggle("win-selectable", value);
|
||||
if (!value) {
|
||||
if (_button.classList.contains("win-selected")) {
|
||||
_button.classList.remove("win-selected");
|
||||
}
|
||||
}
|
||||
if (value) Windows.UI.Event.Util.addEvent(this.element, "click", selectHandler);
|
||||
else Windows.UI.Event.Util.removeEvent(this.element, "click", selectHandler);
|
||||
}
|
||||
});
|
||||
Object.defineProperty(this, "selected", {
|
||||
get: function() { return _button.classList.contains("win-selected"); },
|
||||
set: function(value) { _button.classList.toggle("win-selected", value); }
|
||||
});
|
||||
Object.defineProperty(this, "disabled", {
|
||||
get: function() { try { return this.element.disabled; } catch (e) { return false; } },
|
||||
set: function(value) { try { this.element.disabled = value; } catch (e) {} }
|
||||
});
|
||||
// global 或 selection (始终显示或有选择时显示)
|
||||
Object.defineProperty(this, "section", {
|
||||
get: function() {
|
||||
if (_button.classList.contains("win-global")) return "global";
|
||||
if (_button.classList.contains("win-selection")) return "selection";
|
||||
return "none";
|
||||
},
|
||||
set: function(value) {
|
||||
_button.classList.remove("win-global");
|
||||
_button.classList.remove("win-selection");
|
||||
if (value == "global") _button.classList.add("win-global");
|
||||
if (value == "selection") _button.classList.add("win-selection");
|
||||
}
|
||||
});
|
||||
|
||||
function selectHandler(event) {
|
||||
_button.classList.toggle("win-selected");
|
||||
}
|
||||
this.addEventListener = function(type, listener) {
|
||||
try { Windows.UI.Event.Util.addEvent(this.element, type, listener); } catch (e) {}
|
||||
};
|
||||
this.removeEventListener = function(type, listener) {
|
||||
try { Windows.UI.Event.Util.removeEvent(this.element, type, listener); } catch (e) {}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
function PMAppBarSeparator() {
|
||||
PMAppBarBaseMember.call(this);
|
||||
var _hr = document.createElement("hr");
|
||||
_hr.classList.add("win-command");
|
||||
_hr.classList.add("win-global");
|
||||
_hr.setAttribute("role", "separator");
|
||||
Object.defineProperty(this, "element", {
|
||||
get: function() { return _hr; },
|
||||
set: function(value) { _hr = value; }
|
||||
});
|
||||
}
|
||||
|
||||
function PMAppBar(container) {
|
||||
var _container = container;
|
||||
var _enable = true;
|
||||
|
||||
function init(node) {
|
||||
var classNames = [
|
||||
"win-overlay",
|
||||
"win-commandlayout",
|
||||
"win-appbar",
|
||||
"appbar"
|
||||
]
|
||||
try {
|
||||
for (var i = 0; i < classNames.length; i++) {
|
||||
if (!node.classList.contains(classNames[i]))
|
||||
node.classList.add(classNames[i]);
|
||||
}
|
||||
} catch (e) {}
|
||||
try {
|
||||
node.appBarControl = this;
|
||||
} catch (e) {}
|
||||
}
|
||||
Object.defineProperty(this, "element", {
|
||||
get: function() { return _container; },
|
||||
set: function(value) {
|
||||
_container = value;
|
||||
init(value);
|
||||
// 将已有成员渲染到新的容器中
|
||||
try {
|
||||
// 先移除所有成员 DOM(如果之前挂载过)
|
||||
for (var i = 0; i < this._members.length; i++) {
|
||||
try {
|
||||
var mEl = this._members[i].element;
|
||||
if (mEl && mEl.parentNode === _container) {
|
||||
_container.removeChild(mEl);
|
||||
}
|
||||
} catch (e) {}
|
||||
}
|
||||
// 重新挂载所有成员,按数组顺序
|
||||
for (i = 0; i < this._members.length; i++) {
|
||||
try {
|
||||
var el = this._members[i].element;
|
||||
if (el) _container.appendChild(el);
|
||||
} catch (e) {}
|
||||
}
|
||||
} catch (e) {}
|
||||
}
|
||||
});
|
||||
|
||||
// 成员管理
|
||||
this._members = [];
|
||||
|
||||
// 返回内部数组引用(只读语义上)
|
||||
Object.defineProperty(this, "members", {
|
||||
get: function() { return this._members; }
|
||||
});
|
||||
|
||||
// 添加成员到末尾,返回索引;若失败返回 -1
|
||||
this.add = function(member) {
|
||||
if (!member || !member.element) return -1;
|
||||
this._members.push(member);
|
||||
try {
|
||||
if (_container) _container.appendChild(member.element);
|
||||
} catch (e) {}
|
||||
this._updateSelectionVisibility();
|
||||
return this._members.length - 1;
|
||||
};
|
||||
this.addMember = this.add; // alias
|
||||
|
||||
// 在指定索引处插入(如果 index 为 undefined 或超范围,则 append)
|
||||
this.insertAt = function(member, index) {
|
||||
if (!member || !member.element) return -1;
|
||||
var len = this._members.length;
|
||||
if (typeof index !== "number" || index < 0 || index > len) {
|
||||
return this.add(member);
|
||||
}
|
||||
this._members.splice(index, 0, member);
|
||||
try {
|
||||
if (_container) {
|
||||
var refNode = _container.childNodes[index] || null;
|
||||
_container.insertBefore(member.element, refNode);
|
||||
}
|
||||
} catch (e) {}
|
||||
this._updateSelectionVisibility();
|
||||
return index;
|
||||
};
|
||||
|
||||
// remove 接受成员对象或索引
|
||||
this.remove = function(memberOrIndex) {
|
||||
var idx = -1;
|
||||
if (typeof memberOrIndex === "number") {
|
||||
idx = memberOrIndex;
|
||||
} else {
|
||||
idx = this._members.indexOf(memberOrIndex);
|
||||
}
|
||||
if (idx < 0 || idx >= this._members.length) return false;
|
||||
var removed = this._members.splice(idx, 1)[0];
|
||||
try {
|
||||
if (removed && removed.element && removed.element.parentNode) {
|
||||
removed.element.parentNode.removeChild(removed.element);
|
||||
}
|
||||
} catch (e) {}
|
||||
this._updateSelectionVisibility();
|
||||
return true;
|
||||
};
|
||||
|
||||
// 替换指定索引的成员,返回 true/false
|
||||
this.replaceAt = function(index, member) {
|
||||
if (!member || !member.element) return false;
|
||||
if (typeof index !== "number" || index < 0 || index >= this._members.length) return false;
|
||||
var old = this._members[index];
|
||||
this._members[index] = member;
|
||||
try {
|
||||
if (_container && old && old.element) {
|
||||
// 如果 old.element 在容器中,直接 replaceChild
|
||||
if (old.element.parentNode === _container) {
|
||||
_container.replaceChild(member.element, old.element);
|
||||
} else {
|
||||
// 备用:在位置 index 插入
|
||||
var ref = _container.childNodes[index] || null;
|
||||
_container.insertBefore(member.element, ref);
|
||||
}
|
||||
} else if (_container) {
|
||||
// 没有 old 元素,直接 append
|
||||
_container.appendChild(member.element);
|
||||
}
|
||||
} catch (e) {}
|
||||
this._updateSelectionVisibility();
|
||||
return true;
|
||||
};
|
||||
|
||||
this.getMember = function(index) {
|
||||
return this._members[index];
|
||||
};
|
||||
|
||||
this.indexOf = function(member) {
|
||||
return this._members.indexOf(member);
|
||||
};
|
||||
|
||||
this.clear = function() {
|
||||
while (this._members.length) {
|
||||
var m = this._members.shift();
|
||||
try {
|
||||
if (m && m.element && m.element.parentNode) {
|
||||
m.element.parentNode.removeChild(m.element);
|
||||
}
|
||||
} catch (e) {}
|
||||
}
|
||||
};
|
||||
|
||||
var timer = null;
|
||||
var isupdating = false;
|
||||
|
||||
function waitTimer(ms) {
|
||||
clearTimeout(timer);
|
||||
isupdating = true;
|
||||
timer = setTimeout(function(t) {
|
||||
isupdating = false;
|
||||
t = null;
|
||||
}, ms, timer);
|
||||
}
|
||||
Object.defineProperty(this, "isupdating", {
|
||||
get: function() { return isupdating; }
|
||||
});
|
||||
var touchHide = document.createElement("div");
|
||||
touchHide.classList.add("appbar-touchhide");
|
||||
touchHide.style.display = "none";
|
||||
Windows.UI.Event.Util.addEvent(touchHide, "click", function(event) {
|
||||
touchHide.style.display = "none";
|
||||
this.hide();
|
||||
}.bind(this));
|
||||
document.body.appendChild(touchHide);
|
||||
|
||||
function showTouchHide() {
|
||||
if (touchHide == null || touchHide == void 0) {
|
||||
touchHide = document.createElement("div");
|
||||
touchHide.classList.add("appbar-touchhide");
|
||||
}
|
||||
touchHide.style.display = "";
|
||||
}
|
||||
|
||||
function hideTouchHide() {
|
||||
touchHide.style.display = "none";
|
||||
}
|
||||
this.show = function() {
|
||||
try {
|
||||
if (!_enable) return;
|
||||
if (!this.element.classList.contains("show"))
|
||||
this.element.classList.add("show");
|
||||
waitTimer(500);
|
||||
showTouchHide();
|
||||
} catch (e) {}
|
||||
};
|
||||
this.hide = function() {
|
||||
try {
|
||||
if (this.element.classList.contains("show"))
|
||||
this.element.classList.remove("show");
|
||||
waitTimer(500);
|
||||
hideTouchHide();
|
||||
} catch (e) {}
|
||||
};
|
||||
this.setSelectionActive = function(active) {
|
||||
this._hasSelection = !!active;
|
||||
this._updateSelectionVisibility();
|
||||
};
|
||||
this._updateSelectionVisibility = function() {
|
||||
for (var i = 0; i < this._members.length; i++) {
|
||||
var el = this._members[i].element;
|
||||
if (el && el.classList && el.classList.contains("win-selection")) {
|
||||
el.style.display = this._hasSelection ? "" : "none";
|
||||
}
|
||||
}
|
||||
};
|
||||
Object.defineProperty(this, "enabled", {
|
||||
get: function() { return _enable; },
|
||||
set: function(value) {
|
||||
_enable = value;
|
||||
if (!value) {
|
||||
this.hide();
|
||||
}
|
||||
}
|
||||
});
|
||||
Object.defineProperty(this, "isshowing", {
|
||||
get: function() { return this.element.classList.contains("show"); },
|
||||
set: function(value) {
|
||||
if (value) {
|
||||
this.show();
|
||||
} else {
|
||||
this.hide();
|
||||
}
|
||||
}
|
||||
});
|
||||
this._eventShowHandler = function(event) {
|
||||
if (!this.isshowing) this.show();
|
||||
else this.hide();
|
||||
};
|
||||
this._eventHideHandler = function(event) {
|
||||
this.hide();
|
||||
};
|
||||
var EventUtil = Windows.UI.Event.Util;
|
||||
var self = this;
|
||||
EventUtil.addEvent(document, "contextmenu", function(event) {
|
||||
self._eventShowHandler(event);
|
||||
event.preventDefault();
|
||||
});
|
||||
var pressTimer = null;
|
||||
|
||||
EventUtil.addEvent(document, "mousedown", function(event) {
|
||||
if (!self._enable) return;
|
||||
pressTimer = setTimeout(function(e) {
|
||||
self._eventShowHandler(e);
|
||||
event.preventDefault();
|
||||
}, 600, event);
|
||||
});
|
||||
|
||||
EventUtil.addEvent(document, "mouseup", function() {
|
||||
clearTimeout(pressTimer);
|
||||
});
|
||||
}
|
||||
global.AppBar = {
|
||||
AppBar: PMAppBar,
|
||||
Command: PMAppBarCommand,
|
||||
Separator: PMAppBarSeparator,
|
||||
BaseMember: PMAppBarBaseMember
|
||||
};
|
||||
})(this);
|
||||
479
shared/html/js/datasrc.js
Normal file
479
shared/html/js/datasrc.js
Normal file
@@ -0,0 +1,479 @@
|
||||
(function(global) {
|
||||
"use strict";
|
||||
global.DataView = {
|
||||
ChangeType: {
|
||||
add: "add",
|
||||
remove: "remove",
|
||||
change: "change",
|
||||
clear: "clear",
|
||||
move: "move",
|
||||
sort: "sort",
|
||||
},
|
||||
};
|
||||
var childAnimeDuration = 120;
|
||||
var parentAnimeDuration = 400;
|
||||
|
||||
function showItemAmine(node) {
|
||||
return Windows.UI.Animation.runAsync(node, [
|
||||
Windows.UI.Animation.Keyframes.Scale.up,
|
||||
Windows.UI.Animation.Keyframes.Opacity.visible,
|
||||
], childAnimeDuration);
|
||||
}
|
||||
|
||||
function hideItemAmine(node) {
|
||||
return Windows.UI.Animation.runAsync(node, [
|
||||
Windows.UI.Animation.Keyframes.Scale.down,
|
||||
Windows.UI.Animation.Keyframes.Opacity.hidden,
|
||||
], childAnimeDuration);
|
||||
}
|
||||
|
||||
function updateItemAmine(node, updateCallback) {
|
||||
return Windows.UI.Animation.runAsync(node, [
|
||||
Windows.UI.Animation.Keyframes.Opacity.hidden,
|
||||
Windows.UI.Animation.Keyframes.Scale.down
|
||||
], 120).then(function() {
|
||||
if (updateCallback && typeof updateCallback === 'function') {
|
||||
updateCallback(node);
|
||||
}
|
||||
return Windows.UI.Animation.runAsync(node, [
|
||||
Windows.UI.Animation.Keyframes.Opacity.visible,
|
||||
Windows.UI.Animation.Keyframes.Scale.up
|
||||
], 120);
|
||||
}).then(function() {
|
||||
return node;
|
||||
});
|
||||
}
|
||||
|
||||
function PMChangeEvent(type, datas, detailOperation) {
|
||||
this.type = type; // ChangeType
|
||||
this.datas = datas || []; // 受影响的数据
|
||||
this.detail = detailOperation || null;
|
||||
}
|
||||
|
||||
function PMDataSource() {
|
||||
var _list = [];
|
||||
var _listeners = [];
|
||||
this.subscribe = function(fn) {
|
||||
if (typeof fn === "function") {
|
||||
_listeners.push(fn);
|
||||
}
|
||||
};
|
||||
|
||||
function emit(evt) {
|
||||
for (var i = 0; i < _listeners.length; i++) {
|
||||
_listeners[i](evt);
|
||||
}
|
||||
}
|
||||
this.add = function(item) {
|
||||
_list.push(item);
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.add, [item], { index: _list.length - 1 }
|
||||
));
|
||||
};
|
||||
this.removeAt = function(index) {
|
||||
if (index < 0 || index >= _list.length) return;
|
||||
var item = _list.splice(index, 1)[0];
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.remove, [item], { index: index }
|
||||
));
|
||||
};
|
||||
this.changeAt = function(index, newItem) {
|
||||
if (index < 0 || index >= _list.length) return;
|
||||
_list[index] = newItem;
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.change, [newItem], { index: index }
|
||||
));
|
||||
};
|
||||
this.clear = function() {
|
||||
_list.length = 0;
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.clear
|
||||
));
|
||||
};
|
||||
this.move = function(from, to) {
|
||||
if (from === to ||
|
||||
from < 0 || to < 0 ||
|
||||
from >= _list.length || to >= _list.length) {
|
||||
return;
|
||||
}
|
||||
var item = _list.splice(from, 1)[0];
|
||||
_list.splice(to, 0, item);
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.move, [item], { from: from, to: to }
|
||||
));
|
||||
};
|
||||
this.sort = function(compareFn) {
|
||||
_list.sort(compareFn);
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.sort,
|
||||
_list.slice(0), { compare: compareFn }
|
||||
));
|
||||
};
|
||||
this.get = function() {
|
||||
return _list.slice(0);
|
||||
};
|
||||
this.addList = function(list, keySelector) {
|
||||
if (!list || !list.length) return;
|
||||
|
||||
var added = [];
|
||||
var changed = [];
|
||||
|
||||
var useKey = keySelector !== void 0;
|
||||
var getKey;
|
||||
|
||||
if (keySelector === null) {
|
||||
getKey = function(item) {
|
||||
return item && item.id;
|
||||
};
|
||||
} else if (typeof keySelector === "function") {
|
||||
getKey = keySelector;
|
||||
}
|
||||
|
||||
for (var i = 0; i < list.length; i++) {
|
||||
var item = list[i];
|
||||
|
||||
if (!useKey) {
|
||||
_list.push(item);
|
||||
added.push({ item: item, index: _list.length - 1 });
|
||||
continue;
|
||||
}
|
||||
|
||||
var key = getKey(item);
|
||||
if (key === void 0) {
|
||||
_list.push(item);
|
||||
added.push({ item: item, index: _list.length - 1, key: key });
|
||||
continue;
|
||||
}
|
||||
|
||||
var found = -1;
|
||||
for (var j = 0; j < _list.length; j++) {
|
||||
if (getKey(_list[j]) === key) {
|
||||
found = j;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (found >= 0) {
|
||||
_list[found] = item;
|
||||
changed.push({ item: item, index: found, key: key });
|
||||
} else {
|
||||
_list.push(item);
|
||||
added.push({ item: item, index: _list.length - 1, key: key });
|
||||
}
|
||||
}
|
||||
|
||||
// 统一发出一个事件
|
||||
if (added.length > 0) {
|
||||
emit(new PMChangeEvent(DataView.ChangeType.add, added));
|
||||
}
|
||||
if (changed.length > 0) {
|
||||
emit(new PMChangeEvent(DataView.ChangeType.change, changed));
|
||||
}
|
||||
};
|
||||
this.updateList = function(list, fnGetKey) {
|
||||
if (!list) list = [];
|
||||
|
||||
var getKey;
|
||||
|
||||
if (fnGetKey === null) {
|
||||
getKey = function(item) {
|
||||
return item && item.id;
|
||||
};
|
||||
} else if (typeof fnGetKey === "function") {
|
||||
getKey = fnGetKey;
|
||||
} else {
|
||||
// 不提供 key:直接整体替换
|
||||
_list = list.slice(0);
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.clear
|
||||
));
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.add,
|
||||
list.map(function(item, index) {
|
||||
return { item: item, index: index };
|
||||
})
|
||||
));
|
||||
return;
|
||||
}
|
||||
|
||||
var oldList = _list;
|
||||
var newList = list;
|
||||
|
||||
var oldKeyIndex = {};
|
||||
var newKeyIndex = {};
|
||||
|
||||
var i;
|
||||
|
||||
// 建立旧列表 key → index
|
||||
for (i = 0; i < oldList.length; i++) {
|
||||
var ok = getKey(oldList[i]);
|
||||
if (ok !== void 0) {
|
||||
oldKeyIndex[ok] = i;
|
||||
}
|
||||
}
|
||||
|
||||
// 建立新列表 key → index
|
||||
for (i = 0; i < newList.length; i++) {
|
||||
var nk = getKey(newList[i]);
|
||||
if (nk !== void 0) {
|
||||
newKeyIndex[nk] = i;
|
||||
}
|
||||
}
|
||||
|
||||
var added = [];
|
||||
var changed = [];
|
||||
var removed = [];
|
||||
|
||||
// 1️⃣ 找 remove
|
||||
for (i = oldList.length - 1; i >= 0; i--) {
|
||||
var oldItem = oldList[i];
|
||||
var oldKey = getKey(oldItem);
|
||||
|
||||
if (oldKey === void 0 || newKeyIndex[oldKey] === void 0) {
|
||||
removed.push({
|
||||
item: oldItem,
|
||||
index: i,
|
||||
key: oldKey
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// 2️⃣ 找 add / change
|
||||
for (i = 0; i < newList.length; i++) {
|
||||
var newItem = newList[i];
|
||||
var newKey = getKey(newItem);
|
||||
|
||||
if (newKey === void 0 || oldKeyIndex[newKey] === void 0) {
|
||||
added.push({
|
||||
item: newItem,
|
||||
index: i,
|
||||
key: newKey
|
||||
});
|
||||
} else {
|
||||
var oldIndex = oldKeyIndex[newKey];
|
||||
var oldItem2 = oldList[oldIndex];
|
||||
|
||||
if (oldItem2 !== newItem) {
|
||||
changed.push({
|
||||
item: newItem,
|
||||
index: oldIndex,
|
||||
key: newKey
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 3️⃣ 执行 remove(从后往前)
|
||||
if (removed.length > 0) {
|
||||
for (i = 0; i < removed.length; i++) {
|
||||
_list.splice(removed[i].index, 1);
|
||||
}
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.remove,
|
||||
removed
|
||||
));
|
||||
}
|
||||
|
||||
// 4️⃣ 执行 add / change(重建顺序)
|
||||
_list = newList.slice(0);
|
||||
|
||||
if (added.length > 0) {
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.add,
|
||||
added
|
||||
));
|
||||
}
|
||||
|
||||
if (changed.length > 0) {
|
||||
emit(new PMChangeEvent(
|
||||
DataView.ChangeType.change,
|
||||
changed
|
||||
));
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
function PMDataListView(container, templateFn) {
|
||||
this.container = container;
|
||||
this.templateFn = templateFn;
|
||||
this.listViewControl = this;
|
||||
}
|
||||
PMDataListView.prototype.bind = function(ds) {
|
||||
var self = this;
|
||||
var items = ds.get();
|
||||
self.container.innerHTML = "";
|
||||
|
||||
// 动画队列,保证异步操作不会乱序
|
||||
var queue = Promise.resolve();
|
||||
|
||||
function renderItem(data, index) {
|
||||
var el = self.templateFn(data, index);
|
||||
|
||||
el.addEventListener("click", function() {
|
||||
self._toggleSelect(el);
|
||||
});
|
||||
|
||||
return el;
|
||||
}
|
||||
|
||||
// 初始化渲染
|
||||
for (var i = 0; i < items.length; i++) {
|
||||
self.container.appendChild(renderItem(items[i], i));
|
||||
}
|
||||
|
||||
ds.subscribe(function(evt) {
|
||||
|
||||
// 把每次事件放进队列,保证顺序执行
|
||||
queue = queue.then(function() {
|
||||
switch (evt.type) {
|
||||
|
||||
case DataView.ChangeType.add:
|
||||
{
|
||||
// evt.datas = [{item, index}, ...]
|
||||
var datas = evt.datas;
|
||||
|
||||
// 先批量 append 到 DOM(顺序必须保持)
|
||||
var nodes = [];
|
||||
for (var i = 0; i < datas.length; i++) {
|
||||
var n = renderItem(datas[i].item, datas[i].index);
|
||||
nodes.push(n);
|
||||
self.container.appendChild(n);
|
||||
}
|
||||
|
||||
// 如果数量>=20,动画并行,否则串行
|
||||
if (datas.length >= 20) {
|
||||
var promises = [];
|
||||
for (var j = 0; j < nodes.length; j++) {
|
||||
promises.push(showItemAmine(nodes[j]));
|
||||
}
|
||||
return Promise.all(promises);
|
||||
} else {
|
||||
// 串行
|
||||
var p = Promise.resolve();
|
||||
for (var k = 0; k < nodes.length; k++) {
|
||||
(function(node) {
|
||||
p = p.then(function() {
|
||||
return showItemAmine(node);
|
||||
});
|
||||
})(nodes[k]);
|
||||
}
|
||||
return p;
|
||||
}
|
||||
}
|
||||
|
||||
case DataView.ChangeType.remove:
|
||||
{
|
||||
var node = self.container.children[evt.detail.index];
|
||||
if (!node) return;
|
||||
|
||||
// 隐藏动画完成后再移除
|
||||
return hideItemAmine(node).then(function() {
|
||||
self.container.removeChild(node);
|
||||
});
|
||||
}
|
||||
|
||||
case DataView.ChangeType.change:
|
||||
{
|
||||
var oldNode = self.container.children[evt.detail.index];
|
||||
if (!oldNode) return;
|
||||
|
||||
// 先淡出旧节点
|
||||
return hideItemAmine(oldNode).then(function() {
|
||||
// 替换节点
|
||||
var newNode = renderItem(evt.datas[0], evt.detail.index);
|
||||
self.container.replaceChild(newNode, oldNode);
|
||||
|
||||
// 再淡入新节点
|
||||
return showItemAmine(newNode);
|
||||
});
|
||||
}
|
||||
|
||||
case DataView.ChangeType.clear:
|
||||
self.container.innerHTML = "";
|
||||
return Promise.resolve();
|
||||
|
||||
case DataView.ChangeType.move:
|
||||
{
|
||||
var node = self.container.children[evt.detail.from];
|
||||
var ref = self.container.children[evt.detail.to] || null;
|
||||
if (node) self.container.insertBefore(node, ref);
|
||||
return Promise.resolve();
|
||||
}
|
||||
|
||||
case DataView.ChangeType.sort:
|
||||
{
|
||||
self.container.innerHTML = "";
|
||||
for (var i = 0; i < evt.datas.length; i++) {
|
||||
self.container.appendChild(renderItem(evt.datas[i], i));
|
||||
}
|
||||
return Promise.resolve();
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
PMDataListView.prototype._toggleSelect = function(ele) {
|
||||
// 如果选择模式为 none,则不处理
|
||||
if (this.selectionMode === "none") return;
|
||||
|
||||
var isSelected = ele.classList.contains("selected");
|
||||
|
||||
if (this.selectionMode === "single") {
|
||||
// 单选:先取消所有选中
|
||||
this._clearSelected();
|
||||
if (!isSelected) {
|
||||
ele.classList.add("selected");
|
||||
}
|
||||
} else if (this.selectionMode === "multiple") {
|
||||
// 多选:点一次切换状态
|
||||
if (isSelected) {
|
||||
ele.classList.remove("selected");
|
||||
} else {
|
||||
ele.classList.add("selected");
|
||||
}
|
||||
}
|
||||
};
|
||||
PMDataListView.prototype._clearSelected = function() {
|
||||
var selected = this.container.querySelectorAll(".selected");
|
||||
for (var i = 0; i < selected.length; i++) {
|
||||
selected[i].classList.remove("selected");
|
||||
}
|
||||
};
|
||||
Object.defineProperty(PMDataListView.prototype, "selectionMode", {
|
||||
get: function() {
|
||||
return this._selectionMode || "none";
|
||||
},
|
||||
set: function(value) {
|
||||
var mode = String(value).toLowerCase();
|
||||
if (mode !== "none" && mode !== "single" && mode !== "multiple") {
|
||||
mode = "none";
|
||||
}
|
||||
this._selectionMode = mode;
|
||||
|
||||
// 切换模式时,清空选中状态(可选)
|
||||
if (mode === "none") {
|
||||
this._clearSelected();
|
||||
}
|
||||
if (mode === "single") {
|
||||
// 单选模式:如果多选了多个,保留第一个
|
||||
var selected = this.container.querySelectorAll(".selected");
|
||||
if (selected.length > 1) {
|
||||
for (var i = 1; i < selected.length; i++) {
|
||||
selected[i].classList.remove("selected");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
Object.defineProperty(PMDataListView.prototype, "selectedItems", {
|
||||
get: function() {
|
||||
return Array.prototype.slice.call(this.container.querySelectorAll(".selected"));
|
||||
}
|
||||
});
|
||||
|
||||
global.DataView.ChangeEvent = PMChangeEvent;
|
||||
global.DataView.DataSource = PMDataSource;
|
||||
global.DataView.ListView = PMDataListView;
|
||||
})(this);
|
||||
50
shared/html/js/manager/pages.js
Normal file
50
shared/html/js/manager/pages.js
Normal file
@@ -0,0 +1,50 @@
|
||||
(function(global) {
|
||||
"use strict";
|
||||
var pkg_ns = external.Package;
|
||||
|
||||
function archsToStr(archs) {
|
||||
var arr = [];
|
||||
for (var i = 0; i < archs.length; i++) {
|
||||
switch (archs[i]) {
|
||||
case 0:
|
||||
arr.push("x86");
|
||||
break;
|
||||
case 5:
|
||||
arr.push("ARM");
|
||||
break;
|
||||
case 9:
|
||||
arr.push("x64");
|
||||
break;
|
||||
case 11:
|
||||
arr.push("Neutral");
|
||||
break;
|
||||
case 12:
|
||||
arr.push("ARM64");
|
||||
break;
|
||||
case 65535:
|
||||
arr.push("Unknown");
|
||||
break;
|
||||
}
|
||||
}
|
||||
return arr.join(", ");
|
||||
}
|
||||
|
||||
function setAppInfoPageContent(info) {
|
||||
var page = document.getElementById("page-appinfo");
|
||||
page.querySelector(".display-name").textContent = info.Properties.DisplayName;
|
||||
page.querySelector(".publisher-display-name").textContent = info.Properties.Publisher;
|
||||
page.querySelector(".version").textContent = info.Identity.Version.Expression;
|
||||
page.querySelector(".description").textContent = info.Properties.Description;
|
||||
page.querySelector(".identity .name").textContent = info.Identity.Name;
|
||||
page.querySelector(".identity .publisher").textContent = info.Identity.Publisher;
|
||||
page.querySelector(".identity .publisher-id").textContent = info.Identity.PublisherId;
|
||||
page.querySelector(".identity .family-name").textContent = info.Identity.FamilyName;
|
||||
page.querySelector(".identity .full-name").textContent = info.Identity.FullName;
|
||||
page.querySelector(".identity .architecture").textContent = archsToStr(info.Identity.ProcessArchitecture);
|
||||
var il = info.InstallLocation;
|
||||
var pkg = pkg_ns.fromInstallLocation(il);
|
||||
var json = pkg.jsonText;
|
||||
console.log(JSON.parse(json));
|
||||
}
|
||||
global.setAppInfoPageContent = setAppInfoPageContent;
|
||||
})(this);
|
||||
524
shared/html/js/mgrinit.js
Normal file
524
shared/html/js/mgrinit.js
Normal file
@@ -0,0 +1,524 @@
|
||||
(function(global) {
|
||||
function _createImage(src, onload, onerror) {
|
||||
var img = new Image();
|
||||
|
||||
img.onload = function() {
|
||||
onload(img);
|
||||
};
|
||||
|
||||
img.onerror = function() {
|
||||
onerror && onerror();
|
||||
};
|
||||
|
||||
img.src = src;
|
||||
}
|
||||
|
||||
function getSolidOpaqueBackgroundColor(source, callback) {
|
||||
|
||||
function processImage(img) {
|
||||
if (!img || !img.complete) {
|
||||
callback(null);
|
||||
return;
|
||||
}
|
||||
|
||||
var canvas = document.createElement("canvas");
|
||||
var ctx = canvas.getContext("2d");
|
||||
|
||||
canvas.width = img.naturalWidth || img.width;
|
||||
canvas.height = img.naturalHeight || img.height;
|
||||
|
||||
ctx.drawImage(img, 0, 0);
|
||||
|
||||
try {
|
||||
var imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
|
||||
} catch (e) {
|
||||
// 跨域导致的安全异常
|
||||
callback(null);
|
||||
return;
|
||||
}
|
||||
|
||||
var data = imageData.data;
|
||||
var w = canvas.width;
|
||||
var h = canvas.height;
|
||||
|
||||
var colors = {};
|
||||
var total = 0;
|
||||
|
||||
function pushColor(r, g, b, a) {
|
||||
if (a !== 255) return;
|
||||
var key = r + "," + g + "," + b;
|
||||
colors[key] = (colors[key] || 0) + 1;
|
||||
total++;
|
||||
}
|
||||
|
||||
// top + bottom
|
||||
for (var x = 0; x < w; x++) {
|
||||
var topIndex = (0 * w + x) * 4;
|
||||
var botIndex = ((h - 1) * w + x) * 4;
|
||||
pushColor(data[topIndex], data[topIndex + 1], data[topIndex + 2], data[topIndex + 3]);
|
||||
pushColor(data[botIndex], data[botIndex + 1], data[botIndex + 2], data[botIndex + 3]);
|
||||
}
|
||||
|
||||
// left + right
|
||||
for (var y = 1; y < h - 1; y++) {
|
||||
var leftIndex = (y * w + 0) * 4;
|
||||
var rightIndex = (y * w + (w - 1)) * 4;
|
||||
pushColor(data[leftIndex], data[leftIndex + 1], data[leftIndex + 2], data[leftIndex + 3]);
|
||||
pushColor(data[rightIndex], data[rightIndex + 1], data[rightIndex + 2], data[rightIndex + 3]);
|
||||
}
|
||||
|
||||
if (total === 0) {
|
||||
callback(null);
|
||||
return;
|
||||
}
|
||||
|
||||
var bestKey = null;
|
||||
var bestCount = 0;
|
||||
|
||||
for (var key in colors) {
|
||||
if (colors.hasOwnProperty(key)) {
|
||||
if (colors[key] > bestCount) {
|
||||
bestCount = colors[key];
|
||||
bestKey = key;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 95% 纯色阈值
|
||||
if (bestCount / total < 0.95) {
|
||||
callback(null);
|
||||
return;
|
||||
}
|
||||
|
||||
callback(bestKey);
|
||||
}
|
||||
|
||||
// 如果传入的是 img 元素
|
||||
if (source && source.tagName && source.tagName.toLowerCase() === "img") {
|
||||
processImage(source);
|
||||
return;
|
||||
}
|
||||
|
||||
// 如果传入的是 data url 或普通 url
|
||||
if (typeof source === "string") {
|
||||
_createImage(source, processImage, function() {
|
||||
callback(null);
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
callback(null);
|
||||
}
|
||||
|
||||
function getHamonyColor(source, callback) {
|
||||
|
||||
function _createImage(src, onload, onerror) {
|
||||
var img = new Image();
|
||||
img.onload = function() { onload(img); };
|
||||
img.onerror = function() { onerror && onerror(); };
|
||||
img.src = src;
|
||||
}
|
||||
|
||||
function _toKey(r, g, b) {
|
||||
return r + "," + g + "," + b;
|
||||
}
|
||||
|
||||
function _rgbToHsl(r, g, b) {
|
||||
r /= 255;
|
||||
g /= 255;
|
||||
b /= 255;
|
||||
var max = Math.max(r, g, b);
|
||||
var min = Math.min(r, g, b);
|
||||
var h, s, l = (max + min) / 2;
|
||||
|
||||
if (max === min) {
|
||||
h = s = 0;
|
||||
} else {
|
||||
var d = max - min;
|
||||
s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
|
||||
switch (max) {
|
||||
case r:
|
||||
h = (g - b) / d + (g < b ? 6 : 0);
|
||||
break;
|
||||
case g:
|
||||
h = (b - r) / d + 2;
|
||||
break;
|
||||
case b:
|
||||
h = (r - g) / d + 4;
|
||||
break;
|
||||
}
|
||||
h /= 6;
|
||||
}
|
||||
return { h: h, s: s, l: l };
|
||||
}
|
||||
|
||||
function _hslToRgb(h, s, l) {
|
||||
var r, g, b;
|
||||
|
||||
function hue2rgb(p, q, t) {
|
||||
if (t < 0) t += 1;
|
||||
if (t > 1) t -= 1;
|
||||
if (t < 1 / 6) return p + (q - p) * 6 * t;
|
||||
if (t < 1 / 2) return q;
|
||||
if (t < 2 / 3) return p + (q - p) * (2 / 3 - t) * 6;
|
||||
return p;
|
||||
}
|
||||
|
||||
if (s === 0) {
|
||||
r = g = b = l;
|
||||
} else {
|
||||
var q = l < 0.5 ? l * (1 + s) : l + s - l * s;
|
||||
var p = 2 * l - q;
|
||||
r = hue2rgb(p, q, h + 1 / 3);
|
||||
g = hue2rgb(p, q, h);
|
||||
b = hue2rgb(p, q, h - 1 / 3);
|
||||
}
|
||||
|
||||
return {
|
||||
r: Math.round(r * 255),
|
||||
g: Math.round(g * 255),
|
||||
b: Math.round(b * 255)
|
||||
};
|
||||
}
|
||||
|
||||
function _lum(r, g, b) {
|
||||
function f(x) {
|
||||
x = x / 255;
|
||||
return x <= 0.03928 ? x / 12.92 : Math.pow((x + 0.055) / 1.055, 2.4);
|
||||
}
|
||||
return 0.2126 * f(r) + 0.7152 * f(g) + 0.0722 * f(b);
|
||||
}
|
||||
|
||||
function _contrast(a, b) {
|
||||
var L1 = _lum(a.r, a.g, a.b);
|
||||
var L2 = _lum(b.r, b.g, b.b);
|
||||
var lighter = Math.max(L1, L2);
|
||||
var darker = Math.min(L1, L2);
|
||||
return (lighter + 0.05) / (darker + 0.05);
|
||||
}
|
||||
|
||||
function _tryPureBackground(data, w, h) {
|
||||
var edgeColors = {};
|
||||
var edgeTotal = 0;
|
||||
|
||||
function push(r, g, b, a) {
|
||||
if (a !== 255) return;
|
||||
var k = _toKey(r, g, b);
|
||||
edgeColors[k] = (edgeColors[k] || 0) + 1;
|
||||
edgeTotal++;
|
||||
}
|
||||
|
||||
for (var x = 0; x < w; x++) {
|
||||
var top = (0 * w + x) * 4;
|
||||
var bot = ((h - 1) * w + x) * 4;
|
||||
push(data[top], data[top + 1], data[top + 2], data[top + 3]);
|
||||
push(data[bot], data[bot + 1], data[bot + 2], data[bot + 3]);
|
||||
}
|
||||
for (var y = 1; y < h - 1; y++) {
|
||||
var left = (y * w + 0) * 4;
|
||||
var right = (y * w + (w - 1)) * 4;
|
||||
push(data[left], data[left + 1], data[left + 2], data[left + 3]);
|
||||
push(data[right], data[right + 1], data[right + 2], data[right + 3]);
|
||||
}
|
||||
|
||||
if (edgeTotal === 0) return null;
|
||||
|
||||
var best = null,
|
||||
bestCount = 0;
|
||||
for (var k in edgeColors) {
|
||||
if (edgeColors.hasOwnProperty(k) && edgeColors[k] > bestCount) {
|
||||
bestCount = edgeColors[k];
|
||||
best = k;
|
||||
}
|
||||
}
|
||||
if (best && bestCount / edgeTotal >= 0.95) return best;
|
||||
return null;
|
||||
}
|
||||
|
||||
function _process(img) {
|
||||
if (!img || !img.complete) { callback(null); return; }
|
||||
|
||||
var canvas = document.createElement("canvas");
|
||||
var ctx = canvas.getContext("2d");
|
||||
canvas.width = img.naturalWidth || img.width;
|
||||
canvas.height = img.naturalHeight || img.height;
|
||||
ctx.drawImage(img, 0, 0);
|
||||
|
||||
var imageData;
|
||||
try {
|
||||
imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
|
||||
} catch (e) {
|
||||
callback(null);
|
||||
return;
|
||||
}
|
||||
|
||||
var data = imageData.data;
|
||||
var w = canvas.width,
|
||||
h = canvas.height;
|
||||
|
||||
// 1) 尝试纯色背景
|
||||
var pure = _tryPureBackground(data, w, h);
|
||||
if (pure) { callback(pure); return; }
|
||||
|
||||
// 2) 统计不透明像素(抽样)
|
||||
var sumR = 0,
|
||||
sumG = 0,
|
||||
sumB = 0,
|
||||
count = 0;
|
||||
var samples = 0;
|
||||
var step = 4; // 4x抽样,减少性能消耗
|
||||
for (var y = 0; y < h; y += step) {
|
||||
for (var x = 0; x < w; x += step) {
|
||||
var i = (y * w + x) * 4;
|
||||
var a = data[i + 3];
|
||||
if (a === 255) {
|
||||
sumR += data[i];
|
||||
sumG += data[i + 1];
|
||||
sumB += data[i + 2];
|
||||
count++;
|
||||
}
|
||||
samples++;
|
||||
}
|
||||
}
|
||||
if (count === 0) { callback(null); return; }
|
||||
|
||||
var avgR = sumR / count,
|
||||
avgG = sumG / count,
|
||||
avgB = sumB / count;
|
||||
|
||||
// 3) 生成候选色(借鉴流行配色)
|
||||
var base = _rgbToHsl(avgR, avgG, avgB);
|
||||
|
||||
function clamp(v, min, max) { return Math.max(min, Math.min(max, v)); }
|
||||
|
||||
var candidates = [];
|
||||
|
||||
// 中性色(低饱和)
|
||||
candidates.push(_hslToRgb(base.h, 0.05, 0.5));
|
||||
candidates.push(_hslToRgb(base.h, 0.1, 0.6));
|
||||
candidates.push(_hslToRgb(base.h, 0.1, 0.4));
|
||||
|
||||
// 平均色去饱和
|
||||
candidates.push(_hslToRgb(base.h, clamp(base.s * 0.4, 0.05, 0.2), clamp(base.l, 0.2, 0.8)));
|
||||
|
||||
// 互补色(活泼)
|
||||
candidates.push(_hslToRgb((base.h + 0.5) % 1, clamp(base.s * 0.6, 0.1, 0.8), clamp(base.l, 0.35, 0.7)));
|
||||
|
||||
// 类似色
|
||||
candidates.push(_hslToRgb((base.h + 0.083) % 1, clamp(base.s * 0.5, 0.1, 0.8), clamp(base.l, 0.35, 0.7)));
|
||||
candidates.push(_hslToRgb((base.h - 0.083 + 1) % 1, clamp(base.s * 0.5, 0.1, 0.8), clamp(base.l, 0.35, 0.7)));
|
||||
|
||||
// 三分色
|
||||
candidates.push(_hslToRgb((base.h + 0.333) % 1, clamp(base.s * 0.6, 0.1, 0.8), clamp(base.l, 0.35, 0.7)));
|
||||
candidates.push(_hslToRgb((base.h - 0.333 + 1) % 1, clamp(base.s * 0.6, 0.1, 0.8), clamp(base.l, 0.35, 0.7)));
|
||||
|
||||
// 4) 计算最小对比度(与所有不透明像素)
|
||||
function minContrastWithImage(bg) {
|
||||
var bgObj = { r: bg.r, g: bg.g, b: bg.b };
|
||||
var minC = Infinity;
|
||||
|
||||
for (var y = 0; y < h; y += step) {
|
||||
for (var x = 0; x < w; x += step) {
|
||||
var i = (y * w + x) * 4;
|
||||
if (data[i + 3] !== 255) continue;
|
||||
var px = { r: data[i], g: data[i + 1], b: data[i + 2] };
|
||||
var c = _contrast(bgObj, px);
|
||||
if (c < minC) minC = c;
|
||||
}
|
||||
}
|
||||
return minC;
|
||||
}
|
||||
|
||||
var best = null;
|
||||
for (var i = 0; i < candidates.length; i++) {
|
||||
var c = candidates[i];
|
||||
var minC = minContrastWithImage(c);
|
||||
if (minC >= 4.5) {
|
||||
best = c;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (best) {
|
||||
callback(_toKey(best.r, best.g, best.b));
|
||||
} else {
|
||||
callback(null);
|
||||
}
|
||||
}
|
||||
|
||||
if (source && source.tagName && source.tagName.toLowerCase() === "img") {
|
||||
_process(source);
|
||||
} else if (typeof source === "string") {
|
||||
_createImage(source, _process, function() { callback(null); });
|
||||
} else {
|
||||
callback(null);
|
||||
}
|
||||
}
|
||||
|
||||
function getSuitableBackgroundColor(source, callback) {
|
||||
getSolidOpaqueBackgroundColor(source, function(color) {
|
||||
if (color) {
|
||||
callback(color);
|
||||
} else {
|
||||
getHamonyColor(source, callback);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function createLocalizedCompare(locale) {
|
||||
return function(a, b) {
|
||||
a = a || "";
|
||||
b = b || "";
|
||||
|
||||
return a.localeCompare(b, locale, {
|
||||
numeric: true, // 2 < 10
|
||||
sensitivity: "base" // 不区分大小写 / 重音
|
||||
});
|
||||
};
|
||||
}
|
||||
var pagemgr = new PageManager();
|
||||
OnLoad.add(function() {
|
||||
var listContainer = document.getElementById("applist");
|
||||
var appItemTemplate = document.getElementById("appitem-template");
|
||||
var mgr = Package.manager;
|
||||
var nstr = Bridge.NString;
|
||||
var datasrc = new DataView.DataSource();
|
||||
var themeColor = Bridge.UI.themeColor;
|
||||
var loadingDisplay = document.getElementById("applist-loading");
|
||||
var loadingStatus = loadingDisplay.querySelector(".title");
|
||||
var listView = new DataView.ListView(listContainer, function(item) {
|
||||
var appItem = appItemTemplate.cloneNode(true);
|
||||
appItem.id = "";
|
||||
appItem.style.display = "";
|
||||
var logoimg = appItem.querySelector("img");
|
||||
logoimg.src = item.Properties.LogoBase64 || logoimg.src;
|
||||
logoimg.parentElement.style.backgroundColor = themeColor;
|
||||
var appName = appItem.querySelector(".displayName");
|
||||
appName.textContent = item.Properties.DisplayName || item.Identity.Name;
|
||||
var appPub = appItem.querySelector(".publisher");
|
||||
appPub.textContent = item.Properties.Publisher;
|
||||
appItem.data = item;
|
||||
appItem.setAttribute("data-install-location", item.InstallLocation);
|
||||
appItem.setAttribute("data-development-mode", item.DevelopmentMode);
|
||||
appItem.setAttribute("data-is-bundle", item.IsBundle);
|
||||
appItem.setAttribute("data-is-framework", item.Properties.Framework);
|
||||
appItem.setAttribute("data-family-name", item.Identity.FamilyName);
|
||||
appItem.setAttribute("data-full-name", item.Identity.FullName);
|
||||
appItem.setAttribute("data-version", item.Identity.Version.Expression);
|
||||
appItem.setAttribute("data-users", item.Users);
|
||||
appItem.setAttribute("data-publisher-id", item.Identity.PublisherId);
|
||||
setTimeout(function(a, b) {
|
||||
getSolidOpaqueBackgroundColor(a, function(color) {
|
||||
try {
|
||||
var pipes = color.split(",");
|
||||
var colorobj = new Color(parseInt(pipes[0]), parseInt(pipes[1]), parseInt(pipes[2]));
|
||||
if (colorobj.hex == "#ffffff" || colorobj.hex == "#000000") throw "too white or black";
|
||||
var rgbstr = colorobj.RGB.toString();
|
||||
b.style.backgroundColor = rgbstr;
|
||||
} catch (e) {}
|
||||
});
|
||||
}, 0, item.Properties.LogoBase64, logoimg.parentElement);
|
||||
Windows.UI.Event.Util.addEvent(appItem.querySelector("div[role=advance] a"), "click", function(e) {
|
||||
e.stopPropagation();
|
||||
try {
|
||||
pagemgr.go("appinfo", this.parentNode.parentNode.parentNode.data);
|
||||
} catch (ex) {}
|
||||
});
|
||||
return appItem;
|
||||
});
|
||||
listView.selectionMode = "single";
|
||||
listView.bind(datasrc);
|
||||
var timer = null;
|
||||
|
||||
function refreshAppList() {
|
||||
function update(datas) {
|
||||
var newDatas = [];
|
||||
for (var i = 0; i < datas.length; i++) {
|
||||
var data = datas[i];
|
||||
if (data.Properties.Framework) continue; // 过滤依赖项
|
||||
var isfind = false; // 过滤系统应用
|
||||
for (var j = 0; data && data.Users && j < data.Users.length; j++) {
|
||||
if (Bridge.NString.equals(data.Users[j], "NT AUTHORITY\\SYSTEM")) {
|
||||
isfind = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (isfind) continue;
|
||||
newDatas.push(data);
|
||||
}
|
||||
datasrc.updateList(newDatas, function(item) {
|
||||
return item.Identity.FullName || "";
|
||||
});
|
||||
var compare = function(a, b) { return a - b; };
|
||||
try {
|
||||
compare = createLocalizedCompare(external.System.Locale.currentLocale);
|
||||
} catch (e) {
|
||||
try {
|
||||
compare = createLocalizedCompare(navigator.language);
|
||||
} catch (e) {
|
||||
compare = function(a, b) {
|
||||
if (a < b) return -1;
|
||||
if (a > b) return 1;
|
||||
return 0;
|
||||
};
|
||||
}
|
||||
}
|
||||
datasrc.sort(function(a, b) {
|
||||
return compare(a.Properties.DisplayName, b.Properties.DisplayName);
|
||||
});
|
||||
}
|
||||
if (timer) clearTimeout(timer);
|
||||
timer = null;
|
||||
loadingDisplay.style.display = "";
|
||||
loadingDisplay.classList.remove("noloading");
|
||||
|
||||
function waitAndHide() {
|
||||
if (timer) clearTimeout(timer);
|
||||
timer = null;
|
||||
timer = setTimeout(function() {
|
||||
loadingDisplay.style.display = "none";
|
||||
}, 10000);
|
||||
}
|
||||
loadingStatus.textContent = "正在加载数据...";
|
||||
return mgr.get().then(function(result) {
|
||||
loadingDisplay.classList.add("noloading");
|
||||
loadingStatus.textContent = "已经加载了所有数据";
|
||||
update(result.list);
|
||||
waitAndHide();
|
||||
}, function(error) {
|
||||
loadingDisplay.classList.add("noloading");
|
||||
loadingStatus.textContent = "更新时出错: " + (error.result ? (error.result.message || error.result.ErrorCode || "获取失败") : (error.message || error.error || error));
|
||||
try { update(error.list); } catch (e) {}
|
||||
waitAndHide();
|
||||
})
|
||||
}
|
||||
var appbar = document.getElementById("appBar");
|
||||
var appbarControl = new AppBar.AppBar(appbar);
|
||||
var refreshButton = new AppBar.Command();
|
||||
refreshButton.icon = "";
|
||||
refreshButton.label = "刷新";
|
||||
global.refreshAppList2 = function refreshAppList2() {
|
||||
appbarControl.hide();
|
||||
refreshButton.disabled = true;
|
||||
refreshAppList().done(function() {
|
||||
refreshButton.disabled = false;
|
||||
}, function(error) {
|
||||
refreshButton.disabled = false;
|
||||
});
|
||||
}
|
||||
refreshButton.addEventListener("click", refreshAppList2);
|
||||
appbarControl.add(refreshButton);
|
||||
refreshAppList2();
|
||||
pagemgr.register("manager", document.getElementById("tag-manager"), document.getElementById("page-manager"));
|
||||
pagemgr.register("appinfo", document.getElementById("tag-appinfo"), document.getElementById("page-appinfo"), setAppInfoPageContent);
|
||||
var appinfoBackPage = document.getElementById("page-appinfo").querySelector(".win-backbutton");
|
||||
Windows.UI.Event.Util.addEvent(appinfoBackPage, "click", function(e) {
|
||||
pagemgr.back();
|
||||
});
|
||||
pagemgr.addEventListener("load", function(e) {
|
||||
appbarControl.enabled = e == "manager";
|
||||
refreshButton.style.display = e == "manager" ? "" : "none";
|
||||
});
|
||||
pagemgr.go("manager");
|
||||
});
|
||||
})(this);
|
||||
359
shared/html/js/pagemgr.js
Normal file
359
shared/html/js/pagemgr.js
Normal file
@@ -0,0 +1,359 @@
|
||||
(function(global) {
|
||||
"use strict";
|
||||
var eu = Windows.UI.Event.Util;
|
||||
var anime = Windows.UI.Animation;
|
||||
|
||||
function PagePair(guideNode, pageNode, respHandler) {
|
||||
var _guide = guideNode;
|
||||
var _page = pageNode;
|
||||
var _handler = respHandler || null;
|
||||
Object.defineProperty(this, "guide", {
|
||||
get: function() { return _guide; },
|
||||
set: function(value) { _guide = value; }
|
||||
});
|
||||
Object.defineProperty(this, "page", {
|
||||
get: function() { return _page; },
|
||||
set: function(value) { _page = value; }
|
||||
});
|
||||
Object.defineProperty(this, "handler", {
|
||||
get: function() { return _handler; },
|
||||
set: function(value) { _handler = value; }
|
||||
});
|
||||
}
|
||||
|
||||
function PageManager() {
|
||||
var dict = {};
|
||||
var stack = [];
|
||||
var current = -1;
|
||||
var record = {}; // 记录哪些界面已经第一次加载过
|
||||
var paramStack = [];
|
||||
// scrollStack 与 stack 对齐:scrollStack[i] 对应 stack[i]
|
||||
var scrollStack = [];
|
||||
var nowScroll = 0;
|
||||
var events = {
|
||||
firstload: [],
|
||||
beforeload: [],
|
||||
load: [],
|
||||
afterload: [],
|
||||
willunload: [],
|
||||
unload: []
|
||||
};
|
||||
|
||||
function addHandler(type, fn) {
|
||||
if (typeof fn !== "function") return;
|
||||
events[type].push(fn);
|
||||
}
|
||||
|
||||
function removeHandler(type, fn) {
|
||||
var list = events[type];
|
||||
for (var i = list.length - 1; i >= 0; i--) {
|
||||
if (list[i] === fn) {
|
||||
list.splice(i, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function emit(type, arg) {
|
||||
var list = events[type];
|
||||
for (var i = 0; i < list.length; i++) {
|
||||
try {
|
||||
list[i](arg);
|
||||
} catch (e) {}
|
||||
}
|
||||
}
|
||||
|
||||
function emitCancelable(type, arg) {
|
||||
var list = events[type];
|
||||
for (var i = 0; i < list.length; i++) {
|
||||
try {
|
||||
var r = list[i](arg);
|
||||
if (r === false) return false;
|
||||
} catch (e) {}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
/**
|
||||
* 添加载入事件
|
||||
* @param {string} type 支持:"firstload"
|
||||
"beforeload"
|
||||
"load"
|
||||
"afterload"
|
||||
"willunload"
|
||||
"unload"
|
||||
|
||||
* @param {function} fn
|
||||
*/
|
||||
this.addEventListener = function(type, fn) {
|
||||
addHandler(type, fn);
|
||||
};
|
||||
/**
|
||||
* 移除载入事件
|
||||
* @param {string} type 支持:"firstload"
|
||||
"beforeload"
|
||||
"load"
|
||||
"afterload"
|
||||
"willunload"
|
||||
"unload"
|
||||
|
||||
* @param {function} fn
|
||||
*/
|
||||
this.removeEventListener = function(type, fn) {
|
||||
removeHandler(type, fn);
|
||||
};
|
||||
|
||||
|
||||
function guideClickHandler(e) {
|
||||
var tag = this.__pageTag;
|
||||
if (!tag) return;
|
||||
if (this.classList.contains("selected")) return;
|
||||
self.go(tag);
|
||||
return;
|
||||
var keys = Object.keys(dict);
|
||||
var promises = [];
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var key = keys[i];
|
||||
var pair = dict[key];
|
||||
if (pair.guide.classList.contains("selected")) {
|
||||
promises.push(anime.runAsync(
|
||||
pair.page, [
|
||||
anime.Keyframes.Opacity.hidden,
|
||||
anime.Keyframes.Scale.down
|
||||
]
|
||||
).then(function(el) {
|
||||
el.style.display = "none";
|
||||
}));
|
||||
}
|
||||
}
|
||||
this.classList.add("selected");
|
||||
var after = Promise.join(promises);
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var key = keys[i];
|
||||
var pair = dict[key];
|
||||
if (pair.guide.classList.contains("selected")) {
|
||||
pair.page.style.display = "";
|
||||
after.then(function() {
|
||||
anime.runAsync(
|
||||
pair.page, [
|
||||
anime.Keyframes.Opacity.visible,
|
||||
anime.Keyframes.Flyout.toLeft
|
||||
]
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
var self = this;
|
||||
|
||||
function _activate(tag, args, fromHistory) {
|
||||
var pair = dict[tag];
|
||||
if (!pair) throw "Page not found: " + tag;
|
||||
if (!emitCancelable("beforeload", tag)) {
|
||||
return;
|
||||
}
|
||||
var keys = Object.keys(dict);
|
||||
var promises = [];
|
||||
var oldTags = [];
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var k = keys[i];
|
||||
var p = dict[k];
|
||||
if (p.guide.classList.contains("selected") && k !== tag) {
|
||||
if (!emitCancelable("willunload", k)) {
|
||||
return;
|
||||
}
|
||||
oldTags.push(k);
|
||||
promises.push(
|
||||
anime.runAsync(p.page, [
|
||||
anime.Keyframes.Opacity.hidden
|
||||
]).then((function(page, key) {
|
||||
return function() {
|
||||
page.style.display = "none";
|
||||
page.style.opacity = 0;
|
||||
emit("unload", key);
|
||||
};
|
||||
})(p.page, k))
|
||||
);
|
||||
p.guide.classList.remove("selected");
|
||||
}
|
||||
}
|
||||
pair.guide.classList.add("selected");
|
||||
pair.page.style.display = "";
|
||||
emit("load", tag);
|
||||
var after = Promise.join(promises);
|
||||
after.then(function() {
|
||||
if (!record[tag]) {
|
||||
record[tag] = true;
|
||||
emit("firstload", tag);
|
||||
}
|
||||
pair.page.style.opacity = 1;
|
||||
if (pair.handler) {
|
||||
// fix: use pair.handler
|
||||
pair.handler(args);
|
||||
}
|
||||
try {
|
||||
setTimeout(function(tnode) {
|
||||
try {
|
||||
tnode.scrollTop = nowScroll || 0;
|
||||
} catch (ex) {}
|
||||
}, 10, pair.page.parentNode);
|
||||
} catch (ex) {}
|
||||
return anime.runAsync(pair.page, [
|
||||
anime.Keyframes.Opacity.visible,
|
||||
anime.Keyframes.Flyout.toLeft
|
||||
]).then(function() {
|
||||
|
||||
});
|
||||
}).then(function() {
|
||||
emit("afterload", tag);
|
||||
});
|
||||
}
|
||||
this.register = function(tag, guideNode, pageNode, respHandler) {
|
||||
dict[tag] = new PagePair(guideNode, pageNode, respHandler);
|
||||
guideNode.__pageTag = tag;
|
||||
try {
|
||||
eu.removeEvent(guideNode, "click", guideClickHandler);
|
||||
eu.addEvent(guideNode, "click", guideClickHandler);
|
||||
} catch (e) {}
|
||||
};
|
||||
this.edit = function(tag, pagePair) {
|
||||
try {
|
||||
if (dict[tag] && dict[tag].guide) {
|
||||
dict[tag].guide.__pageTag = null;
|
||||
}
|
||||
} catch (e) {}
|
||||
dict[tag] = pagePair;
|
||||
try {
|
||||
pagePair.guide.__pageTag = tag;
|
||||
eu.removeEvent(pagePair.guide, "click", guideClickHandler);
|
||||
eu.addEvent(pagePair.guide, "click", guideClickHandler);
|
||||
} catch (e) {}
|
||||
};
|
||||
this.get = function(tag) {
|
||||
return dict[tag];
|
||||
};
|
||||
this.getGuide = function(tag) {
|
||||
return dict[tag].guide;
|
||||
};
|
||||
this.getPage = function(tag) {
|
||||
return dict[tag].page;
|
||||
};
|
||||
this.getHandler = function(tag) {
|
||||
return dict[tag].handler;
|
||||
};
|
||||
this.setGuide = function(tag, guideNode) {
|
||||
try {
|
||||
if (dict[tag] && dict[tag].guide) {
|
||||
eu.removeEvent(dict[tag].guide, "click", guideClickHandler);
|
||||
dict[tag].guide.__pageTag = null;
|
||||
}
|
||||
} catch (e) {}
|
||||
dict[tag].guide = guideNode;
|
||||
try {
|
||||
guideNode.__pageTag = tag;
|
||||
eu.removeEvent(guideNode, "click", guideClickHandler);
|
||||
eu.addEvent(guideNode, "click", guideClickHandler);
|
||||
} catch (e) {}
|
||||
};
|
||||
this.setPage = function(tag, pageNode) {
|
||||
dict[tag].page = pageNode;
|
||||
};
|
||||
this.setHandler = function(tag, handler) {
|
||||
dict[tag].handler = handler;
|
||||
};
|
||||
this.remove = function(tag) {
|
||||
try {
|
||||
try {
|
||||
if (dict[tag] && dict[tag].guide) {
|
||||
eu.removeEvent(dict[tag].guide, "click", guideClickHandler);
|
||||
}
|
||||
} catch (e) {}
|
||||
delete dict[tag];
|
||||
} catch (e) {}
|
||||
};
|
||||
this.clear = function() {
|
||||
try {
|
||||
var keys = Object.keys(dict);
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
this.remove(keys[i]);
|
||||
}
|
||||
} catch (e) {}
|
||||
};
|
||||
this.jump = function(tag, args) {
|
||||
_activate(tag, args, true);
|
||||
};
|
||||
this.go = function(tag, params) {
|
||||
// limit history
|
||||
if (stack.length > 300) {
|
||||
stack.length = 0;
|
||||
paramStack.length = 0;
|
||||
scrollStack.length = 0;
|
||||
current = -1;
|
||||
}
|
||||
// if we are in the middle, truncate forward history
|
||||
if (current < stack.length - 1) {
|
||||
stack.splice(current + 1);
|
||||
paramStack.splice(current + 1);
|
||||
scrollStack.splice(current + 1);
|
||||
}
|
||||
// save current page scrollTop
|
||||
try {
|
||||
if (current >= 0 && stack[current] && dict[stack[current]] && dict[stack[current]].page && dict[stack[current]].page.parentNode) {
|
||||
scrollStack[current] = dict[stack[current]].page.parentNode.scrollTop;
|
||||
}
|
||||
} catch (e) {}
|
||||
// push new entry
|
||||
stack.push(tag);
|
||||
paramStack.push(params);
|
||||
// initialize scroll value for the new page (will be used if user goes back to it later)
|
||||
scrollStack.push(0);
|
||||
current++;
|
||||
_activate(tag, params, false);
|
||||
};
|
||||
this.back = function() {
|
||||
if (current <= 0) return false;
|
||||
// save scroll of current page
|
||||
try {
|
||||
if (stack[current] && dict[stack[current]] && dict[stack[current]].page && dict[stack[current]].page.parentNode) {
|
||||
scrollStack[current] = dict[stack[current]].page.parentNode.scrollTop;
|
||||
}
|
||||
} catch (e) {}
|
||||
// move back
|
||||
current--;
|
||||
// restore scroll for new current
|
||||
nowScroll = scrollStack[current] || 0;
|
||||
_activate(stack[current], paramStack[current], true);
|
||||
return true;
|
||||
};
|
||||
this.next = function() {
|
||||
if (current >= stack.length - 1) return false;
|
||||
// save scroll of current page
|
||||
try {
|
||||
if (stack[current] && dict[stack[current]] && dict[stack[current]].page && dict[stack[current]].page.parentNode) {
|
||||
scrollStack[current] = dict[stack[current]].page.parentNode.scrollTop;
|
||||
}
|
||||
} catch (e) {}
|
||||
// move forward
|
||||
current++;
|
||||
// restore scroll for new current
|
||||
nowScroll = scrollStack[current] || 0;
|
||||
_activate(stack[current], paramStack[current], true);
|
||||
return true;
|
||||
};
|
||||
Object.defineProperty(this, "current", {
|
||||
get: function() { return stack[current]; },
|
||||
set: function(value) {
|
||||
if (value < 0 || value >= stack.length) return;
|
||||
current = value;
|
||||
// restore scroll for assigned current
|
||||
nowScroll = scrollStack[current] || 0;
|
||||
_activate(stack[current], paramStack[current], true);
|
||||
}
|
||||
});
|
||||
Object.defineProperty(this, "canback", {
|
||||
get: function() { return current > 0; }
|
||||
});
|
||||
Object.defineProperty(this, "cannext", {
|
||||
get: function() { return current < stack.length - 1; }
|
||||
});
|
||||
}
|
||||
global.PageManager = PageManager;
|
||||
})(this);
|
||||
128
shared/html/js/pkginfo.js
Normal file
128
shared/html/js/pkginfo.js
Normal file
@@ -0,0 +1,128 @@
|
||||
(function(global) {
|
||||
"use strict";
|
||||
var mgr = external.Package.manager;
|
||||
|
||||
function parseJsonCallback(swJson, callback) {
|
||||
var ret = swJson;
|
||||
try {
|
||||
if (swJson) ret = JSON.parse(swJson);
|
||||
} catch (e) {}
|
||||
if (callback) callback(ret);
|
||||
}
|
||||
global.Package = {
|
||||
reader: function(pkgPath) { external.Package.reader(pkgPath); },
|
||||
manager: {
|
||||
add: function(swPkgPath, uOptions) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.addPackage(swPkgPath, uOptions, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
})
|
||||
},
|
||||
get: function() {
|
||||
return new Promise(function(resolve, reject) {
|
||||
mgr.getPackages(function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
});
|
||||
});
|
||||
},
|
||||
remove: function(swPkgFullName) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.removePackage(swPkgFullName, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
clearup: function(swPkgName, swUserSID) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.clearupPackage(swPkgName, swUserSID, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
register: function(swPkgPath, uOptions) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.registerPackage(swPkgPath, uOptions, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
registerByFullName: function(swPkgFullName, uOptions) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.registerPackageByFullName(swPkgFullName, uOptions, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
setStatus: function(swPkgFullName, uStatus) {
|
||||
mgr.setPackageStatus(swPkgFullName, uStatus);
|
||||
},
|
||||
stage: function(swPkgPath, uOptions) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.stagePackage(swPkgPath, uOptions, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
stageUserData: function(swPkgFullName) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.stagePackageUserData(swPkgFullName, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
update: function(swPkgPath, uOptions) {
|
||||
return new Promise(function(resolve, reject, progress) {
|
||||
mgr.updatePackage(swPkgPath, uOptions, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
}, progress);
|
||||
});
|
||||
},
|
||||
findByIdentity: function(swIdName, swIdPublisher) {
|
||||
return new Promise(function(resolve, reject) {
|
||||
mgr.findPackageByIdentity(swIdName, swIdPublisher, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
});
|
||||
});
|
||||
},
|
||||
findByFamilyName: function(swFamilyName) {
|
||||
return new Promise(function(resolve, reject) {
|
||||
mgr.findPackageByFamilyName(swFamilyName, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
});
|
||||
});
|
||||
},
|
||||
findByFullName: function(swPkgFullName) {
|
||||
return new Promise(function(resolve, reject) {
|
||||
mgr.findPackageByFullName(swPkgFullName, function(result) {
|
||||
parseJsonCallback(result, resolve);
|
||||
}, function(result) {
|
||||
parseJsonCallback(result, reject);
|
||||
});
|
||||
});
|
||||
},
|
||||
},
|
||||
};
|
||||
})(this);
|
||||
@@ -380,4 +380,153 @@ function messageBoxAsync(swText, swTitle, uType, swColor, pfCallback) {
|
||||
if (reject) reject(ex);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function MessageBoxButton(swDisplayName, nValueReturn) {
|
||||
this.displayName = swDisplayName;
|
||||
this.value = nValueReturn;
|
||||
}
|
||||
|
||||
function messageBoxAdvance(swText, swCaption, aCommands, swColor, pfCallback) {
|
||||
var _lpText = swText;
|
||||
var _lpCaption = swCaption;
|
||||
var msgbox = document.createElement("div");
|
||||
msgbox.classList.add("notice-back");
|
||||
msgbox.classList.add("win-ui-dark");
|
||||
var uniqueId = "msgbox_" + new Date().getTime();
|
||||
msgbox.id = uniqueId;
|
||||
var msgbody = document.createElement("div");
|
||||
msgbody.classList.add("notice-body");
|
||||
if (!IsBlackLabel(swColor)) {
|
||||
msgbody.style.backgroundColor = swColor;
|
||||
}
|
||||
msgbox.appendChild(msgbody);
|
||||
var msgcontainter = document.createElement("div");
|
||||
msgcontainter.style.height = "100%";
|
||||
msgcontainter.style.width = "100%";
|
||||
msgcontainter.style.maxHeight = "100%";
|
||||
msgcontainter.style.minHeight = "0px";
|
||||
msgcontainter.style.boxSizing = "border-box";
|
||||
msgbody.appendChild(msgcontainter);
|
||||
var msgcaption = document.createElement("div");
|
||||
msgcontainter.appendChild(msgcaption);
|
||||
msgcontainter.style.display = "flex";
|
||||
msgcontainter.style.flexDirection = "column";
|
||||
var msgcontent = document.createElement("div");
|
||||
msgcontent.style.flex = "1 1 auto";
|
||||
msgcontent.style.marginRight = "3px";
|
||||
msgcontent.style.overflowX = "hidden";
|
||||
msgcontent.style.overflowY = "auto";
|
||||
msgcontent.style.minHeight = "0px";
|
||||
msgcontainter.appendChild(msgcontent);
|
||||
if (_lpCaption instanceof HTMLElement) {
|
||||
msgcaption.appendChild(_lpCaption);
|
||||
msgcaption.classList.add("notice-title");
|
||||
} else {
|
||||
if (!IsBlackLabel(_lpCaption)) {
|
||||
var msgtitle = document.createElement("h2");
|
||||
msgtitle.textContent = _lpCaption;
|
||||
msgtitle.classList.add("notice-title");
|
||||
msgcaption.appendChild(msgtitle);
|
||||
} else {
|
||||
var msgtitle = document.createElement("h2");
|
||||
msgtitle.textContent = "";
|
||||
msgtitle.classList.add("notice-title");
|
||||
msgcaption.appendChild(msgtitle);
|
||||
}
|
||||
}
|
||||
if (_lpText instanceof HTMLElement || _lpText instanceof HTMLDivElement || typeof _lpText !== "string") {
|
||||
try {
|
||||
_lpText.classList.add("notice-text");
|
||||
msgcontent.appendChild(_lpText);
|
||||
} catch (e) {
|
||||
if (!IsBlackLabel(_lpText)) {
|
||||
var msgtext = document.createElement("p");
|
||||
msgtext.textContent = _lpText;
|
||||
msgtext.classList.add("notice-text");
|
||||
if (IsBlackLabel(_lpCaption)) {
|
||||
msgtext.style.marginTop = "0";
|
||||
}
|
||||
msgcontent.appendChild(msgtext);
|
||||
} else {
|
||||
var msgtext = document.createElement("p");
|
||||
msgtext.innerText = "";
|
||||
msgtext.classList.add("notice-text");
|
||||
if (IsBlackLabel(_lpCaption)) {
|
||||
msgtext.style.marginTop = "0";
|
||||
}
|
||||
msgcontent.appendChild(msgtext);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (!IsBlackLabel(_lpText)) {
|
||||
var msgtext = document.createElement("p");
|
||||
msgtext.textContent = _lpText;
|
||||
msgtext.classList.add("notice-text");
|
||||
if (IsBlackLabel(_lpCaption)) {
|
||||
msgtext.style.marginTop = "0";
|
||||
}
|
||||
msgcontent.appendChild(msgtext);
|
||||
} else {
|
||||
var msgtext = document.createElement("p");
|
||||
msgtext.innerText = "";
|
||||
msgtext.classList.add("notice-text");
|
||||
if (IsBlackLabel(_lpCaption)) {
|
||||
msgtext.style.marginTop = "0";
|
||||
}
|
||||
msgcontent.appendChild(msgtext);
|
||||
}
|
||||
}
|
||||
var msgctrls = document.createElement("div");
|
||||
msgctrls.classList.add("notice-controls");
|
||||
msgcontainter.appendChild(msgctrls);
|
||||
if (aCommands.length <= 0) {
|
||||
aCommands.push(new MessageBoxButton(GetLocaleStringFromResId(800) || "OK", MBRET.IDOK));
|
||||
}
|
||||
for (var i = 0; i < aCommands.length; i++) {
|
||||
var cmd = aCommands[i];
|
||||
var btn = document.createElement("button");
|
||||
btn.textContent = cmd.displayName;
|
||||
btn.setAttribute("data-msgbox-value", cmd.value);
|
||||
Windows.UI.Event.Util.addEvent(btn, "click", function(event) {
|
||||
var btns = this.parentNode.querySelectorAll("button");
|
||||
var lastbtnstatus = [];
|
||||
for (var j = 0; j < btns.length; j++) {
|
||||
lastbtnstatus.push(btns[j].disabled);
|
||||
btns[j].disabled = true;
|
||||
}
|
||||
try {
|
||||
pfCallback(this.getAttribute("data-msgbox-value"));
|
||||
} catch (e) {}
|
||||
msgbox.style.opacity = 0;
|
||||
setTimeout(function(nodes, laststatus) {
|
||||
for (var k = 0; k < nodes.length; k++) {
|
||||
nodes[k].disabled = laststatus[k];
|
||||
}
|
||||
document.body.removeChild(msgbox);
|
||||
}, 500, btns, lastbtnstatus);
|
||||
});
|
||||
msgctrls.appendChild(btn);
|
||||
}
|
||||
document.body.appendChild(msgbox);
|
||||
setTimeout(function() {
|
||||
msgbox.style.opacity = 1;
|
||||
}, 1);
|
||||
return msgbox.id;
|
||||
}
|
||||
|
||||
function messageBoxAdvanceAsync(swText, swCaption, aCommands, swColor) {
|
||||
if (typeof Promise === "undefined") {
|
||||
console.error("Promise is not supported in this environment.");
|
||||
messageBoxAdvance(swText, swCaption, aCommands, swColor);
|
||||
}
|
||||
return new Promise(function(resolve, reject) {
|
||||
try {
|
||||
messageBoxAdvance(swText, swCaption, aCommands, swColor, function(valueReturn) {
|
||||
if (resolve) resolve(valueReturn);
|
||||
});
|
||||
} catch (ex) {
|
||||
if (reject) reject(ex);
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -8,6 +8,7 @@
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<script type="text/javascript" src="js/module.js"></script>
|
||||
<script type="text/javascript" src="js/polyfill-ie.js"></script>
|
||||
<link rel="stylesheet" href="libs/winjs/1.0/css/ui-light.css" id="winjs-style-1">
|
||||
<link rel="stylesheet" href="libs/winjs/2.0/css/ui-light.css" id="winjs-style">
|
||||
<script type="text/javascript" src="libs/winjs/1.0/js/base.js"></script>
|
||||
<script type="text/javascript" src="libs/winjs/1.0/js/ui.js"></script>
|
||||
@@ -21,38 +22,77 @@
|
||||
<link rel="stylesheet" href="fonts/segx.css">
|
||||
<link rel="stylesheet" href="manager/page.css">
|
||||
<link rel="stylesheet" href="manager/appitem.css">
|
||||
<link rel="stylesheet" href="manager/appbar.css">
|
||||
<script type="text/javascript" src="js/event.js"></script>
|
||||
<script type="text/javascript" src="js/tileback.js"></script>
|
||||
<script type="text/javascript" src="js/load.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="libs/msgbox/msgbox.css">
|
||||
<script type="text/javascript" src="libs/msgbox/msgbox.js"></script>
|
||||
<script type="text/javascript" src="js/init.js"></script>
|
||||
<script type="text/javascript" src="js/pkginfo.js"></script>
|
||||
<script type="text/javascript" src="js/datasrc.js"></script>
|
||||
<script type="text/javascript" src="js/appbar.js"></script>
|
||||
<script type="text/javascript" src="js/pagemgr.js"></script>
|
||||
<script type="text/javascript" src="js/manager/pages.js"></script>
|
||||
<script type="text/javascript" src="js/mgrinit.js"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="settingpage" class="pagecontainer full">
|
||||
<div id="managerpage" class="pagecontainer full">
|
||||
<div class="page full guide fold">
|
||||
<main class="main padding">
|
||||
<div id="page-manager">
|
||||
<div id="page-manager" style="display: none;" class="ispage">
|
||||
<h2>应用</h2>
|
||||
<p>在这里,可以对安装的 Windows 商店应用进行管理。</p>
|
||||
<h3>安装的应用</h3>
|
||||
<template id="appitem-template">
|
||||
|
||||
</template>
|
||||
<div class="appitem selected">
|
||||
<div role="img">
|
||||
<img width="24" height="24" src="images/applogo.default.png" />
|
||||
<br>
|
||||
<div class="app-loading" id="applist-loading" style="display: none;">
|
||||
<progress class="win-ring"></progress>
|
||||
<span class="win-label title">正在加载应用...</span>
|
||||
<br>
|
||||
</div>
|
||||
<div class="appitem" id="appitem-template" style="display: none;">
|
||||
<div role="img" style="pointer-events: none;">
|
||||
<img width="" height="" src="images/applogo.default.png" />
|
||||
</div>
|
||||
<div role="divide"></div>
|
||||
<div role="divide" style="pointer-events: none;"></div>
|
||||
<div role="excepticon">
|
||||
<div role="title" class="win-type-x-small"><span>App Name</span></div>
|
||||
<div role="control"><button>卸载</button></div>
|
||||
<div role="title" class="win-type-x-small" style="pointer-events: none;">
|
||||
<span class="displayName">App Name</span><br>
|
||||
<span class="publisher">Publisher</span>
|
||||
</div>
|
||||
<div role="advance">
|
||||
<a>高级选项</a>
|
||||
</div>
|
||||
<div role="control">
|
||||
<button name="uninstall">卸载</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<ul>
|
||||
<li></li>
|
||||
</ul>
|
||||
<div id="applist" class="appitem-list" style="width: 100%; height: auto;">
|
||||
</div>
|
||||
<div class="bottom-compensate"></div>
|
||||
</div>
|
||||
<div id="page-appinfo" class="ispage app-detailpage">
|
||||
<header>
|
||||
<button class="win-backbutton"></button>
|
||||
<h2 class="display-name">App DisplayName</h2>
|
||||
</header>
|
||||
<span class="publisher-display-name">App PublisherDisplayName</span><br>
|
||||
<span class="version">App Version</span><br>
|
||||
<span class="description">App Description</span>
|
||||
<p><strong>应用身份</strong></p>
|
||||
<div class="identity win-type-body" style="width: 100%; max-width: 100%; box-sizing: border-box; -ms-user-select: element;">
|
||||
<span style="font-weight: bold;">名称</span><span>: </span><span class="name"></span><br>
|
||||
<span style="font-weight: bold;">发布者</span><span>: </span><span class="publisher"></span><br>
|
||||
<span style="font-weight: bold;">发布者 ID</span><span>: </span><span class="publisher-id"></span><br>
|
||||
<span style="font-weight: bold;">系列名</span><span>: </span><span class="family-name"></span><br>
|
||||
<span style="font-weight: bold;">全名</span><span>: </span><span class="full-name"></span><br>
|
||||
<span style="font-weight: bold;">支持的处理器架构</span><span>: </span><span class="architecture"></span><br>
|
||||
</div>
|
||||
<p><strong>卸载</strong></p>
|
||||
<p>卸载此应用及其设置。</p>
|
||||
<button id="detail-uninstall-btn" data-app-fullname="">卸载</button>
|
||||
</div>
|
||||
</main>
|
||||
<aside class="win-ui-dark">
|
||||
@@ -75,10 +115,14 @@
|
||||
</ul>
|
||||
<hr>
|
||||
<ul class="list">
|
||||
<li>
|
||||
<li id="tag-manager">
|
||||
<div role="img"></div>
|
||||
<span class="win-type-base">管理</span>
|
||||
</li>
|
||||
<li id="tag-appinfo" class="subitem">
|
||||
<div role="img"></div>
|
||||
<span class="win-type-base">应用信息</span>
|
||||
</li>
|
||||
<li>
|
||||
<div role="img"></div>
|
||||
<span class="win-type-base">Manager</span>
|
||||
@@ -88,6 +132,8 @@
|
||||
</aside>
|
||||
</div>
|
||||
</div>
|
||||
<div class="win-overlay win-commandlayout win-appbar win-bottom appbar win-ui-dark" id="appBar" role="menubar">
|
||||
</div>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
49
shared/html/manager/appbar.css
Normal file
49
shared/html/manager/appbar.css
Normal file
@@ -0,0 +1,49 @@
|
||||
.win-bottom {
|
||||
position: absolute;
|
||||
bottom: 0;
|
||||
top: auto;
|
||||
left: 0;
|
||||
right: 0;
|
||||
}
|
||||
|
||||
.appbar {
|
||||
-ms-transform: translateY(100%);
|
||||
transform: translateY(100%);
|
||||
transition: all 0.5s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
|
||||
.appbar.show {
|
||||
-ms-transform: translateY(0);
|
||||
transform: translateY(0);
|
||||
}
|
||||
|
||||
.appbar.win-ui-dark .win-label {
|
||||
color: white;
|
||||
}
|
||||
|
||||
.appbar-touchhide {
|
||||
background-color: transparent;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 88px;
|
||||
}
|
||||
|
||||
.appbar button.win-command,
|
||||
.win-appbar .win-commandlayout button.win-command {
|
||||
box-sizing: border-box;
|
||||
/* 含 padding/border 计算宽度 */
|
||||
min-width: 100px;
|
||||
/* 强制最小宽度 100px */
|
||||
}
|
||||
|
||||
|
||||
/* 同时覆盖在窄屏 media query 中的行为(确保在 @media (max-width:1023px) 之后或在文件末尾定义) */
|
||||
|
||||
@media (max-width: 1023px) {
|
||||
.appbar button.win-command,
|
||||
.win-appbar .win-commandlayout button.win-command {
|
||||
min-width: 100px;
|
||||
}
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
padding: 10px;
|
||||
box-sizing: border-box;
|
||||
height: 60px;
|
||||
width: 450px;
|
||||
width: 460px;
|
||||
max-width: 100%;
|
||||
display: -ms-flexbox;
|
||||
/* IE10 */
|
||||
@@ -53,6 +53,14 @@
|
||||
-ms-flex-line-pack: center;
|
||||
/* IE10 -> align-content */
|
||||
align-content: center;
|
||||
overflow-x: hidden;
|
||||
overflow-y: hidden;
|
||||
transition: all 0.3s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
|
||||
.appitem div[role=img] img {
|
||||
width: 30px;
|
||||
height: 30px;
|
||||
}
|
||||
|
||||
.appitem div[role=divide] {
|
||||
@@ -65,6 +73,23 @@
|
||||
font-weight: normal;
|
||||
flex: 1;
|
||||
-ms-flex: 1;
|
||||
width: 100%;
|
||||
overflow-x: hidden;
|
||||
overflow-y: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
.appitem div[role=excepticon] div[role=advance] {
|
||||
display: none;
|
||||
opacity: 0;
|
||||
height: 0;
|
||||
transition: all 0.3s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
|
||||
.appitem.selected div[role=excepticon] div[role=advance] {
|
||||
display: block;
|
||||
opacity: 1;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.appitem div[role=excepticon] {
|
||||
@@ -85,12 +110,12 @@
|
||||
-ms-flex-pack: start;
|
||||
/* IE10 -> justify-content */
|
||||
justify-content: flex-start;
|
||||
width: calc(100% - 40px - 10px);
|
||||
}
|
||||
|
||||
.appitem div[role=excepticon] div[role=control] {
|
||||
display: none;
|
||||
/* IE10 */
|
||||
display: flex;
|
||||
-ms-flex-direction: row-reverse;
|
||||
/* IE10 */
|
||||
flex-direction: row-reverse;
|
||||
@@ -106,13 +131,95 @@
|
||||
-ms-flex-align: center;
|
||||
/* IE10 -> align-items */
|
||||
align-items: center;
|
||||
transition: all 0.3s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
opacity: 0;
|
||||
height: 0;
|
||||
}
|
||||
|
||||
.appitem.selected {
|
||||
height: 119px;
|
||||
background-color: rgba(232, 232, 232, 1);
|
||||
}
|
||||
|
||||
.appitem.selected div[role=excepticon] div[role=control] {
|
||||
display: flex;
|
||||
display: -ms-flexbox;
|
||||
opacity: 1;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
ul.appitem-list,
|
||||
ul.appitem-list li {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
.appitem .displayName,
|
||||
.appitem .publisher {
|
||||
text-overflow: ellipsis;
|
||||
overflow-x: hidden;
|
||||
overflow-y: hidden;
|
||||
white-space: nowrap;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.appitem .publisher {
|
||||
color: rgb(102, 102, 102);
|
||||
}
|
||||
|
||||
.app-loading {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
flex-wrap: wrap;
|
||||
align-content: center;
|
||||
justify-content: flex-start;
|
||||
align-items: center;
|
||||
width: 100%;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.app-loading.noloading progress {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.app-loading .title {
|
||||
margin-left: 10px;
|
||||
}
|
||||
|
||||
.app-loading.noloading .title {
|
||||
margin-left: 0;
|
||||
}
|
||||
|
||||
.app-detailpage header {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
flex-wrap: nowrap;
|
||||
align-content: flex-start;
|
||||
justify-content: flex-start;
|
||||
overflow-x: hidden;
|
||||
overflow-y: hidden;
|
||||
text-overflow: ellipsis;
|
||||
width: 100%;
|
||||
height: 67px;
|
||||
box-sizing: border-box;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.app-detailpage header .win-backbutton {
|
||||
width: 35px;
|
||||
height: 35px;
|
||||
font-size: 11.9pt;
|
||||
line-height: 32px;
|
||||
min-width: 35px;
|
||||
min-height: 35px;
|
||||
}
|
||||
|
||||
.app-detailpage header .display-name {
|
||||
padding-left: 10px;
|
||||
box-sizing: border-box;
|
||||
width: calc(100% - 35px - 10px);
|
||||
overflow-y: hidden;
|
||||
overflow-x: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
@@ -168,6 +168,7 @@ aside>nav ul li {
|
||||
|
||||
.page.fold>aside>nav ul li {
|
||||
padding: 0;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
aside>nav ul li div[role=img] {
|
||||
@@ -189,6 +190,33 @@ aside>nav ul li div[role=img] {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.selected {
|
||||
background-color: #159d9d;
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.selected:hover {
|
||||
background-color: rgb(23, 187, 187);
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.selected:active {
|
||||
background-color: rgb(29, 224, 224);
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.subitem {
|
||||
opacity: 0;
|
||||
height: 0;
|
||||
min-height: 0;
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.subitem.selected {
|
||||
opacity: 1;
|
||||
height: 50px;
|
||||
}
|
||||
|
||||
.page.fold>aside>nav ul li * {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.page.fold>aside>nav ul li div[role=img] {
|
||||
min-width: 90px;
|
||||
width: 90px;
|
||||
@@ -213,7 +241,8 @@ aside>nav ul li div[role=img] {
|
||||
|
||||
.page>aside>nav ul li div[role=img] {
|
||||
font-size: 15pt;
|
||||
margin-right: 5px;
|
||||
margin-right: 10px;
|
||||
width: 1em;
|
||||
}
|
||||
|
||||
.page>aside>nav ul li.title div[role=img] {
|
||||
@@ -256,7 +285,7 @@ aside>nav ul li div[role=img] {
|
||||
|
||||
.page.fold>aside>nav ul li:hover div[role=img] {
|
||||
min-width: 0;
|
||||
width: auto;
|
||||
width: 1em;
|
||||
}
|
||||
|
||||
.page.fold>aside>nav ul li:hover span {
|
||||
@@ -292,6 +321,10 @@ aside>nav ul li div[role=img] {
|
||||
overflow-y: visible;
|
||||
}
|
||||
|
||||
.main {
|
||||
transition: all 0.3s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
|
||||
.main.padding {
|
||||
padding: 44px 60px;
|
||||
}
|
||||
@@ -307,12 +340,18 @@ aside>nav ul li div[role=img] {
|
||||
top: 0px;
|
||||
left: 0px;
|
||||
background-color: white;
|
||||
transition: all 0.3s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
|
||||
.section.padding {
|
||||
padding: 44px 60px;
|
||||
}
|
||||
|
||||
.section.padding .bottom-compensate {
|
||||
.bottom-compensate {
|
||||
padding-bottom: 44px;
|
||||
}
|
||||
|
||||
.ispage {
|
||||
opacity: 1;
|
||||
transition: all 0.4s cubic-bezier(0.1, 0.9, 0.2, 1);
|
||||
}
|
||||
Reference in New Issue
Block a user